@sekyro/node 0.0.0-stage → 0.1.0-rc.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +23 -0
- package/LICENSE +20 -0
- package/README.md +157 -2
- package/dist/index.cjs +308 -0
- package/dist/index.cjs.map +1 -0
- package/dist/index.d.cts +404 -0
- package/dist/index.d.ts +404 -0
- package/dist/index.js +272 -0
- package/dist/index.js.map +1 -0
- package/package.json +66 -4
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../src/errors.ts","../src/version.ts","../src/client.ts","../src/webhooks.ts"],"sourcesContent":["/** Why {@link verifyWebhook} rejected a delivery. @public */\nexport type SekyroWebhookErrorCode = \"invalid_signature\" | \"stale\" | \"malformed\";\n\nconst WEBHOOK_MESSAGES: Record<SekyroWebhookErrorCode, string> = {\n invalid_signature: \"No v1 signature in the header matches this body and secret\",\n stale: \"Delivery timestamp is outside the tolerance window\",\n malformed: \"Signature header or body is not in the expected format\",\n};\n\n/**\n * Thrown by {@link verifyWebhook}. Respond with a 4xx and do not process the\n * body; Sekyro retries deliveries that do not receive a 2xx.\n * @public\n */\nexport class SekyroWebhookError extends Error {\n override readonly name = \"SekyroWebhookError\";\n readonly code: SekyroWebhookErrorCode;\n\n constructor(code: SekyroWebhookErrorCode, message: string = WEBHOOK_MESSAGES[code]) {\n super(message);\n this.code = code;\n }\n}\n\n/** Why the {@link Sekyro} constructor rejected its options. @public */\nexport type SekyroConfigErrorCode = \"missing_api_key\" | \"invalid_base_url\";\n\nconst CONFIG_MESSAGES: Record<SekyroConfigErrorCode, string> = {\n missing_api_key: \"Sekyro: `apiKey` is required\",\n invalid_base_url:\n \"Sekyro: `baseUrl` must be an https: URL (http: is allowed only for localhost, 127.0.0.1 or [::1])\",\n};\n\n/**\n * Thrown synchronously by `new Sekyro(...)` for an unusable configuration —\n * before any request is made. Extends `TypeError` so existing\n * `instanceof TypeError` guards keep working.\n * @public\n */\nexport class SekyroConfigError extends TypeError {\n override readonly name = \"SekyroConfigError\";\n readonly code: SekyroConfigErrorCode;\n\n constructor(code: SekyroConfigErrorCode, message: string = CONFIG_MESSAGES[code]) {\n super(message);\n this.code = code;\n }\n}\n\n/** Constructor input of {@link SekyroApiError}. @public */\nexport interface SekyroApiErrorInit {\n /** HTTP status; `0` when no response was received (network / timeout). */\n status: number;\n /** API error code, or `network` | `timeout` | `http_error` | `malformed_response`. */\n code: string;\n message: string;\n /** The API's `request_id`, when the response carried one. */\n requestId?: string;\n /** Underlying error (network failures, abort reasons, JSON parse errors). */\n cause?: unknown;\n}\n\n/** Error codes the SDK itself produces (as opposed to codes from the API). @public */\nexport type SekyroClientErrorCode = \"network\" | \"timeout\" | \"http_error\" | \"malformed_response\";\n\n/**\n * Any failed call through {@link Sekyro}: a non-2xx partner envelope\n * `{ status: 'error', error: { code, message, request_id } }`, a non-JSON\n * response, a network failure or a timeout.\n *\n * `retryable` is `true` for `network`, `timeout`, HTTP 429, HTTP 5xx and the\n * `idempotency_in_progress` code — retry with the SAME idempotency key.\n * @public\n */\nexport class SekyroApiError extends Error {\n override readonly name = \"SekyroApiError\";\n readonly status: number;\n readonly code: string;\n readonly requestId: string | undefined;\n readonly retryable: boolean;\n\n constructor(init: SekyroApiErrorInit) {\n super(init.message, init.cause === undefined ? undefined : { cause: init.cause });\n this.status = init.status;\n this.code = init.code;\n this.requestId = init.requestId;\n this.retryable = isRetryable(init.status, init.code);\n }\n}\n\n/** The retry taxonomy, in one place. */\nexport function isRetryable(status: number, code: string): boolean {\n if (code === \"network\" || code === \"timeout\") return true;\n if (code === \"idempotency_in_progress\") return true;\n if (status === 429) return true;\n return status >= 500 && status <= 599;\n}\n","/**\n * Build-time constant injected from `package.json#version` by tsup (`define`,\n * see tsup.config.ts) and by vitest (vitest.config.ts), so a Changesets version\n * bump flows into the `User-Agent` with no hand edit. `test/version.test.ts`\n * asserts both the injection and that the built dist embeds the version.\n * The fallback only appears when the source runs without either (bare `tsx`).\n */\ndeclare const __SEKYRO_NODE_VERSION__: string | undefined;\n\nexport const SDK_VERSION: string =\n typeof __SEKYRO_NODE_VERSION__ === \"string\" ? __SEKYRO_NODE_VERSION__ : \"0.0.0-dev\";\n","import { SekyroApiError, SekyroConfigError } from \"./errors\";\nimport type { CreatedSession, CreateSessionInput, RequestOptions, Session } from \"./types\";\nimport { SDK_VERSION } from \"./version\";\n\n/** Sent as the `User-Agent` so support can tell SDK versions apart (`SDK_VERSION` is injected from package.json at build time). */\nconst USER_AGENT = `@sekyro/node/${SDK_VERSION}`;\n\n/** Default partner API origin + version prefix. @public */\nexport const DEFAULT_BASE_URL = \"https://api.sekyro.ai/api/v2\";\n\n/** Default per-request timeout. @public */\nexport const DEFAULT_TIMEOUT_MS = 30_000;\n\n/** `fetch`-compatible function; the global `fetch` by default. @public */\nexport type FetchLike = typeof globalThis.fetch;\n\n/** Constructor options of {@link Sekyro}. @public */\nexport interface SekyroOptions {\n /** Partner API key (server-side only). Sent as `Authorization: Bearer`. */\n apiKey: string;\n /** API base URL incl. the `/api/v2` prefix. Default {@link DEFAULT_BASE_URL}. */\n baseUrl?: string;\n /** Per-request timeout in ms. Default {@link DEFAULT_TIMEOUT_MS}. */\n timeoutMs?: number;\n /** Custom `fetch` (tests, proxies, custom agents). Default `globalThis.fetch`. */\n fetch?: FetchLike;\n}\n\ntype HttpMethod = \"GET\" | \"POST\";\n\n/** The successful partner envelope. */\ninterface SuccessEnvelope<T> {\n success: true;\n data: T;\n}\n\n/** The partner error envelope shaped by the API for the `partner` audience. */\ninterface ErrorEnvelope {\n status: \"error\";\n error: { code: string; message: string; request_id?: string };\n}\n\n/** Wire shape of `POST /sessions` (snake_case fields are mapped by the SDK). */\ninterface CreateSessionWire {\n id: string;\n status: CreatedSession[\"status\"];\n steps: CreatedSession[\"steps\"];\n hosted_url: string;\n client_token: string;\n expiresAt: string;\n}\n\nfunction isSuccessEnvelope(value: unknown): value is SuccessEnvelope<unknown> {\n return (\n typeof value === \"object\" &&\n value !== null &&\n (value as { success?: unknown }).success === true &&\n \"data\" in value\n );\n}\n\nfunction isErrorEnvelope(value: unknown): value is ErrorEnvelope {\n if (typeof value !== \"object\" || value === null) return false;\n const v = value as { status?: unknown; error?: unknown };\n if (v.status !== \"error\" || typeof v.error !== \"object\" || v.error === null) return false;\n const e = v.error as { code?: unknown; message?: unknown };\n return typeof e.code === \"string\" && typeof e.message === \"string\";\n}\n\nfunction isAbortLike(err: unknown): boolean {\n if (typeof err !== \"object\" || err === null) return false;\n const name = (err as { name?: unknown }).name;\n return name === \"TimeoutError\" || name === \"AbortError\";\n}\n\n/** Hosts that may be reached over plain `http:` — a developer's own machine only. */\nconst LOOPBACK_HOSTS = new Set([\"localhost\", \"127.0.0.1\", \"[::1]\"]);\n\n/**\n * The API key travels as a Bearer header on every call, so the base URL MUST be\n * `https:` — except a loopback host (local API during development), where\n * `http:` is accepted. Anything else (an `http:` production host, a non-URL,\n * another scheme) is a configuration error thrown at construction.\n */\nfunction assertSafeBaseUrl(baseUrl: string): void {\n let url: URL;\n try {\n url = new URL(baseUrl);\n } catch {\n throw new SekyroConfigError(\"invalid_base_url\");\n }\n if (url.protocol === \"https:\") return;\n if (url.protocol === \"http:\" && LOOPBACK_HOSTS.has(url.hostname)) return;\n throw new SekyroConfigError(\"invalid_base_url\");\n}\n\n/**\n * Low-level transport shared by the resources: one `fetch` per call with a\n * timeout, Bearer auth, optional idempotency key, the `{ success, data }`\n * unwrap and the error mapping to {@link SekyroApiError}.\n */\nclass Transport {\n private readonly apiKey: string;\n private readonly baseUrl: string;\n private readonly timeoutMs: number;\n private readonly fetchImpl: FetchLike;\n\n constructor(opts: SekyroOptions) {\n const baseUrl = (opts.baseUrl ?? DEFAULT_BASE_URL).replace(/\\/+$/, \"\");\n assertSafeBaseUrl(baseUrl);\n this.apiKey = opts.apiKey;\n this.baseUrl = baseUrl;\n this.timeoutMs = opts.timeoutMs ?? DEFAULT_TIMEOUT_MS;\n this.fetchImpl = opts.fetch ?? globalThis.fetch;\n }\n\n async call<T>(method: HttpMethod, path: string, body?: unknown, idempotencyKey?: string): Promise<T> {\n const headers: Record<string, string> = {\n authorization: `Bearer ${this.apiKey}`,\n accept: \"application/json\",\n \"user-agent\": USER_AGENT,\n };\n if (body !== undefined) headers[\"content-type\"] = \"application/json\";\n if (idempotencyKey !== undefined) headers[\"x-idempotency-key\"] = idempotencyKey;\n\n const init: RequestInit = {\n method,\n headers,\n signal: AbortSignal.timeout(this.timeoutMs),\n };\n if (body !== undefined) init.body = JSON.stringify(body);\n\n let res: Response;\n try {\n res = await this.fetchImpl(`${this.baseUrl}${path}`, init);\n } catch (err) {\n if (isAbortLike(err)) {\n throw new SekyroApiError({\n status: 0,\n code: \"timeout\",\n message: `Request timed out after ${this.timeoutMs}ms`,\n cause: err,\n });\n }\n throw new SekyroApiError({\n status: 0,\n code: \"network\",\n message: `Network error: ${err instanceof Error ? err.message : String(err)}`,\n cause: err,\n });\n }\n\n const text = await res.text();\n let parsed: unknown;\n let parseError: unknown;\n try {\n parsed = text.length > 0 ? JSON.parse(text) : undefined;\n } catch (err) {\n parseError = err;\n }\n\n if (!res.ok) {\n if (isErrorEnvelope(parsed)) {\n const init: ConstructorParameters<typeof SekyroApiError>[0] = {\n status: res.status,\n code: parsed.error.code,\n message: parsed.error.message,\n };\n if (parsed.error.request_id !== undefined) init.requestId = parsed.error.request_id;\n throw new SekyroApiError(init);\n }\n throw new SekyroApiError({\n status: res.status,\n code: \"http_error\",\n message: `HTTP ${res.status}${res.statusText ? ` ${res.statusText}` : \"\"}`,\n });\n }\n\n if (!isSuccessEnvelope(parsed)) {\n throw new SekyroApiError({\n status: res.status,\n code: \"malformed_response\",\n message: \"Response is not a `{ success: true, data }` envelope\",\n cause: parseError,\n });\n }\n return parsed.data as T;\n }\n}\n\n/**\n * `sekyro.sessions` — create and read verification sessions.\n *\n * Exported as a TYPE only (`import type { SessionsApi }`): the class value is\n * not part of the package surface, so it can only be obtained through\n * {@link Sekyro.sessions} — never constructed by hand with an unchecked\n * transport.\n * @public\n */\nexport class SessionsApi {\n /**\n * Constructed by {@link Sekyro}; the transport is kept out of the public\n * surface on purpose (only its bound `call` crosses this boundary).\n * @internal\n */\n constructor(\n private readonly call: <T>(\n method: \"GET\" | \"POST\",\n path: string,\n body?: unknown,\n idempotencyKey?: string,\n ) => Promise<T>,\n ) {}\n\n /**\n * `POST /sessions`. Returns the one-time `clientToken` — hand it to the\n * browser, never persist it. Pass an `idempotencyKey` so a retried call\n * cannot create a second session.\n */\n async create(input: CreateSessionInput = {}, opts: RequestOptions = {}): Promise<CreatedSession> {\n const wire = await this.call<CreateSessionWire>(\"POST\", \"/sessions\", input, opts.idempotencyKey);\n return {\n id: wire.id,\n status: wire.status,\n clientToken: wire.client_token,\n hostedUrl: wire.hosted_url,\n steps: wire.steps,\n expiresAt: wire.expiresAt,\n };\n }\n\n /** `GET /sessions/:id` — the whitelisted view (no client token). */\n async get(id: string): Promise<Session> {\n if (typeof id !== \"string\" || id.length === 0) {\n throw new TypeError(\"sessions.get: `id` must be a non-empty string\");\n }\n return this.call<Session>(\"GET\", `/sessions/${encodeURIComponent(id)}`);\n }\n}\n\n/**\n * Sekyro partner API client. Server-side only: it carries your API key.\n *\n * Throws {@link SekyroConfigError} synchronously when `apiKey` is missing or\n * `baseUrl` is not `https:` (plain `http:` is accepted for `localhost`,\n * `127.0.0.1` and `[::1]` only).\n *\n * @example\n * ```ts\n * const sekyro = new Sekyro({ apiKey: process.env.SEKYRO_API_KEY! });\n * const { id, clientToken } = await sekyro.sessions.create({ input: { nni: \"1357924632\" } });\n * ```\n * @public\n */\nexport class Sekyro {\n readonly sessions: SessionsApi;\n\n constructor(opts: SekyroOptions) {\n if (typeof opts?.apiKey !== \"string\" || opts.apiKey.length === 0) {\n throw new SekyroConfigError(\"missing_api_key\");\n }\n const transport = new Transport(opts);\n this.sessions = new SessionsApi(transport.call.bind(transport));\n }\n}\n","import { createHmac, timingSafeEqual } from \"node:crypto\";\nimport { SekyroWebhookError } from \"./errors\";\nimport type { WebhookEnvelope } from \"./types\";\n\n/**\n * The HTTP header carrying the webhook signature:\n * `t=<unix seconds>,v1=<hex>[,v1=<hex>]`.\n * @public\n */\nexport const SEKYRO_SIGNATURE_HEADER = \"x-sekyro-signature\";\n\n/**\n * The pre-rebrand name of the signature header. Sekyro sends BOTH headers with\n * the same value during the transition; prefer {@link SEKYRO_SIGNATURE_HEADER}\n * and use {@link signatureFromHeaders} to accept either.\n * @public\n */\nexport const LEGACY_SIGNATURE_HEADER = \"x-ibtikar-signature\";\n\n/**\n * Pick the signature header out of an incoming request's headers: the\n * `x-sekyro-signature` value when present, else the legacy\n * `x-ibtikar-signature`, else `undefined`. Accepts a Fetch `Headers` object or\n * a Node-style plain record (lower- or mixed-case keys; a multi-valued header\n * yields its first value).\n *\n * @example\n * ```ts\n * verifyWebhook(rawBody, signatureFromHeaders(req.headers), secret);\n * ```\n * @public\n */\nexport function signatureFromHeaders(\n headers: Headers | Record<string, string | string[] | undefined>,\n): string | undefined {\n return readHeader(headers, SEKYRO_SIGNATURE_HEADER) ?? readHeader(headers, LEGACY_SIGNATURE_HEADER);\n}\n\nfunction readHeader(\n headers: Headers | Record<string, string | string[] | undefined>,\n name: string,\n): string | undefined {\n if (typeof (headers as Headers).get === \"function\") {\n const v = (headers as Headers).get(name);\n return v === null || v === \"\" ? undefined : v;\n }\n const record = headers as Record<string, string | string[] | undefined>;\n const key = Object.keys(record).find((k) => k.toLowerCase() === name);\n if (key === undefined) return undefined;\n const raw = record[key];\n const v = Array.isArray(raw) ? raw[0] : raw;\n return v === undefined || v === \"\" ? undefined : v;\n}\n\n/** Options of {@link verifyWebhook}. @public */\nexport interface VerifyWebhookOptions {\n /** Max |now − t| in seconds before a delivery is rejected as `stale`. Default 300. */\n toleranceSec?: number;\n /** Clock returning epoch milliseconds. Default `Date.now`. */\n now?: () => number;\n}\n\nconst HEX64 = /^[0-9a-f]{64}$/i;\n\n/**\n * Verify a Sekyro webhook delivery and return its parsed envelope, discriminated\n * on `event` (narrow with a `switch` to type `data`).\n *\n * - `rawBody` MUST be the request body exactly as received (before any JSON\n * parsing / re-serialisation); the signature covers those bytes.\n * - Accepts the delivery when ANY `v1` in the header matches, which is what\n * makes secret rotation seamless (Sekyro signs with current + previous).\n * - Uses `node:crypto` only; the digest compare is constant-time.\n *\n * Checks run in this order: header/secret present → header well-formed →\n * timestamp within tolerance → signature → body is a JSON object.\n *\n * @param rawBody - The raw UTF-8 request body.\n * @param header - The `x-sekyro-signature` header value (or the legacy\n * `x-ibtikar-signature` — same format; see {@link signatureFromHeaders}).\n * @param secret - The endpoint secret you hold (current or previous).\n * @throws {@link SekyroWebhookError} with `code` `invalid_signature` | `stale` | `malformed`.\n * @public\n */\nexport function verifyWebhook(\n rawBody: string,\n header: string | null | undefined,\n secret: string,\n opts: VerifyWebhookOptions = {},\n): WebhookEnvelope {\n if (!header || !secret) throw new SekyroWebhookError(\"invalid_signature\");\n\n const parts = header.split(\",\").map((part): [string, string] => {\n const trimmed = part.trim();\n const eq = trimmed.indexOf(\"=\");\n return eq === -1 ? [trimmed, \"\"] : [trimmed.slice(0, eq).trim(), trimmed.slice(eq + 1).trim()];\n });\n const tRaw = parts.find(([k]) => k === \"t\")?.[1];\n const t = tRaw !== undefined && /^\\d+$/.test(tRaw) ? Number(tRaw) : Number.NaN;\n const sigs = parts.filter(([k]) => k === \"v1\").map(([, v]) => v);\n if (!Number.isSafeInteger(t) || sigs.length === 0) throw new SekyroWebhookError(\"malformed\");\n\n const nowSec = Math.floor((opts.now?.() ?? Date.now()) / 1000);\n const tolerance = opts.toleranceSec ?? 300;\n if (Math.abs(nowSec - t) > tolerance) throw new SekyroWebhookError(\"stale\");\n\n const expected = createHmac(\"sha256\", secret).update(`${t}.${rawBody}`).digest();\n const ok = sigs.some((hex) => {\n if (!HEX64.test(hex)) return false;\n const got = Buffer.from(hex, \"hex\");\n return got.length === expected.length && timingSafeEqual(got, expected);\n });\n if (!ok) throw new SekyroWebhookError(\"invalid_signature\");\n\n let parsed: unknown;\n try {\n parsed = JSON.parse(rawBody);\n } catch {\n throw new SekyroWebhookError(\"malformed\", \"Signed body is not valid JSON\");\n }\n if (parsed === null || typeof parsed !== \"object\" || Array.isArray(parsed)) {\n throw new SekyroWebhookError(\"malformed\", \"Signed body is not a JSON object\");\n }\n return parsed as WebhookEnvelope;\n}\n"],"mappings":"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","names":["init","v"]}
|
package/package.json
CHANGED
|
@@ -1,6 +1,68 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@sekyro/node",
|
|
3
|
-
"version": "0.
|
|
4
|
-
"
|
|
5
|
-
"
|
|
6
|
-
|
|
3
|
+
"version": "0.1.0-rc.2",
|
|
4
|
+
"description": "Sekyro server SDK for Node.js — create and read verification sessions, verify signed webhooks. Zero runtime dependencies.",
|
|
5
|
+
"license": "UNLICENSED",
|
|
6
|
+
"type": "module",
|
|
7
|
+
"sideEffects": false,
|
|
8
|
+
"main": "./dist/index.cjs",
|
|
9
|
+
"module": "./dist/index.js",
|
|
10
|
+
"types": "./dist/index.d.ts",
|
|
11
|
+
"exports": {
|
|
12
|
+
".": {
|
|
13
|
+
"import": {
|
|
14
|
+
"types": "./dist/index.d.ts",
|
|
15
|
+
"default": "./dist/index.js"
|
|
16
|
+
},
|
|
17
|
+
"require": {
|
|
18
|
+
"types": "./dist/index.d.cts",
|
|
19
|
+
"default": "./dist/index.cjs"
|
|
20
|
+
}
|
|
21
|
+
},
|
|
22
|
+
"./package.json": "./package.json"
|
|
23
|
+
},
|
|
24
|
+
"files": [
|
|
25
|
+
"dist",
|
|
26
|
+
"README.md",
|
|
27
|
+
"CHANGELOG.md",
|
|
28
|
+
"LICENSE"
|
|
29
|
+
],
|
|
30
|
+
"engines": {
|
|
31
|
+
"node": ">=20"
|
|
32
|
+
},
|
|
33
|
+
"publishConfig": {
|
|
34
|
+
"access": "public"
|
|
35
|
+
},
|
|
36
|
+
"repository": {
|
|
37
|
+
"type": "git",
|
|
38
|
+
"url": "git+https://github.com/IBTIKAR-Technologies/sekyro-sdks.git",
|
|
39
|
+
"directory": "packages/sekyro-node"
|
|
40
|
+
},
|
|
41
|
+
"homepage": "https://github.com/IBTIKAR-Technologies/sekyro-sdks/tree/main/packages/sekyro-node#readme",
|
|
42
|
+
"bugs": {
|
|
43
|
+
"url": "https://github.com/IBTIKAR-Technologies/sekyro-sdks/issues"
|
|
44
|
+
},
|
|
45
|
+
"keywords": [
|
|
46
|
+
"sekyro",
|
|
47
|
+
"kyc",
|
|
48
|
+
"identity-verification",
|
|
49
|
+
"liveness",
|
|
50
|
+
"webhooks",
|
|
51
|
+
"mauritania",
|
|
52
|
+
"sdk"
|
|
53
|
+
],
|
|
54
|
+
"scripts": {
|
|
55
|
+
"build": "tsup",
|
|
56
|
+
"test": "vitest run",
|
|
57
|
+
"typecheck": "tsc --noEmit",
|
|
58
|
+
"api:report": "api-extractor run --local",
|
|
59
|
+
"api:check": "api-extractor run"
|
|
60
|
+
},
|
|
61
|
+
"devDependencies": {
|
|
62
|
+
"@microsoft/api-extractor": "^7",
|
|
63
|
+
"@types/node": "^20",
|
|
64
|
+
"tsup": "^8",
|
|
65
|
+
"typescript": "^5.7",
|
|
66
|
+
"vitest": "^3"
|
|
67
|
+
}
|
|
68
|
+
}
|