Skip to main contentSkip to templates

Developers · Pro

QR API

Create QR codes from your own app. Send the content and a design, and get back the same PNG or SVG file that Download gives in the editor.

POSThttps://pretty-qr.com/api/v1/qr

Quick start

  1. The API is part of Pretty QR Pro. Sign in with your Pro account.
  2. Create a key on the API keys page and keep it somewhere safe: it is shown once.
  3. Set it as PRETTY_QR_KEY and send your first request. This one saves qr.png:
curl https://pretty-qr.com/api/v1/qr \
  -H "Authorization: Bearer $PRETTY_QR_KEY" \
  -H "Content-Type: application/json" \
  -d '{
      "content": "https://example.com",
      "design": {
        "backgroundColor": "#ffffff",
        "foregroundStyle": {
          "colors": [
            "#000000"
          ]
        }
      },
      "format": "png"
    }' \
  -o qr.png

Authentication

Send the key as a bearer token: Authorization: Bearer pqr_…. A key works while its account has Pro. Treat it like a password: keep it on your server, never in a web page or app that others can download. You can revoke a key on the API keys page at any time; you can have up to 10.

Request

POST /api/v1/qr with a JSON body of three fields. Everything about the look lives in design, which uses the same options as the editor.

contentstringrequired
What the code encodes: a URL or any text. At most 2331 bytes (UTF-8), or 1273 with a logo or the shield shape.
formatstringrequired
png (2048 × 2048 px) or svg.
designobjectrequired
How the code looks. Unknown fields are refused with a 400, so a typo never gives a different code.
design.backgroundColorstringrequired
Background colour as #rrggbb.
design.foregroundStyle.colorsstring[]required
Module colour as #rrggbb. Accepts 1 to 5 colours; only the first is drawn until gradients launch.
design.foregroundStyle.typestring
Gradient type: linear, radial.
design.foregroundStyle.directionstring
Gradient direction: top-bottom, left-right, top-left-bottom-right, top-right-bottom-left.
design.moduleShapestring
square, circle, rounded, dot. Default square.
design.eyeShapestring
Shape of the three corner squares: square, circle, rounded. Default square.
design.cornerRadiusnumber
Rounds the code's background, 0 to 1000.
design.shape.typestring
Silhouette: square, circle, heart, shield, house, pin. Silhouettes hold at most 213 bytes of content (119 with a logo or the shield).
design.logoobject | null
A logo in the middle of the code. Omit it or send null for none.
design.logo.srcstringrequired
Base64 data URL of a PNG, JPEG, WebP or SVG image. SVGs must not reference external files or contain scripts.
design.logo.sizenumberrequired
Share of the code's width, 0.1 to 0.5.
design.logo.marginnumberrequired
Space around the logo, 0 to 50.
design.logo.hideBackgroundDotsbooleanrequired
Clear the modules behind the logo.
design.frameobject | null
A frame around the code. Omit it or send null for none.
design.frame.enabledtruerequired
Always true.
design.frame.typestringrequired
rectangle, speech-bubble, banner, shopping-bag, coffee-cup.
design.frame.borderWidthnumberrequired
1 to 20.
design.frame.borderColorstringrequired
#rrggbb.
design.frame.paddingnumberrequired
8 to 48.
design.frame.cornerRadiusnumberrequired
0 to 50.
design.frame.textobject
Label: { "enabled": boolean, "content": string }, at most 24 characters. Shown on every frame except rectangle.
design.frame.outerColorstring
Colour outside the frame, #rrggbb.

Fields under design.logo and design.frame marked required are required only when you send that object.

Response and errors

A 200 is the file itself: image/png (2048 × 2048 px) or image/svg+xml. Anything else is JSON with one field, { "error": "…" }, a sentence that says what to fix.

StatusWhen
400Bad requestThe body is not JSON, a field is unknown or out of range, the logo does not decode, or the content is too long for the chosen silhouette.
401UnauthorizedNo Authorization: Bearer header, or the key is unknown or revoked.
403ForbiddenThe account the key belongs to no longer has Pro.
413Too largeThe body is over 1 MB, or the content is over what a QR code holds.
429Too many requestsOver 1,000 requests in the last hour or 10,000 this calendar month (UTC). Wait for the seconds in Retry-After.
503UnavailableThe renderer is busy or restarting. Retry after a few seconds.

Limits

  • 1,000 requests in any hour and 10,000 per calendar month (UTC, resets on the 1st), per account across all its keys.
  • Every request with a valid key counts, including ones that fail with 400 or 413.
  • Request bodies up to 1 MB, logo included.
  • Requests are rendered one after another. Send them in sequence rather than hundreds at once, and retry a 503 after a few seconds.

