CLI

stable

Scan, generate and parse barcodes from the command line with the qrgen CLI, and start the REST API server. Commands, flags, JSON output, stdin and exit codes.

Edit on GitHub

The qrgen command ships with the qrgen-sdk npm package. It scans image files, generates barcode images, parses scanned text, lists symbologies and starts the REST API. It runs anywhere Node.js 18.17+ runs, including Raspberry Pi and CI runners.

Install

Run it without installing:

npx qrgen-sdk --help

Or install it globally, which puts qrgen on your PATH:

npm install -g qrgen-sdk
qrgen --help

Note: Until the first npm release is published, install the latest build with npm install -g https://rockyljewell.github.io/QR-GEN/downloads/qrgen-sdk.tgz.

In a project that depends on qrgen-sdk, use npx qrgen (the bin is named qrgen) or call it from package.json scripts.

Commands

Command Aliases Description
qrgen scan <image...> decode, read Decode barcodes in one or more image files (PNG, JPEG, GIF, BMP). - reads an image from stdin.
qrgen generate <data> encode, write Generate a barcode. Writes a file with -o, otherwise prints a text rendering to the terminal.
qrgen parse <data> Parse scanned text with parseContent() and print JSON.
qrgen serve server Start the REST API.
qrgen symbologies List symbologies and whether they can be read and written.

Global flags: -h, --help prints usage; -v, --version prints the version.

scan

qrgen scan label.jpg
QR Code	https://example.com

Each code is printed as symbology name<TAB>data. With several files, results are grouped under each file name:

qrgen scan front.png back.png
front.png:
  QR Code	https://example.com
back.png:
  (no barcode found)
Flag Short Description
--symbologies <list> -s Only look for these ids, aliases or groups: -s qr,ean13, -s retail. Default: all.
--json Print JSON instead of text.
--no-parse Leave out the parsed field in JSON output.
--fast Skip the thorough search (faster on large, clean images).

Scanning uses the thorough mode (tryHarder) by default, which finds small, rotated and inverted codes. Pass --fast to turn it off.

JSON output

With a single file, --json prints an array of Barcode objects, each with a parsed field from parseContent():

qrgen scan qr.png --json
[
  {
    "data": "https://example.com",
    "symbology": "qr",
    "symbologyName": "QR Code",
    "rawBytes": "aHR0cHM6Ly9leGFtcGxlLmNvbQ==",
    "contentType": "text",
    "isGS1": false,
    "location": {
      "topLeft": { "x": 16, "y": 16 },
      "topRight": { "x": 116, "y": 16 },
      "bottomRight": { "x": 116, "y": 116 },
      "bottomLeft": { "x": 16, "y": 116 }
    },
    "frameSize": { "width": 132, "height": 132 },
    "orientation": 0,
    "ecLevel": "Q",
    "symbologyIdentifier": "]Q1",
    "timestamp": 1790467200000,
    "parsed": { "type": "url", "url": "https://example.com" }
  }
]

With several files, it prints an array of { "file": "...", "barcodes": [...] } objects instead. Combine with jq:

qrgen scan *.png --json | jq -r '.[] | "\(.file)\t\(.barcodes[0].data // "-")"'

stdin

Use - as the file name to read an image from standard input:

curl -s https://example.com/label.png | qrgen scan -
convert page.tiff png:- | qrgen scan - --json   # ImageMagick, for formats the engine can't read

Exit codes

Code Meaning
0 Success. For scan: at least one code was found in at least one file.
1 Error: bad arguments, an unreadable file, or data that can’t be encoded. The message goes to stderr, prefixed with qrgen:.
2 scan ran but found no code in any file.

This makes scan easy to use in scripts:

if qrgen scan receipt.jpg -s qr > /dev/null; then
  echo "Receipt has a QR code"
fi

generate

qrgen generate "https://example.com" -o qr.svg
qrgen generate "https://example.com" -o qr.png --scale 8 --ec H
qrgen generate "5901234123457" -t ean13 --hrt -o ean.png
qrgen generate "(01)09501101530003(17)250101(10)ABC123" -t data-matrix --gs1 -o dm.png
qrgen generate "Hello"   # prints the code to the terminal

All positional arguments after generate are joined with spaces, so quotes are only needed for shell special characters. On success with -o, it prints wrote qr.svg (qr, 25x25 modules).

Flag Short Description
--output <file> -o Output file. The extension picks the format: .png, .txt (text rendering), anything else SVG. Without -o, a text rendering is printed.
--symbology <id> -t Symbology id or alias. Default qr.
--scale <n> Module size in pixels. Default 4.
--ec <level> Error correction: L, M, Q, H for QR, or a percentage for Aztec and PDF417.
--gs1 Encode as GS1. Pass the data in HRI form, (01)...(10)....
--hrt Print the human-readable text under linear barcodes.
--no-margin Leave out the quiet zone.
--fg <color> Bar color. Default #000000.
--bg <color> Background color or transparent. Default #ffffff.

--fg and --bg apply to SVG and PNG output alike. See Barcode generation for what each symbology accepts.

parse

qrgen parse "WIFI:T:WPA;S:Office;P:correct horse;;"
{
  "type": "wifi",
  "ssid": "Office",
  "password": "correct horse",
  "security": "WPA",
  "hidden": false
}

Works for every content type: URLs, contacts, GS1 element strings, product codes and more. Pass --symbology (-t) when you know where the text came from, for example qrgen parse 01234565 -t upce expands a UPC-E to its GTIN.

serve

qrgen serve --port 8080 --host 0.0.0.0
qrgen REST API listening on http://0.0.0.0:8080  (GET /health)
Flag Short Default Description
--port <n> -p $PORT or 8080 Port to listen on.
--host <addr> $HOST or 0.0.0.0 Interface to bind. Use 127.0.0.1 to accept local connections only.

The server logs one line per request and shuts down cleanly on SIGINT and SIGTERM. Endpoints are documented in REST API & Docker.

symbologies

qrgen symbologies
qr                 QR Code                  read/write
micro-qr           Micro QR Code            read/write
rmqr               rMQR Code                read/write
data-matrix        Data Matrix              read/write
...

qrgen symbologies --json prints the full table, including zxing-cpp format names and aliases.

Examples

Rename scanned documents by the QR code they carry:

for f in scans/*.jpg; do
  code=$(qrgen scan "$f" -s qr --json | jq -r '.[0].data // empty')
  [ -n "$code" ] && mv "$f" "scans/${code//[^A-Za-z0-9._-]/_}.jpg"
done

Generate a sheet of asset labels from a CSV (id,name):

tail -n +2 assets.csv | while IFS=, read -r id name; do
  qrgen generate "https://assets.example.com/$id" -o "labels/$id.svg" --ec M
done

Check in CI that a printed label still decodes to the expected value:

test "$(qrgen scan build/label.png --json | jq -r '.[0].data')" = "https://example.com/p/42"
Esc

Share this page

CLI · Docs | QRGen

Star QRGen on GitHub Add a "Powered by QRGen" badge