@spfn/auth 0.2.0-beta.45 → 0.2.0-beta.47

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/server.d.ts CHANGED
@@ -1,11 +1,12 @@
1
- import { k as AuthInitOptions, l as KeyAlgorithmType, n as InvitationStatus, f as VerificationPurpose, j as PermissionCategory, p as SocialProvider, q as AuthContext } from './authenticate-CRDUKQbi.js';
2
- export { B as ChangePasswordParams, w as CheckAccountExistsParams, C as CheckAccountExistsResult, a6 as EmailSchema, I as INVITATION_STATUSES, K as KEY_ALGORITHM, y as LoginParams, L as LoginResult, z as LogoutParams, a2 as OAuthCallbackParams, a3 as OAuthCallbackResult, a1 as OAuthStartParams, O as OAuthStartResult, a8 as PasswordSchema, a7 as PhoneSchema, x as RegisterParams, Q as RegisterPublicKeyParams, a as RegisterResult, W as RevokeKeyParams, T as RotateKeyParams, b as RotateKeyResult, e as SOCIAL_PROVIDERS, F as SendVerificationCodeParams, S as SendVerificationCodeResult, a9 as TargetTypeSchema, d as USER_STATUSES, o as UserStatus, h as VERIFICATION_PURPOSES, g as VERIFICATION_TARGET_TYPES, aa as VerificationPurposeSchema, V as VerificationTargetType, G as VerifyCodeParams, H as VerifyCodeResult, m as authRouter, a4 as authenticate, Z as buildOAuthErrorUrl, v as changePasswordService, r as checkAccountExistsService, $ as getEnabledOAuthProviders, a0 as getGoogleAccessToken, _ as isOAuthProviderEnabled, t as loginService, u as logoutService, Y as oauthCallbackService, X as oauthStartService, a5 as optionalAuth, J as registerPublicKeyService, s as registerService, N as revokeKeyService, M as rotateKeyService, D as sendVerificationCodeService, E as verifyCodeService } from './authenticate-CRDUKQbi.js';
1
+ import { l as AuthInitOptions, n as KeyAlgorithmType, o as InvitationStatus, g as VerificationPurpose, k as PermissionCategory, q as SocialProvider, r as AuthContext } from './authenticate-eucncHxN.js';
2
+ export { D as ChangePasswordParams, x as CheckAccountExistsParams, C as CheckAccountExistsResult, a9 as EmailSchema, d as INVITATION_STATUSES, I as IssueOneTimeTokenResult, K as KEY_ALGORITHM, z as LoginParams, L as LoginResult, B as LogoutParams, a5 as OAuthCallbackParams, a6 as OAuthCallbackResult, a4 as OAuthStartParams, O as OAuthStartResult, ab as PasswordSchema, aa as PhoneSchema, y as RegisterParams, T as RegisterPublicKeyParams, a as RegisterResult, X as RevokeKeyParams, W as RotateKeyParams, b as RotateKeyResult, f as SOCIAL_PROVIDERS, G as SendVerificationCodeParams, S as SendVerificationCodeResult, ac as TargetTypeSchema, e as USER_STATUSES, p as UserStatus, i as VERIFICATION_PURPOSES, h as VERIFICATION_TARGET_TYPES, ad as VerificationPurposeSchema, V as VerificationTargetType, H as VerifyCodeParams, J as VerifyCodeResult, m as authRouter, a7 as authenticate, a0 as buildOAuthErrorUrl, w as changePasswordService, s as checkAccountExistsService, a2 as getEnabledOAuthProviders, a3 as getGoogleAccessToken, a1 as isOAuthProviderEnabled, Y as issueOneTimeTokenService, u as loginService, v as logoutService, $ as oauthCallbackService, _ as oauthStartService, a8 as optionalAuth, M as registerPublicKeyService, t as registerService, Q as revokeKeyService, N as rotateKeyService, E as sendVerificationCodeService, F as verifyCodeService, Z as verifyOneTimeTokenService } from './authenticate-eucncHxN.js';
3
3
  import * as drizzle_orm_pg_core from 'drizzle-orm/pg-core';
