Skip to content

Authentication Reference

Every option, binding key, class, and method the Authentication component exposes. See the Overview for the guided introduction.

Files:

Import paths

typescript
import {
  // Component + registry
  AuthenticateComponent,
  AuthenticateBindingKeys,
  Authentication,
  AuthenticationFieldCodecs,
  AuthenticationModes,
  AuthenticationTokenTypes,
  AuthenticationStrategyRegistry,

  // JOSE standards + constants
  JOSEStandards,
  JWKSModes,
  JWKSKeyDrivers,
  JWKSKeyFormats,

  // Strategies
  JWSAuthenticationStrategy,
  JWKSIssuerAuthenticationStrategy,
  JWKSVerifierAuthenticationStrategy,
  BasicAuthenticationStrategy,

  // Services
  AbstractBearerTokenService,
  JWSTokenService,
  JWKSIssuerTokenService,
  JWKSVerifierTokenService,
  BasicTokenService,

  // Controllers
  defineAuthController,
  JWKSController,
  authenticate,

  // Entity column helpers
  extraUserColumns,
  extraRoleColumns,
  extraPermissionColumns,
  extraPolicyDefinitionColumns,
  UserStatuses,
  UserTypes,
  RoleStatuses,
} from '@venizia/ignis';

import type {
  TAuthenticationRestOptions,
  TJWTTokenServiceOptions,
  IJWSTokenServiceOptions,
  IJWKSIssuerOptions,
  IJWKSVerifierOptions,
  TJWKSTokenServiceOptions,
  TBasicTokenServiceOptions,
  IAuthenticateOptions,
  IAuthUser,
  IJWTTokenPayload,
  IPayloadFieldCodec,
  IAuthService,
  IAuthenticationStrategy,
  TDefineAuthControllerOpts,
  TAuthStrategy,
  TAuthMode,
  TGetTokenExpiresFn,
  TJWKSAlgorithm,
  TJWKSKeyDriver,
  TJWKSKeyFormat,
  TJOSEStandard,
  TJWKSMode,
  TPermissionOptions,
  TPermissionCommonColumns,
  TPolicyDefinitionOptions,
  TPolicyDefinitionCommonColumns,
} from '@venizia/ignis';

Architecture

Application.preConfigure()
  ├── bind JWT_OPTIONS (TJWTTokenServiceOptions, discriminated on `standard`)
  ├── bind BASIC_OPTIONS / REST_OPTIONS
  ├── this.component(AuthenticateComponent)
  └── AuthenticationStrategyRegistry.register() -- manual, after the component

AuthenticateComponent.binding()
  ├── switch on jwtOptions.standard
  │     ├── JWS  -> defineJWSAuth()  -> registers JWSTokenService
  │     └── JWKS -> defineJWKSAuth() -> switch on mode
  │                   ├── issuer   -> JWKSIssuerTokenService + JWKSController (/certs)
  │                   └── verifier -> JWKSVerifierTokenService
  ├── defineBasicAuth() -> registers BasicTokenService (if basicOptions bound)
  ├── defineControllers() -> registers AuthController (if useAuthController: true)
  └── defineOAuth2() -> stub, not implemented

Bearer token service hierarchy:
  AbstractBearerTokenService (extractCredentials, verify, generate, encryptPayload/decryptPayload)
    ├── JWSTokenService (symmetric HS256)
    └── AbstractJWKSTokenService (lazy ensureInitialized() + retry-on-failure)
          ├── JWKSIssuerTokenService (sign + verify + getJWKS/getJWKSAsync)
          └── JWKSVerifierTokenService (verify only, via createRemoteJWKSet())

Tech stack

TechnologyPurpose
joseJWT signing (SignJWT), verification (jwtVerify), JWKS (createRemoteJWKSet, exportJWK, importPKCS8, importSPKI, importJWK)
@venizia/ignis-helpersAES payload encryption, BaseHelper/BaseService, getError, HTTP result codes
Hono middlewareRoute-level integration via createMiddleware from hono/factory
node:fs/promisesAsync key file reads for JWKS

