halkyon_oidc_server and its generated client halkyon_oidc_client: any provider following OpenID Connect's code flow, beside Serverpod's own providers, with a preset for SimpleLogin (no PKCE, no `typ`). Nothing of Halkyon's is in it; BSD-3-Clause, `publish_to: none` for now. - Attempts in `halkyon_oidc_attempt` (ADR 0020's D13): the ID PostgreSQL's gen_random_uuid(), a state and a nonce of 32 random bytes, PKCE's verifier where used, the caller if signed in; ten minutes, taken once. A host may begin the state with a marker. - The code exchanged by the module itself, so a provider out of reach (a timeout, a 5xx) is told apart from a refused code; the ID token checked with dart_jsonwebtoken's algorithms (ADR 0020's D12): the provider's algorithms alone, the key its `kid` names, of the right type; issuer, audience and `azp`, expiry, time issued, `nbf`, a minute's leeway; the attempt's nonce; a `sub`. - Keys kept an hour, fetched again for an unknown `kid` at most once a minute; discovery checked against the issuer; every request with a timeout. - Identities in `halkyon_oidc_identity`: the provider's key and the `sub`, one per person and provider, deleted with the person. - The stock endpoint (`OidcIdpBaseEndpoint`), and the parts for a host with rules of its own: begin, verify, keep and takeKept, link, accountOf, unlink; merging people; a limit per network. - The forwarding page, moved here from halkyon_base in the next commit. The package's main library is the code generator's, as halkyon_base's; a host imports `package:halkyon_oidc_server/oidc.dart`. ADR 0023's point 5 no longer names OAuth2PkceUtil, which the module doesn't use. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Signed-off-by: Tizian 「ティツィアーン」 <raisondetredev@pm.me>
852 lines
27 KiB
PL/PgSQL
852 lines
27 KiB
PL/PgSQL
BEGIN;
|
|
|
|
--
|
|
-- Function: gen_random_uuid_v7()
|
|
-- Source: https://gist.github.com/kjmph/5bd772b2c2df145aa645b837da7eca74
|
|
-- License: MIT (copyright notice included on the generator source code).
|
|
--
|
|
create or replace function gen_random_uuid_v7()
|
|
returns uuid
|
|
as $$
|
|
begin
|
|
-- use random v4 uuid as starting point (which has the same variant we need)
|
|
-- then overlay timestamp
|
|
-- then set version 7 by flipping the 2 and 1 bit in the version 4 string
|
|
return encode(
|
|
set_bit(
|
|
set_bit(
|
|
overlay(uuid_send(gen_random_uuid())
|
|
placing substring(int8send(floor(extract(epoch from clock_timestamp()) * 1000)::bigint) from 3)
|
|
from 1 for 6
|
|
),
|
|
52, 1
|
|
),
|
|
53, 1
|
|
),
|
|
'hex')::uuid;
|
|
end
|
|
$$
|
|
language plpgsql
|
|
volatile;
|
|
|
|
--
|
|
-- Class OidcAttempt as table halkyon_oidc_attempt
|
|
--
|
|
CREATE TABLE "halkyon_oidc_attempt" (
|
|
"id" uuid PRIMARY KEY DEFAULT gen_random_uuid(),
|
|
"provider" text NOT NULL,
|
|
"state" text NOT NULL,
|
|
"nonce" text NOT NULL,
|
|
"codeVerifier" text,
|
|
"callerId" uuid,
|
|
"subject" text,
|
|
"expiresAt" timestamp without time zone NOT NULL
|
|
);
|
|
|
|
-- Indexes
|
|
CREATE INDEX "halkyon_oidc_attempt_expires_idx" ON "halkyon_oidc_attempt" USING btree ("expiresAt");
|
|
|
|
--
|
|
-- Class OidcIdentity as table halkyon_oidc_identity
|
|
--
|
|
CREATE TABLE "halkyon_oidc_identity" (
|
|
"id" uuid PRIMARY KEY DEFAULT gen_random_uuid_v7(),
|
|
"authUserId" uuid NOT NULL,
|
|
"provider" text NOT NULL,
|
|
"subject" text NOT NULL,
|
|
"createdAt" timestamp without time zone NOT NULL
|
|
);
|
|
|
|
-- Indexes
|
|
CREATE UNIQUE INDEX "halkyon_oidc_identity_subject_idx" ON "halkyon_oidc_identity" USING btree ("provider", "subject");
|
|
CREATE UNIQUE INDEX "halkyon_oidc_identity_person_idx" ON "halkyon_oidc_identity" USING btree ("authUserId", "provider");
|
|
|
|
--
|
|
-- Class CloudStorageEntry as table serverpod_cloud_storage
|
|
--
|
|
CREATE TABLE "serverpod_cloud_storage" (
|
|
"id" bigserial PRIMARY KEY,
|
|
"storageId" text NOT NULL,
|
|
"path" text NOT NULL,
|
|
"addedTime" timestamp without time zone NOT NULL,
|
|
"expiration" timestamp without time zone,
|
|
"byteData" bytea NOT NULL,
|
|
"verified" boolean NOT NULL,
|
|
"contentType" text,
|
|
"cacheControl" text,
|
|
"contentDisposition" text,
|
|
"contentEncoding" text,
|
|
"customMetadata" text
|
|
);
|
|
|
|
-- Indexes
|
|
CREATE UNIQUE INDEX "serverpod_cloud_storage_path_idx" ON "serverpod_cloud_storage" USING btree ("storageId", "path");
|
|
CREATE INDEX "serverpod_cloud_storage_expiration" ON "serverpod_cloud_storage" USING btree ("expiration");
|
|
|
|
--
|
|
-- Class CloudStorageDirectDownloadEntry as table serverpod_cloud_storage_direct_download
|
|
--
|
|
CREATE TABLE "serverpod_cloud_storage_direct_download" (
|
|
"id" bigserial PRIMARY KEY,
|
|
"storageId" text NOT NULL,
|
|
"path" text NOT NULL,
|
|
"expiration" timestamp without time zone NOT NULL,
|
|
"authKey" text NOT NULL,
|
|
"downloadFileName" text,
|
|
"contentType" text
|
|
);
|
|
|
|
-- Indexes
|
|
CREATE UNIQUE INDEX "serverpod_cloud_storage_direct_download_auth_key" ON "serverpod_cloud_storage_direct_download" USING btree ("authKey");
|
|
CREATE INDEX "serverpod_cloud_storage_direct_download_expiration" ON "serverpod_cloud_storage_direct_download" USING btree ("expiration");
|
|
|
|
--
|
|
-- Class CloudStorageDirectUploadEntry as table serverpod_cloud_storage_direct_upload
|
|
--
|
|
CREATE TABLE "serverpod_cloud_storage_direct_upload" (
|
|
"id" bigserial PRIMARY KEY,
|
|
"storageId" text NOT NULL,
|
|
"path" text NOT NULL,
|
|
"expiration" timestamp without time zone NOT NULL,
|
|
"authKey" text NOT NULL,
|
|
"maxFileSize" bigint NOT NULL DEFAULT 10485760,
|
|
"contentLength" bigint,
|
|
"preventOverwrite" boolean NOT NULL DEFAULT false,
|
|
"contentType" text,
|
|
"cacheControl" text,
|
|
"contentDisposition" text,
|
|
"contentEncoding" text,
|
|
"customMetadata" text
|
|
);
|
|
|
|
-- Indexes
|
|
CREATE UNIQUE INDEX "serverpod_cloud_storage_direct_upload_storage_path" ON "serverpod_cloud_storage_direct_upload" USING btree ("storageId", "path");
|
|
|
|
--
|
|
-- Class FutureCallEntry as table serverpod_future_call
|
|
--
|
|
CREATE TABLE "serverpod_future_call" (
|
|
"id" bigserial PRIMARY KEY,
|
|
"name" text NOT NULL,
|
|
"time" timestamp without time zone NOT NULL,
|
|
"serializedObject" text,
|
|
"serverId" text NOT NULL,
|
|
"identifier" text,
|
|
"scheduling" json
|
|
);
|
|
|
|
-- Indexes
|
|
CREATE INDEX "serverpod_future_call_time_idx" ON "serverpod_future_call" USING btree ("time");
|
|
CREATE INDEX "serverpod_future_call_serverId_idx" ON "serverpod_future_call" USING btree ("serverId");
|
|
CREATE INDEX "serverpod_future_call_identifier_idx" ON "serverpod_future_call" USING btree ("identifier");
|
|
|
|
--
|
|
-- Class FutureCallClaimEntry as table serverpod_future_call_claim
|
|
--
|
|
CREATE TABLE "serverpod_future_call_claim" (
|
|
"id" bigserial PRIMARY KEY,
|
|
"futureCallId" bigint,
|
|
"lastHeartbeatTime" timestamp without time zone NOT NULL
|
|
);
|
|
|
|
-- Indexes
|
|
CREATE UNIQUE INDEX "future_call_unique_idx" ON "serverpod_future_call_claim" USING btree ("futureCallId");
|
|
|
|
--
|
|
-- Class ServerHealthConnectionInfo as table serverpod_health_connection_info
|
|
--
|
|
CREATE TABLE "serverpod_health_connection_info" (
|
|
"id" bigserial PRIMARY KEY,
|
|
"serverId" text NOT NULL,
|
|
"timestamp" timestamp without time zone NOT NULL,
|
|
"active" bigint NOT NULL,
|
|
"closing" bigint NOT NULL,
|
|
"idle" bigint NOT NULL,
|
|
"granularity" bigint NOT NULL
|
|
);
|
|
|
|
-- Indexes
|
|
CREATE UNIQUE INDEX "serverpod_health_connection_info_timestamp_idx" ON "serverpod_health_connection_info" USING btree ("timestamp", "serverId", "granularity");
|
|
|
|
--
|
|
-- Class ServerHealthMetric as table serverpod_health_metric
|
|
--
|
|
CREATE TABLE "serverpod_health_metric" (
|
|
"id" bigserial PRIMARY KEY,
|
|
"name" text NOT NULL,
|
|
"serverId" text NOT NULL,
|
|
"timestamp" timestamp without time zone NOT NULL,
|
|
"isHealthy" boolean NOT NULL,
|
|
"value" double precision NOT NULL,
|
|
"granularity" bigint NOT NULL
|
|
);
|
|
|
|
-- Indexes
|
|
CREATE UNIQUE INDEX "serverpod_health_metric_timestamp_idx" ON "serverpod_health_metric" USING btree ("timestamp", "serverId", "name", "granularity");
|
|
|
|
--
|
|
-- Class LogEntry as table serverpod_log
|
|
--
|
|
CREATE TABLE "serverpod_log" (
|
|
"id" bigserial PRIMARY KEY,
|
|
"sessionLogId" bigint NOT NULL,
|
|
"messageId" bigint,
|
|
"reference" text,
|
|
"serverId" text NOT NULL,
|
|
"time" timestamp without time zone NOT NULL,
|
|
"logLevel" bigint NOT NULL,
|
|
"message" text NOT NULL,
|
|
"error" text,
|
|
"stackTrace" text,
|
|
"order" bigint NOT NULL
|
|
);
|
|
|
|
-- Indexes
|
|
CREATE INDEX "serverpod_log_sessionLogId_idx" ON "serverpod_log" USING btree ("sessionLogId", "order");
|
|
|
|
--
|
|
-- Class MessageLogEntry as table serverpod_message_log
|
|
--
|
|
CREATE TABLE "serverpod_message_log" (
|
|
"id" bigserial PRIMARY KEY,
|
|
"sessionLogId" bigint NOT NULL,
|
|
"serverId" text NOT NULL,
|
|
"messageId" bigint NOT NULL,
|
|
"endpoint" text NOT NULL,
|
|
"messageName" text NOT NULL,
|
|
"duration" double precision NOT NULL,
|
|
"error" text,
|
|
"stackTrace" text,
|
|
"slow" boolean NOT NULL,
|
|
"order" bigint NOT NULL
|
|
);
|
|
|
|
-- Indexes
|
|
CREATE INDEX "serverpod_message_log_sessionLogId_idx" ON "serverpod_message_log" USING btree ("sessionLogId", "order");
|
|
|
|
--
|
|
-- Class MethodInfo as table serverpod_method
|
|
--
|
|
CREATE TABLE "serverpod_method" (
|
|
"id" bigserial PRIMARY KEY,
|
|
"endpoint" text NOT NULL,
|
|
"method" text NOT NULL
|
|
);
|
|
|
|
-- Indexes
|
|
CREATE UNIQUE INDEX "serverpod_method_endpoint_method_idx" ON "serverpod_method" USING btree ("endpoint", "method");
|
|
|
|
--
|
|
-- Class DatabaseMigrationVersion as table serverpod_migrations
|
|
--
|
|
CREATE TABLE "serverpod_migrations" (
|
|
"id" bigserial PRIMARY KEY,
|
|
"module" text NOT NULL,
|
|
"version" text NOT NULL,
|
|
"timestamp" timestamp without time zone
|
|
);
|
|
|
|
-- Indexes
|
|
CREATE UNIQUE INDEX "serverpod_migrations_ids" ON "serverpod_migrations" USING btree ("module");
|
|
|
|
--
|
|
-- Class QueryLogEntry as table serverpod_query_log
|
|
--
|
|
CREATE TABLE "serverpod_query_log" (
|
|
"id" bigserial PRIMARY KEY,
|
|
"serverId" text NOT NULL,
|
|
"sessionLogId" bigint NOT NULL,
|
|
"messageId" bigint,
|
|
"query" text NOT NULL,
|
|
"duration" double precision NOT NULL,
|
|
"numRows" bigint,
|
|
"error" text,
|
|
"stackTrace" text,
|
|
"slow" boolean NOT NULL,
|
|
"order" bigint NOT NULL
|
|
);
|
|
|
|
-- Indexes
|
|
CREATE INDEX "serverpod_query_log_sessionLogId_idx" ON "serverpod_query_log" USING btree ("sessionLogId", "order");
|
|
|
|
--
|
|
-- Class ReadWriteTestEntry as table serverpod_readwrite_test
|
|
--
|
|
CREATE TABLE "serverpod_readwrite_test" (
|
|
"id" bigserial PRIMARY KEY,
|
|
"number" bigint NOT NULL
|
|
);
|
|
|
|
--
|
|
-- Class RuntimeSettings as table serverpod_runtime_settings
|
|
--
|
|
CREATE TABLE "serverpod_runtime_settings" (
|
|
"id" bigserial PRIMARY KEY,
|
|
"logSettings" json NOT NULL,
|
|
"logSettingsOverrides" json NOT NULL,
|
|
"logServiceCalls" boolean NOT NULL,
|
|
"logMalformedCalls" boolean NOT NULL
|
|
);
|
|
|
|
--
|
|
-- Class SessionLogEntry as table serverpod_session_log
|
|
--
|
|
CREATE TABLE "serverpod_session_log" (
|
|
"id" bigserial PRIMARY KEY,
|
|
"serverId" text NOT NULL,
|
|
"time" timestamp without time zone NOT NULL,
|
|
"module" text,
|
|
"endpoint" text,
|
|
"method" text,
|
|
"duration" double precision,
|
|
"numQueries" bigint,
|
|
"slow" boolean,
|
|
"error" text,
|
|
"stackTrace" text,
|
|
"authenticatedUserId" bigint,
|
|
"userId" text,
|
|
"isOpen" boolean,
|
|
"touched" timestamp without time zone NOT NULL
|
|
);
|
|
|
|
-- Indexes
|
|
CREATE INDEX "serverpod_session_log_serverid_idx" ON "serverpod_session_log" USING btree ("serverId");
|
|
CREATE INDEX "serverpod_session_log_time_idx" ON "serverpod_session_log" USING btree ("time");
|
|
CREATE INDEX "serverpod_session_log_touched_idx" ON "serverpod_session_log" USING btree ("touched");
|
|
CREATE INDEX "serverpod_session_log_isopen_idx" ON "serverpod_session_log" USING btree ("isOpen");
|
|
|
|
--
|
|
-- Class AnonymousAccount as table serverpod_auth_idp_anonymous_account
|
|
--
|
|
CREATE TABLE "serverpod_auth_idp_anonymous_account" (
|
|
"id" uuid PRIMARY KEY DEFAULT gen_random_uuid_v7(),
|
|
"authUserId" uuid NOT NULL,
|
|
"createdAt" timestamp without time zone NOT NULL
|
|
);
|
|
|
|
--
|
|
-- Class AppleAccount as table serverpod_auth_idp_apple_account
|
|
--
|
|
CREATE TABLE "serverpod_auth_idp_apple_account" (
|
|
"id" uuid PRIMARY KEY DEFAULT gen_random_uuid_v7(),
|
|
"userIdentifier" text NOT NULL,
|
|
"refreshToken" text NOT NULL,
|
|
"refreshTokenRequestedWithBundleIdentifier" boolean NOT NULL,
|
|
"lastRefreshedAt" timestamp without time zone NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
|
"authUserId" uuid NOT NULL,
|
|
"createdAt" timestamp without time zone NOT NULL,
|
|
"email" text,
|
|
"isEmailVerified" boolean,
|
|
"isPrivateEmail" boolean,
|
|
"firstName" text,
|
|
"lastName" text
|
|
);
|
|
|
|
-- Indexes
|
|
CREATE UNIQUE INDEX "serverpod_auth_apple_account_identifier" ON "serverpod_auth_idp_apple_account" USING btree ("userIdentifier");
|
|
|
|
--
|
|
-- Class EmailAccount as table serverpod_auth_idp_email_account
|
|
--
|
|
CREATE TABLE "serverpod_auth_idp_email_account" (
|
|
"id" uuid PRIMARY KEY DEFAULT gen_random_uuid_v7(),
|
|
"authUserId" uuid NOT NULL,
|
|
"createdAt" timestamp without time zone NOT NULL,
|
|
"email" text NOT NULL,
|
|
"passwordHash" text NOT NULL
|
|
);
|
|
|
|
-- Indexes
|
|
CREATE UNIQUE INDEX "serverpod_auth_idp_email_account_email" ON "serverpod_auth_idp_email_account" USING btree ("email");
|
|
|
|
--
|
|
-- Class EmailAccountPasswordResetRequest as table serverpod_auth_idp_email_account_password_reset_request
|
|
--
|
|
CREATE TABLE "serverpod_auth_idp_email_account_password_reset_request" (
|
|
"id" uuid PRIMARY KEY DEFAULT gen_random_uuid_v7(),
|
|
"emailAccountId" uuid NOT NULL,
|
|
"createdAt" timestamp without time zone NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
|
"challengeId" uuid NOT NULL,
|
|
"setPasswordChallengeId" uuid
|
|
);
|
|
|
|
--
|
|
-- Class EmailAccountRequest as table serverpod_auth_idp_email_account_request
|
|
--
|
|
CREATE TABLE "serverpod_auth_idp_email_account_request" (
|
|
"id" uuid PRIMARY KEY DEFAULT gen_random_uuid_v7(),
|
|
"createdAt" timestamp without time zone NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
|
"email" text NOT NULL,
|
|
"challengeId" uuid NOT NULL,
|
|
"createAccountChallengeId" uuid
|
|
);
|
|
|
|
-- Indexes
|
|
CREATE UNIQUE INDEX "serverpod_auth_idp_email_account_request_email" ON "serverpod_auth_idp_email_account_request" USING btree ("email");
|
|
|
|
--
|
|
-- Class FacebookAccount as table serverpod_auth_idp_facebook_account
|
|
--
|
|
CREATE TABLE "serverpod_auth_idp_facebook_account" (
|
|
"id" uuid PRIMARY KEY DEFAULT gen_random_uuid_v7(),
|
|
"authUserId" uuid NOT NULL,
|
|
"createdAt" timestamp without time zone NOT NULL,
|
|
"userIdentifier" text NOT NULL,
|
|
"email" text,
|
|
"fullName" text,
|
|
"firstName" text,
|
|
"lastName" text
|
|
);
|
|
|
|
-- Indexes
|
|
CREATE UNIQUE INDEX "serverpod_auth_facebook_account_user_identifier" ON "serverpod_auth_idp_facebook_account" USING btree ("userIdentifier");
|
|
|
|
--
|
|
-- Class FirebaseAccount as table serverpod_auth_idp_firebase_account
|
|
--
|
|
CREATE TABLE "serverpod_auth_idp_firebase_account" (
|
|
"id" uuid PRIMARY KEY DEFAULT gen_random_uuid_v7(),
|
|
"authUserId" uuid NOT NULL,
|
|
"created" timestamp without time zone NOT NULL,
|
|
"email" text,
|
|
"phone" text,
|
|
"userIdentifier" text NOT NULL
|
|
);
|
|
|
|
-- Indexes
|
|
CREATE UNIQUE INDEX "serverpod_auth_firebase_account_user_identifier" ON "serverpod_auth_idp_firebase_account" USING btree ("userIdentifier");
|
|
|
|
--
|
|
-- Class GitHubAccount as table serverpod_auth_idp_github_account
|
|
--
|
|
CREATE TABLE "serverpod_auth_idp_github_account" (
|
|
"id" uuid PRIMARY KEY DEFAULT gen_random_uuid_v7(),
|
|
"authUserId" uuid NOT NULL,
|
|
"userIdentifier" text NOT NULL,
|
|
"email" text,
|
|
"created" timestamp without time zone NOT NULL
|
|
);
|
|
|
|
-- Indexes
|
|
CREATE UNIQUE INDEX "serverpod_auth_github_account_user_identifier" ON "serverpod_auth_idp_github_account" USING btree ("userIdentifier");
|
|
|
|
--
|
|
-- Class GoogleAccount as table serverpod_auth_idp_google_account
|
|
--
|
|
CREATE TABLE "serverpod_auth_idp_google_account" (
|
|
"id" uuid PRIMARY KEY DEFAULT gen_random_uuid_v7(),
|
|
"authUserId" uuid NOT NULL,
|
|
"created" timestamp without time zone NOT NULL,
|
|
"email" text NOT NULL,
|
|
"userIdentifier" text NOT NULL
|
|
);
|
|
|
|
-- Indexes
|
|
CREATE UNIQUE INDEX "serverpod_auth_google_account_user_identifier" ON "serverpod_auth_idp_google_account" USING btree ("userIdentifier");
|
|
|
|
--
|
|
-- Class MicrosoftAccount as table serverpod_auth_idp_microsoft_account
|
|
--
|
|
CREATE TABLE "serverpod_auth_idp_microsoft_account" (
|
|
"id" uuid PRIMARY KEY DEFAULT gen_random_uuid_v7(),
|
|
"authUserId" uuid NOT NULL,
|
|
"userIdentifier" text NOT NULL,
|
|
"email" text,
|
|
"created" timestamp without time zone NOT NULL
|
|
);
|
|
|
|
-- Indexes
|
|
CREATE UNIQUE INDEX "serverpod_auth_microsoft_account_user_identifier" ON "serverpod_auth_idp_microsoft_account" USING btree ("userIdentifier");
|
|
|
|
--
|
|
-- Class PasskeyAccount as table serverpod_auth_idp_passkey_account
|
|
--
|
|
CREATE TABLE "serverpod_auth_idp_passkey_account" (
|
|
"id" uuid PRIMARY KEY DEFAULT gen_random_uuid_v7(),
|
|
"authUserId" uuid NOT NULL,
|
|
"createdAt" timestamp without time zone NOT NULL,
|
|
"keyId" bytea NOT NULL,
|
|
"keyIdBase64" text NOT NULL,
|
|
"clientDataJSON" bytea NOT NULL,
|
|
"attestationObject" bytea NOT NULL,
|
|
"originalChallenge" bytea NOT NULL
|
|
);
|
|
|
|
-- Indexes
|
|
CREATE UNIQUE INDEX "serverpod_auth_idp_passkey_account_key_id_base64" ON "serverpod_auth_idp_passkey_account" USING btree ("keyIdBase64");
|
|
|
|
--
|
|
-- Class PasskeyChallenge as table serverpod_auth_idp_passkey_challenge
|
|
--
|
|
CREATE TABLE "serverpod_auth_idp_passkey_challenge" (
|
|
"id" uuid PRIMARY KEY DEFAULT gen_random_uuid_v7(),
|
|
"createdAt" timestamp without time zone NOT NULL,
|
|
"challenge" bytea NOT NULL
|
|
);
|
|
|
|
--
|
|
-- Class RateLimitedRequestAttempt as table serverpod_auth_idp_rate_limited_request_attempt
|
|
--
|
|
CREATE TABLE "serverpod_auth_idp_rate_limited_request_attempt" (
|
|
"id" uuid PRIMARY KEY DEFAULT gen_random_uuid_v7(),
|
|
"domain" text NOT NULL,
|
|
"source" text NOT NULL,
|
|
"key" text NOT NULL,
|
|
"ipAddress" text,
|
|
"attemptedAt" timestamp without time zone NOT NULL,
|
|
"extraData" json
|
|
);
|
|
|
|
-- Indexes
|
|
CREATE INDEX "serverpod_auth_idp_rate_limited_request_attempt_composite" ON "serverpod_auth_idp_rate_limited_request_attempt" USING btree ("domain", "source", "key", "attemptedAt");
|
|
|
|
--
|
|
-- Class SecretChallenge as table serverpod_auth_idp_secret_challenge
|
|
--
|
|
CREATE TABLE "serverpod_auth_idp_secret_challenge" (
|
|
"id" uuid PRIMARY KEY DEFAULT gen_random_uuid_v7(),
|
|
"challengeCodeHash" text NOT NULL
|
|
);
|
|
|
|
--
|
|
-- Class RefreshToken as table serverpod_auth_core_jwt_refresh_token
|
|
--
|
|
CREATE TABLE "serverpod_auth_core_jwt_refresh_token" (
|
|
"id" uuid PRIMARY KEY DEFAULT gen_random_uuid_v7(),
|
|
"authUserId" uuid NOT NULL,
|
|
"scopeNames" json NOT NULL,
|
|
"extraClaims" text,
|
|
"method" text NOT NULL,
|
|
"fixedSecret" bytea NOT NULL,
|
|
"rotatingSecretHash" text NOT NULL,
|
|
"lastUpdatedAt" timestamp without time zone NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
|
"createdAt" timestamp without time zone NOT NULL DEFAULT CURRENT_TIMESTAMP
|
|
);
|
|
|
|
-- Indexes
|
|
CREATE INDEX "serverpod_auth_core_jwt_refresh_token_last_updated_at" ON "serverpod_auth_core_jwt_refresh_token" USING btree ("lastUpdatedAt");
|
|
|
|
--
|
|
-- Class UserProfile as table serverpod_auth_core_profile
|
|
--
|
|
CREATE TABLE "serverpod_auth_core_profile" (
|
|
"id" uuid PRIMARY KEY DEFAULT gen_random_uuid_v7(),
|
|
"authUserId" uuid NOT NULL,
|
|
"userName" text,
|
|
"fullName" text,
|
|
"email" text,
|
|
"createdAt" timestamp without time zone NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
|
"imageId" uuid
|
|
);
|
|
|
|
-- Indexes
|
|
CREATE UNIQUE INDEX "serverpod_auth_profile_user_profile_email_auth_user_id" ON "serverpod_auth_core_profile" USING btree ("authUserId");
|
|
|
|
--
|
|
-- Class UserProfileImage as table serverpod_auth_core_profile_image
|
|
--
|
|
CREATE TABLE "serverpod_auth_core_profile_image" (
|
|
"id" uuid PRIMARY KEY DEFAULT gen_random_uuid_v7(),
|
|
"userProfileId" uuid NOT NULL,
|
|
"createdAt" timestamp without time zone NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
|
"storageId" text NOT NULL,
|
|
"path" text NOT NULL,
|
|
"url" text NOT NULL
|
|
);
|
|
|
|
--
|
|
-- Class ServerSideSession as table serverpod_auth_core_session
|
|
--
|
|
CREATE TABLE "serverpod_auth_core_session" (
|
|
"id" uuid PRIMARY KEY DEFAULT gen_random_uuid_v7(),
|
|
"authUserId" uuid NOT NULL,
|
|
"scopeNames" json NOT NULL,
|
|
"createdAt" timestamp without time zone NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
|
"lastUsedAt" timestamp without time zone NOT NULL DEFAULT CURRENT_TIMESTAMP,
|
|
"expiresAt" timestamp without time zone,
|
|
"expireAfterUnusedFor" bigint,
|
|
"sessionKeyHash" bytea NOT NULL,
|
|
"sessionKeySalt" bytea NOT NULL,
|
|
"method" text NOT NULL
|
|
);
|
|
|
|
--
|
|
-- Class AuthUser as table serverpod_auth_core_user
|
|
--
|
|
CREATE TABLE "serverpod_auth_core_user" (
|
|
"id" uuid PRIMARY KEY DEFAULT gen_random_uuid_v7(),
|
|
"createdAt" timestamp without time zone NOT NULL,
|
|
"scopeNames" json NOT NULL,
|
|
"blocked" boolean NOT NULL
|
|
);
|
|
|
|
--
|
|
-- Foreign relations for "halkyon_oidc_attempt" table
|
|
--
|
|
ALTER TABLE ONLY "halkyon_oidc_attempt"
|
|
ADD CONSTRAINT "halkyon_oidc_attempt_fk_0"
|
|
FOREIGN KEY("callerId")
|
|
REFERENCES "serverpod_auth_core_user"("id")
|
|
ON DELETE CASCADE
|
|
ON UPDATE NO ACTION;
|
|
|
|
--
|
|
-- Foreign relations for "halkyon_oidc_identity" table
|
|
--
|
|
ALTER TABLE ONLY "halkyon_oidc_identity"
|
|
ADD CONSTRAINT "halkyon_oidc_identity_fk_0"
|
|
FOREIGN KEY("authUserId")
|
|
REFERENCES "serverpod_auth_core_user"("id")
|
|
ON DELETE CASCADE
|
|
ON UPDATE NO ACTION;
|
|
|
|
--
|
|
-- Foreign relations for "serverpod_future_call_claim" table
|
|
--
|
|
ALTER TABLE ONLY "serverpod_future_call_claim"
|
|
ADD CONSTRAINT "serverpod_future_call_claim_fk_0"
|
|
FOREIGN KEY("futureCallId")
|
|
REFERENCES "serverpod_future_call"("id")
|
|
ON DELETE CASCADE
|
|
ON UPDATE NO ACTION;
|
|
|
|
--
|
|
-- Foreign relations for "serverpod_log" table
|
|
--
|
|
ALTER TABLE ONLY "serverpod_log"
|
|
ADD CONSTRAINT "serverpod_log_fk_0"
|
|
FOREIGN KEY("sessionLogId")
|
|
REFERENCES "serverpod_session_log"("id")
|
|
ON DELETE CASCADE
|
|
ON UPDATE NO ACTION;
|
|
|
|
--
|
|
-- Foreign relations for "serverpod_message_log" table
|
|
--
|
|
ALTER TABLE ONLY "serverpod_message_log"
|
|
ADD CONSTRAINT "serverpod_message_log_fk_0"
|
|
FOREIGN KEY("sessionLogId")
|
|
REFERENCES "serverpod_session_log"("id")
|
|
ON DELETE CASCADE
|
|
ON UPDATE NO ACTION;
|
|
|
|
--
|
|
-- Foreign relations for "serverpod_query_log" table
|
|
--
|
|
ALTER TABLE ONLY "serverpod_query_log"
|
|
ADD CONSTRAINT "serverpod_query_log_fk_0"
|
|
FOREIGN KEY("sessionLogId")
|
|
REFERENCES "serverpod_session_log"("id")
|
|
ON DELETE CASCADE
|
|
ON UPDATE NO ACTION;
|
|
|
|
--
|
|
-- Foreign relations for "serverpod_auth_idp_anonymous_account" table
|
|
--
|
|
ALTER TABLE ONLY "serverpod_auth_idp_anonymous_account"
|
|
ADD CONSTRAINT "serverpod_auth_idp_anonymous_account_fk_0"
|
|
FOREIGN KEY("authUserId")
|
|
REFERENCES "serverpod_auth_core_user"("id")
|
|
ON DELETE CASCADE
|
|
ON UPDATE NO ACTION;
|
|
|
|
--
|
|
-- Foreign relations for "serverpod_auth_idp_apple_account" table
|
|
--
|
|
ALTER TABLE ONLY "serverpod_auth_idp_apple_account"
|
|
ADD CONSTRAINT "serverpod_auth_idp_apple_account_fk_0"
|
|
FOREIGN KEY("authUserId")
|
|
REFERENCES "serverpod_auth_core_user"("id")
|
|
ON DELETE CASCADE
|
|
ON UPDATE NO ACTION;
|
|
|
|
--
|
|
-- Foreign relations for "serverpod_auth_idp_email_account" table
|
|
--
|
|
ALTER TABLE ONLY "serverpod_auth_idp_email_account"
|
|
ADD CONSTRAINT "serverpod_auth_idp_email_account_fk_0"
|
|
FOREIGN KEY("authUserId")
|
|
REFERENCES "serverpod_auth_core_user"("id")
|
|
ON DELETE CASCADE
|
|
ON UPDATE NO ACTION;
|
|
|
|
--
|
|
-- Foreign relations for "serverpod_auth_idp_email_account_password_reset_request" table
|
|
--
|
|
ALTER TABLE ONLY "serverpod_auth_idp_email_account_password_reset_request"
|
|
ADD CONSTRAINT "serverpod_auth_idp_email_account_password_reset_request_fk_0"
|
|
FOREIGN KEY("emailAccountId")
|
|
REFERENCES "serverpod_auth_idp_email_account"("id")
|
|
ON DELETE CASCADE
|
|
ON UPDATE NO ACTION;
|
|
ALTER TABLE ONLY "serverpod_auth_idp_email_account_password_reset_request"
|
|
ADD CONSTRAINT "serverpod_auth_idp_email_account_password_reset_request_fk_1"
|
|
FOREIGN KEY("challengeId")
|
|
REFERENCES "serverpod_auth_idp_secret_challenge"("id")
|
|
ON DELETE CASCADE
|
|
ON UPDATE NO ACTION;
|
|
ALTER TABLE ONLY "serverpod_auth_idp_email_account_password_reset_request"
|
|
ADD CONSTRAINT "serverpod_auth_idp_email_account_password_reset_request_fk_2"
|
|
FOREIGN KEY("setPasswordChallengeId")
|
|
REFERENCES "serverpod_auth_idp_secret_challenge"("id")
|
|
ON DELETE CASCADE
|
|
ON UPDATE NO ACTION;
|
|
|
|
--
|
|
-- Foreign relations for "serverpod_auth_idp_email_account_request" table
|
|
--
|
|
ALTER TABLE ONLY "serverpod_auth_idp_email_account_request"
|
|
ADD CONSTRAINT "serverpod_auth_idp_email_account_request_fk_0"
|
|
FOREIGN KEY("challengeId")
|
|
REFERENCES "serverpod_auth_idp_secret_challenge"("id")
|
|
ON DELETE CASCADE
|
|
ON UPDATE NO ACTION;
|
|
ALTER TABLE ONLY "serverpod_auth_idp_email_account_request"
|
|
ADD CONSTRAINT "serverpod_auth_idp_email_account_request_fk_1"
|
|
FOREIGN KEY("createAccountChallengeId")
|
|
REFERENCES "serverpod_auth_idp_secret_challenge"("id")
|
|
ON DELETE CASCADE
|
|
ON UPDATE NO ACTION;
|
|
|
|
--
|
|
-- Foreign relations for "serverpod_auth_idp_facebook_account" table
|
|
--
|
|
ALTER TABLE ONLY "serverpod_auth_idp_facebook_account"
|
|
ADD CONSTRAINT "serverpod_auth_idp_facebook_account_fk_0"
|
|
FOREIGN KEY("authUserId")
|
|
REFERENCES "serverpod_auth_core_user"("id")
|
|
ON DELETE CASCADE
|
|
ON UPDATE NO ACTION;
|
|
|
|
--
|
|
-- Foreign relations for "serverpod_auth_idp_firebase_account" table
|
|
--
|
|
ALTER TABLE ONLY "serverpod_auth_idp_firebase_account"
|
|
ADD CONSTRAINT "serverpod_auth_idp_firebase_account_fk_0"
|
|
FOREIGN KEY("authUserId")
|
|
REFERENCES "serverpod_auth_core_user"("id")
|
|
ON DELETE CASCADE
|
|
ON UPDATE NO ACTION;
|
|
|
|
--
|
|
-- Foreign relations for "serverpod_auth_idp_github_account" table
|
|
--
|
|
ALTER TABLE ONLY "serverpod_auth_idp_github_account"
|
|
ADD CONSTRAINT "serverpod_auth_idp_github_account_fk_0"
|
|
FOREIGN KEY("authUserId")
|
|
REFERENCES "serverpod_auth_core_user"("id")
|
|
ON DELETE CASCADE
|
|
ON UPDATE NO ACTION;
|
|
|
|
--
|
|
-- Foreign relations for "serverpod_auth_idp_google_account" table
|
|
--
|
|
ALTER TABLE ONLY "serverpod_auth_idp_google_account"
|
|
ADD CONSTRAINT "serverpod_auth_idp_google_account_fk_0"
|
|
FOREIGN KEY("authUserId")
|
|
REFERENCES "serverpod_auth_core_user"("id")
|
|
ON DELETE CASCADE
|
|
ON UPDATE NO ACTION;
|
|
|
|
--
|
|
-- Foreign relations for "serverpod_auth_idp_microsoft_account" table
|
|
--
|
|
ALTER TABLE ONLY "serverpod_auth_idp_microsoft_account"
|
|
ADD CONSTRAINT "serverpod_auth_idp_microsoft_account_fk_0"
|
|
FOREIGN KEY("authUserId")
|
|
REFERENCES "serverpod_auth_core_user"("id")
|
|
ON DELETE CASCADE
|
|
ON UPDATE NO ACTION;
|
|
|
|
--
|
|
-- Foreign relations for "serverpod_auth_idp_passkey_account" table
|
|
--
|
|
ALTER TABLE ONLY "serverpod_auth_idp_passkey_account"
|
|
ADD CONSTRAINT "serverpod_auth_idp_passkey_account_fk_0"
|
|
FOREIGN KEY("authUserId")
|
|
REFERENCES "serverpod_auth_core_user"("id")
|
|
ON DELETE CASCADE
|
|
ON UPDATE NO ACTION;
|
|
|
|
--
|
|
-- Foreign relations for "serverpod_auth_core_jwt_refresh_token" table
|
|
--
|
|
ALTER TABLE ONLY "serverpod_auth_core_jwt_refresh_token"
|
|
ADD CONSTRAINT "serverpod_auth_core_jwt_refresh_token_fk_0"
|
|
FOREIGN KEY("authUserId")
|
|
REFERENCES "serverpod_auth_core_user"("id")
|
|
ON DELETE CASCADE
|
|
ON UPDATE NO ACTION;
|
|
|
|
--
|
|
-- Foreign relations for "serverpod_auth_core_profile" table
|
|
--
|
|
ALTER TABLE ONLY "serverpod_auth_core_profile"
|
|
ADD CONSTRAINT "serverpod_auth_core_profile_fk_0"
|
|
FOREIGN KEY("authUserId")
|
|
REFERENCES "serverpod_auth_core_user"("id")
|
|
ON DELETE CASCADE
|
|
ON UPDATE NO ACTION;
|
|
ALTER TABLE ONLY "serverpod_auth_core_profile"
|
|
ADD CONSTRAINT "serverpod_auth_core_profile_fk_1"
|
|
FOREIGN KEY("imageId")
|
|
REFERENCES "serverpod_auth_core_profile_image"("id")
|
|
ON DELETE NO ACTION
|
|
ON UPDATE NO ACTION
|
|
DEFERRABLE INITIALLY DEFERRED;
|
|
|
|
--
|
|
-- Foreign relations for "serverpod_auth_core_profile_image" table
|
|
--
|
|
ALTER TABLE ONLY "serverpod_auth_core_profile_image"
|
|
ADD CONSTRAINT "serverpod_auth_core_profile_image_fk_0"
|
|
FOREIGN KEY("userProfileId")
|
|
REFERENCES "serverpod_auth_core_profile"("id")
|
|
ON DELETE CASCADE
|
|
ON UPDATE NO ACTION;
|
|
|
|
--
|
|
-- Foreign relations for "serverpod_auth_core_session" table
|
|
--
|
|
ALTER TABLE ONLY "serverpod_auth_core_session"
|
|
ADD CONSTRAINT "serverpod_auth_core_session_fk_0"
|
|
FOREIGN KEY("authUserId")
|
|
REFERENCES "serverpod_auth_core_user"("id")
|
|
ON DELETE CASCADE
|
|
ON UPDATE NO ACTION;
|
|
|
|
|
|
--
|
|
-- MIGRATION VERSION FOR halkyon_oidc
|
|
--
|
|
INSERT INTO "serverpod_migrations" ("module", "version", "timestamp")
|
|
VALUES ('halkyon_oidc', '20261023180644988', now())
|
|
ON CONFLICT ("module")
|
|
DO UPDATE SET "version" = '20261023180644988', "timestamp" = now();
|
|
|
|
--
|
|
-- MIGRATION VERSION FOR serverpod
|
|
--
|
|
INSERT INTO "serverpod_migrations" ("module", "version", "timestamp")
|
|
VALUES ('serverpod', '20260824182259319', now())
|
|
ON CONFLICT ("module")
|
|
DO UPDATE SET "version" = '20260824182259319', "timestamp" = now();
|
|
|
|
--
|
|
-- MIGRATION VERSION FOR serverpod_auth_idp
|
|
--
|
|
INSERT INTO "serverpod_migrations" ("module", "version", "timestamp")
|
|
VALUES ('serverpod_auth_idp', '20260924105404509', now())
|
|
ON CONFLICT ("module")
|
|
DO UPDATE SET "version" = '20260924105404509', "timestamp" = now();
|
|
|
|
--
|
|
-- MIGRATION VERSION FOR serverpod_auth_core
|
|
--
|
|
INSERT INTO "serverpod_migrations" ("module", "version", "timestamp")
|
|
VALUES ('serverpod_auth_core', '20260924105232991', now())
|
|
ON CONFLICT ("module")
|
|
DO UPDATE SET "version" = '20260924105232991', "timestamp" = now();
|
|
|
|
|
|
COMMIT;
|