import { platform, useCapability } from "@yaakapp-internal/platform"; import { Icon } from "@yaakapp-internal/ui"; import * as m from "motion/react-m"; import { useEffect, useState } from "react"; import { importCurl, looksLikeCurl } from "../commands/importCurl"; import { useWindowFocus } from "../hooks/useWindowFocus"; import { showToast } from "../lib/toast"; import { Button } from "./core/Button"; /** * Offers to create a request from a Curl command on the clipboard. A host that can read * the clipboard on its own offers it whenever the window is focused; one that would have * to prompt for permission first waits for the user to paste instead. */ export function ImportCurl() { return useCapability("clipboardRead") ? : ; } function ImportCurlButton() { const focused = useWindowFocus(); const [clipboardText, setClipboardText] = useState(""); const [isLoading, setIsLoading] = useState(false); // oxlint-disable-next-line react-hooks/exhaustive-deps -- none useEffect(() => { void platform.clipboard.readText().then(setClipboardText); }, [focused]); if (!looksLikeCurl(clipboardText)) { return null; } return ( ); } function ImportCurlOnPaste() { useEffect(() => { const handlePaste = (e: ClipboardEvent) => { const command = e.clipboardData?.getData("text/plain") ?? ""; if (!looksLikeCurl(command)) return; // Editable targets keep the text as text. The URL editor imports it itself. if (isEditable(e.target)) return; showToast({ id: "curl-paste", color: "success", message: (

Curl command detected

Create a request from the pasted command?

), action: ({ hide }) => ( ), }); }; document.addEventListener("paste", handlePaste); return () => document.removeEventListener("paste", handlePaste); }, []); return null; } function isEditable(target: EventTarget | null) { if (!(target instanceof HTMLElement)) return false; if (target.isContentEditable) return true; if (target.closest(".cm-editor") != null) return true; return ["INPUT", "TEXTAREA", "SELECT"].includes(target.tagName); }