Component methods

AuthenticateComponent.binding() runs four private configuration methods and one public stub:

MethodPurpose
defineJWSAuth(opts)Validates jwtSecret and getTokenExpiresFn, binds IJWSTokenServiceOptions to JWT_OPTIONS, registers JWSTokenService
defineJWKSAuth(opts)Switches on mode. Issuer: validates keys/format/kid/getTokenExpiresFn, binds to JWKS_OPTIONS, registers JWKSIssuerTokenService + JWKSController. Verifier: validates jwksUrl, binds to JWKS_OPTIONS, registers JWKSVerifierTokenService
defineBasicAuth(opts)Validates verifyCredentials presence, registers BasicTokenService. Skips (debug log) if basicOptions not bound
defineControllers(opts)Requires jwtOptions when useAuthController: true. Calls defineAuthController() and registers the generated controller
defineOAuth2()Public stub, called during binding(), performs no action - not yet implemented

NOTE

The component reads the discriminated union from JWT_OPTIONS, then re-binds just the inner options object (IJWSTokenServiceOptions or IJWKSIssuerOptions/IJWKSVerifierOptions) to JWKS_OPTIONS or back to JWT_OPTIONS, so the token service can resolve it via a plain @inject.

Binding keys

ConstantKey stringTypeRequiredDefault
AuthenticateBindingKeys.REST_OPTIONS@app/authenticate/rest-optionsTAuthenticationRestOptionsNo{ useAuthController: false }
AuthenticateBindingKeys.JWT_OPTIONS@app/authenticate/jwt-optionsTJWTTokenServiceOptionsConditional--
AuthenticateBindingKeys.JWKS_OPTIONS@app/authenticate/jwks-optionsIJWKSIssuerOptions | IJWKSVerifierOptionsInternalBound by the component from JWT_OPTIONS
AuthenticateBindingKeys.BASIC_OPTIONS@app/authenticate/basic-optionsTBasicTokenServiceOptionsConditional--

IMPORTANT

At least one of JWT_OPTIONS or BASIC_OPTIONS must be bound, or AuthenticateComponent.binding() throws.

Option interfaces

TJWTTokenServiceOptions

Discriminated union on standard:

typescript
type TJWTTokenServiceOptions =
  | { standard: typeof JOSEStandards.JWS; options: IJWSTokenServiceOptions }
  | { standard: typeof JOSEStandards.JWKS; options: TJWKSTokenServiceOptions };

type TJWKSTokenServiceOptions = IJWKSIssuerOptions | IJWKSVerifierOptions; // discriminated on `mode`

IJWSTokenServiceOptions

OptionTypeDefaultRequiredDescription
jwtSecretstring--YesSecret for signing and verifying the JWT signature
getTokenExpiresFnTGetTokenExpiresFn--YesReturns token expiration in seconds
applicationSecretstring--NoEnables AES payload field encryption when set
aesAlgorithmAESAlgorithmType'aes-256-cbc'NoAES algorithm for payload encryption
headerAlgorithmstring'HS256'NoJWT signing algorithm
fieldCodecsIPayloadFieldCodec[][]NoCustom serialize/deserialize per field name

WARNING

jwtSecret is mandatory - the component throws if it is missing or equals the placeholder 'unknown_secret'. applicationSecret is optional: when omitted, the JWT payload is standard plaintext; standard fields (iss, sub, aud, jti, nbf, exp, iat) are never encrypted either way.

IJWKSIssuerOptions

OptionTypeDefaultRequiredDescription
modetypeof JWKSModes.ISSUER--YesMust be 'issuer'
algorithmTJWKSAlgorithm--Yes'ES256', 'RS256', or 'EdDSA'
keys.driverTJWKSKeyDriver--Yes'text' (inline) or 'file' (path)
keys.formatTJWKSKeyFormat--Yes'pem' or 'jwk'
keys.privatestring--YesPrivate key content or file path
keys.publicstring--YesPublic key content or file path
kidstring--YesKey ID exposed in the JWKS endpoint and JWT header
getTokenExpiresFnTGetTokenExpiresFn--YesReturns token expiration in seconds
rest.pathstring'/certs'NoPath of the generated JWKSController
aesAlgorithmAESAlgorithmType'aes-256-cbc'NoAES algorithm for payload encryption
applicationSecretstring--NoEnables AES payload field encryption when set
fieldCodecsIPayloadFieldCodec[][]NoCustom serialize/deserialize per field name