Examples

Each image is what the request next to it returns. Start from one and change the fields you need.

QR code from the "Banner frame with a label" request
Banner frame with a labelRounded modules and eyes inside a banner frame that reads "SCAN ME".
curl https://pretty-qr.com/api/v1/qr \
  -H "Authorization: Bearer $PRETTY_QR_KEY" \
  -H "Content-Type: application/json" \
  -d '{
      "content": "https://example.com/menu",
      "design": {
        "backgroundColor": "#ffffff",
        "foregroundStyle": {
          "colors": [
            "#4338ca"
          ]
        },
        "moduleShape": "rounded",
        "eyeShape": "rounded",
        "cornerRadius": 24,
        "frame": {
          "enabled": true,
          "type": "banner",
          "borderWidth": 8,
          "borderColor": "#4338ca",
          "padding": 16,
          "cornerRadius": 16,
          "text": {
            "enabled": true,
            "content": "SCAN ME"
          }
        }
      },
      "format": "png"
    }' \
  -o qr.png
QR code from the "Heart with a logo" request
Heart with a logoHeart silhouette, speech-bubble frame and an SVG logo sent as a data URL.
curl https://pretty-qr.com/api/v1/qr \
  -H "Authorization: Bearer $PRETTY_QR_KEY" \
  -H "Content-Type: application/json" \
  -d '{
      "content": "https://example.com/love",
      "design": {
        "backgroundColor": "#111827",
        "foregroundStyle": {
          "colors": [
            "#ffffff"
          ]
        },
        "moduleShape": "square",
        "eyeShape": "rounded",
        "logo": {
          "src": "data:image/svg+xml;base64,PHN2ZyB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHZpZXdCb3g9IjAgMCAxMDAgMTAwIj48cmVjdCB3aWR0aD0iMTAwIiBoZWlnaHQ9IjEwMCIgcng9IjIyIiBmaWxsPSIjZWY0NDQ0Ii8+PGNpcmNsZSBjeD0iNTAiIGN5PSI1MCIgcj0iMjYiIGZpbGw9IiNmZmZmZmYiLz48cGF0aCBkPSJNMzggNTJsOCA4IDE2LTE4IiBmaWxsPSJub25lIiBzdHJva2U9IiNlZjQ0NDQiIHN0cm9rZS13aWR0aD0iOCIgc3Ryb2tlLWxpbmVjYXA9InJvdW5kIiBzdHJva2UtbGluZWpvaW49InJvdW5kIi8+PC9zdmc+",
          "size": 0.4,
          "margin": 0,
          "hideBackgroundDots": false
        },
        "frame": {
          "enabled": true,
          "type": "speech-bubble",
          "borderWidth": 12,
          "borderColor": "#ffffff",
          "padding": 8,
          "cornerRadius": 16,
          "text": {
            "enabled": true,
            "content": "SCAN ME"
          }
        },
        "shape": {
          "type": "heart"
        }
      },
      "format": "png"
    }' \
  -o qr.png
QR code from the "Coffee cup" request
Coffee cupCircle silhouette with dot modules in a coffee-cup frame with an outer colour.
curl https://pretty-qr.com/api/v1/qr \
  -H "Authorization: Bearer $PRETTY_QR_KEY" \
  -H "Content-Type: application/json" \
  -d '{
      "content": "https://example.com/coffee",
      "design": {
        "backgroundColor": "#fdf2f8",
        "foregroundStyle": {
          "colors": [
            "#312e81"
          ]
        },
        "moduleShape": "dot",
        "eyeShape": "rounded",
        "frame": {
          "enabled": true,
          "type": "coffee-cup",
          "borderWidth": 12,
          "borderColor": "#312e81",
          "padding": 8,
          "cornerRadius": 16,
          "text": {
            "enabled": true,
            "content": "Scan for 10% off"
          },
          "outerColor": "#db2777"
        },
        "shape": {
          "type": "circle"
        }
      },
      "format": "png"
    }' \
  -o qr.png

Postman and OpenAPI

The Postman collection has every example on this page and the common errors, each with a test. To use it:

  1. In Postman, choose Import and drop in both the collection and the environment.
  2. Select the Pretty QR environment and paste your key into apiKey.
  3. Send a request. Use Send and Download to save the file.

The OpenAPI file describes the same request and responses. Import it into Insomnia, Bruno or any OpenAPI tool, or generate a client from it.

Questions or a field you need? Write to [email protected].