Standards/apple-pkpass
Apple PKPass
Overview
Apple PKPass (file extension .pkpass, MIME type application/vnd.apple.pkpass) is the container format for digital passes in Apple Wallet [1, 3]. It is not a barcode symbology: a .pkpass is a signed ZIP bundle holding a JSON description of a pass plus its images, and it embeds a machine-readable barcode that the format itself merely describes and renders. The supported embedded symbologies are qr-code, aztec, pdf417, and Code 128 [1, 2].
A pass is what a phone presents at a gate, turnstile, counter, or ticket scanner — a boarding pass, an event ticket, a loyalty card, a coupon. The barcode inside it carries the actual scannable payload; the surrounding container handles layout, branding, lock-screen relevance, and updates [1].
History
Passbook / iOS 6 (2012) [1, 3]: Apple introduced the pass concept as Passbook with iOS 6 in 2012, defining the .pkpass bundle, the pass.json schema, and the PassKit framework for creating and distributing passes.
Rename to Wallet [3]: With iOS 9 (2015) Passbook was rebranded Apple Wallet, and the same release expanded barcode support — the single barcode dictionary used in iOS 8 and earlier was superseded by a barcodes array, and QR, PDF417, and Aztec joined the previously supported Code 128 [1].
The .pkpass format and pass.json schema have remained backward-compatible since 2012, with formatVersion still 1 [1].
Technical specification
A .pkpass file is a ZIP archive of the pass package's contents containing at minimum [1, 3]:
| File | Required | Purpose |
|---|---|---|
pass.json |
yes | The pass definition (fields, style, colours, barcode) |
manifest.json |
yes | SHA-1 hash of every other file in the bundle |
signature |
yes | PKCS #7 detached signature of manifest.json |
icon.png |
yes | Lock-screen / Mail icon (with @2x, @3x variants) |
logo.png, strip.png, background.png, thumbnail.png, footer.png |
optional | Style-dependent imagery |
*.lproj/ |
optional | Localization directories (pass.strings, localized images) |
Core pass.json keys [1]: formatVersion (1), passTypeIdentifier (reverse-DNS, e.g. pass.com.example.boarding), serialNumber, teamIdentifier (must match the signing certificate), organizationName, and description. Exactly one pass-style key is present and carries the field dictionaries: boardingPass, coupon, eventTicket, generic, or storeCard [1, 6].
The barcode [1, 2]: Passes declare a top-level barcodes array (iOS 9+) of barcode dictionaries; PassKit displays the first format the device supports. iOS 8 and earlier used a single barcode dictionary of the same shape (still emitted for backward compatibility). Each barcode dictionary has:
message— the string encoded into the barcode.format— one ofPKBarcodeFormatQR,PKBarcodeFormatPDF417,PKBarcodeFormatAztec,PKBarcodeFormatCode128[1, 2].messageEncoding— the IANA charset name, typicallyiso-8859-1(Latin-1) because most scanners expect it; PassKit supports allNSStringencodings [1].altText— optional human-readable text shown near the barcode for manual entry.
Example:
"barcodes": [
{
"message": "M1DOE/JOHN EABC123 SFOLHRBA 0123 ...",
"format": "PKBarcodeFormatAztec",
"messageEncoding": "iso-8859-1",
"altText": "ABC123"
}
]
Platform notes [1, 2]: QR, PDF417, and Aztec are supported on iOS 9+ and watchOS; Code 128 is not supported on watchOS, so a pass relying on it should include a 2D fallback. On Apple Watch, rectangular barcodes are rotated to portrait.
Signing [1]: manifest.json lists SHA-1 hashes of all bundle files; signature is a PKCS #7 detached signature of that manifest, produced with the private key of an Apple-issued Pass Type ID certificate whose identifier matches passTypeIdentifier, and it must include Apple's WWDR intermediate certificate. The contents are then zipped into the .pkpass.
Use cases
The five pass styles map directly to deployment patterns [1, 6]:
boardingPass— airline boarding passes, train and bus tickets. Boarding passes commonly carry aztec or pdf417 to match IATA BCBP gate scanners.eventTicket— concert, sports, cinema and conference admission, typically with a qr-code or PDF417.coupon— discounts and promotional offers.storeCard— loyalty cards, gift cards, stored-value cards (often a qr-code or Code 128).generic— gym memberships, coat-check tags, transit passes and anything not covered by the other styles.
Passes can be delivered by linking to the .pkpass file (served with the application/vnd.apple.pkpass MIME type) from a web page, email, or app; tapping it on iOS offers "Add to Apple Wallet" [1]. Passes can also update over the air and surface on the lock screen based on relevantDate, locations, and iBeacon beacons [1].
Implementations
PassKit's open semantics have produced mature open-source generators that build pass.json, hash the manifest, sign it, and zip the .pkpass [4, 5]:
- TypeScript / Node.js — alexandercerutti/passkit-generator — 1 213★, active 2025. Template-driven generation of custom Apple Wallet passes; the most-starred Node library.
- TypeScript / Node.js — tinovyatkin/pass-js — 733★, active 2026. Pass generation with template-based shared fields and signing.
- Go — alvinbaena/passkit — 119★, active 2026. Go
Passstruct mirroringpass.json, with manifest/signature helpers. - Python —
PyPKPass— objects for constructing, managing, and serialising PassKit passes, with Flask-based PassKit web-service support [5].
These libraries handle the manifest SHA-1 hashing, PKCS #7 signing with the Pass Type ID certificate, and ZIP packaging described in the spec [1].
Comparison
vs. Google Wallet pass — Both deliver a brandable mobile pass that can render a qr-code / barcode at a scanner, but their architecture differs fundamentally [7]:
| Apple PKPass | Google Wallet pass | |
|---|---|---|
| Artifact | Self-contained signed .pkpass ZIP file |
Pass object stored on Google's cloud, referenced by a signed JWT |
| Definition | pass.json inside the bundle |
JSON pass classes/objects via the Google Wallet REST API |
| Distribution | Link/serve the .pkpass file (MIME application/vnd.apple.pkpass) |
"Add to Google Wallet" button passing a signed JWT to the Wallet API |
| Signing | PKCS #7 signature with an Apple Pass Type ID certificate | JWT signed with a Google Cloud service-account key |
| Barcode | barcodes array (QR, PDF417, Aztec, Code128) |
QR/barcode plus NFC for contactless |
In short, Apple's model is file-centric (a signed bundle you can hand the user directly), while Google's is service-centric (a server-side object retrieved via a signed token) [7]. Cross-platform tools such as Google's open-source pass-converter exist to translate between the two formats [7].
Fun facts
The format's first life was Passbook in iOS 6 (2012); the rename to Apple Wallet came with iOS 9 in 2015 — the same release that turned the single barcode dictionary into a barcodes array and added QR, PDF417 and Aztec alongside the original Code 128 [1, 3].
Apple's documentation explicitly recommends iso-8859-1 (Latin-1) for messageEncoding rather than UTF-8, noting that real-world barcode scanners and back-end software handle Unicode poorly — a reminder that the pass has to satisfy physical gate hardware, not just the phone screen [1].
Status
- The
.pkpassbundle,pass.jsonschema (formatVersion1), and PassKit signing model remain the supported way to ship passes to Apple Wallet, documented under Apple's current Wallet Passes reference [2]. - The four embedded barcode formats (QR, PDF417, Aztec, Code 128) are unchanged; Code 128 remains unsupported on watchOS [1].
- A broad open-source ecosystem (Node, Go, Python) continues active maintenance into 2026 [4, 5b].
Sources
- Wallet Developer Guide: Pass Design and Creation — Apple
- PKPassType.barcode — Apple Developer Documentation
- PKPASS File: The Complete Reference — WalletWallet
- alexandercerutti/passkit-generator — GitHub
- PyPKPass — GitHub
- Anatomy of an Apple Wallet Pass — WalletWallet
- How passes in Google Wallet work — Passcreator
Deployments
No country reports mention this standard by name.
Regions / aggregations not mapped to a single country
- Universal