IJWKSVerifierOptions

OptionTypeDefaultRequiredDescription
modetypeof JWKSModes.VERIFIER--YesMust be 'verifier'
jwksUrlstring--YesURL of the issuer's JWKS endpoint
cacheTtlMsnumber43_200_000 (12h)NocreateRemoteJWKSet cacheMaxAge
cooldownMsnumber30_000 (30s)NocreateRemoteJWKSet cooldownDuration
aesAlgorithmAESAlgorithmType'aes-256-cbc'NoAES algorithm for payload decryption
applicationSecretstring--NoMust match the issuer's secret to decrypt payloads
fieldCodecsIPayloadFieldCodec[][]NoMust match the issuer's codecs to decrypt custom fields

IMPORTANT

JWKSVerifierTokenService cannot sign tokens - getSigner(), getSigningKey(), and getDefaultTokenExpiresFn() all throw. Only verify() and extractCredentials() are functional.

TBasicTokenServiceOptions

OptionTypeDescription
verifyCredentials(opts: { credentials: { username: string; password: string }; context: TContext }) => Promise<IAuthUser | null>Callback that validates Basic credentials and returns the authenticated user, or null

TAuthenticationRestOptions

Discriminated union on useAuthController - when true, controllerOpts becomes required:

typescript
type TAuthenticationRestOptions = {} & (
  | { useAuthController?: false | undefined }
  | { useAuthController: true; controllerOpts: TDefineAuthControllerOpts }
);

TDefineAuthControllerOpts

OptionTypeDefaultDescription
restPathstring'/auth'Base path for the generated controller
serviceKeystring--DI key for the IAuthService implementation (required)
requireAuthenticatedSignUpbooleanfalseWhether POST /sign-up requires a valid JWT
payload.signIn{ request: { schema }, response: { schema } }Built-in schemasCustom Zod schemas for /sign-in
payload.signUp{ request: { schema }, response: { schema } }Built-in schemasCustom Zod schemas for /sign-up
payload.changePassword{ request: { schema? }, response: { schema } }Built-in schemasCustom Zod schemas for /change-password
payload.refreshToken{ response: { schema } }AnyObjectSchemaCustom response schema for /token/refresh
payload.getUserInformation{ response: { schema } }AnyObjectSchemaCustom response schema for /me and the who-am-i userInformation field

Route authenticate config

typescript
type TRouteAuthenticateConfig =
  | { skip: true }
  | { skip?: false; strategies?: TAuthStrategy[]; mode?: TAuthMode };
FieldTypeDefaultDescription
authenticate.strategiesTAuthStrategy[]--Strategy names to try, e.g. ['jwt'], ['jwt', 'basic']
authenticate.mode'any' | 'all''any''any': first success wins. 'all': every strategy must pass
authenticate.skiptrue--Skips authentication for this route entirely

IAuthUser / IJWTTokenPayload

typescript
interface IAuthUser {
  userId: IdType;
  [extra: string | symbol]: any;
}

interface IJWTTokenPayload extends JWTPayload, IAuthUser {
  userId: IdType;
  roles: { id: IdType; identifier: string; priority: number }[];
  clientId?: string;
  provider?: string;
  email?: string;
  name?: string;
  [extra: string | symbol]: any;
}

TIP

IAuthUser is intentionally minimal. Your IAuthService can return extra fields (roles, email, provider) - they pass through JWT generation and are available on Authentication.CURRENT_USER after authentication.

IAuthService

