webcapture Get a free key

Convert HTML to PDF from Lovable

Keep the key in Lovable's secrets, call /v1/convert from a backend function, and fetch the download url with the same Bearer header.

Wire it up

The shared request is Authorization: Bearer wc_your_key and {"url": "https://example.com/"}. Lovable changes the wrapper, not those values or the authenticated download.

  1. Put the API key in the project's secrets (Lovable's secrets manager), not in client code.
  2. Ask Lovable for a backend function that calls the convert endpoint, or add the fetch to the generated code yourself; the function shape is the same either way.
  3. The function POSTs to your serving origin plus /v1/convert with the Authorization header and the JSON body, then reads the receipt's download url.
  4. The function fetches that download url with the same Authorization header (the endpoint is key-scoped: 401 without it, 404 for another key's id) and hands the bytes, not a bare url, to the UI's save or share action.

The full request

const res = await fetch(`https://webcapture.io/v1/convert`, {
  method: "POST",
  headers: {
    Authorization: `Bearer wc_your_key`,
    "Content-Type": "application/json",
  },
  body: JSON.stringify({ url: "https://example.com/" }),
});
const receipt = await res.json();
// receipt.download is key-scoped: the GET needs the same header
const file = await fetch(receipt.download, {
  headers: { Authorization: `Bearer wc_your_key` },
});

The first response is the receipt, not the bytes: id, bytes, attempts, remaining, sourceUrl, sourceType, and download. Fetching download returns the pdf itself, and that fetch carries the same Authorization header: the download endpoint is key-scoped, answering 401 without the header and 404 for another key's id, so the url is not a shareable link. Keeping both calls in a backend function keeps the key server-side and away from the browser bundle.

Limits

The convert endpoint rate limits at 120 requests a minute per client IP; a full window answers 429 with retryAfterSec. The monthly quota is per account: exhausted, the endpoint answers 429 carrying used, limit, resetDate, and upgradeUrl, and the receipt's remaining field reports the count after each render. A browser-driven call that must not hold the tab open can send ?wait=false and take the 202 ticket's poll and download urls.

Related

Method

Checked 2026-10-05 against Lovable: The snippet follows Lovable's integration documentation for calling external APIs with fetch and storing credentials in the secrets manager. Source: https://docs.lovable.dev/integrations/any-api. Corrections: hello@webcapture.io.

Get a free key or read the API reference to wire Lovable.