Docs / QR & PIN access▾

Core flows

QR & PIN access

At the gate, the host scans the driver's QR code, or types a 6-digit PIN when there is no camera or no signal. Both prove the same thing: this person holds a live booking for this host's spot, right now.

Two credentials, two strengths#

QR code6-digit PIN
What it isA signed token with the booking id and a random one-time id (jti)HMAC(secret, booking id), shown as 6 digits
Lifetime120 seconds; the app fetches a new one 15 s before expiry while the pass is openThe whole booking
ReplayEach jti is accepted once (Redis SET NX), so a screenshot of an old QR failsOnly valid for this host's listings and the booking's time window
Works offlineThe driver needs a connection to refresh itYes: the driver can always re-display it
Stored secretNone: the server signs and verifiesNone: re-derived from the booking id on every check
app/domain/access.pypython
class AccessCodeService:
def pin_for(self, booking_id: uuid.UUID) -> str:
# Nothing secret is stored in the database; rotating ACCESS_CODE_SECRET invalidates every PIN.
digest = int(hmac_hex(self._secret, f"pin:{booking_id}"), 16)
return str(digest % 10**self._pin_length).zfill(self._pin_length)
def verify_pin(self, booking_id: uuid.UUID, pin: str) -> bool:
return constant_time_equals(self.pin_for(booking_id), pin)

Check-in at the gate#

QR check-in sequenceDriver appHost scannerParkezy APIRedisGET /bookings/{id}/accessQR token (120 s) + PINscan QR on screenPOST /host/access/verifycheck signature + expirySET used:qr:{jti} NX EX 120first use? yesbooking belongs to this host · confirmed · within 15 min of startaccess granted, booking checked_in

Swipe sideways to see the whole figure.

The host's app sends the scanned token to the API. The one-time id is consumed atomically, so the same QR can never open the gate twice.
  • Check-in opens 15 minutes before the booked start and closes at the booked end.
  • Verification is rate limited per host, which matters for PINs: 6 digits are only safe if nobody can try thousands of them.
  • If Redis is unavailable, QR check-in fails rather than skip the replay check; the PIN, which needs no Redis, is the fallback at the gate.

Check-out and overstay#

The driver ends the session in the app with POST /bookings/{id}/check-out. The server compares the time with the booked end: 5 minutes of grace, then ₹20 (plus GST) for every started 15-minute block. The final amount, receipt and ledger entries are all written in one transaction.

Overstay fee02040608005102030405060minutes after the booked endfee (₹)
overstay fee (₹, before GST)

Swipe sideways to see the whole figure.

Overstay fee before GST as a function of minutes past the booked end. Each step is one started 15-minute block.