typescript
interface IAuthService<
  E extends Env = Env,
  SIRQ extends TSignInRequest = TSignInRequest, SIRS = AnyObject,
  SURQ extends TSignUpRequest = TSignUpRequest, SURS = AnyObject,
  CPRQ extends TChangePasswordRequest = TChangePasswordRequest, CPRS = AnyObject,
  UIRQ = AnyObject, UIRS = AnyObject,
  RTRS = AnyObject,
> {
  signIn(context: TContext<E>, opts: SIRQ): Promise<SIRS>;
  signUp(context: TContext<E>, opts: SURQ): Promise<SURS>;
  changePassword(context: TContext<E>, opts: CPRQ): Promise<CPRS>;
  getUserInformation?(context: TContext<E>, opts: UIRQ): Promise<UIRS>;
  refreshToken?(context: TContext<E>): Promise<RTRS>;
}

NOTE

getUserInformation and refreshToken are optional. The generated auth controller returns 501 for /me, /token/refresh, or ?withUserInformation=true on /who-am-i if the bound service doesn't implement the corresponding method.

Field codecs

typescript
interface IPayloadFieldCodec<T = unknown> {
  key: string;
  serialize(opts: { value: T }): string;
  deserialize(opts: { raw: string }): T;
}

AuthenticationFieldCodecs.ROLES_CODEC is a ready-made codec for the roles field (pipe-separated id|identifier|priority strings). It is not applied automatically - pass it explicitly via fieldCodecs: [AuthenticationFieldCodecs.ROLES_CODEC] in the JWS/JWKS options. Without it, roles (and every other non-standard field) is serialized with plain JSON.stringify before AES encryption.

typescript
class AuthenticationFieldCodecs {
  static readonly ROLES_CODEC: IPayloadFieldCodec<IJWTTokenPayload['roles']>;
  static build<T>(opts: { key: string; serialize; deserialize }): IPayloadFieldCodec<T>;
}

Context variables

Set on the Hono Context during authentication, readable via context.get():

ConstantKey stringTypeDescription
Authentication.CURRENT_USERauth.current.userIAuthUserAuthenticated user payload
Authentication.AUDIT_USER_IDaudit.user.idIdTypeAuthenticated user's ID
Authentication.SKIP_AUTHENTICATIONauthentication.skipbooleanSet true in a preceding middleware to bypass auth

Constants

Authentication

ConstantValueDescription
Authentication.STRATEGY_JWT'jwt'JWT strategy name
Authentication.STRATEGY_BASIC'basic'Basic strategy name
Authentication.TYPE_BEARER'Bearer'Bearer token type prefix
Authentication.TYPE_BASIC'Basic'Basic token type prefix
Authentication.AUTHENTICATION_STRATEGY'authentication.strategy'Binding key prefix for registered strategies

AuthenticationTokenTypes

ConstantValue
TYPE_AUTHORIZATION_CODE'000_AUTHORIZATION_CODE'
TYPE_ACCESS_TOKEN'100_ACCESS_TOKEN'
TYPE_REFRESH_TOKEN'200_REFRESH_TOKEN'

JOSE / JWKS constants - each class also exposes SCHEME_SET: Set<string> and isValid(input): boolean

ClassMembers
JOSEStandardsJWS ('JWS'), JWKS ('JWKS')
JWKSModesISSUER ('issuer'), VERIFIER ('verifier')
JWKSKeyDriversTEXT ('text'), FILE ('file')
JWKSKeyFormatsPEM ('pem'), JWK ('jwk')
AuthenticateStrategyBASIC ('basic'), JWT ('jwt') - same values as Authentication.STRATEGY_*
AuthenticationModesANY ('any'), ALL ('all')

Strategy registry

AuthenticationStrategyRegistry is a singleton extending AbstractAuthRegistry<IAuthenticationStrategy>.