4
4
  import { UserProfile as UserProfile$1, ProfileInfo } from '@spfn/auth';
5
5
  import { BaseRepository } from '@spfn/core/db';
6
6
  import { Context } from 'hono';
7
7
  import * as _spfn_core_route from '@spfn/core/route';
8
8
  import { Algorithm } from 'jsonwebtoken';
9
+ import { SSETokenManager } from '@spfn/core/event/sse';
9
10
  import * as _spfn_core_logger from '@spfn/core/logger';
10
11
  import * as _spfn_core_event from '@spfn/core/event';
11
12
  import * as _sinclair_typebox from '@sinclair/typebox';
@@ -4879,6 +4880,29 @@ interface RoleGuardOptions {
4879
4880
  */
4880
4881
  declare const roleGuard: _spfn_core_route.NamedMiddlewareFactory<"roleGuard", [options: RoleGuardOptions]>;
4881
4882
 
4883
+ /**
4884
+ * One-Time Token Authentication Middleware
4885
+ *
4886
+ * Authenticates requests using a one-time token instead of JWT.
4887
+ * Extracts token from query parameter `?token=xxx` or `Authorization: OTT xxx` header.
4888
+ *
4889
+ * On success, injects AuthContext identical to the `authenticate` middleware,
4890
+ * making it transparent to downstream handlers using `getAuth(c)`.
4891
+ *
4892
+ * Auto-skips the global 'auth' middleware.
4893
+ *
4894
+ * @example
4895
+ * ```typescript
4896
+ * export const uploadFile = route.post('/files/upload')
4897
+ * .use([oneTimeTokenAuth])
4898
+ * .handler(async (c) => {
4899
+ * const { userId } = getAuth(c);
4900
+ * // handle file upload...
4901
+ * });
4902
+ * ```
4903
+ */
4904
+ declare const oneTimeTokenAuth: _spfn_core_route.NamedMiddleware<"oneTimeTokenAuth">;
4905
+
4882
4906
  /**
4883
4907
  * Auth Context Helpers
4884
4908
  *
@@ -5309,6 +5333,45 @@ declare function createOAuthState(params: CreateOAuthStateParams): Promise<strin
5309
5333
  */
5310
5334
  declare function verifyOAuthState(encryptedState: string): Promise<OAuthState>;
5311
5335
 
5336
+ /**
5337
+ * One-Time Token Manager
5338
+ *
5339
+ * Singleton wrapper around SSETokenManager for one-time token authentication.
5340
+ * Used for direct API access (file uploads, SSE streaming, etc.) bypassing RPC proxy.
5341
+ */
5342
+
5343
+ /**
5344
+ * Initialize the one-time token manager
5345
+ *
5346
+ * Called during auth lifecycle initialization.
5347
+ * Creates a singleton SSETokenManager instance.
5348
+ *
5349
+ * @param config - Optional configuration
5350
+ * @param config.ttl - Token time-to-live in milliseconds (default: 30000)
5351
+ */
5352
+ declare function initOneTimeTokenManager(config?: {
5353
+ ttl?: number;
5354
+ }): void;
5355
+ /**
5356
+ * Get the one-time token manager instance
5357
+ *
5358
+ * @throws Error if initOneTimeTokenManager() has not been called
5359
+ *
5360
+ * @example
5361
+ * ```typescript
5362
+ * import { getOneTimeTokenManager } from '@spfn/auth/server';
5363
+ *
5364
+ * // Use as SSE tokenManager
5365
+ * .eventsConfig({
5366
+ * auth: {
5367
+ * enabled: true,
5368
+ * tokenManager: getOneTimeTokenManager(),
5369
+ * },
5370
+ * })
5371
+ * ```
5372
+ */
5373
+ declare function getOneTimeTokenManager(): SSETokenManager;
5374
+
5312
5375
  /**
5313
5376
  * @spfn/auth - Centralized Logger
5314
5377
  *
@@ -5403,7 +5466,32 @@ interface AuthLifecycleConfig {
5403
5466
  * .build();
5404
5467
  * ```
5405
5468
  */
5406
- declare function createAuthLifecycle(options?: AuthInitOptions): AuthLifecycleConfig;
5469
+ /**
5470
+ * Options for createAuthLifecycle
5471
+ */
5472
+ interface AuthLifecycleOptions extends AuthInitOptions {
5473
+ /**
5474
+ * One-time token configuration
5475
+ *
5476
+ * Enables one-time token issuance for direct API access
5477
+ * (file uploads, SSE streaming, etc.)
5478
+ *
5479
+ * @example
5480
+ * ```typescript
5481
+ * createAuthLifecycle({
5482
+ * oneTimeToken: { ttl: 60000 }, // 60 seconds
5483
+ * })
5484
+ * ```
5485
+ */
5486
+ oneTimeToken?: {
5487
+ /**
5488
+ * Token time-to-live in milliseconds
5489
+ * @default 30000
5490
+ */
5491
+ ttl?: number;
5492
+ };
5493
+ }
5494
+ declare function createAuthLifecycle(options?: AuthLifecycleOptions): AuthLifecycleConfig;
5407
5495
 
5408
5496
  /**
5409
5497
  * @spfn/auth - Auth Events
@@ -5522,4 +5610,4 @@ type AuthRegisterPayload = typeof authRegisterEvent._payload;
5522
5610
  type InvitationCreatedPayload = typeof invitationCreatedEvent._payload;
5523
5611
  type InvitationAcceptedPayload = typeof invitationAcceptedEvent._payload;
5524
5612
 
5525
- export { type AuthConfig, AuthContext, type AuthLoginPayload, type AuthMetadataEntity, AuthMetadataRepository, AuthProviderSchema, type AuthRegisterPayload, COOKIE_NAMES, type CreateOAuthStateParams, type GoogleTokenResponse, type GoogleUserInfo, type Invitation, type InvitationAcceptedPayload, type InvitationCreatedPayload, InvitationStatus, InvitationsRepository, KeyAlgorithmType, type KeyPair, KeysRepository, type NewAuthMetadataEntity, type NewInvitation, type NewPermission, type NewPermissionEntity, type NewRole, type NewRoleEntity, type NewRolePermission, type NewUser, type NewUserPermission, type NewUserProfile, type NewUserPublicKey, type NewUserSocialAccount, type NewVerificationCode, type OAuthState, type Permission, type PermissionEntity, PermissionsRepository, type Role, type RoleEntity, type RoleGuardOptions, type RolePermission, RolePermissionsRepository, RolesRepository, type SessionData, type SessionPayload, SocialAccountsRepository, SocialProvider, type TokenPayload, type UpdateProfileParams, type User, type UserPermission, UserPermissionsRepository, type UserProfile, UserProfilesRepository, type UserPublicKey, type UserSocialAccount, UsersRepository, type VerificationCode, VerificationCodesRepository, VerificationPurpose, acceptInvitation, addPermissionToRole, authLogger, authLoginEvent, authMetadata, authMetadataRepository, authRegisterEvent, authSchema, cancelInvitation, checkUsernameAvailableService, configureAuth, createAuthLifecycle, createInvitation, createOAuthState, createRole, decodeToken, deleteInvitation, deleteRole, exchangeCodeForTokens, expireOldInvitations, generateClientToken, generateKeyPair, generateKeyPairES256, generateKeyPairRS256, generateToken, getAllRoles, getAuth, getAuthConfig, getAuthSessionService, getGoogleAuthUrl, getGoogleOAuthConfig, getGoogleUserInfo, getInvitationByToken, getInvitationWithDetails, getKeyId, getKeySize, getLocale, getOptionalAuth, getRole, getRoleByName, getRolePermissions, getSessionInfo, getSessionTtl, getUser, getUserByEmailService, getUserByIdService, getUserByPhoneService, getUserId, getUserPermissions, getUserProfileService, getUserRole, hasAllPermissions, hasAnyPermission, hasAnyRole, hasPermission, hasRole, hashPassword, initializeAuth, invitationAcceptedEvent, invitationCreatedEvent, invitationsRepository, isGoogleOAuthEnabled, keysRepository, listInvitations, parseDuration, permissions, permissionsRepository, refreshAccessToken, removePermissionFromRole, requireAnyPermission, requirePermissions, requireRole, resendInvitation, roleGuard, rolePermissions, rolePermissionsRepository, roles, rolesRepository, sealSession, setRolePermissions, shouldRefreshSession, shouldRotateKey, socialAccountsRepository, unsealSession, updateLastLoginService, updateLocaleService, updateRole, updateUserProfileService, updateUserService, updateUsernameService, userInvitations, userPermissions, userPermissionsRepository, userProfiles, userProfilesRepository, userPublicKeys, userSocialAccounts, users, usersRepository, validateInvitation, validatePasswordStrength, verificationCodes, verificationCodesRepository, verifyClientToken, verifyKeyFingerprint, verifyOAuthState, verifyPassword, verifyToken };
5613
+ export { type AuthConfig, AuthContext, type AuthLifecycleConfig, type AuthLifecycleOptions, type AuthLoginPayload, type AuthMetadataEntity, AuthMetadataRepository, AuthProviderSchema, type AuthRegisterPayload, COOKIE_NAMES, type CreateOAuthStateParams, type GoogleTokenResponse, type GoogleUserInfo, type Invitation, type InvitationAcceptedPayload, type InvitationCreatedPayload, InvitationStatus, InvitationsRepository, KeyAlgorithmType, type KeyPair, KeysRepository, type NewAuthMetadataEntity, type NewInvitation, type NewPermission, type NewPermissionEntity, type NewRole, type NewRoleEntity, type NewRolePermission, type NewUser, type NewUserPermission, type NewUserProfile, type NewUserPublicKey, type NewUserSocialAccount, type NewVerificationCode, type OAuthState, type Permission, type PermissionEntity, PermissionsRepository, type Role, type RoleEntity, type RoleGuardOptions, type RolePermission, RolePermissionsRepository, RolesRepository, type SessionData, type SessionPayload, SocialAccountsRepository, SocialProvider, type TokenPayload, type UpdateProfileParams, type User, type UserPermission, UserPermissionsRepository, type UserProfile, UserProfilesRepository, type UserPublicKey, type UserSocialAccount, UsersRepository, type VerificationCode, VerificationCodesRepository, VerificationPurpose, acceptInvitation, addPermissionToRole, authLogger, authLoginEvent, authMetadata, authMetadataRepository, authRegisterEvent, authSchema, cancelInvitation, checkUsernameAvailableService, configureAuth, createAuthLifecycle, createInvitation, createOAuthState, createRole, decodeToken, deleteInvitation, deleteRole, exchangeCodeForTokens, expireOldInvitations, generateClientToken, generateKeyPair, generateKeyPairES256, generateKeyPairRS256, generateToken, getAllRoles, getAuth, getAuthConfig, getAuthSessionService, getGoogleAuthUrl, getGoogleOAuthConfig, getGoogleUserInfo, getInvitationByToken, getInvitationWithDetails, getKeyId, getKeySize, getLocale, getOneTimeTokenManager, getOptionalAuth, getRole, getRoleByName, getRolePermissions, getSessionInfo, getSessionTtl, getUser, getUserByEmailService, getUserByIdService, getUserByPhoneService, getUserId, getUserPermissions, getUserProfileService, getUserRole, hasAllPermissions, hasAnyPermission, hasAnyRole, hasPermission, hasRole, hashPassword, initOneTimeTokenManager, initializeAuth, invitationAcceptedEvent, invitationCreatedEvent, invitationsRepository, isGoogleOAuthEnabled, keysRepository, listInvitations, oneTimeTokenAuth, parseDuration, permissions, permissionsRepository, refreshAccessToken, removePermissionFromRole, requireAnyPermission, requirePermissions, requireRole, resendInvitation, roleGuard, rolePermissions, rolePermissionsRepository, roles, rolesRepository, sealSession, setRolePermissions, shouldRefreshSession, shouldRotateKey, socialAccountsRepository, unsealSession, updateLastLoginService, updateLocaleService, updateRole, updateUserProfileService, updateUserService, updateUsernameService, userInvitations, userPermissions, userPermissionsRepository, userProfiles, userProfilesRepository, userPublicKeys, userSocialAccounts, users, usersRepository, validateInvitation, validatePasswordStrength, verificationCodes, verificationCodesRepository, verifyClientToken, verifyKeyFingerprint, verifyOAuthState, verifyPassword, verifyToken };
package/dist/server.js CHANGED
@@ -7884,6 +7884,38 @@ async function getAuthSessionService(userId) {
7884
7884
  };
7885
7885
  }
7886
7886
 
7887
+ // src/server/lib/one-time-token.ts
7888
+ import { SSETokenManager } from "@spfn/core/event/sse";
7889
+ var manager = null;
7890
+ function initOneTimeTokenManager(config) {
7891
+ if (manager) {
7892
+ manager.destroy();
7893
+ }
7894
+ manager = new SSETokenManager({
7895
+ ttl: config?.ttl
7896
+ });
7897
+ }
7898
+ function getOneTimeTokenManager() {
7899
+ if (!manager) {
7900
+ throw new Error(
7901
+ "OneTimeTokenManager not initialized. Ensure createAuthLifecycle() is configured in your server config."
7902
+ );
7903
+ }
7904
+ return manager;
7905
+ }
7906
+
7907
+ // src/server/services/one-time-token.service.ts
7908
+ async function issueOneTimeTokenService(userId) {
7909
+ const manager2 = getOneTimeTokenManager();
7910
+ const token = await manager2.issue(userId);
7911
+ const expiresAt = new Date(Date.now() + 3e4).toISOString();
7912
+ return { token, expiresAt };
7913
+ }
7914
+ async function verifyOneTimeTokenService(token) {
7915
+ const manager2 = getOneTimeTokenManager();
7916
+ return await manager2.verify(token);
7917
+ }
7918
+
7887
7919
  // src/server/services/user-profile.service.ts
7888
7920
  init_repositories();
7889
7921
  async function getUserProfileService(userId) {
@@ -8457,6 +8489,10 @@ var getAuthSession = route.get("/_auth/session").handler(async (c) => {
8457
8489
  const { userId } = getAuth(c);
8458
8490
  return await getAuthSessionService(userId);
8459
8491
  });
8492
+ var issueOneTimeToken = route.post("/_auth/tokens").handler(async (c) => {
8493
+ const { userId } = getAuth(c);
8494
+ return await issueOneTimeTokenService(userId);
8495
+ });
8460
8496
  var authRouter = defineRouter({
8461
8497
  checkAccountExists,
8462
8498
  sendVerificationCode,
@@ -8466,7 +8502,8 @@ var authRouter = defineRouter({
8466
8502
  logout,
8467
8503
  rotateKey,
8468
8504
  changePassword,
8469
- getAuthSession
8505
+ getAuthSession,
8506
+ issueOneTimeToken
8470
8507
  });
8471
8508
 
8472
8509
  // src/server/routes/invitations/index.ts
@@ -8753,6 +8790,47 @@ var roleGuard = defineMiddleware4(
8753
8790
  }
8754
8791
  );
8755
8792
 
8793
+ // src/server/middleware/one-time-token-auth.ts
8794
+ import { defineMiddleware as defineMiddleware5 } from "@spfn/core/route";
8795
+ import { UnauthorizedError as UnauthorizedError2 } from "@spfn/core/errors";
8796
+ import { usersRepository as usersRepository3, userProfilesRepository as userProfilesRepository3 } from "@spfn/auth/server";
8797
+ var oneTimeTokenAuth = defineMiddleware5("oneTimeTokenAuth", async (c, next) => {
8798
+ const token = c.req.query("token") ?? extractOTTHeader(c.req.header("Authorization"));
8799
+ if (!token) {
8800
+ throw new UnauthorizedError2({ message: "One-time token required: ?token=xxx or Authorization: OTT xxx" });
8801
+ }
8802
+ const userId = await verifyOneTimeTokenService(token);
8803
+ if (!userId) {
8804
+ throw new UnauthorizedError2({ message: "Invalid or expired one-time token" });
8805
+ }
8806
+ const [result, locale] = await Promise.all([
8807
+ usersRepository3.findByIdWithRole(Number(userId)),
8808
+ userProfilesRepository3.findLocaleByUserId(Number(userId))
8809
+ ]);
8810
+ if (!result) {
8811
+ throw new UnauthorizedError2({ message: "User not found" });
8812
+ }
8813
+ const { user, role } = result;
8814
+ if (user.status !== "active") {
8815
+ throw new UnauthorizedError2({ message: "Account is not active" });
8816
+ }
8817
+ c.set("auth", {
8818
+ user,
8819
+ userId: String(user.id),
8820
+ keyId: "",
8821
+ // No key involved in OTT auth
8822
+ role: role?.name ?? null,
8823
+ locale
8824
+ });
8825
+ await next();
8826
+ }, { skips: ["auth"] });
8827
+ function extractOTTHeader(header) {
8828
+ if (!header || !header.startsWith("OTT ")) {
8829
+ return null;
8830
+ }
8831
+ return header.substring(4);
8832
+ }
8833
+
8756
8834
  // src/server/routes/invitations/index.ts
8757
8835
  init_types();
8758
8836
  init_esm();
@@ -9242,6 +9320,8 @@ var mainAuthRouter = defineRouter5({
9242
9320
  rotateKey,
9243
9321
  changePassword,
9244
9322
  getAuthSession,
9323
+ // One-Time Token routes
9324
+ issueOneTimeToken,
9245
9325
  // OAuth routes
9246
9326
  oauthGoogleStart,
9247
9327
  oauthGoogleCallback,
@@ -9571,10 +9651,12 @@ function createAuthLifecycle(options = {}) {
9571
9651
  * Performs:
9572
9652
  * 1. Ensures admin account exists (creates if missing)
9573
9653
  * 2. Initializes RBAC system with built-in + custom roles/permissions
9654
+ * 3. Initializes one-time token manager
9574
9655
  */
9575
9656
  afterInfrastructure: async () => {
9576
9657
  await initializeAuth(options);
9577
9658
  await ensureAdminExists();
9659
+ initOneTimeTokenManager(options.oneTimeToken);
9578
9660
  }
9579
9661
  };
