docs(openspec): archive fingerprint-token-auth after the production pass
The wizard's a2loft calls now authenticate with the session token and carry no OTP. Field pass in production: the lookup and both fingerprint saves succeeded with no OTP, so task 3.2 is done. Merged the fingerprint-wizard and tools-app deltas into the main specs and archived the change.
This commit is contained in:
@@ -114,16 +114,16 @@ and SHALL display the agent version reported on connect.
|
||||
|
||||
### Requirement: Two-finger enrollment flow
|
||||
The wizard SHALL enroll a profile by: selecting a permitted domain, looking
|
||||
up staff by reference (OTP-validated through the a2loft proxy), displaying
|
||||
up staff by reference (token-validated through the a2loft proxy), displaying
|
||||
the staff details, capturing the right thumb and right index finger, and
|
||||
saving both fingerprints through the a2loft proxy with an OTP. The wizard
|
||||
SHALL offer per-finger recapture until save, SHALL require both fingers
|
||||
before save, and SHALL reset domain-independent state (reference, staff
|
||||
details, captured artifacts) when starting a new enrollment.
|
||||
saving both fingerprints through the a2loft proxy authenticated with the
|
||||
session token. The wizard SHALL offer per-finger recapture until save, SHALL
|
||||
require both fingers before save, and SHALL reset domain-independent state
|
||||
(reference, staff details, captured artifacts) when starting a new
|
||||
enrollment.
|
||||
|
||||
#### Scenario: Complete enrollment
|
||||
- **WHEN** the operator looks up staff, captures both fingers, and saves
|
||||
with an OTP
|
||||
- **THEN** both fingerprints are saved through the a2loft proxy and the
|
||||
wizard reports success
|
||||
|
||||
@@ -137,24 +137,6 @@ details, captured artifacts) when starting a new enrollment.
|
||||
- **THEN** the reference, staff details, and captured finger artifacts are
|
||||
cleared while the permitted domain list persists
|
||||
|
||||
### Requirement: OTP validated on every a2loft call
|
||||
The wizard SHALL collect an OTP for each a2loft call — staff lookup and
|
||||
fingerprint save — and pass it to the same-origin proxy; a2loft validates it.
|
||||
Submission SHALL be blocked while the OTP is missing.
|
||||
|
||||
#### Scenario: Lookup with OTP
|
||||
- **WHEN** the operator submits a reference with an OTP
|
||||
- **THEN** the wizard calls the staff-lookup proxy with that OTP and
|
||||
displays the returned staff details
|
||||
|
||||
#### Scenario: Save requires a fresh OTP
|
||||
- **WHEN** the operator saves the captured fingerprints
|
||||
- **THEN** the wizard sends the OTP entered for the save call
|
||||
|
||||
#### Scenario: Missing OTP blocks submission
|
||||
- **WHEN** the OTP field is empty for a lookup or save
|
||||
- **THEN** the corresponding submit control is disabled
|
||||
|
||||
### Requirement: Scanner availability is shown and gates capture
|
||||
The wizard SHALL consume fpagent's `fprint-device-status`
|
||||
`{available, device, captureAgentId}` event and SHALL distinguish the agent
|
||||
@@ -195,3 +177,23 @@ guarantee a capture will succeed.
|
||||
- **WHEN** the agent socket disconnects
|
||||
- **THEN** the wizard shows the agent offline and does not present the reader as
|
||||
available
|
||||
|
||||
### Requirement: Token authenticated on every a2loft call
|
||||
The wizard SHALL authenticate each a2loft call — staff lookup and fingerprint
|
||||
save — with the signed-in operator's PocketBase session token, sent by the
|
||||
same-origin proxy as an `Authorization: Bearer` credential. The wizard SHALL
|
||||
NOT collect an OTP.
|
||||
|
||||
#### Scenario: Lookup uses the session token
|
||||
- **WHEN** the operator submits a reference
|
||||
- **THEN** the wizard calls the staff-lookup proxy and a2loft authenticates the
|
||||
session token
|
||||
|
||||
#### Scenario: Save uses the session token
|
||||
- **WHEN** the operator saves the captured fingerprints
|
||||
- **THEN** the wizard calls the fingerprint-save proxy and a2loft authenticates
|
||||
the session token
|
||||
|
||||
#### Scenario: No OTP field
|
||||
- **WHEN** the wizard page is served
|
||||
- **THEN** it offers no OTP input for lookup or save
|
||||
|
||||
@@ -17,6 +17,7 @@ Cropper (`/cropper`) and to the Fingerprint Agent page (`/fingerprint`).
|
||||
- **WHEN** a user opens the app root URL
|
||||
- **THEN** the page shows a link to the Image Cropper pointing at
|
||||
`/cropper` and a link to `/fingerprint`
|
||||
|
||||
### Requirement: YOUreka Auth login establishes a cookie session
|
||||
The app SHALL authenticate operators through the YOUreka portal web-auth
|
||||
flow: create a web auth session at the portal with a local callback URL,
|
||||
@@ -100,17 +101,21 @@ portal.
|
||||
### Requirement: a2loft proxies inject operator identity
|
||||
The app SHALL proxy staff lookup and fingerprint-save calls to
|
||||
`https://apis.a2loft.net` under same-origin API routes. The proxy SHALL
|
||||
attach the operator's phone from the server-side session and forward the
|
||||
OTP supplied by the page as query parameters (`phone`, `otp`), preserving
|
||||
the a2loft request and response shapes. The proxies SHALL require a
|
||||
session; the OTP SHALL NOT be accepted without one.
|
||||
authenticate the operator with the signed-in session's PocketBase token, sent
|
||||
as an `Authorization: Bearer` credential, preserving the a2loft request and
|
||||
response shapes. The proxies SHALL require a session; a request without one
|
||||
SHALL be rejected without contacting a2loft. The proxies SHALL NOT forward or
|
||||
require an OTP.
|
||||
|
||||
#### Scenario: Staff lookup via proxy
|
||||
- **WHEN** the page requests staff details for a domain and reference with
|
||||
an OTP
|
||||
- **THEN** the app calls a2loft's identity endpoint with the operator's
|
||||
phone from the session and the supplied OTP, and returns a2loft's
|
||||
response unchanged
|
||||
- **WHEN** the page requests staff details for a domain and reference
|
||||
- **THEN** the app calls a2loft's identity endpoint with the session token as a
|
||||
bearer credential and returns a2loft's response unchanged
|
||||
|
||||
#### Scenario: Fingerprint save via proxy
|
||||
- **WHEN** the page saves fingerprints for a domain and reference
|
||||
- **THEN** the app posts them to a2loft's fingerprint endpoint with the session
|
||||
token as a bearer credential
|
||||
|
||||
#### Scenario: Unauthenticated proxy call rejected
|
||||
- **WHEN** a proxy route is called without a valid session
|
||||
|
||||
Reference in New Issue
Block a user