MethodSignatureDescription
getInstance()static (): AuthenticationStrategyRegistryReturns (creating if needed) the singleton
register(opts: { container: Container; strategies: { name: string; strategy: TClass<IAuthenticationStrategy> }[] }) => thisBinds each strategy into the container as a singleton under authentication.strategy.<name>. Returns this
resolveStrategy(opts: { name: string }) => IAuthenticationStrategyResolves a registered strategy instance by name
typescript
AuthenticationStrategyRegistry.getInstance().register({
  container: this,
  strategies: [
    { name: Authentication.STRATEGY_JWT, strategy: JWKSIssuerAuthenticationStrategy },
    { name: Authentication.STRATEGY_BASIC, strategy: BasicAuthenticationStrategy },
  ],
});

Standalone authenticate() function - the primary export for creating middleware outside the route-config authenticate field:

typescript
const authenticationProvider = new AuthenticationProvider();
const authenticateFn = authenticationProvider.value();

export const authenticate = (opts: { strategies: string[]; mode?: TAuthMode }) => authenticateFn(opts);

AuthenticationProvider middleware behavior:

  1. If Authentication.SKIP_AUTHENTICATION is set on context, skips entirely (debug log)
  2. If Authentication.CURRENT_USER is already set, skips (already authenticated)
  3. Runs strategies per mode ('any' or 'all')
  4. On success, sets Authentication.CURRENT_USER and Authentication.AUDIT_USER_ID
  5. On failure, throws 401

NOTE

'any' mode discards each failing strategy's error (logs at debug) and only throws once every strategy is exhausted. 'all' mode uses the first strategy's user payload as the identity source; if that payload has no userId, it throws 401 even though every strategy technically passed.

Service class hierarchy

AbstractBearerTokenService<E>          (extends BaseService)
  #aes, #applicationSecret, #fieldCodecs
  +extractCredentials(context)         Extract Bearer token from Authorization header
  +verify(opts)                        Template method -> doVerify()
  +generate(opts)                      Template method -> getSigner() + getSigningKey()
  +encryptPayload(payload) / decryptPayload(opts)
  #doVerify(token)*  +getSigner(opts)*  #getSigningKey()*  #getDefaultTokenExpiresFn()*

  JWSTokenService                       Symmetric HS256, shared secret
    used by JWSAuthenticationStrategy

  AbstractJWKSTokenService              Lazy ensureInitialized() + retry-on-failure
    #initialized, #initPromise
    +ensureInitialized()   #initialize()*

    JWKSIssuerTokenService               Sign with private key, verify with public key
      +getJWKS() (sync, throws if uninitialized)  +getJWKSAsync()
      used by JWKSIssuerAuthenticationStrategy

    JWKSVerifierTokenService             Verify only, via remote JWKS
      used by JWKSVerifierAuthenticationStrategy

AbstractBearerTokenService

File: packages/core/src/components/auth/authenticate/services/bearer/abstract.service.ts

MethodSignatureDescription
configurePayloadEncryption(opts: { aesAlgorithm?; applicationSecret?; fieldCodecs?: IPayloadFieldCodec[] }) => voidSets up AES + field codecs. AES only activates if applicationSecret is provided
extractCredentials(context) => { type: string; token: string }Parses Authorization: Bearer <token>
verify(opts: { type, token }) => Promise<IJWTTokenPayload>Calls doVerify(), wraps errors as sanitized 401
generate(opts: { payload, getTokenExpiresFn? }) => Promise<string>Calls getSigner() then signs with getSigningKey()
serializeField / deserializeField(opts) => string / anyPer-field codec lookup, JSON.stringify/JSON.parse fallback
encryptPayload(payload) => Record<string, any>AES-encrypts non-standard fields (keys and values). No-op if AES not configured
decryptPayload(opts: { result }) => IJWTTokenPayloadReverses encryptPayload. No-op if AES not configured

Static: JWT_COMMON_FIELDS: Set<'iss'|'sub'|'aud'|'jti'|'nbf'|'exp'|'iat'> - never encrypted or touched by field codecs.

JWSTokenService

File: packages/core/src/components/auth/authenticate/services/bearer/jws.service.ts

