cURL Command Builder — Generate curl Commands from a Form

cURL Command Builder · Dev · Plain HTML, CSS & JS · Live preview

Share & Support

What's included

Features

Correctly shell-escapes every dynamic value using the POSIX single-quote-close-escape-reopen trick
Omits the -X flag for GET requests, matching curl's real default behavior
Editable header list stored as an array, pre-populated with Content-Type and Authorization
Live JSON.parse() validation on the request body with non-blocking visual warning
Multi-line pretty-print mode using standard backslash-newline shell continuation syntax
Empty header rows are automatically skipped when generating the command
One-click Copy of the generated command via the Clipboard API
Updates live on every field change — method, URL, headers, and body

About this UI Snippet

cURL Command Builder — Generate a Correctly Escaped curl Request from Method, Headers & Body

Screenshot of the cURL Command Builder snippet rendered live

Hand-writing a curl command with multiple headers and a JSON body means juggling quote characters, escaping, and line-continuation backslashes — and one misplaced quote silently breaks the whole command. This snippet flips that process around: fill in a method, a URL, a list of headers, and a JSON body through ordinary form fields, and it assembles a correctly shell-escaped curl command as you type, ready to paste straight into a terminal.

Why every value goes through shellEscape()

The single most important function in this tool is shellEscape(), which wraps every dynamic value — the URL, each header's key: value pair, and the JSON body — in single quotes, and handles the one tricky case: a literal single quote appearing inside a value. POSIX shells cannot escape a quote character *inside* single quotes directly, so the standard trick is used: close the quote, insert an escaped single quote, then reopen the quote ('\''). Every value passed through shellEscape() is safe to paste into bash, zsh, or any POSIX-compatible shell without breaking the command or allowing accidental shell injection, regardless of what punctuation the header value or JSON body contains.

Method flag omitted for GET, matching curl's actual default

The -X method flag is only added when the method is not GET, because curl defaults to GET and explicitly adding -X GET is both redundant and, in one curl-specific edge case, can subtly change how a request with a body is sent. This mirrors what an experienced engineer writing curl commands by hand would actually do — omit flags that aren't needed rather than including every option unconditionally.

Headers as an editable array with a default useful pair

Headers are stored as an array of { key, value } objects, pre-populated with a realistic Content-Type: application/json and Authorization: Bearer YOUR_TOKEN pair since those two headers appear in the overwhelming majority of authenticated JSON API requests. Each header contributes its own -H flag with the shell-escaped "key: value" string, and empty-key rows are silently skipped when building the command so an in-progress blank row never corrupts the output.

Live JSON validation on the body without blocking the command

The body textarea is validated with JSON.parse() inside a try/catch purely for feedback — an invalid JSON body highlights the textarea in red as a warning, but the command is still generated and includes the -d flag with whatever text is present. This is a deliberate choice: sometimes a request body is intentionally not strict JSON (form-encoded data, a GraphQL query string, or a body under active editing), so validation should warn without ever blocking output.

Pretty-print mode for multi-line readability

Toggling "multi-line" changes the separator between each part of the command from a plain space to \\\n — a trailing backslash followed by a newline and indentation, which is the standard shell line-continuation syntax. This produces a command that reads cleanly across multiple lines in documentation or a README, functionally identical to the single-line version when pasted into a terminal, since the shell treats a backslash-newline sequence as if it were not there at all.

Build with AI

Build, Understand, Optimize, and Extend It With AI

Paste this snippet's JavaScript into an AI assistant like Claude and ask it to explain exactly why the single-quote-close-escape-reopen trick in shellEscape() is necessary for safe shell escaping, and what could go wrong with a naive approach that just wraps values in double quotes instead. It is also a solid base to extend: ask for a reverse mode that parses a pasted curl command back into the form fields, support for --data-urlencode for form-encoded bodies, or a "copy as fetch()" button that generates equivalent JavaScript fetch code from the same form state.

Prompt to recreate it

Copy this into your AI assistant of choice to build the effect from scratch, or as a jumping-off point for your own variant:

text
Build a curl command builder in plain HTML, CSS, and JavaScript, no libraries.

