Paste any curl command — including one copied straight out of your browser's network tab with "Copy as cURL" — and get the same request written out in nine languages. The command is parsed in the page: method, URL, headers and body are read out of it and then re-rendered, so what comes back is the request you pasted rather than a template with your URL dropped into it.
This command:
curl -X POST 'https://funapi.dev/api/friends/v1/characters' \
-H 'Authorization: Bearer qa-admin-token' \
-H 'Content-Type: application/json' \
-d '{"name":"Gunther","job":"Head barista"}'
is parsed as POST https://funapi.dev/api/friends/v1/characters with 2 header(s) and a 39-byte body, and converts to:
const res = await fetch("https://funapi.dev/api/friends/v1/characters", {
method: "POST",
headers: {
"Authorization": "Bearer qa-admin-token",
"Content-Type": "application/json"
},
body: "{\"name\":\"Gunther\",\"job\":\"Head barista\"}"
});
console.log(res.status, await res.json());import axios from 'axios';
const res = await axios({
method: "post",
url: "https://funapi.dev/api/friends/v1/characters",
headers: {
"Authorization": "Bearer qa-admin-token",
"Content-Type": "application/json"
},
data: {"name":"Gunther","job":"Head barista"}
});
console.log(res.status, res.data);import requests
url = "https://funapi.dev/api/friends/v1/characters"
headers = {
"Authorization": "Bearer qa-admin-token",
"Content-Type": "application/json"
}
payload = {"name":"Gunther","job":"Head barista"}
res = requests.post(url, headers=headers, json=payload)
print(res.status_code, res.json())package main
import (
"fmt"
"io"
"net/http"
"strings"
)
func main() {
req, _ := http.NewRequest("POST", "https://funapi.dev/api/friends/v1/characters", strings.NewReader("{\"name\":\"Gunther\",\"job\":\"Head barista\"}"))
req.Header.Set("Authorization", "Bearer qa-admin-token")
req.Header.Set("Content-Type", "application/json")
res, err := http.DefaultClient.Do(req)
if err != nil {
panic(err)
}
defer res.Body.Close()
out, _ := io.ReadAll(res.Body)
fmt.Println(res.StatusCode, string(out))
}using var client = new HttpClient();
var req = new HttpRequestMessage(HttpMethod.Post, "https://funapi.dev/api/friends/v1/characters");
req.Headers.TryAddWithoutValidation("Authorization", "Bearer qa-admin-token");
req.Content = new StringContent("{\"name\":\"Gunther\",\"job\":\"Head barista\"}", Encoding.UTF8, "application/json");
var res = await client.SendAsync(req);
Console.WriteLine((int)res.StatusCode);
Console.WriteLine(await res.Content.ReadAsStringAsync());given()
.header("Authorization", "Bearer qa-admin-token")
.header("Content-Type", "application/json")
.body("{\"name\":\"Gunther\",\"job\":\"Head barista\"}")
.when()
.post("https://funapi.dev/api/friends/v1/characters")
.then()
.statusCode(200);import { test, expect } from '@playwright/test';
test('POST request', async ({ request }) => {
const res = await request.post("https://funapi.dev/api/friends/v1/characters", {
headers: {
"Authorization": "Bearer qa-admin-token",
"Content-Type": "application/json"
},
data: {"name":"Gunther","job":"Head barista"}
});
expect(res.status()).toBe(200);
});import http from 'k6/http';
import { check } from 'k6';
export default function () {
const res = http.request("POST", "https://funapi.dev/api/friends/v1/characters", "{\"name\":\"Gunther\",\"job\":\"Head barista\"}", { headers: {
"Authorization": "Bearer qa-admin-token",
"Content-Type": "application/json"
} });
check(res, { 'status is 200': r => r.status === 200 });
}echo "{\"name\":\"Gunther\",\"job\":\"Head barista\"}" | http POST "https://funapi.dev/api/friends/v1/characters" Authorization:"Bearer qa-admin-token" Content-Type:"application/json"
Backslash line continuations and the caret form cmd.exe uses, single and double quoting with escapes, repeated -H headers, repeated -d bodies joined the way curl joins them, -u basic auth normalised into an Authorization header, and the pile of flags a devtools copy brings along (--compressed, -s, -L, --max-time and friends), which are recognised and dropped rather than mistaken for the URL.
curl defaults to POST when you give it a body and no method, and it sets a content type you never wrote. Every other client in the list does neither. Both are therefore made explicit in the output — an inferred POST and an inferred Content-Type — because the most common way a converted request stops working is that the implicit half of the curl command did not come with it.
An unknown flag that might take a value stops the conversion instead of being skipped, because skipping it would swallow the URL that followed it and produce a plausible, wrong result. An unbalanced quote does the same. A converter that fails loudly is worth more than one that guesses.