Constructor validates jwtSecret and getTokenExpiresFn (throws 500 if missing), encodes the secret to Uint8Array, calls configurePayloadEncryption(). doVerify calls jose.jwtVerify() with the shared secret; getSigner signs with header HS256 (or headerAlgorithm override).

AbstractJWKSTokenService

File: packages/core/src/components/auth/authenticate/services/bearer/jwks/abstract.service.ts

ensureInitialized() lazily runs initialize() on first call; concurrent callers share the pending promise. If initialize() rejects, the promise is reset so the next call retries instead of caching the failure.

JWKSIssuerTokenService

File: packages/core/src/components/auth/authenticate/services/bearer/jwks/issuer.service.ts

initialize(): reads key content (file via readFile or inline text, per keys.driver) → imports it (importPKCS8/importSPKI for PEM, importJWK for JWK) → exports the public JWK with kid/alg/use: 'sig' → caches { keys: [publicJWK] }.

MethodSignatureDescription
getJWKS() => { keys: JWK[] }Synchronous, returns the cached JWKS. Throws if called before initialize() completes
getJWKSAsync() => Promise<{ keys: JWK[] }>Calls ensureInitialized() first

JWKSVerifierTokenService

File: packages/core/src/components/auth/authenticate/services/bearer/jwks/verifier.service.ts

initialize() calls createRemoteJWKSet(jwksUrl, { cacheMaxAge: cacheTtlMs ?? 43_200_000, cooldownDuration: cooldownMs ?? 30_000 }). getSigner/getSigningKey/getDefaultTokenExpiresFn all throw - this service is verify-only.

BasicTokenService

File: packages/core/src/components/auth/authenticate/services/basic/service.ts

MethodSignatureDescription
extractCredentials(context) => { username: string; password: string }Decodes Authorization: Basic <base64>
verify(opts: { credentials, context }) => Promise<IAuthUser>Calls the user-provided verifyCredentials

Constructor throws 500 if verifyCredentials is missing from the injected options.

Strategy classes

All four strategies extend BaseHelper, implement IAuthenticationStrategy<E>, and follow the same shape: a name field, a standard field (Bearer strategies only), one injected token service, and an authenticate(context) method that calls extractCredentials() then verify().

StrategynameInjectsFile
JWSAuthenticationStrategyAuthentication.STRATEGY_JWTJWSTokenServicestrategies/jws.strategy.ts
JWKSIssuerAuthenticationStrategyAuthentication.STRATEGY_JWTJWKSIssuerTokenServicestrategies/jwks.strategy.ts
JWKSVerifierAuthenticationStrategyAuthentication.STRATEGY_JWTJWKSVerifierTokenServicesame file
BasicAuthenticationStrategyAuthentication.STRATEGY_BASICBasicTokenServicestrategies/basic.strategy.ts

NOTE

Choose the strategy class matching your JOSE standard - JWKSIssuerAuthenticationStrategy and JWKSVerifierAuthenticationStrategy both register under the same 'jwt' name, so a JWKS issuer service uses only one of the two.

JWKSController

Serves the JWKS endpoint (default path /certs, configurable via rest.path). Intentionally unauthenticated - it serves the public keys external verifiers need.

File: packages/core/src/components/auth/authenticate/controllers/jwks/controller.ts

typescript
class JWKSController extends BaseRestController {
  constructor(@inject(...) private jwksService: JWKSIssuerTokenService) {
    super({ scope: JWKSController.name, path: '/certs', isStrict: true });
  }

  override binding() {
    this.defineRoute({
      configs: RouteConfigs.GET_JWKS_CERTS, // GET '/'
      handler: async context => {
        const jwks = await this.jwksService.getJWKSAsync();
        context.header('Cache-Control', 'public, max-age=3600, stale-while-revalidate=86400');
        return context.json(jwks, HTTP.ResultCodes.RS_2.Ok);
      },
    });
  }
}

The component applies @controller({ path }) to JWKSController dynamically at binding time (via Reflect.decorate), since the path depends on a runtime option.

Controller factory

