Add image upload to your TipTap editor in one prompt
TipTap is a rich contenteditable editor, so it uses PixelVault's upload helper rather than the textarea widget. This prompt wires paste + drop to upload images and insert them as image nodes — no upload backend. Copy it into your AI coding agent.
Claude CodeCursorWindsurfCopilot - 1Copy the prompt
The one big button below.
- 2Paste it into your agent
In your project — Claude Code, Cursor, etc.
- 3Drop in your key
Swap
pv_pub_REPLACE_MEfor a free key. Done.
Add image paste-and-host to my TipTap editor using PixelVault.
Context — read this first and use only the documented API:
- Overview + API: https://pixelvault.dev/llms.txt
- PixelVault upload helper (from @pixelvault-dev/paste):
import { uploadImage } from "@pixelvault-dev/paste";
const { url } = await uploadImage(file, { publishableKey: "pv_pub_REPLACE_ME" });
// returns { id, url, mimeType, size }; throws PixelVaultPasteError on failure
Important: TipTap is a contenteditable/ProseMirror editor, not a <textarea>, so
do NOT use the paste-react/usePaste widget here — use uploadImage() directly.
Do this:
1. Install: npm install @pixelvault-dev/paste
(and @tiptap/extension-image if my editor doesn't already have an image node)
2. Make sure my editor has the Image extension registered.
3. In my useEditor config, add editorProps.handlePaste and editorProps.handleDrop
(standard TipTap/ProseMirror hooks). IMPORTANT: these handlers must be
SYNCHRONOUS — do NOT make them async. In each handler: pull any image File out
of the event, kick off the upload WITHOUT awaiting it (e.g. call an async
helper as: void uploadAndInsert(file) ), and return true immediately so
TipTap skips its default paste. Inside that helper: await
uploadImage(file, { publishableKey }), then insert a TipTap image node with
the returned url via the Image extension's setImage command
(editor.chain().focus().setImage({ src: url }).run()). Show a sensible
fallback if the upload throws PixelVaultPasteError.
4. Use my publishable key where I wrote pv_pub_REPLACE_ME (I'll paste my own).
Rules:
- For the PixelVault part, use ONLY uploadImage(file, options) as documented above —
do NOT invent PixelVault endpoints, options, or other packages.
- Use TipTap's own documented handlePaste/handleDrop and Image APIs for the editor side.
- Handle the async upload without blocking the editor, and show a sensible fallback on error. What the agent will do
- Install
@pixelvault-dev/paste(core) — and TipTap's Image extension if needed - Add
handlePaste/handleDropthat upload viauploadImage() - Insert the returned CDN URL as a TipTap image node
- No backend changes — uploads go straight to PixelVault with your key
Grab your free key
The one thing the agent can't generate is your publishable key (pv_pub_…) — it's origin-scoped and upload-only, safe to ship in browser code. Create one, add your app's origin, and paste it in.
Free tier: 200 MB storage, 500 uploads/mo, 1 GB bandwidth. No card.
How this differs from the textarea prompts
The React, Vue,
and plain-HTML prompts use our drop-in widget, which
attaches to a <textarea>. TipTap renders a contenteditable ProseMirror
surface instead, so the widget can't attach to it. The right tool is the lower-level
uploadImage() helper: you upload the file yourself inside TipTap's own paste/drop
hooks, then insert a native image node with the returned CDN URL.
The PixelVault part, by hand
Everything editor-specific is standard TipTap. The only PixelVault call is one function:
import { uploadImage } from "@pixelvault-dev/paste";
const { url } = await uploadImage(file, {
publishableKey: "pv_pub_xxxxxxxx",
});
// url → https://img.pixelvault.dev/… (a permanent CDN URL)
// then: editor.chain().focus().setImage({ src: url }).run();
Wire that into TipTap's editorProps.handlePaste and handleDrop, upload
any image file the event carries, and insert it on success. The
docs and llms.txt have the full
reference.
Why a prompt instead of docs?
Because "add image upload to my TipTap editor" is exactly the kind of thing you'd hand a coding
agent — and it needs to know to use uploadImage(), not guess at a nonexistent
widget. This prompt grounds the PixelVault call and lets the agent handle TipTap's well-documented
paste hooks. Copy, paste, ship.
FAQ
How do I add image upload to a TipTap editor?
Copy the prompt above into your AI coding agent. Because TipTap is contenteditable (not a textarea), it uses PixelVault's uploadImage() helper inside TipTap's handlePaste/handleDrop hooks, then inserts the returned CDN URL as a TipTap image node.
Why doesn't the usePaste widget work with TipTap?
The usePaste / attachPaste widget attaches to a <textarea> or <input>. TipTap renders a contenteditable ProseMirror surface, so you upload with the lower-level uploadImage() function and insert a native TipTap image node instead.
Do I need an upload backend for TipTap image uploads?
No. uploadImage() sends the file straight from the browser to PixelVault with an origin-scoped, upload-only publishable key. There's no server route to build.