9580
9662
  }
@@ -9647,6 +9729,7 @@ export {
9647
9729
  getKeyId,
9648
9730
  getKeySize,
9649
9731
  getLocale,
9732
+ getOneTimeTokenManager,
9650
9733
  getOptionalAuth,
9651
9734
  getRole,
9652
9735
  getRoleByName,
@@ -9667,18 +9750,21 @@ export {
9667
9750
  hasPermission,
9668
9751
  hasRole,
9669
9752
  hashPassword,
9753
+ initOneTimeTokenManager,
9670
9754
  initializeAuth,
9671
9755
  invitationAcceptedEvent,
9672
9756
  invitationCreatedEvent,
9673
9757
  invitationsRepository,
9674
9758
  isGoogleOAuthEnabled,
9675
9759
  isOAuthProviderEnabled,
9760
+ issueOneTimeTokenService,
9676
9761
  keysRepository,
9677
9762
  listInvitations,
9678
9763
  loginService,
9679
9764
  logoutService,
9680
9765
  oauthCallbackService,
9681
9766
  oauthStartService,
9767
+ oneTimeTokenAuth,
9682
9768
  optionalAuth,
9683
9769
  parseDuration,
9684
9770
  permissions,
@@ -9728,6 +9814,7 @@ export {
9728
9814
  verifyCodeService,
9729
9815
  verifyKeyFingerprint,
9730
9816
  verifyOAuthState,
9817
+ verifyOneTimeTokenService,
9731
9818
  verifyPassword,
9732
9819
  verifyToken
9733
9820
  };