defineAuthController(opts: TDefineAuthControllerOpts): typeof AuthController builds a BaseRestController subclass at runtime.

File: packages/core/src/components/auth/authenticate/controllers/factory.ts

How it works:

  1. Class creation. class AuthController extends BaseRestController {} inside the factory closure, decorated with @controller({ path: restPath }), isStrict: true.
  2. Service injection. inject({ key: serviceKey })(AuthController, undefined, 0) is applied after class definition - the programmatic equivalent of decorating constructor parameter 0. The constructor throws 400 if the resolved service is falsy.
  3. Routes. Defined in binding() via this.defineRoute() - see the endpoint table in Usage & Examples.
  4. Schemas. Each endpoint uses payload.<name>.{request,response}.schema if provided, else a built-in default (or AnyObjectSchema for responses with no built-in schema).

Also exports JWTTokenPayloadSchema, the Zod schema backing /who-am-i's response - extended at runtime with an optional userInformation field typed from payload.getUserInformation.response.schema (or AnyObjectSchema).

Entity column helper types

Exported for extending the auth entity column helpers - see Usage & Examples for the columns themselves.

typescript
type TPermissionOptions = { idType?: 'string' | 'number' };
type TPermissionCommonColumns = {
  code: NotNull<PgTextBuilderInitial<...>>;
  name: NotNull<PgTextBuilderInitial<...>>;
  subject: NotNull<PgTextBuilderInitial<...>>;
  method: NotNull<PgTextBuilderInitial<...>>;
  action: NotNull<PgTextBuilderInitial<...>>;
  scope: NotNull<PgTextBuilderInitial<...>>;
  description: PgTextBuilderInitial<...>;
};

type TPolicyDefinitionOptions = { idType?: 'string' | 'number' };
type TPolicyDefinitionCommonColumns = {
  variant: ReturnType<typeof text>;
  subjectType: ReturnType<typeof text>;
  targetType: ReturnType<typeof text>;
  action: ReturnType<typeof text>;
  effect: ReturnType<typeof text>;
  domain: ReturnType<typeof text>;
};

File structure

packages/core/src/components/auth/
├── authenticate/
│   ├── common/
│   │   ├── codecs.ts             # AuthenticationFieldCodecs (ROLES_CODEC, build() factory)
│   │   ├── constants.ts          # AuthenticateStrategy, JOSEStandards, JWKSModes, JWKSKeyDrivers, JWKSKeyFormats, Authentication, AuthenticationTokenTypes, AuthenticationModes
│   │   ├── keys.ts               # AuthenticateBindingKeys
│   │   ├── types.ts              # Option interfaces, discriminated unions, IAuthUser, IJWTTokenPayload, IAuthService
│   │   └── index.ts
│   ├── controllers/
│   │   ├── factory.ts            # defineAuthController() + JWTTokenPayloadSchema
│   │   └── jwks/                 # JWKSController + route config
│   ├── middlewares/
│   │   └── authenticate.middleware.ts   # Standalone authenticate() function
│   ├── providers/
│   │   └── authentication.provider.ts   # AuthenticationProvider
│   ├── services/
│   │   ├── basic/service.ts             # BasicTokenService
│   │   └── bearer/
│   │       ├── abstract.service.ts      # AbstractBearerTokenService
│   │       ├── jws.service.ts           # JWSTokenService
│   │       └── jwks/                    # AbstractJWKSTokenService, JWKSIssuerTokenService, JWKSVerifierTokenService
│   ├── strategies/                      # JWSAuthenticationStrategy, JWKS*, BasicAuthenticationStrategy, AuthenticationStrategyRegistry
│   └── component.ts                     # AuthenticateComponent
├── base/
│   └── abstract-auth-registry.ts        # AbstractAuthRegistry (shared by authenticate + authorize)
└── models/
    ├── entities/                        # extraUserColumns, extraRoleColumns, extraPermissionColumns, extraPolicyDefinitionColumns
    └── requests/                        # SignInRequestSchema, SignUpRequestSchema, ChangePasswordRequestSchema

See also