@nuggetslife/vc-verifier-server
v1.0.1
Published
OIDC4VP verifier server — create verification requests for Verifiable Presentations and validate wallet responses.
Keywords
Readme
@nuggetslife/vc-verifier-server
OIDC4VP verifier server — create verification requests for Verifiable Presentations and validate wallet responses.
Install
pnpm add @nuggetslife/vc-verifier-serverQuick start
import { createVerifierServer } from "@nuggetslife/vc-verifier-server";
const { router, createRequest } = await createVerifierServer({
clientId: "did:web:example.com",
domain: "https://example.com",
privateKey: /* ES256 JWK */,
publicKey: /* ES256 JWK */,
onVerificationResult: (payload) => {
if (payload.status === "verified") {
console.log("VP verified", payload.vpToken);
} else {
console.error("Verification failed", payload.error);
}
},
});
// Wire routes into a Bun server
Bun.serve({ port: 3000, fetch: router });
// Create a presentation request
const result = await createRequest({ type: "kye-basic-v1" });
console.log(result.qrUrl); // nuggets://present?request_uri=...Configuration
| Field | Type | Required | Description |
|---|---|---|---|
| clientId | string | Yes | did:web: DID of the verifier |
| domain | string | Yes | Public domain the server is hosted on |
| privateKey | JWK | Yes | ES256 private key for signing requests |
| publicKey | JWK | Yes | Matching ES256 public key |
| onVerificationResult | (payload) => void | Yes | Callback when a VP is verified or fails |
| onStatusChange | (requestId, status) => void | No | Callback on request status transitions |
| ttl | Partial<TtlConfig> | No | TTL overrides (see below) |
| storage | StorageAdapter | No | Custom storage adapter (defaults to in-memory) |
Request types
| Key | Description |
|---|---|
| kye-basic-v1 | Know Your Entity — address, email, phone, social |
| kyb-basic-v1 | Know Your Business — business identity, DUNS, address |
| right-to-work-basic-v1 | Right to Work — identity, document type, selfie |
Pass via createRequest({ type: "kye-basic-v1" }). Optional fields: ttlSeconds, purpose, transactionData.
API endpoints
| Method | Path | Description |
|---|---|---|
| GET | /did.json | DID document with verification method |
| GET | /.well-known/did.json | Alias for /did.json |
| POST | /oidc/requests | Create a new presentation request |
| GET | /oidc/requests/:id | Retrieve signed request object (marks as SCANNED) |
| POST | /oidc/response | Submit VP token + presentation submission |
Custom storage
Implement the StorageAdapter interface for production use:
type StorageAdapter = {
save(record: RequestRecord): Promise<void>;
get(recordId: string): Promise<RequestRecord | null>;
markUsed(recordId: string): Promise<void>;
markExpired(recordId: string): Promise<void>;
markScanned(recordId: string): Promise<void>;
getByState(state: string): Promise<RequestRecord | null>;
nonceUsed(record: RequestRecord): Promise<boolean>;
};If no adapter is provided, an in-memory store is used (not suitable for production).
TTL config
| Field | Default | Description |
|---|---|---|
| defaultTtlSeconds | 120 | Default request lifetime |
| minTtlSeconds | 30 | Minimum allowed TTL |
| maxTtlSeconds | 300 | Maximum allowed TTL |
| skewSeconds | 30 | Grace period for expiry checks |
License
MIT
