1042 lines · 36.3 KB · TypeScript
RawDownload
import {  AuthAccessTokenType,  AuthAccessWriteScope,  AuthAdministrativeScopes,  AuthStandardClientScopes,  type AuthAccessTokenResult,  type AuthBrowserSessionResult,  type AuthClientMetadata,  type AuthClientSession,  type AuthCreatePairingCredentialInput,  type AuthEnvironmentScope,  type AuthPairingLink,  type AuthPairingCredentialResult,  type AuthSessionId,  type AuthSessionState,  type ServerAuthDescriptor,  type ServerAuthSessionMethod,  type AuthWebSocketTicketResult,  DpopFailureReason,  type DpopFailureReason as DpopFailureReasonType,} from "@t3tools/contracts";import { encodeOAuthScope } from "@t3tools/shared/oauthScope";import * as Context from "effect/Context";import * as Crypto from "effect/Crypto";import * as DateTime from "effect/DateTime";import * as Duration from "effect/Duration";import * as Effect from "effect/Effect";import * as Layer from "effect/Layer";import * as Option from "effect/Option";import * as Schema from "effect/Schema";import * as HttpServerRequest from "effect/unstable/http/HttpServerRequest"; import * as ServerEnvironment from "../environment/ServerEnvironment.ts";import * as EnvironmentAuthPolicy from "./EnvironmentAuthPolicy.ts";import * as PairingGrantStore from "./PairingGrantStore.ts";import * as ServerSecretStore from "./ServerSecretStore.ts";import * as SessionStore from "./SessionStore.ts";import { verifyRequestDpopProof } from "./dpop.ts";import { layerConfig as SqlitePersistenceLayer } from "../persistence/Layers/Sqlite.ts"; const DEFAULT_SESSION_SUBJECT = "cli-issued-session";export const INTERNAL_ADMINISTRATIVE_BOOTSTRAP_SUBJECT = "administrative-bootstrap"; export interface IssuedPairingLink {  readonly id: string;  readonly credential: string;  readonly scopes: ReadonlyArray<AuthEnvironmentScope>;  readonly subject: string;  readonly label?: string;  readonly createdAt: DateTime.Utc;  readonly expiresAt: DateTime.Utc;} export interface IssuedBearerSession {  readonly sessionId: AuthSessionId;  readonly token: string;  readonly method: "bearer-access-token";  readonly scopes: ReadonlyArray<AuthEnvironmentScope>;  readonly subject: string;  readonly client: AuthClientMetadata;  readonly expiresAt: DateTime.Utc;} export interface AuthenticatedSession {  readonly sessionId: AuthSessionId;  readonly subject: string;  readonly method: ServerAuthSessionMethod;  readonly scopes: ReadonlyArray<AuthEnvironmentScope>;  readonly proofKeyThumbprint?: string;  readonly expiresAt?: DateTime.DateTime;} const serverAuthInternalErrorContext = {  cause: Schema.Defect(),}; export class ServerAuthBootstrapCredentialValidationError extends Schema.TaggedError<ServerAuthBootstrapCredentialValidationError>()(  "ServerAuthBootstrapCredentialValidationError",  {    ...serverAuthInternalErrorContext,  },) {  override get message(): string {    return "Failed to validate bootstrap credential.";  }} export class ServerAuthSessionCredentialValidationError extends Schema.TaggedError<ServerAuthSessionCredentialValidationError>()(  "ServerAuthSessionCredentialValidationError",  {    ...serverAuthInternalErrorContext,  },) {  override get message(): string {    return "Failed to validate session credential.";  }} export class ServerAuthAuthenticatedSessionIssueError extends Schema.TaggedError<ServerAuthAuthenticatedSessionIssueError>()(  "ServerAuthAuthenticatedSessionIssueError",  {    ...serverAuthInternalErrorContext,  },) {  override get message(): string {    return "Failed to issue authenticated session.";  }} export class ServerAuthAuthenticatedAccessTokenIssueError extends Schema.TaggedError<ServerAuthAuthenticatedAccessTokenIssueError>()(  "ServerAuthAuthenticatedAccessTokenIssueError",  {    ...serverAuthInternalErrorContext,  },) {  override get message(): string {    return "Failed to issue authenticated access token.";  }} export class ServerAuthPairingLinkCreationError extends Schema.TaggedError<ServerAuthPairingLinkCreationError>()(  "ServerAuthPairingLinkCreationError",  {    ...serverAuthInternalErrorContext,  },) {  override get message(): string {    return "Failed to create pairing link.";  }} export class ServerAuthPairingLinksListError extends Schema.TaggedError<ServerAuthPairingLinksListError>()(  "ServerAuthPairingLinksListError",  {    ...serverAuthInternalErrorContext,  },) {  override get message(): string {    return "Failed to list pairing links.";  }} export class ServerAuthPairingLinkRevocationError extends Schema.TaggedError<ServerAuthPairingLinkRevocationError>()(  "ServerAuthPairingLinkRevocationError",  {    ...serverAuthInternalErrorContext,  },) {  override get message(): string {    return "Failed to revoke pairing link.";  }} export class ServerAuthSessionTokenIssueError extends Schema.TaggedError<ServerAuthSessionTokenIssueError>()(  "ServerAuthSessionTokenIssueError",  {    ...serverAuthInternalErrorContext,  },) {  override get message(): string {    return "Failed to issue session token.";  }} export class ServerAuthSessionsListError extends Schema.TaggedError<ServerAuthSessionsListError>()(  "ServerAuthSessionsListError",  {    ...serverAuthInternalErrorContext,  },) {  override get message(): string {    return "Failed to list sessions.";  }} export class ServerAuthSessionRevocationError extends Schema.TaggedError<ServerAuthSessionRevocationError>()(  "ServerAuthSessionRevocationError",  {    ...serverAuthInternalErrorContext,  },) {  override get message(): string {    return "Failed to revoke session.";  }} export class ServerAuthOtherSessionsRevocationError extends Schema.TaggedError<ServerAuthOtherSessionsRevocationError>()(  "ServerAuthOtherSessionsRevocationError",  {    ...serverAuthInternalErrorContext,  },) {  override get message(): string {    return "Failed to revoke other sessions.";  }} export class ServerAuthWebSocketTokenIssueError extends Schema.TaggedError<ServerAuthWebSocketTokenIssueError>()(  "ServerAuthWebSocketTokenIssueError",  {    ...serverAuthInternalErrorContext,  },) {  override get message(): string {    return "Failed to issue websocket token.";  }} export class ServerAuthDpopReplayStateRecordError extends Schema.TaggedError<ServerAuthDpopReplayStateRecordError>()(  "ServerAuthDpopReplayStateRecordError",  {    ...serverAuthInternalErrorContext,  },) {  override get message(): string {    return "Failed to record DPoP proof replay state.";  }} export class ServerAuthDpopReplayKeyCalculationError extends Schema.TaggedError<ServerAuthDpopReplayKeyCalculationError>()(  "ServerAuthDpopReplayKeyCalculationError",  {    ...serverAuthInternalErrorContext,  },) {  override get message(): string {    return "Failed to calculate DPoP replay key.";  }} export class ServerAuthLinkedCloudAccountVerificationError extends Schema.TaggedError<ServerAuthLinkedCloudAccountVerificationError>()(  "ServerAuthLinkedCloudAccountVerificationError",  {    ...serverAuthInternalErrorContext,  },) {  override get message(): string {    return "Could not verify the linked cloud account.";  }} export class ServerAuthLinkedCloudAccountReadError extends Schema.TaggedError<ServerAuthLinkedCloudAccountReadError>()(  "ServerAuthLinkedCloudAccountReadError",  {    ...serverAuthInternalErrorContext,  },) {  override get message(): string {    return "Could not read the linked cloud account.";  }} export class ServerAuthLinkedCloudAccountMissingError extends Schema.TaggedError<ServerAuthLinkedCloudAccountMissingError>()(  "ServerAuthLinkedCloudAccountMissingError",  {},) {  override get message(): string {    return "Cloud linked user is not installed for this environment.";  }} export class ServerAuthCloudLinkJwtSigningError extends Schema.TaggedError<ServerAuthCloudLinkJwtSigningError>()(  "ServerAuthCloudLinkJwtSigningError",  {    ...serverAuthInternalErrorContext,  },) {  override get message(): string {    return "Failed to sign cloud link JWT.";  }} export class ServerAuthCloudMintPublicKeyMissingError extends Schema.TaggedError<ServerAuthCloudMintPublicKeyMissingError>()(  "ServerAuthCloudMintPublicKeyMissingError",  {},) {  override get message(): string {    return "Cloud mint public key is not installed for this environment.";  }} export class ServerAuthCloudRelayIssuerMissingError extends Schema.TaggedError<ServerAuthCloudRelayIssuerMissingError>()(  "ServerAuthCloudRelayIssuerMissingError",  {},) {  override get message(): string {    return "Cloud relay issuer is not installed for this environment.";  }} export class ServerAuthCloudHealthJwtSigningError extends Schema.TaggedError<ServerAuthCloudHealthJwtSigningError>()(  "ServerAuthCloudHealthJwtSigningError",  {    ...serverAuthInternalErrorContext,  },) {  override get message(): string {    return "Failed to sign cloud health JWT.";  }} export class ServerAuthCloudMintJwtSigningError extends Schema.TaggedError<ServerAuthCloudMintJwtSigningError>()(  "ServerAuthCloudMintJwtSigningError",  {    ...serverAuthInternalErrorContext,  },) {  override get message(): string {    return "Failed to sign cloud mint JWT.";  }} export const ServerAuthInternalError = Schema.Union([  ServerAuthBootstrapCredentialValidationError,  ServerAuthSessionCredentialValidationError,  ServerAuthAuthenticatedSessionIssueError,  ServerAuthAuthenticatedAccessTokenIssueError,  ServerAuthPairingLinkCreationError,  ServerAuthPairingLinksListError,  ServerAuthPairingLinkRevocationError,  ServerAuthSessionTokenIssueError,  ServerAuthSessionsListError,  ServerAuthSessionRevocationError,  ServerAuthOtherSessionsRevocationError,  ServerAuthWebSocketTokenIssueError,  ServerAuthDpopReplayStateRecordError,  ServerAuthDpopReplayKeyCalculationError,  ServerAuthLinkedCloudAccountVerificationError,  ServerAuthLinkedCloudAccountReadError,  ServerAuthLinkedCloudAccountMissingError,  ServerAuthCloudLinkJwtSigningError,  ServerAuthCloudMintPublicKeyMissingError,  ServerAuthCloudRelayIssuerMissingError,  ServerAuthCloudHealthJwtSigningError,  ServerAuthCloudMintJwtSigningError,]);export type ServerAuthInternalError = typeof ServerAuthInternalError.Type;export const isServerAuthInternalError = Schema.is(ServerAuthInternalError); export class ServerAuthMissingCredentialError extends Schema.TaggedError<ServerAuthMissingCredentialError>()(  "ServerAuthMissingCredentialError",  {},) {  override get message(): string {    return "Server authentication credential is missing.";  }} export class ServerAuthInvalidCredentialError extends Schema.TaggedError<ServerAuthInvalidCredentialError>()(  "ServerAuthInvalidCredentialError",  {    diagnostic: Schema.optional(Schema.String),    dpopFailureReason: Schema.optionalKey(DpopFailureReason),    cause: Schema.optional(Schema.Defect()),  },) {  override get message(): string {    return "Server authentication credential is invalid.";  }} export const ServerAuthCredentialError = Schema.Union([  ServerAuthMissingCredentialError,  ServerAuthInvalidCredentialError,]);export type ServerAuthCredentialError = typeof ServerAuthCredentialError.Type;export const isServerAuthCredentialError = Schema.is(ServerAuthCredentialError);export const serverAuthCredentialReason = (  error: ServerAuthCredentialError,): "missing_credential" | "invalid_credential" =>  error._tag === "ServerAuthMissingCredentialError" ? "missing_credential" : "invalid_credential"; export const serverAuthDpopFailureReason = (  error: ServerAuthCredentialError,): DpopFailureReasonType | undefined =>  error._tag === "ServerAuthInvalidCredentialError" ? error.dpopFailureReason : undefined; export class ServerAuthInvalidScopeError extends Schema.TaggedError<ServerAuthInvalidScopeError>()(  "ServerAuthInvalidScopeError",  {},) {  override get message(): string {    return "The requested authentication scope is invalid.";  }} export class ServerAuthScopeNotGrantedError extends Schema.TaggedError<ServerAuthScopeNotGrantedError>()(  "ServerAuthScopeNotGrantedError",  {},) {  override get message(): string {    return "The requested authentication scope was not granted.";  }} export const ServerAuthInvalidRequestError = Schema.Union([  ServerAuthInvalidScopeError,  ServerAuthScopeNotGrantedError,]);export type ServerAuthInvalidRequestError = typeof ServerAuthInvalidRequestError.Type;export const isServerAuthInvalidRequestError = Schema.is(ServerAuthInvalidRequestError);export const serverAuthInvalidRequestReason = (  error: ServerAuthInvalidRequestError,): "invalid_scope" | "scope_not_granted" =>  error._tag === "ServerAuthInvalidScopeError" ? "invalid_scope" : "scope_not_granted"; export class ServerAuthForbiddenOperationError extends Schema.TaggedError<ServerAuthForbiddenOperationError>()(  "ServerAuthForbiddenOperationError",  {},) {  override get message(): string {    return "The current authentication session cannot revoke itself.";  }} export class EnvironmentAuth extends Context.Service<  EnvironmentAuth,  {    readonly getDescriptor: () => Effect.Effect<ServerAuthDescriptor>;    readonly getSessionState: (      request: HttpServerRequest.HttpServerRequest,    ) => Effect.Effect<AuthSessionState, ServerAuthInternalError>;    readonly createBrowserSession: (      credential: string,      requestMetadata: AuthClientMetadata,    ) => Effect.Effect<      {        readonly response: AuthBrowserSessionResult;        readonly sessionToken: string;      },      ServerAuthInvalidCredentialError | ServerAuthInternalError    >;    readonly exchangeBootstrapCredentialForAccessToken: (      credential: string,      requestedScopes: ReadonlyArray<AuthEnvironmentScope> | undefined,      requestMetadata: AuthClientMetadata,      input?: {        readonly proofKeyThumbprint?: string;      },    ) => Effect.Effect<      AuthAccessTokenResult,      ServerAuthInvalidCredentialError | ServerAuthInvalidRequestError | ServerAuthInternalError    >;    readonly createPairingLink: (input?: {      readonly ttl?: Duration.Duration;      readonly label?: string;      readonly scopes?: ReadonlyArray<AuthEnvironmentScope>;      readonly subject?: string;      readonly proofKeyThumbprint?: string;      readonly purpose?: "startup";    }) => Effect.Effect<IssuedPairingLink, ServerAuthInternalError>;    readonly issuePairingCredential: (      input?: AuthCreatePairingCredentialInput,    ) => Effect.Effect<AuthPairingCredentialResult, ServerAuthInternalError>;    readonly issueStartupPairingCredential: () => Effect.Effect<      AuthPairingCredentialResult,      ServerAuthInternalError    >;    readonly listPairingLinks: (input?: {      readonly excludeSubjects?: ReadonlyArray<string>;    }) => Effect.Effect<ReadonlyArray<AuthPairingLink>, ServerAuthInternalError>;    readonly revokePairingLink: (id: string) => Effect.Effect<boolean, ServerAuthInternalError>;    readonly issueSession: (input?: {      readonly ttl?: Duration.Duration;      readonly subject?: string;      readonly scopes?: ReadonlyArray<AuthEnvironmentScope>;      readonly label?: string;    }) => Effect.Effect<IssuedBearerSession, ServerAuthInternalError>;    readonly listSessions: () => Effect.Effect<      ReadonlyArray<AuthClientSession>,      ServerAuthInternalError    >;    readonly revokeSession: (      sessionId: AuthSessionId,    ) => Effect.Effect<boolean, ServerAuthInternalError>;    readonly revokeOtherSessionsExcept: (      sessionId: AuthSessionId,    ) => Effect.Effect<number, ServerAuthInternalError>;    readonly listClientSessions: (      currentSessionId: AuthSessionId,    ) => Effect.Effect<ReadonlyArray<AuthClientSession>, ServerAuthInternalError>;    readonly revokeClientSession: (      currentSessionId: AuthSessionId,      targetSessionId: AuthSessionId,    ) => Effect.Effect<boolean, ServerAuthForbiddenOperationError | ServerAuthInternalError>;    readonly revokeOtherClientSessions: (      currentSessionId: AuthSessionId,    ) => Effect.Effect<number, ServerAuthInternalError>;    readonly authenticateHttpRequest: (      request: HttpServerRequest.HttpServerRequest,    ) => Effect.Effect<AuthenticatedSession, ServerAuthCredentialError | ServerAuthInternalError>;    readonly authenticateWebSocketUpgrade: (      request: HttpServerRequest.HttpServerRequest,    ) => Effect.Effect<AuthenticatedSession, ServerAuthCredentialError | ServerAuthInternalError>;    readonly issueWebSocketTicket: (      session: Pick<AuthenticatedSession, "sessionId">,    ) => Effect.Effect<AuthWebSocketTicketResult, ServerAuthInternalError>;    readonly issueStartupPairingUrl: (      baseUrl: string,    ) => Effect.Effect<string, ServerAuthInternalError>;

Lines 1–500 of 1042.