Requirements:
- A method dropdown (GET, POST, PUT, PATCH, DELETE, HEAD) and a URL text input, both driving a live-generated curl command.
- An editable list of HTTP header rows (key and value text inputs each), with an add button that appends a new blank row and a remove button per row, pre-populated with one or two realistic example headers.
- A textarea for a JSON request body, validated with JSON.parse() inside a try/catch purely to show a non-blocking visual warning on invalid JSON — the body must still be included in the generated command even if it fails validation.
- A shell-escaping function applied to every dynamic value (URL, each header's "key: value" string, and the body) that wraps values in single quotes and correctly handles a literal single quote appearing inside the value using the standard POSIX close-quote/escaped-quote/reopen-quote technique, so the output is always safe to paste into a real shell.
- Omit the -X method flag entirely when the method is GET, matching curl's actual default behavior, and skip any header row whose key is empty.
- A "multi-line" checkbox toggle that reformats the command using backslash-newline shell line-continuation syntax between each part instead of plain spaces.
- A Copy button that copies the final generated command to the clipboard using the Clipboard API, with a brief visual confirmation.

Want to tighten it up first? Run this prompt through the AI Prompt Studio to score it across 8 quality dimensions, catch anti-patterns, and tune the wording for Claude, ChatGPT, or Gemini before you paste it in.

Step by step

How to Use

  1. 1
    Choose a method and enter a URLSelect GET, POST, PUT, PATCH, DELETE, or HEAD, and type the target endpoint URL.
  2. 2
    Add or edit headersTwo common headers are pre-filled. Click "+ Add header" for more, or edit the key/value fields directly.
  3. 3
    Write the JSON request bodyType or paste a JSON body. Invalid JSON is highlighted in red as a warning without blocking the generated command.
  4. 4
    Toggle multi-line formattingCheck "multi-line" to format the command across multiple lines with backslash continuations, ideal for documentation.
  5. 5
    Copy the generated commandClick "Copy" to copy the fully shell-escaped curl command to your clipboard.
  6. 6
    Export in your formatClick HTML for a standalone file, JSX for a React component, or Tailwind for a React + Tailwind version.

Real-world uses

Common Use Cases

Sharing a reproducible API request
Build a request once through the form and copy a curl command a teammate can paste directly into their terminal to reproduce the exact same request.
Writing API documentation
Use the multi-line mode to generate clean, readable curl examples for a README or internal API reference document.
Teaching curl and shell escaping
Show why values need quoting in shell commands by typing an apostrophe into a header value and watching shellEscape() produce the correct escaped output.
Quickly testing an endpoint
Fill in a URL, an Authorization header, and a body, then copy straight into a terminal to hit an API without writing the curl syntax from memory.
Internal developer tooling
Pair with the Query String Parser & Builder or JWT Decoder in an internal dev-tools dashboard for API debugging workflows.
Related: HTTP Status Code Reference
See the HTTP Status Code Reference for a related dev tool worth pairing with this one.

Got questions?

Frequently Asked Questions

It wraps the whole value in single quotes, and for any literal single quote inside the value it uses the standard POSIX trick of closing the quote, inserting an escaped quote, and reopening the quote ('\''). This produces a string that is always safe to paste into bash or zsh regardless of what characters the value contains.

curl defaults to a GET request when no -X flag is given, so omitting it for GET requests produces a cleaner command and avoids a curl-specific edge case where -X GET combined with certain other flags can behave slightly differently than a true default GET.

The textarea border turns red as a non-blocking warning, but the command is still generated using whatever text is present in the -d flag. This is intentional since the body field is sometimes used for non-JSON payloads like form-encoded data or a GraphQL query.

It replaces the plain space separator between each command part with a backslash, a newline, and two spaces of indentation — the standard shell line-continuation syntax. The resulting multi-line command behaves identically when pasted into a terminal.

No. A header row with an empty key is skipped entirely when building the command, so adding a blank row while editing never produces a broken -H flag.

No. Everything is assembled client-side as a plain string; no request is actually made and nothing is transmitted to a server, so it is safe to fill in real tokens and payloads while building the command.