@nextera.one/axis-server-sdk 0.8.0 → 0.9.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/dist/index.mjs CHANGED
@@ -1368,10 +1368,10 @@ function tlv(type, value) {
1368
1368
  ]);
1369
1369
  }
1370
1370
  function buildTLVs(items, opts) {
1371
- const allow = opts?.allowDupTypes ?? /* @__PURE__ */ new Set();
1371
+ const allow2 = opts?.allowDupTypes ?? /* @__PURE__ */ new Set();
1372
1372
  const sorted = [...items].sort((a, b) => a.type - b.type);
1373
1373
  for (let i = 1; i < sorted.length; i++) {
1374
- if (sorted[i].type === sorted[i - 1].type && !allow.has(sorted[i].type)) {
1374
+ if (sorted[i].type === sorted[i - 1].type && !allow2.has(sorted[i].type)) {
1375
1375
  throw new Error(`TLV_DUP_TYPE_${sorted[i].type}`);
1376
1376
  }
1377
1377
  }
@@ -1941,9 +1941,33 @@ var INTENT_REQUIREMENTS = {
1941
1941
  "passport.revoke": ["write", "witness"],
1942
1942
  "stream.publish": ["write"],
1943
1943
  "stream.subscribe": ["read"],
1944
+ // NestFlow intents
1945
+ "auth.web.login.*": ["execute"],
1946
+ "tickauth.challenge.*": ["execute"],
1947
+ "capsule.issue.*": ["write", "execute"],
1948
+ "session.*": ["execute"],
1949
+ "device.list": ["read"],
1950
+ "device.rename": ["write"],
1951
+ "device.trust.*": ["write", "execute"],
1952
+ "device.revoke": ["write", "execute"],
1953
+ "identity.*": ["admin", "execute"],
1954
+ "primary.device.*": ["admin", "execute"],
1955
+ "secret.rotate": ["admin"],
1956
+ "org.security.*": ["admin"],
1957
+ "production.execution.*": ["admin", "execute"],
1944
1958
  "admin.*": ["admin"]
1945
1959
  };
1946
1960
 
1961
+ // src/risk/index.ts
1962
+ var RiskDecision = /* @__PURE__ */ ((RiskDecision2) => {
1963
+ RiskDecision2["ALLOW"] = "ALLOW";
1964
+ RiskDecision2["THROTTLE"] = "THROTTLE";
1965
+ RiskDecision2["STEP_UP"] = "STEP_UP";
1966
+ RiskDecision2["WITNESS"] = "WITNESS";
1967
+ RiskDecision2["DENY"] = "DENY";
1968
+ return RiskDecision2;
1969
+ })(RiskDecision || {});
1970
+
1947
1971
  // src/core/opcodes.ts
1948
1972
  var AXIS_OPCODES = /* @__PURE__ */ new Set([
1949
1973
  "CAPSULE.ISSUE",
@@ -1952,13 +1976,29 @@ var AXIS_OPCODES = /* @__PURE__ */ new Set([
1952
1976
  "INTENT.EXEC",
1953
1977
  "ACTOR.KEY.ROTATE",
1954
1978
  "ACTOR.KEY.REVOKE",
1955
- "ISSUER.KEY.ROTATE"
1979
+ "ISSUER.KEY.ROTATE",
1980
+ // NestFlow opcodes
1981
+ "AUTH.WEB.LOGIN",
1982
+ "AUTH.WEB.SCAN",
1983
+ "TICKAUTH.CREATE",
1984
+ "TICKAUTH.FULFILL",
1985
+ "TICKAUTH.REJECT",
1986
+ "SESSION.ACTIVATE",
1987
+ "SESSION.REFRESH",
1988
+ "SESSION.LOGOUT",
1989
+ "DEVICE.TRUST",
1990
+ "DEVICE.PROMOTE",
1991
+ "DEVICE.REVOKE",
1992
+ "DEVICE.LIST",
1993
+ "DEVICE.RENAME",
1994
+ "IDENTITY.RECOVERY",
1995
+ "IDENTITY.LOCK"
1956
1996
  ]);
1957
1997
  function isKnownOpcode(op) {
1958
1998
  return AXIS_OPCODES.has(op);
1959
1999
  }
1960
2000
  function isAdminOpcode(op) {
1961
- return op.startsWith("ACTOR.KEY.") || op.startsWith("ISSUER.KEY.");
2001
+ return op.startsWith("ACTOR.KEY.") || op.startsWith("ISSUER.KEY.") || op.startsWith("IDENTITY.");
1962
2002
  }
1963
2003
 
1964
2004
  // src/core/receipt.ts
@@ -2008,7 +2048,42 @@ var INTENT_SENSITIVITY_MAP = {
2008
2048
  // Admin intents
2009
2049
  "admin.create_capsule": 4 /* CRITICAL */,
2010
2050
  "admin.revoke_capsule": 4 /* CRITICAL */,
2011
- "admin.issue_node_cert": 4 /* CRITICAL */
2051
+ "admin.issue_node_cert": 4 /* CRITICAL */,
2052
+ // NestFlow: Auth
2053
+ "auth.web.login.request": 2 /* MEDIUM */,
2054
+ "auth.web.login.scan": 3 /* HIGH */,
2055
+ // NestFlow: TickAuth
2056
+ "tickauth.challenge.create": 2 /* MEDIUM */,
2057
+ "tickauth.challenge.fulfill": 3 /* HIGH */,
2058
+ "tickauth.challenge.reject": 2 /* MEDIUM */,
2059
+ // NestFlow: Capsule issuance
2060
+ "capsule.issue.login": 3 /* HIGH */,
2061
+ "capsule.issue.device_registration": 3 /* HIGH */,
2062
+ "capsule.issue.step_up": 3 /* HIGH */,
2063
+ "capsule.issue.recovery": 4 /* CRITICAL */,
2064
+ // NestFlow: Session
2065
+ "session.activate": 3 /* HIGH */,
2066
+ "session.refresh": 2 /* MEDIUM */,
2067
+ "session.logout": 1 /* LOW */,
2068
+ // NestFlow: Device trust
2069
+ "device.trust.request": 3 /* HIGH */,
2070
+ "device.trust.promote": 4 /* CRITICAL */,
2071
+ "device.revoke": 4 /* CRITICAL */,
2072
+ "device.list": 1 /* LOW */,
2073
+ "device.rename": 1 /* LOW */,
2074
+ // NestFlow: Protected operations
2075
+ "flow.publish": 2 /* MEDIUM */,
2076
+ "flow.delete": 3 /* HIGH */,
2077
+ "node.delete": 4 /* CRITICAL */,
2078
+ "secret.rotate": 4 /* CRITICAL */,
2079
+ "org.security.update": 4 /* CRITICAL */,
2080
+ "production.execution.approve": 4 /* CRITICAL */,
2081
+ // NestFlow: Recovery
2082
+ "identity.recovery.start": 4 /* CRITICAL */,
2083
+ "identity.recovery.complete": 4 /* CRITICAL */,
2084
+ "primary.device.rotate": 4 /* CRITICAL */,
2085
+ "identity.lock": 4 /* CRITICAL */,
2086
+ "identity.unlock": 4 /* CRITICAL */
2012
2087
  };
2013
2088
  function classifyIntent(intent) {
2014
2089
  if (INTENT_SENSITIVITY_MAP[intent]) {
@@ -2063,6 +2138,468 @@ function resolveTimeout(intent) {
2063
2138
  }
2064
2139
  return DEFAULT_TIMEOUT;
2065
2140
  }
2141
+
2142
+ // src/core/frame-validator.ts
2143
+ function validateFrameShape(frame) {
2144
+ if (!frame || typeof frame !== "object") {
2145
+ return false;
2146
+ }
2147
+ if (frame.v !== 1) {
2148
+ return false;
2149
+ }
2150
+ const requiredStrings = ["pid", "nonce", "actorId", "opcode"];
2151
+ for (const key of requiredStrings) {
2152
+ if (typeof frame[key] !== "string" || frame[key].length < 6) {
2153
+ return false;
2154
+ }
2155
+ }
2156
+ if (typeof frame.ts !== "number" || !Number.isFinite(frame.ts)) {
2157
+ return false;
2158
+ }
2159
+ if (frame.aud !== void 0 && (typeof frame.aud !== "string" || frame.aud.length === 0)) {
2160
+ return false;
2161
+ }
2162
+ if (!frame.sig || typeof frame.sig !== "object") {
2163
+ return false;
2164
+ }
2165
+ if (frame.sig.alg !== "EdDSA") {
2166
+ return false;
2167
+ }
2168
+ if (typeof frame.sig.kid !== "string" || frame.sig.kid.length < 8) {
2169
+ return false;
2170
+ }
2171
+ if (typeof frame.sig.value !== "string" || frame.sig.value.length < 32) {
2172
+ return false;
2173
+ }
2174
+ if (typeof frame.body !== "object" || frame.body === null) {
2175
+ return false;
2176
+ }
2177
+ return true;
2178
+ }
2179
+ function isTimestampValid(ts, skewSeconds = 120) {
2180
+ const now = Math.floor(Date.now() / 1e3);
2181
+ const diff = Math.abs(now - ts);
2182
+ return diff <= skewSeconds;
2183
+ }
2184
+
2185
+ // src/nestflow/types.ts
2186
+ var DeviceType = /* @__PURE__ */ ((DeviceType2) => {
2187
+ DeviceType2["MOBILE"] = "mobile";
2188
+ DeviceType2["BROWSER"] = "browser";
2189
+ DeviceType2["CLI"] = "cli";
2190
+ DeviceType2["SERVICE"] = "service";
2191
+ return DeviceType2;
2192
+ })(DeviceType || {});
2193
+ var DeviceTrustLevel = /* @__PURE__ */ ((DeviceTrustLevel2) => {
2194
+ DeviceTrustLevel2["PRIMARY"] = "primary";
2195
+ DeviceTrustLevel2["TRUSTED"] = "trusted";
2196
+ DeviceTrustLevel2["EPHEMERAL"] = "ephemeral";
2197
+ return DeviceTrustLevel2;
2198
+ })(DeviceTrustLevel || {});
2199
+ var DeviceStatus = /* @__PURE__ */ ((DeviceStatus2) => {
2200
+ DeviceStatus2["ACTIVE"] = "active";
2201
+ DeviceStatus2["REVOKED"] = "revoked";
2202
+ DeviceStatus2["SUSPENDED"] = "suspended";
2203
+ return DeviceStatus2;
2204
+ })(DeviceStatus || {});
2205
+ var LoginChallengeStatus = /* @__PURE__ */ ((LoginChallengeStatus3) => {
2206
+ LoginChallengeStatus3["PENDING"] = "pending";
2207
+ LoginChallengeStatus3["SCANNED"] = "scanned";
2208
+ LoginChallengeStatus3["APPROVED"] = "approved";
2209
+ LoginChallengeStatus3["REJECTED"] = "rejected";
2210
+ LoginChallengeStatus3["EXPIRED"] = "expired";
2211
+ return LoginChallengeStatus3;
2212
+ })(LoginChallengeStatus || {});
2213
+ var TickAuthChallengeStatus = /* @__PURE__ */ ((TickAuthChallengeStatus2) => {
2214
+ TickAuthChallengeStatus2["PENDING"] = "pending";
2215
+ TickAuthChallengeStatus2["FULFILLED"] = "fulfilled";
2216
+ TickAuthChallengeStatus2["REJECTED"] = "rejected";
2217
+ TickAuthChallengeStatus2["EXPIRED"] = "expired";
2218
+ return TickAuthChallengeStatus2;
2219
+ })(TickAuthChallengeStatus || {});
2220
+ var NestFlowCapsuleType = /* @__PURE__ */ ((NestFlowCapsuleType2) => {
2221
+ NestFlowCapsuleType2["LOGIN"] = "login";
2222
+ NestFlowCapsuleType2["DEVICE_REGISTRATION"] = "device_registration";
2223
+ NestFlowCapsuleType2["STEP_UP"] = "step_up";
2224
+ NestFlowCapsuleType2["RECOVERY"] = "recovery";
2225
+ return NestFlowCapsuleType2;
2226
+ })(NestFlowCapsuleType || {});
2227
+ var CapsuleStatus = /* @__PURE__ */ ((CapsuleStatus2) => {
2228
+ CapsuleStatus2["ACTIVE"] = "active";
2229
+ CapsuleStatus2["CONSUMED"] = "consumed";
2230
+ CapsuleStatus2["REVOKED"] = "revoked";
2231
+ CapsuleStatus2["EXPIRED"] = "expired";
2232
+ return CapsuleStatus2;
2233
+ })(CapsuleStatus || {});
2234
+ var SessionStatus = /* @__PURE__ */ ((SessionStatus2) => {
2235
+ SessionStatus2["ACTIVE"] = "active";
2236
+ SessionStatus2["EXPIRED"] = "expired";
2237
+ SessionStatus2["REVOKED"] = "revoked";
2238
+ return SessionStatus2;
2239
+ })(SessionStatus || {});
2240
+ var TrustLinkType = /* @__PURE__ */ ((TrustLinkType2) => {
2241
+ TrustLinkType2["LOGIN"] = "login";
2242
+ TrustLinkType2["PROMOTION"] = "promotion";
2243
+ TrustLinkType2["RECOVERY"] = "recovery";
2244
+ return TrustLinkType2;
2245
+ })(TrustLinkType || {});
2246
+ var TrustLinkStatus = /* @__PURE__ */ ((TrustLinkStatus2) => {
2247
+ TrustLinkStatus2["ACTIVE"] = "active";
2248
+ TrustLinkStatus2["REVOKED"] = "revoked";
2249
+ return TrustLinkStatus2;
2250
+ })(TrustLinkStatus || {});
2251
+ var AuthLevel = /* @__PURE__ */ ((AuthLevel2) => {
2252
+ AuthLevel2["SESSION"] = "session";
2253
+ AuthLevel2["SESSION_BROWSER"] = "session_browser";
2254
+ AuthLevel2["STEP_UP"] = "step_up";
2255
+ AuthLevel2["PRIMARY_DEVICE"] = "primary_device";
2256
+ return AuthLevel2;
2257
+ })(AuthLevel || {});
2258
+
2259
+ // src/nestflow/intents.ts
2260
+ var NESTFLOW_INTENTS = {
2261
+ // Auth
2262
+ AUTH_WEB_LOGIN_REQUEST: "auth.web.login.request",
2263
+ AUTH_WEB_LOGIN_SCAN: "auth.web.login.scan",
2264
+ // TickAuth
2265
+ TICKAUTH_CHALLENGE_CREATE: "tickauth.challenge.create",
2266
+ TICKAUTH_CHALLENGE_FULFILL: "tickauth.challenge.fulfill",
2267
+ TICKAUTH_CHALLENGE_REJECT: "tickauth.challenge.reject",
2268
+ // Capsule
2269
+ CAPSULE_ISSUE_LOGIN: "capsule.issue.login",
2270
+ CAPSULE_ISSUE_DEVICE_REGISTRATION: "capsule.issue.device_registration",
2271
+ CAPSULE_ISSUE_STEP_UP: "capsule.issue.step_up",
2272
+ CAPSULE_ISSUE_RECOVERY: "capsule.issue.recovery",
2273
+ // Session
2274
+ SESSION_ACTIVATE: "session.activate",
2275
+ SESSION_REFRESH: "session.refresh",
2276
+ SESSION_LOGOUT: "session.logout",
2277
+ // Device Trust
2278
+ DEVICE_TRUST_REQUEST: "device.trust.request",
2279
+ DEVICE_TRUST_PROMOTE: "device.trust.promote",
2280
+ DEVICE_REVOKE: "device.revoke",
2281
+ DEVICE_LIST: "device.list",
2282
+ DEVICE_RENAME: "device.rename",
2283
+ // Protected Operations
2284
+ FLOW_PUBLISH: "flow.publish",
2285
+ FLOW_DELETE: "flow.delete",
2286
+ NODE_DELETE: "node.delete",
2287
+ SECRET_ROTATE: "secret.rotate",
2288
+ ORG_SECURITY_UPDATE: "org.security.update",
2289
+ PRODUCTION_EXECUTION_APPROVE: "production.execution.approve",
2290
+ // Recovery
2291
+ IDENTITY_RECOVERY_START: "identity.recovery.start",
2292
+ IDENTITY_RECOVERY_COMPLETE: "identity.recovery.complete",
2293
+ PRIMARY_DEVICE_ROTATE: "primary.device.rotate",
2294
+ IDENTITY_LOCK: "identity.lock",
2295
+ IDENTITY_UNLOCK: "identity.unlock"
2296
+ };
2297
+ var NESTFLOW_INTENT_SET = new Set(
2298
+ Object.values(NESTFLOW_INTENTS)
2299
+ );
2300
+ function isNestFlowIntent(intent) {
2301
+ return NESTFLOW_INTENT_SET.has(intent);
2302
+ }
2303
+
2304
+ // src/nestflow/policy-map.ts
2305
+ var NESTFLOW_POLICY_MAP = {
2306
+ // Auth — unauthenticated initiator (session issued after)
2307
+ [NESTFLOW_INTENTS.AUTH_WEB_LOGIN_REQUEST]: "session" /* SESSION */,
2308
+ [NESTFLOW_INTENTS.AUTH_WEB_LOGIN_SCAN]: "primary_device" /* PRIMARY_DEVICE */,
2309
+ // TickAuth — primary device handles challenges
2310
+ [NESTFLOW_INTENTS.TICKAUTH_CHALLENGE_CREATE]: "session" /* SESSION */,
2311
+ [NESTFLOW_INTENTS.TICKAUTH_CHALLENGE_FULFILL]: "primary_device" /* PRIMARY_DEVICE */,
2312
+ [NESTFLOW_INTENTS.TICKAUTH_CHALLENGE_REJECT]: "primary_device" /* PRIMARY_DEVICE */,
2313
+ // Capsule issuance — varies per type
2314
+ [NESTFLOW_INTENTS.CAPSULE_ISSUE_LOGIN]: "primary_device" /* PRIMARY_DEVICE */,
2315
+ [NESTFLOW_INTENTS.CAPSULE_ISSUE_DEVICE_REGISTRATION]: "primary_device" /* PRIMARY_DEVICE */,
2316
+ [NESTFLOW_INTENTS.CAPSULE_ISSUE_STEP_UP]: "primary_device" /* PRIMARY_DEVICE */,
2317
+ [NESTFLOW_INTENTS.CAPSULE_ISSUE_RECOVERY]: "primary_device" /* PRIMARY_DEVICE */,
2318
+ // Session management
2319
+ [NESTFLOW_INTENTS.SESSION_ACTIVATE]: "session" /* SESSION */,
2320
+ [NESTFLOW_INTENTS.SESSION_REFRESH]: "session_browser" /* SESSION_BROWSER */,
2321
+ [NESTFLOW_INTENTS.SESSION_LOGOUT]: "session" /* SESSION */,
2322
+ // Device trust management
2323
+ [NESTFLOW_INTENTS.DEVICE_TRUST_REQUEST]: "session_browser" /* SESSION_BROWSER */,
2324
+ [NESTFLOW_INTENTS.DEVICE_TRUST_PROMOTE]: "step_up" /* STEP_UP */,
2325
+ [NESTFLOW_INTENTS.DEVICE_REVOKE]: "step_up" /* STEP_UP */,
2326
+ [NESTFLOW_INTENTS.DEVICE_LIST]: "session" /* SESSION */,
2327
+ [NESTFLOW_INTENTS.DEVICE_RENAME]: "session_browser" /* SESSION_BROWSER */,
2328
+ // Protected operations — require step-up auth
2329
+ [NESTFLOW_INTENTS.FLOW_PUBLISH]: "session_browser" /* SESSION_BROWSER */,
2330
+ [NESTFLOW_INTENTS.FLOW_DELETE]: "step_up" /* STEP_UP */,
2331
+ [NESTFLOW_INTENTS.NODE_DELETE]: "step_up" /* STEP_UP */,
2332
+ [NESTFLOW_INTENTS.SECRET_ROTATE]: "step_up" /* STEP_UP */,
2333
+ [NESTFLOW_INTENTS.ORG_SECURITY_UPDATE]: "step_up" /* STEP_UP */,
2334
+ [NESTFLOW_INTENTS.PRODUCTION_EXECUTION_APPROVE]: "step_up" /* STEP_UP */,
2335
+ // Recovery — highest privilege
2336
+ [NESTFLOW_INTENTS.IDENTITY_RECOVERY_START]: "primary_device" /* PRIMARY_DEVICE */,
2337
+ [NESTFLOW_INTENTS.IDENTITY_RECOVERY_COMPLETE]: "primary_device" /* PRIMARY_DEVICE */,
2338
+ [NESTFLOW_INTENTS.PRIMARY_DEVICE_ROTATE]: "primary_device" /* PRIMARY_DEVICE */,
2339
+ [NESTFLOW_INTENTS.IDENTITY_LOCK]: "primary_device" /* PRIMARY_DEVICE */,
2340
+ [NESTFLOW_INTENTS.IDENTITY_UNLOCK]: "primary_device" /* PRIMARY_DEVICE */
2341
+ };
2342
+ function getRequiredAuthLevel(intent) {
2343
+ return NESTFLOW_POLICY_MAP[intent];
2344
+ }
2345
+ var AUTH_LEVEL_ORDER = [
2346
+ "session" /* SESSION */,
2347
+ "session_browser" /* SESSION_BROWSER */,
2348
+ "step_up" /* STEP_UP */,
2349
+ "primary_device" /* PRIMARY_DEVICE */
2350
+ ];
2351
+ function satisfiesAuthLevel(provided, required) {
2352
+ const providedIdx = AUTH_LEVEL_ORDER.indexOf(provided);
2353
+ const requiredIdx = AUTH_LEVEL_ORDER.indexOf(required);
2354
+ return providedIdx >= requiredIdx;
2355
+ }
2356
+
2357
+ // src/nestflow/guards.ts
2358
+ var allow = () => ({ allowed: true });
2359
+ var deny = (reason) => ({ allowed: false, reason });
2360
+ function checkIntentPolicy(intent, currentAuthLevel) {
2361
+ const required = getRequiredAuthLevel(intent);
2362
+ if (!required) {
2363
+ return allow();
2364
+ }
2365
+ if (satisfiesAuthLevel(currentAuthLevel, required)) {
2366
+ return allow();
2367
+ }
2368
+ return {
2369
+ allowed: false,
2370
+ reason: `Intent '${intent}' requires auth level '${required}', got '${currentAuthLevel}'`,
2371
+ step_up_intent: required === "step_up" /* STEP_UP */ ? intent : void 0
2372
+ };
2373
+ }
2374
+ function checkSession(session) {
2375
+ if (!session) {
2376
+ return deny("No session found");
2377
+ }
2378
+ if (session.status !== "active" /* ACTIVE */) {
2379
+ return deny(`Session status is '${session.status}', expected 'active'`);
2380
+ }
2381
+ if (new Date(session.expires_at).getTime() < Date.now()) {
2382
+ return deny("Session has expired");
2383
+ }
2384
+ return allow();
2385
+ }
2386
+ function checkBrowserProof(proof, expectedNonce) {
2387
+ if (!proof) {
2388
+ return deny("Browser proof-of-possession required but not provided");
2389
+ }
2390
+ if (!proof.server_nonce || !proof.signature || !proof.signature_algorithm) {
2391
+ return deny("Browser proof is missing required fields");
2392
+ }
2393
+ if (proof.server_nonce !== expectedNonce) {
2394
+ return deny("Browser proof nonce does not match expected server nonce");
2395
+ }
2396
+ return allow();
2397
+ }
2398
+ var TRUST_ORDER = [
2399
+ "ephemeral" /* EPHEMERAL */,
2400
+ "trusted" /* TRUSTED */,
2401
+ "primary" /* PRIMARY */
2402
+ ];
2403
+ function checkDeviceTrust(device, minimumTrust) {
2404
+ if (!device) {
2405
+ return deny("Device not found");
2406
+ }
2407
+ if (device.status !== "active" /* ACTIVE */) {
2408
+ return deny(`Device status is '${device.status}', expected 'active'`);
2409
+ }
2410
+ const deviceIdx = TRUST_ORDER.indexOf(device.trust_level);
2411
+ const requiredIdx = TRUST_ORDER.indexOf(minimumTrust);
2412
+ if (deviceIdx < requiredIdx) {
2413
+ return deny(
2414
+ `Device trust level '${device.trust_level}' does not meet minimum '${minimumTrust}'`
2415
+ );
2416
+ }
2417
+ return allow();
2418
+ }
2419
+ function checkCapsule(capsule, intent, requestingDeviceUid) {
2420
+ if (!capsule) {
2421
+ return deny("Capsule not found");
2422
+ }
2423
+ if (capsule.status !== "active" /* ACTIVE */) {
2424
+ return deny(`Capsule status is '${capsule.status}', expected 'active'`);
2425
+ }
2426
+ if (new Date(capsule.expires_at).getTime() < Date.now()) {
2427
+ return deny("Capsule has expired");
2428
+ }
2429
+ const intentAllowed = capsule.intents.some((pattern) => {
2430
+ if (pattern === "*") return true;
2431
+ if (pattern === intent) return true;
2432
+ if (pattern.endsWith(".*")) {
2433
+ return intent.startsWith(pattern.slice(0, -1));
2434
+ }
2435
+ return false;
2436
+ });
2437
+ if (!intentAllowed) {
2438
+ return deny(`Capsule does not authorize intent '${intent}'`);
2439
+ }
2440
+ if (capsule.device_uid && requestingDeviceUid && capsule.device_uid !== requestingDeviceUid) {
2441
+ return deny("Capsule is bound to a different device");
2442
+ }
2443
+ return allow();
2444
+ }
2445
+ function checkLoginChallenge(challenge, expectedStatus) {
2446
+ if (!challenge) {
2447
+ return deny("Login challenge not found");
2448
+ }
2449
+ if (new Date(challenge.expires_at).getTime() < Date.now()) {
2450
+ return deny("Login challenge has expired");
2451
+ }
2452
+ if (challenge.status !== expectedStatus) {
2453
+ return deny(
2454
+ `Login challenge status is '${challenge.status}', expected '${expectedStatus}'`
2455
+ );
2456
+ }
2457
+ return allow();
2458
+ }
2459
+ function checkTickAuth(challenge) {
2460
+ if (!challenge) {
2461
+ return deny("TickAuth challenge not found");
2462
+ }
2463
+ if (challenge.status !== "pending" /* PENDING */) {
2464
+ return deny(
2465
+ `TickAuth challenge status is '${challenge.status}', expected 'pending'`
2466
+ );
2467
+ }
2468
+ const now = Date.now();
2469
+ const start = new Date(challenge.tick_window.start).getTime();
2470
+ const end = new Date(challenge.tick_window.end).getTime();
2471
+ if (now < start || now > end) {
2472
+ return deny("TickAuth challenge is outside its tick window");
2473
+ }
2474
+ return allow();
2475
+ }
2476
+ async function checkReplayProtection(nonce, store, windowMs = 5 * 60 * 1e3) {
2477
+ if (!nonce) {
2478
+ return deny("Nonce is required for replay protection");
2479
+ }
2480
+ const seen = await store.has(nonce);
2481
+ if (seen) {
2482
+ return deny("Nonce has already been used (replay detected)");
2483
+ }
2484
+ await store.add(nonce, new Date(Date.now() + windowMs));
2485
+ return allow();
2486
+ }
2487
+
2488
+ // src/nestflow/invariants.ts
2489
+ var LOGIN_CHALLENGE_TRANSITIONS = {
2490
+ ["pending" /* PENDING */]: [
2491
+ "scanned" /* SCANNED */,
2492
+ "expired" /* EXPIRED */
2493
+ ],
2494
+ ["scanned" /* SCANNED */]: [
2495
+ "approved" /* APPROVED */,
2496
+ "rejected" /* REJECTED */,
2497
+ "expired" /* EXPIRED */
2498
+ ],
2499
+ ["approved" /* APPROVED */]: [],
2500
+ ["rejected" /* REJECTED */]: [],
2501
+ ["expired" /* EXPIRED */]: []
2502
+ };
2503
+ var TICKAUTH_TRANSITIONS = {
2504
+ ["pending" /* PENDING */]: [
2505
+ "fulfilled" /* FULFILLED */,
2506
+ "rejected" /* REJECTED */,
2507
+ "expired" /* EXPIRED */
2508
+ ],
2509
+ ["fulfilled" /* FULFILLED */]: [],
2510
+ ["rejected" /* REJECTED */]: [],
2511
+ ["expired" /* EXPIRED */]: []
2512
+ };
2513
+ var CAPSULE_TRANSITIONS = {
2514
+ ["active" /* ACTIVE */]: [
2515
+ "consumed" /* CONSUMED */,
2516
+ "revoked" /* REVOKED */,
2517
+ "expired" /* EXPIRED */
2518
+ ],
2519
+ ["consumed" /* CONSUMED */]: [],
2520
+ ["revoked" /* REVOKED */]: [],
2521
+ ["expired" /* EXPIRED */]: []
2522
+ };
2523
+ var SESSION_TRANSITIONS = {
2524
+ ["active" /* ACTIVE */]: ["expired" /* EXPIRED */, "revoked" /* REVOKED */],
2525
+ ["expired" /* EXPIRED */]: [],
2526
+ ["revoked" /* REVOKED */]: []
2527
+ };
2528
+ var DEVICE_TRANSITIONS = {
2529
+ ["active" /* ACTIVE */]: ["suspended" /* SUSPENDED */, "revoked" /* REVOKED */],
2530
+ ["suspended" /* SUSPENDED */]: ["active" /* ACTIVE */, "revoked" /* REVOKED */],
2531
+ ["revoked" /* REVOKED */]: []
2532
+ };
2533
+ var TRUST_LINK_TRANSITIONS = {
2534
+ ["active" /* ACTIVE */]: ["revoked" /* REVOKED */],
2535
+ ["revoked" /* REVOKED */]: []
2536
+ };
2537
+ function checkTransition(entity, transitions, from, to) {
2538
+ const allowed = transitions[from];
2539
+ if (!allowed) {
2540
+ return {
2541
+ valid: false,
2542
+ reason: `${entity}: unknown current state '${from}'`
2543
+ };
2544
+ }
2545
+ if (!allowed.includes(to)) {
2546
+ return {
2547
+ valid: false,
2548
+ reason: `${entity}: invalid transition '${from}' \u2192 '${to}'. Allowed: [${allowed.join(", ")}]`
2549
+ };
2550
+ }
2551
+ return { valid: true };
2552
+ }
2553
+ function validateLoginChallengeTransition(from, to) {
2554
+ return checkTransition(
2555
+ "LoginChallenge",
2556
+ LOGIN_CHALLENGE_TRANSITIONS,
2557
+ from,
2558
+ to
2559
+ );
2560
+ }
2561
+ function validateTickAuthTransition(from, to) {
2562
+ return checkTransition("TickAuthChallenge", TICKAUTH_TRANSITIONS, from, to);
2563
+ }
2564
+ function validateCapsuleTransition(from, to) {
2565
+ return checkTransition("Capsule", CAPSULE_TRANSITIONS, from, to);
2566
+ }
2567
+ function validateSessionTransition(from, to) {
2568
+ return checkTransition("Session", SESSION_TRANSITIONS, from, to);
2569
+ }
2570
+ function validateDeviceTransition(from, to) {
2571
+ return checkTransition("Device", DEVICE_TRANSITIONS, from, to);
2572
+ }
2573
+ function validateTrustLinkTransition(from, to) {
2574
+ return checkTransition("TrustLink", TRUST_LINK_TRANSITIONS, from, to);
2575
+ }
2576
+ function isLoginChallengeTerminal(status) {
2577
+ return [
2578
+ "approved" /* APPROVED */,
2579
+ "rejected" /* REJECTED */,
2580
+ "expired" /* EXPIRED */
2581
+ ].includes(status);
2582
+ }
2583
+ function isTickAuthTerminal(status) {
2584
+ return [
2585
+ "fulfilled" /* FULFILLED */,
2586
+ "rejected" /* REJECTED */,
2587
+ "expired" /* EXPIRED */
2588
+ ].includes(status);
2589
+ }
2590
+ function isCapsuleTerminal(status) {
2591
+ return [
2592
+ "consumed" /* CONSUMED */,
2593
+ "revoked" /* REVOKED */,
2594
+ "expired" /* EXPIRED */
2595
+ ].includes(status);
2596
+ }
2597
+ function isSessionTerminal(status) {
2598
+ return ["expired" /* EXPIRED */, "revoked" /* REVOKED */].includes(status);
2599
+ }
2600
+ function isDeviceTerminal(status) {
2601
+ return status === "revoked" /* REVOKED */;
2602
+ }
2066
2603
  export {
2067
2604
  ATS1_HDR,
2068
2605
  ATS1_SCHEMA,
@@ -2070,14 +2607,19 @@ export {
2070
2607
  AXIS_OPCODES,
2071
2608
  AXIS_VERSION,
2072
2609
  ats1_exports as Ats1Codec,
2610
+ AuthLevel,
2073
2611
  AxisFrameZ,
2074
2612
  T as AxisPacketTags,
2075
2613
  BodyProfile,
2076
2614
  CAPABILITIES,
2615
+ CapsuleStatus,
2077
2616
  ContractViolationError,
2078
2617
  DEFAULT_CONTRACTS,
2079
2618
  DEFAULT_TIMEOUT,
2080
2619
  Decision,
2620
+ DeviceStatus,
2621
+ DeviceTrustLevel,
2622
+ DeviceType,
2081
2623
  ERR_BAD_SIGNATURE,
2082
2624
  ERR_CONTRACT_VIOLATION,
2083
2625
  ERR_INVALID_PACKET,
@@ -2096,6 +2638,7 @@ export {
2096
2638
  Intent,
2097
2639
  IntentRouter,
2098
2640
  IntentSensitivity,
2641
+ LoginChallengeStatus,
2099
2642
  MAX_BODY_LEN,
2100
2643
  MAX_FRAME_LEN,
2101
2644
  MAX_HDR_LEN,
@@ -2110,6 +2653,10 @@ export {
2110
2653
  NCERT_PUB,
2111
2654
  NCERT_SCOPE,
2112
2655
  NCERT_SIG,
2656
+ NESTFLOW_INTENTS,
2657
+ NESTFLOW_INTENT_SET,
2658
+ NESTFLOW_POLICY_MAP,
2659
+ NestFlowCapsuleType,
2113
2660
  PROOF_CAPABILITIES,
2114
2661
  PROOF_CAPSULE,
2115
2662
  PROOF_JWT,
@@ -2118,11 +2665,13 @@ export {
2118
2665
  PROOF_NONE,
2119
2666
  PROOF_WITNESS,
2120
2667
  ProofType,
2668
+ RiskDecision,
2121
2669
  Schema2002_PasskeyLoginOptionsRes,
2122
2670
  Schema2011_PasskeyLoginVerifyReq,
2123
2671
  Schema2012_PasskeyLoginVerifyRes,
2124
2672
  Schema2021_PasskeyRegisterOptionsReq,
2125
2673
  SensorDecisions,
2674
+ SessionStatus,
2126
2675
  TLV_ACTOR_ID,
2127
2676
  TLV_AUD,
2128
2677
  TLV_BODY_ARR,
@@ -2154,6 +2703,9 @@ export {
2154
2703
  TLV_TRACE_ID,
2155
2704
  TLV_TS,
2156
2705
  TLV_UPLOAD_ID,
2706
+ TickAuthChallengeStatus,
2707
+ TrustLinkStatus,
2708
+ TrustLinkType,
2157
2709
  axis1SigningBytes,
2158
2710
  b64urlDecode,
2159
2711
  b64urlDecodeString,
@@ -2167,6 +2719,14 @@ export {
2167
2719
  canAccessResource,
2168
2720
  canonicalJson,
2169
2721
  canonicalJsonExcluding,
2722
+ checkBrowserProof,
2723
+ checkCapsule,
2724
+ checkDeviceTrust,
2725
+ checkIntentPolicy,
2726
+ checkLoginChallenge,
2727
+ checkReplayProtection,
2728
+ checkSession,
2729
+ checkTickAuth,
2170
2730
  classifyIntent,
2171
2731
  computeReceiptHash,
2172
2732
  computeSignaturePayload,
@@ -2183,10 +2743,18 @@ export {
2183
2743
  encodeTLVs,
2184
2744
  encodeVarint,
2185
2745
  generateEd25519KeyPair,
2746
+ getRequiredAuthLevel,
2186
2747
  getSignTarget,
2187
2748
  hasScope,
2188
2749
  isAdminOpcode,
2750
+ isCapsuleTerminal,
2751
+ isDeviceTerminal,
2189
2752
  isKnownOpcode,
2753
+ isLoginChallengeTerminal,
2754
+ isNestFlowIntent,
2755
+ isSessionTerminal,
2756
+ isTickAuthTerminal,
2757
+ isTimestampValid,
2190
2758
  nonce16,
2191
2759
  normalizeSensorDecision,
2192
2760
  packPasskeyLoginOptionsReq,
@@ -2196,6 +2764,7 @@ export {
2196
2764
  packPasskeyRegisterOptionsReq,
2197
2765
  parseScope,
2198
2766
  resolveTimeout,
2767
+ satisfiesAuthLevel,
2199
2768
  sensitivityName,
2200
2769
  sha256,
2201
2770
  signFrame,
@@ -2205,6 +2774,13 @@ export {
2205
2774
  unpackPasskeyLoginVerifyReq,
2206
2775
  unpackPasskeyRegisterOptionsReq,
2207
2776
  utf8,
2777
+ validateCapsuleTransition,
2778
+ validateDeviceTransition,
2779
+ validateFrameShape,
2780
+ validateLoginChallengeTransition,
2781
+ validateSessionTransition,
2782
+ validateTickAuthTransition,
2783
+ validateTrustLinkTransition,
2208
2784
  varintLength,
2209
2785
  varintU,
2210
2786
  verifyFrameSignature