From 8964b1080d5eb2940149dec0111f3f0bc3d9afa8 Mon Sep 17 00:00:00 2001 From: Leendert de Borst Date: Tue, 14 Oct 2025 14:37:33 +0200 Subject: [PATCH] Update passkey schema (#520) --- .../pages/passkeys/PasskeyAuthenticate.tsx | 17 ++++++- .../popup/pages/passkeys/PasskeyCreate.tsx | 51 +++++++++++++++---- .../src/utils/SqliteClient.ts | 22 +++++--- .../utils/dist/shared/models/vault/index.d.ts | 4 +- .../utils/dist/shared/vault-sql/index.d.mts | 2 +- .../utils/dist/shared/vault-sql/index.d.ts | 2 +- .../src/utils/dist/shared/vault-sql/index.js | 8 +-- .../src/utils/dist/shared/vault-sql/index.mjs | 8 +-- .../VaultStoreKit/VaultStore+Passkey.swift | 23 ++++----- .../utils/dist/shared/models/vault/index.d.ts | 4 +- .../utils/dist/shared/vault-sql/index.d.mts | 2 +- .../utils/dist/shared/vault-sql/index.d.ts | 2 +- .../utils/dist/shared/vault-sql/index.js | 8 +-- .../utils/dist/shared/vault-sql/index.mjs | 8 +-- .../wwwroot/css/tailwind.css | 8 +-- .../js/dist/shared/vault-sql/index.d.mts | 2 +- .../js/dist/shared/vault-sql/index.d.ts | 2 +- .../wwwroot/js/dist/shared/vault-sql/index.js | 8 +-- .../js/dist/shared/vault-sql/index.mjs | 8 +-- ...51014122838_1.6.0-AddPasskeys.Designer.cs} | 8 +-- ...cs => 20251014122838_1.6.0-AddPasskeys.cs} | 4 +- .../AliasClientDbContextModelSnapshot.cs | 6 +-- .../server/Databases/AliasClientDb/Passkey.cs | 6 +-- .../Scripts/MigrationSql/000_FullSchema.sql | 4 +- ...s_to_20251014122838_1.6.0-AddPasskeys.sql} | 4 +- shared/models/src/vault/Passkey.ts | 4 +- shared/vault-sql/src/sql/SqlConstants.ts | 8 +-- 27 files changed, 140 insertions(+), 93 deletions(-) rename apps/server/Databases/AliasClientDb/Migrations/{20251007085746_1.6.0-AddPasskeys.Designer.cs => 20251014122838_1.6.0-AddPasskeys.Designer.cs} (98%) rename apps/server/Databases/AliasClientDb/Migrations/{20251007085746_1.6.0-AddPasskeys.cs => 20251014122838_1.6.0-AddPasskeys.cs} (98%) rename apps/server/Databases/AliasClientDb/Scripts/MigrationSql/{010_20250310131554_1.5.0-AddTotpCodes_to_20251007085746_1.6.0-AddPasskeys.sql => 010_20250310131554_1.5.0-AddTotpCodes_to_20251014122838_1.6.0-AddPasskeys.sql} (98%) diff --git a/apps/browser-extension/src/entrypoints/popup/pages/passkeys/PasskeyAuthenticate.tsx b/apps/browser-extension/src/entrypoints/popup/pages/passkeys/PasskeyAuthenticate.tsx index 7028146d3..6d7b7cc9a 100644 --- a/apps/browser-extension/src/entrypoints/popup/pages/passkeys/PasskeyAuthenticate.tsx +++ b/apps/browser-extension/src/entrypoints/popup/pages/passkeys/PasskeyAuthenticate.tsx @@ -168,13 +168,26 @@ const PasskeyAuthenticate: React.FC = () => { } } - // Build the stored record for the provider + /** + * Build the stored record for the provider + * Convert UserHandle from byte array to base64 string for serialization + */ + let userIdBase64: string | null = null; + if (storedPasskey.UserHandle) { + try { + const userHandleBytes = storedPasskey.UserHandle instanceof Uint8Array ? storedPasskey.UserHandle : new Uint8Array(storedPasskey.UserHandle); + userIdBase64 = PasskeyHelper.bytesToBase64url(userHandleBytes); + } catch (e) { + console.warn('Failed to convert UserHandle to base64', e); + } + } + const storedRecord: StoredPasskeyRecord = { rpId: storedPasskey.RpId, credentialId: PasskeyHelper.guidToBase64url(storedPasskey.Id), publicKey, privateKey, - userId: storedPasskey.UserId, + userId: userIdBase64, userName: storedPasskey.Username ?? undefined, userDisplayName: storedPasskey.ServiceName ?? undefined, prfSecret diff --git a/apps/browser-extension/src/entrypoints/popup/pages/passkeys/PasskeyCreate.tsx b/apps/browser-extension/src/entrypoints/popup/pages/passkeys/PasskeyCreate.tsx index 2cd725c08..26049e50f 100644 --- a/apps/browser-extension/src/entrypoints/popup/pages/passkeys/PasskeyCreate.tsx +++ b/apps/browser-extension/src/entrypoints/popup/pages/passkeys/PasskeyCreate.tsx @@ -88,13 +88,22 @@ const PasskeyCreate: React.FC = () => { if (data.publicKey.user?.id || data.publicKey.user?.name) { filtered = allPasskeysForRpId.filter(passkey => { /** - * Match by user ID if both are available - * The request has base64url encoded user.id, passkey has base64 encoded UserId - * For now, compare as strings (both should represent the same user identifier) + * Match by user handle if both are available + * The request has base64url encoded user.id, passkey has UserHandle as byte array + * Convert request's user.id to bytes for comparison */ - if (data.publicKey.user?.id && passkey.UserId) { - if (passkey.UserId === data.publicKey.user.id) { - return true; + if (data.publicKey.user?.id && passkey.UserHandle) { + try { + const requestUserIdBytes = PasskeyHelper.base64urlToBytes(data.publicKey.user.id); + const passkeyUserHandle = passkey.UserHandle instanceof Uint8Array ? passkey.UserHandle : new Uint8Array(passkey.UserHandle); + + // Compare byte arrays + if (requestUserIdBytes.length === passkeyUserHandle.length && + requestUserIdBytes.every((byte, idx) => byte === passkeyUserHandle[idx])) { + return true; + } + } catch { + // If conversion fails, skip this passkey } } @@ -279,12 +288,25 @@ const PasskeyCreate: React.FC = () => { // Delete the old passkey await dbContext.sqliteClient!.deletePasskeyById(selectedPasskeyToReplace); - // Create new passkey with same credential + /** + * Create new passkey with same credential + * Convert userId from base64 string to byte array for database storage + */ + let userHandleBytes: Uint8Array | null = null; + if (stored.userId) { + try { + userHandleBytes = PasskeyHelper.base64urlToBytes(stored.userId); + } catch { + // If conversion fails, store as null + userHandleBytes = null; + } + } + await dbContext.sqliteClient!.createPasskey({ Id: newPasskeyGuid, CredentialId: existingPasskey.CredentialId, RpId: stored.rpId, - UserId: stored.userId ?? null, + UserHandle: userHandleBytes, PublicKey: JSON.stringify(stored.publicKey), PrivateKey: JSON.stringify(stored.privateKey), DisplayName: displayName, @@ -318,12 +340,23 @@ const PasskeyCreate: React.FC = () => { /** * Create the Passkey linked to the credential * Note: We let the database generate a GUID for Id, which we'll convert to base64url for the RP + * Convert userId from base64 string to byte array for database storage */ + let userHandleBytes: Uint8Array | null = null; + if (stored.userId) { + try { + userHandleBytes = PasskeyHelper.base64urlToBytes(stored.userId); + } catch { + // If conversion fails, store as null + userHandleBytes = null; + } + } + await dbContext.sqliteClient!.createPasskey({ Id: newPasskeyGuid, CredentialId: credentialId, RpId: stored.rpId, - UserId: stored.userId ?? null, + UserHandle: userHandleBytes, PublicKey: JSON.stringify(stored.publicKey), PrivateKey: JSON.stringify(stored.privateKey), DisplayName: displayName, diff --git a/apps/browser-extension/src/utils/SqliteClient.ts b/apps/browser-extension/src/utils/SqliteClient.ts index 588a1407c..db0ec53f3 100644 --- a/apps/browser-extension/src/utils/SqliteClient.ts +++ b/apps/browser-extension/src/utils/SqliteClient.ts @@ -1151,7 +1151,7 @@ export class SqliteClient { p.Id, p.CredentialId, p.RpId, - p.UserId, + p.UserHandle, p.PublicKey, p.PrivateKey, p.DisplayName, @@ -1176,7 +1176,7 @@ export class SqliteClient { Id: row.Id, CredentialId: row.CredentialId, RpId: row.RpId, - UserId: row.UserId, + UserHandle: row.UserHandle, PublicKey: row.PublicKey, PrivateKey: row.PrivateKey, DisplayName: row.DisplayName, @@ -1205,7 +1205,7 @@ export class SqliteClient { p.Id, p.CredentialId, p.RpId, - p.UserId, + p.UserHandle, p.PublicKey, p.PrivateKey, p.DisplayName, @@ -1234,7 +1234,7 @@ export class SqliteClient { Id: row.Id, CredentialId: row.CredentialId, RpId: row.RpId, - UserId: row.UserId, + UserHandle: row.UserHandle, PublicKey: row.PublicKey, PrivateKey: row.PrivateKey, DisplayName: row.DisplayName, @@ -1263,7 +1263,7 @@ export class SqliteClient { p.Id, p.CredentialId, p.RpId, - p.UserId, + p.UserHandle, p.PublicKey, p.PrivateKey, p.DisplayName, @@ -1284,7 +1284,7 @@ export class SqliteClient { Id: row.Id, CredentialId: row.CredentialId, RpId: row.RpId, - UserId: row.UserId, + UserHandle: row.UserHandle, PublicKey: row.PublicKey, PrivateKey: row.PrivateKey, DisplayName: row.DisplayName, @@ -1315,7 +1315,7 @@ export class SqliteClient { const query = ` INSERT INTO Passkeys ( - Id, CredentialId, RpId, UserId, PublicKey, PrivateKey, + Id, CredentialId, RpId, UserHandle, PublicKey, PrivateKey, PrfKey, DisplayName, AdditionalData, CreatedAt, UpdatedAt, IsDeleted ) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?) @@ -1327,11 +1327,17 @@ export class SqliteClient { prfKeyData = passkey.PrfKey instanceof Uint8Array ? passkey.PrfKey : new Uint8Array(passkey.PrfKey); } + // Convert UserHandle to Uint8Array if it's a number array + let userHandleData: Uint8Array | null = null; + if (passkey.UserHandle) { + userHandleData = passkey.UserHandle instanceof Uint8Array ? passkey.UserHandle : new Uint8Array(passkey.UserHandle); + } + this.executeUpdate(query, [ passkey.Id, passkey.CredentialId, passkey.RpId, - passkey.UserId ?? null, + userHandleData, passkey.PublicKey, passkey.PrivateKey, prfKeyData, diff --git a/apps/browser-extension/src/utils/dist/shared/models/vault/index.d.ts b/apps/browser-extension/src/utils/dist/shared/models/vault/index.d.ts index 815aa0843..a44df8a3b 100644 --- a/apps/browser-extension/src/utils/dist/shared/models/vault/index.d.ts +++ b/apps/browser-extension/src/utils/dist/shared/models/vault/index.d.ts @@ -106,8 +106,8 @@ type Passkey = { CredentialId: string; /** The relying party identifier */ RpId: string; - /** The user ID provided by the relying party */ - UserId?: string | null; + /** The user handle (user ID) provided by the relying party - stored as byte array (BLOB) */ + UserHandle?: Uint8Array | number[] | null; /** The public key */ PublicKey: string; /** The private key */ diff --git a/apps/browser-extension/src/utils/dist/shared/vault-sql/index.d.mts b/apps/browser-extension/src/utils/dist/shared/vault-sql/index.d.mts index ea25cb473..871c1b2f1 100644 --- a/apps/browser-extension/src/utils/dist/shared/vault-sql/index.d.mts +++ b/apps/browser-extension/src/utils/dist/shared/vault-sql/index.d.mts @@ -122,7 +122,7 @@ declare const VAULT_VERSIONS: VaultVersion[]; * Complete database schema SQL (latest version) * Auto-generated from EF Core migrations */ -declare const COMPLETE_SCHEMA_SQL = "\n\uFEFFCREATE TABLE IF NOT EXISTS \"__EFMigrationsHistory\" (\n \"MigrationId\" TEXT NOT NULL CONSTRAINT \"PK___EFMigrationsHistory\" PRIMARY KEY,\n \"ProductVersion\" TEXT NOT NULL\n);\n\nBEGIN TRANSACTION;\nCREATE TABLE \"Aliases\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Aliases\" PRIMARY KEY,\n \"Gender\" VARCHAR NULL,\n \"FirstName\" VARCHAR NULL,\n \"LastName\" VARCHAR NULL,\n \"NickName\" VARCHAR NULL,\n \"BirthDate\" TEXT NOT NULL,\n \"AddressStreet\" VARCHAR NULL,\n \"AddressCity\" VARCHAR NULL,\n \"AddressState\" VARCHAR NULL,\n \"AddressZipCode\" VARCHAR NULL,\n \"AddressCountry\" VARCHAR NULL,\n \"Hobbies\" TEXT NULL,\n \"EmailPrefix\" TEXT NULL,\n \"PhoneMobile\" TEXT NULL,\n \"BankAccountIBAN\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nCREATE TABLE \"Services\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Services\" PRIMARY KEY,\n \"Name\" TEXT NULL,\n \"Url\" TEXT NULL,\n \"Logo\" BLOB NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nCREATE TABLE \"Credentials\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Credentials\" PRIMARY KEY,\n \"AliasId\" TEXT NOT NULL,\n \"Notes\" TEXT NULL,\n \"Username\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"ServiceId\" TEXT NOT NULL,\n CONSTRAINT \"FK_Credentials_Aliases_AliasId\" FOREIGN KEY (\"AliasId\") REFERENCES \"Aliases\" (\"Id\") ON DELETE CASCADE,\n CONSTRAINT \"FK_Credentials_Services_ServiceId\" FOREIGN KEY (\"ServiceId\") REFERENCES \"Services\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"Attachment\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Attachment\" PRIMARY KEY,\n \"Filename\" TEXT NOT NULL,\n \"Blob\" BLOB NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n CONSTRAINT \"FK_Attachment_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"Passwords\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Passwords\" PRIMARY KEY,\n \"Value\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n CONSTRAINT \"FK_Passwords_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE INDEX \"IX_Attachment_CredentialId\" ON \"Attachment\" (\"CredentialId\");\n\nCREATE INDEX \"IX_Credentials_AliasId\" ON \"Credentials\" (\"AliasId\");\n\nCREATE INDEX \"IX_Credentials_ServiceId\" ON \"Credentials\" (\"ServiceId\");\n\nCREATE INDEX \"IX_Passwords_CredentialId\" ON \"Passwords\" (\"CredentialId\");\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240708094944_1.0.0-InitialMigration', '9.0.4');\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240708224522_1.0.1-EmptyTestMigration', '9.0.4');\n\nALTER TABLE \"Aliases\" RENAME COLUMN \"EmailPrefix\" TO \"Email\";\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240711204207_1.0.2-ChangeEmailColumn', '9.0.4');\n\nCREATE TABLE \"EncryptionKeys\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_EncryptionKeys\" PRIMARY KEY,\n \"PublicKey\" TEXT NOT NULL,\n \"PrivateKey\" TEXT NOT NULL,\n \"IsPrimary\" INTEGER NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240729105618_1.1.0-AddPkiTables', '9.0.4');\n\nCREATE TABLE \"Settings\" (\n \"Key\" TEXT NOT NULL CONSTRAINT \"PK_Settings\" PRIMARY KEY,\n \"Value\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240805073413_1.2.0-AddSettingsTable', '9.0.4');\n\nCREATE TABLE \"ef_temp_Aliases\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Aliases\" PRIMARY KEY,\n \"BirthDate\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"Email\" TEXT NULL,\n \"FirstName\" VARCHAR NULL,\n \"Gender\" VARCHAR NULL,\n \"LastName\" VARCHAR NULL,\n \"NickName\" VARCHAR NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nINSERT INTO \"ef_temp_Aliases\" (\"Id\", \"BirthDate\", \"CreatedAt\", \"Email\", \"FirstName\", \"Gender\", \"LastName\", \"NickName\", \"UpdatedAt\")\nSELECT \"Id\", \"BirthDate\", \"CreatedAt\", \"Email\", \"FirstName\", \"Gender\", \"LastName\", \"NickName\", \"UpdatedAt\"\nFROM \"Aliases\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 0;\n\nBEGIN TRANSACTION;\nDROP TABLE \"Aliases\";\n\nALTER TABLE \"ef_temp_Aliases\" RENAME TO \"Aliases\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 1;\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240805122422_1.3.0-UpdateIdentityStructure', '9.0.4');\n\nBEGIN TRANSACTION;\nCREATE TABLE \"ef_temp_Credentials\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Credentials\" PRIMARY KEY,\n \"AliasId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"Notes\" TEXT NULL,\n \"ServiceId\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"Username\" TEXT NULL,\n CONSTRAINT \"FK_Credentials_Aliases_AliasId\" FOREIGN KEY (\"AliasId\") REFERENCES \"Aliases\" (\"Id\") ON DELETE CASCADE,\n CONSTRAINT \"FK_Credentials_Services_ServiceId\" FOREIGN KEY (\"ServiceId\") REFERENCES \"Services\" (\"Id\") ON DELETE CASCADE\n);\n\nINSERT INTO \"ef_temp_Credentials\" (\"Id\", \"AliasId\", \"CreatedAt\", \"Notes\", \"ServiceId\", \"UpdatedAt\", \"Username\")\nSELECT \"Id\", \"AliasId\", \"CreatedAt\", \"Notes\", \"ServiceId\", \"UpdatedAt\", \"Username\"\nFROM \"Credentials\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 0;\n\nBEGIN TRANSACTION;\nDROP TABLE \"Credentials\";\n\nALTER TABLE \"ef_temp_Credentials\" RENAME TO \"Credentials\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 1;\n\nBEGIN TRANSACTION;\nCREATE INDEX \"IX_Credentials_AliasId\" ON \"Credentials\" (\"AliasId\");\n\nCREATE INDEX \"IX_Credentials_ServiceId\" ON \"Credentials\" (\"ServiceId\");\n\nCOMMIT;\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240812141727_1.3.1-MakeUsernameOptional', '9.0.4');\n\nBEGIN TRANSACTION;\nALTER TABLE \"Settings\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Services\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Passwords\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"EncryptionKeys\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Credentials\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Attachment\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Aliases\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240916105320_1.4.0-AddSyncSupport', '9.0.4');\n\nALTER TABLE \"Attachment\" RENAME TO \"Attachments\";\n\nCREATE TABLE \"ef_temp_Attachments\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Attachments\" PRIMARY KEY,\n \"Blob\" BLOB NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"Filename\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n CONSTRAINT \"FK_Attachments_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nINSERT INTO \"ef_temp_Attachments\" (\"Id\", \"Blob\", \"CreatedAt\", \"CredentialId\", \"Filename\", \"IsDeleted\", \"UpdatedAt\")\nSELECT \"Id\", \"Blob\", \"CreatedAt\", \"CredentialId\", \"Filename\", \"IsDeleted\", \"UpdatedAt\"\nFROM \"Attachments\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 0;\n\nBEGIN TRANSACTION;\nDROP TABLE \"Attachments\";\n\nALTER TABLE \"ef_temp_Attachments\" RENAME TO \"Attachments\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 1;\n\nBEGIN TRANSACTION;\nCREATE INDEX \"IX_Attachments_CredentialId\" ON \"Attachments\" (\"CredentialId\");\n\nCOMMIT;\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240917191243_1.4.1-RenameAttachmentsPlural', '9.0.4');\n\nBEGIN TRANSACTION;\nCREATE TABLE \"TotpCodes\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_TotpCodes\" PRIMARY KEY,\n \"Name\" TEXT NOT NULL,\n \"SecretKey\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL,\n CONSTRAINT \"FK_TotpCodes_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE INDEX \"IX_TotpCodes_CredentialId\" ON \"TotpCodes\" (\"CredentialId\");\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20250310131554_1.5.0-AddTotpCodes', '9.0.4');\n\n\nPRAGMA foreign_keys = OFF;\n\n-- Clean up any existing temp tables first\nDROP TABLE IF EXISTS \"__EFMigrationsHistory_temp\";\nDROP TABLE IF EXISTS \"Aliases_temp\";\nDROP TABLE IF EXISTS \"Services_temp\";\nDROP TABLE IF EXISTS \"EncryptionKeys_temp\";\nDROP TABLE IF EXISTS \"Settings_temp\";\nDROP TABLE IF EXISTS \"Credentials_temp\";\nDROP TABLE IF EXISTS \"Attachments_temp\";\nDROP TABLE IF EXISTS \"Passwords_temp\";\nDROP TABLE IF EXISTS \"TotpCodes_temp\";\n\n-- Create backup tables for all data\nCREATE TABLE \"__EFMigrationsHistory_temp\" AS SELECT * FROM \"__EFMigrationsHistory\";\nCREATE TABLE \"Aliases_temp\" AS SELECT * FROM \"Aliases\";\nCREATE TABLE \"Services_temp\" AS SELECT * FROM \"Services\";\nCREATE TABLE \"EncryptionKeys_temp\" AS SELECT * FROM \"EncryptionKeys\";\nCREATE TABLE \"Settings_temp\" AS SELECT * FROM \"Settings\";\nCREATE TABLE \"Credentials_temp\" AS SELECT * FROM \"Credentials\";\nCREATE TABLE \"Attachments_temp\" AS SELECT * FROM \"Attachments\";\nCREATE TABLE \"Passwords_temp\" AS SELECT * FROM \"Passwords\";\nCREATE TABLE \"TotpCodes_temp\" AS SELECT * FROM \"TotpCodes\";\n\n-- Delete orphaned records that do not have a valid FK to the credential object\nDELETE FROM \"Attachments_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\nDELETE FROM \"Passwords_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\nDELETE FROM \"TotpCodes_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\n\n-- Delete orphaned credentials that do not have valid FKs to alias or service objects\nDELETE FROM \"Credentials_temp\" WHERE \"AliasId\" NOT IN (SELECT \"Id\" FROM \"Aliases_temp\");\nDELETE FROM \"Credentials_temp\" WHERE \"ServiceId\" NOT IN (SELECT \"Id\" FROM \"Services_temp\");\n\n-- After cleaning credentials, clean dependent tables again in case we removed credentials\nDELETE FROM \"Attachments_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\nDELETE FROM \"Passwords_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\nDELETE FROM \"TotpCodes_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\n\n-- Drop all existing tables\nDROP TABLE \"TotpCodes\";\nDROP TABLE \"Passwords\";\nDROP TABLE \"Attachments\";\nDROP TABLE \"Credentials\";\nDROP TABLE \"Settings\";\nDROP TABLE \"EncryptionKeys\";\nDROP TABLE \"Services\";\nDROP TABLE \"Aliases\";\nDROP TABLE \"__EFMigrationsHistory\";\n\n-- Recreate tables with proper constraints (no dependencies first)\nCREATE TABLE \"__EFMigrationsHistory\" (\n \"MigrationId\" TEXT NOT NULL CONSTRAINT \"PK___EFMigrationsHistory\" PRIMARY KEY,\n \"ProductVersion\" TEXT NOT NULL\n);\n\nCREATE TABLE \"Aliases\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Aliases\" PRIMARY KEY,\n \"BirthDate\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"Email\" TEXT NULL,\n \"FirstName\" VARCHAR NULL,\n \"Gender\" VARCHAR NULL,\n \"LastName\" VARCHAR NULL,\n \"NickName\" VARCHAR NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0\n);\n\nCREATE TABLE \"Services\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Services\" PRIMARY KEY,\n \"Name\" TEXT NULL,\n \"Url\" TEXT NULL,\n \"Logo\" BLOB NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0\n);\n\nCREATE TABLE \"EncryptionKeys\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_EncryptionKeys\" PRIMARY KEY,\n \"PublicKey\" TEXT NOT NULL,\n \"PrivateKey\" TEXT NOT NULL,\n \"IsPrimary\" INTEGER NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0\n);\n\nCREATE TABLE \"Settings\" (\n \"Key\" TEXT NOT NULL CONSTRAINT \"PK_Settings\" PRIMARY KEY,\n \"Value\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0\n);\n\n-- Tables with foreign keys\nCREATE TABLE \"Credentials\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Credentials\" PRIMARY KEY,\n \"AliasId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"Notes\" TEXT NULL,\n \"ServiceId\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"Username\" TEXT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0,\n CONSTRAINT \"FK_Credentials_Aliases_AliasId\" FOREIGN KEY (\"AliasId\") REFERENCES \"Aliases\" (\"Id\") ON DELETE CASCADE,\n CONSTRAINT \"FK_Credentials_Services_ServiceId\" FOREIGN KEY (\"ServiceId\") REFERENCES \"Services\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"Attachments\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Attachments\" PRIMARY KEY,\n \"Blob\" BLOB NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"Filename\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0,\n \"UpdatedAt\" TEXT NOT NULL,\n CONSTRAINT \"FK_Attachments_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"Passwords\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Passwords\" PRIMARY KEY,\n \"Value\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0,\n CONSTRAINT \"FK_Passwords_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"TotpCodes\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_TotpCodes\" PRIMARY KEY,\n \"Name\" TEXT NOT NULL,\n \"SecretKey\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0,\n CONSTRAINT \"FK_TotpCodes_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\n\n-- Restore data from temp tables\nINSERT INTO \"__EFMigrationsHistory\" SELECT * FROM \"__EFMigrationsHistory_temp\";\nINSERT INTO \"Aliases\" SELECT * FROM \"Aliases_temp\";\nINSERT INTO \"Services\" SELECT * FROM \"Services_temp\";\nINSERT INTO \"EncryptionKeys\" SELECT * FROM \"EncryptionKeys_temp\";\nINSERT INTO \"Settings\" SELECT * FROM \"Settings_temp\";\nINSERT INTO \"Credentials\" SELECT * FROM \"Credentials_temp\";\nINSERT INTO \"Attachments\" SELECT * FROM \"Attachments_temp\";\nINSERT INTO \"Passwords\" SELECT * FROM \"Passwords_temp\";\nINSERT INTO \"TotpCodes\" SELECT * FROM \"TotpCodes_temp\";\n\n-- Recreate indexes\nCREATE INDEX \"IX_Credentials_AliasId\" ON \"Credentials\" (\"AliasId\");\nCREATE INDEX \"IX_Credentials_ServiceId\" ON \"Credentials\" (\"ServiceId\");\nCREATE INDEX \"IX_Attachments_CredentialId\" ON \"Attachments\" (\"CredentialId\");\nCREATE INDEX \"IX_Passwords_CredentialId\" ON \"Passwords\" (\"CredentialId\");\nCREATE INDEX \"IX_TotpCodes_CredentialId\" ON \"TotpCodes\" (\"CredentialId\");\n\n-- Clean up temp tables\nDROP TABLE \"__EFMigrationsHistory_temp\";\nDROP TABLE \"Aliases_temp\";\nDROP TABLE \"Services_temp\";\nDROP TABLE \"EncryptionKeys_temp\";\nDROP TABLE \"Settings_temp\";\nDROP TABLE \"Credentials_temp\";\nDROP TABLE \"Attachments_temp\";\nDROP TABLE \"Passwords_temp\";\nDROP TABLE \"TotpCodes_temp\";\n\nPRAGMA foreign_keys = ON;\n\n\nCREATE TABLE \"Passkeys\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Passkeys\" PRIMARY KEY,\n \"RpId\" TEXT COLLATE NOCASE NOT NULL,\n \"UserId\" TEXT NULL,\n \"PublicKey\" TEXT NOT NULL,\n \"PrivateKey\" TEXT NOT NULL,\n \"PrfKey\" BLOB NULL,\n \"DisplayName\" TEXT NOT NULL,\n \"AdditionalData\" BLOB NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL,\n CONSTRAINT \"FK_Passkeys_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE INDEX \"IX_Passkeys_CredentialId\" ON \"Passkeys\" (\"CredentialId\");\n\nCREATE INDEX \"IX_Passkeys_RpId\" ON \"Passkeys\" (\"RpId\");\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20251007085746_1.6.0-AddPasskeys', '9.0.4');\n\nCOMMIT;\n"; +declare const COMPLETE_SCHEMA_SQL = "\n\uFEFFCREATE TABLE IF NOT EXISTS \"__EFMigrationsHistory\" (\n \"MigrationId\" TEXT NOT NULL CONSTRAINT \"PK___EFMigrationsHistory\" PRIMARY KEY,\n \"ProductVersion\" TEXT NOT NULL\n);\n\nBEGIN TRANSACTION;\nCREATE TABLE \"Aliases\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Aliases\" PRIMARY KEY,\n \"Gender\" VARCHAR NULL,\n \"FirstName\" VARCHAR NULL,\n \"LastName\" VARCHAR NULL,\n \"NickName\" VARCHAR NULL,\n \"BirthDate\" TEXT NOT NULL,\n \"AddressStreet\" VARCHAR NULL,\n \"AddressCity\" VARCHAR NULL,\n \"AddressState\" VARCHAR NULL,\n \"AddressZipCode\" VARCHAR NULL,\n \"AddressCountry\" VARCHAR NULL,\n \"Hobbies\" TEXT NULL,\n \"EmailPrefix\" TEXT NULL,\n \"PhoneMobile\" TEXT NULL,\n \"BankAccountIBAN\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nCREATE TABLE \"Services\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Services\" PRIMARY KEY,\n \"Name\" TEXT NULL,\n \"Url\" TEXT NULL,\n \"Logo\" BLOB NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nCREATE TABLE \"Credentials\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Credentials\" PRIMARY KEY,\n \"AliasId\" TEXT NOT NULL,\n \"Notes\" TEXT NULL,\n \"Username\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"ServiceId\" TEXT NOT NULL,\n CONSTRAINT \"FK_Credentials_Aliases_AliasId\" FOREIGN KEY (\"AliasId\") REFERENCES \"Aliases\" (\"Id\") ON DELETE CASCADE,\n CONSTRAINT \"FK_Credentials_Services_ServiceId\" FOREIGN KEY (\"ServiceId\") REFERENCES \"Services\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"Attachment\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Attachment\" PRIMARY KEY,\n \"Filename\" TEXT NOT NULL,\n \"Blob\" BLOB NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n CONSTRAINT \"FK_Attachment_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"Passwords\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Passwords\" PRIMARY KEY,\n \"Value\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n CONSTRAINT \"FK_Passwords_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE INDEX \"IX_Attachment_CredentialId\" ON \"Attachment\" (\"CredentialId\");\n\nCREATE INDEX \"IX_Credentials_AliasId\" ON \"Credentials\" (\"AliasId\");\n\nCREATE INDEX \"IX_Credentials_ServiceId\" ON \"Credentials\" (\"ServiceId\");\n\nCREATE INDEX \"IX_Passwords_CredentialId\" ON \"Passwords\" (\"CredentialId\");\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240708094944_1.0.0-InitialMigration', '9.0.4');\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240708224522_1.0.1-EmptyTestMigration', '9.0.4');\n\nALTER TABLE \"Aliases\" RENAME COLUMN \"EmailPrefix\" TO \"Email\";\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240711204207_1.0.2-ChangeEmailColumn', '9.0.4');\n\nCREATE TABLE \"EncryptionKeys\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_EncryptionKeys\" PRIMARY KEY,\n \"PublicKey\" TEXT NOT NULL,\n \"PrivateKey\" TEXT NOT NULL,\n \"IsPrimary\" INTEGER NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240729105618_1.1.0-AddPkiTables', '9.0.4');\n\nCREATE TABLE \"Settings\" (\n \"Key\" TEXT NOT NULL CONSTRAINT \"PK_Settings\" PRIMARY KEY,\n \"Value\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240805073413_1.2.0-AddSettingsTable', '9.0.4');\n\nCREATE TABLE \"ef_temp_Aliases\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Aliases\" PRIMARY KEY,\n \"BirthDate\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"Email\" TEXT NULL,\n \"FirstName\" VARCHAR NULL,\n \"Gender\" VARCHAR NULL,\n \"LastName\" VARCHAR NULL,\n \"NickName\" VARCHAR NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nINSERT INTO \"ef_temp_Aliases\" (\"Id\", \"BirthDate\", \"CreatedAt\", \"Email\", \"FirstName\", \"Gender\", \"LastName\", \"NickName\", \"UpdatedAt\")\nSELECT \"Id\", \"BirthDate\", \"CreatedAt\", \"Email\", \"FirstName\", \"Gender\", \"LastName\", \"NickName\", \"UpdatedAt\"\nFROM \"Aliases\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 0;\n\nBEGIN TRANSACTION;\nDROP TABLE \"Aliases\";\n\nALTER TABLE \"ef_temp_Aliases\" RENAME TO \"Aliases\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 1;\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240805122422_1.3.0-UpdateIdentityStructure', '9.0.4');\n\nBEGIN TRANSACTION;\nCREATE TABLE \"ef_temp_Credentials\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Credentials\" PRIMARY KEY,\n \"AliasId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"Notes\" TEXT NULL,\n \"ServiceId\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"Username\" TEXT NULL,\n CONSTRAINT \"FK_Credentials_Aliases_AliasId\" FOREIGN KEY (\"AliasId\") REFERENCES \"Aliases\" (\"Id\") ON DELETE CASCADE,\n CONSTRAINT \"FK_Credentials_Services_ServiceId\" FOREIGN KEY (\"ServiceId\") REFERENCES \"Services\" (\"Id\") ON DELETE CASCADE\n);\n\nINSERT INTO \"ef_temp_Credentials\" (\"Id\", \"AliasId\", \"CreatedAt\", \"Notes\", \"ServiceId\", \"UpdatedAt\", \"Username\")\nSELECT \"Id\", \"AliasId\", \"CreatedAt\", \"Notes\", \"ServiceId\", \"UpdatedAt\", \"Username\"\nFROM \"Credentials\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 0;\n\nBEGIN TRANSACTION;\nDROP TABLE \"Credentials\";\n\nALTER TABLE \"ef_temp_Credentials\" RENAME TO \"Credentials\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 1;\n\nBEGIN TRANSACTION;\nCREATE INDEX \"IX_Credentials_AliasId\" ON \"Credentials\" (\"AliasId\");\n\nCREATE INDEX \"IX_Credentials_ServiceId\" ON \"Credentials\" (\"ServiceId\");\n\nCOMMIT;\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240812141727_1.3.1-MakeUsernameOptional', '9.0.4');\n\nBEGIN TRANSACTION;\nALTER TABLE \"Settings\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Services\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Passwords\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"EncryptionKeys\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Credentials\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Attachment\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Aliases\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240916105320_1.4.0-AddSyncSupport', '9.0.4');\n\nALTER TABLE \"Attachment\" RENAME TO \"Attachments\";\n\nCREATE TABLE \"ef_temp_Attachments\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Attachments\" PRIMARY KEY,\n \"Blob\" BLOB NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"Filename\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n CONSTRAINT \"FK_Attachments_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nINSERT INTO \"ef_temp_Attachments\" (\"Id\", \"Blob\", \"CreatedAt\", \"CredentialId\", \"Filename\", \"IsDeleted\", \"UpdatedAt\")\nSELECT \"Id\", \"Blob\", \"CreatedAt\", \"CredentialId\", \"Filename\", \"IsDeleted\", \"UpdatedAt\"\nFROM \"Attachments\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 0;\n\nBEGIN TRANSACTION;\nDROP TABLE \"Attachments\";\n\nALTER TABLE \"ef_temp_Attachments\" RENAME TO \"Attachments\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 1;\n\nBEGIN TRANSACTION;\nCREATE INDEX \"IX_Attachments_CredentialId\" ON \"Attachments\" (\"CredentialId\");\n\nCOMMIT;\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240917191243_1.4.1-RenameAttachmentsPlural', '9.0.4');\n\nBEGIN TRANSACTION;\nCREATE TABLE \"TotpCodes\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_TotpCodes\" PRIMARY KEY,\n \"Name\" TEXT NOT NULL,\n \"SecretKey\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL,\n CONSTRAINT \"FK_TotpCodes_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE INDEX \"IX_TotpCodes_CredentialId\" ON \"TotpCodes\" (\"CredentialId\");\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20250310131554_1.5.0-AddTotpCodes', '9.0.4');\n\n\nPRAGMA foreign_keys = OFF;\n\n-- Clean up any existing temp tables first\nDROP TABLE IF EXISTS \"__EFMigrationsHistory_temp\";\nDROP TABLE IF EXISTS \"Aliases_temp\";\nDROP TABLE IF EXISTS \"Services_temp\";\nDROP TABLE IF EXISTS \"EncryptionKeys_temp\";\nDROP TABLE IF EXISTS \"Settings_temp\";\nDROP TABLE IF EXISTS \"Credentials_temp\";\nDROP TABLE IF EXISTS \"Attachments_temp\";\nDROP TABLE IF EXISTS \"Passwords_temp\";\nDROP TABLE IF EXISTS \"TotpCodes_temp\";\n\n-- Create backup tables for all data\nCREATE TABLE \"__EFMigrationsHistory_temp\" AS SELECT * FROM \"__EFMigrationsHistory\";\nCREATE TABLE \"Aliases_temp\" AS SELECT * FROM \"Aliases\";\nCREATE TABLE \"Services_temp\" AS SELECT * FROM \"Services\";\nCREATE TABLE \"EncryptionKeys_temp\" AS SELECT * FROM \"EncryptionKeys\";\nCREATE TABLE \"Settings_temp\" AS SELECT * FROM \"Settings\";\nCREATE TABLE \"Credentials_temp\" AS SELECT * FROM \"Credentials\";\nCREATE TABLE \"Attachments_temp\" AS SELECT * FROM \"Attachments\";\nCREATE TABLE \"Passwords_temp\" AS SELECT * FROM \"Passwords\";\nCREATE TABLE \"TotpCodes_temp\" AS SELECT * FROM \"TotpCodes\";\n\n-- Delete orphaned records that do not have a valid FK to the credential object\nDELETE FROM \"Attachments_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\nDELETE FROM \"Passwords_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\nDELETE FROM \"TotpCodes_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\n\n-- Delete orphaned credentials that do not have valid FKs to alias or service objects\nDELETE FROM \"Credentials_temp\" WHERE \"AliasId\" NOT IN (SELECT \"Id\" FROM \"Aliases_temp\");\nDELETE FROM \"Credentials_temp\" WHERE \"ServiceId\" NOT IN (SELECT \"Id\" FROM \"Services_temp\");\n\n-- After cleaning credentials, clean dependent tables again in case we removed credentials\nDELETE FROM \"Attachments_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\nDELETE FROM \"Passwords_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\nDELETE FROM \"TotpCodes_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\n\n-- Drop all existing tables\nDROP TABLE \"TotpCodes\";\nDROP TABLE \"Passwords\";\nDROP TABLE \"Attachments\";\nDROP TABLE \"Credentials\";\nDROP TABLE \"Settings\";\nDROP TABLE \"EncryptionKeys\";\nDROP TABLE \"Services\";\nDROP TABLE \"Aliases\";\nDROP TABLE \"__EFMigrationsHistory\";\n\n-- Recreate tables with proper constraints (no dependencies first)\nCREATE TABLE \"__EFMigrationsHistory\" (\n \"MigrationId\" TEXT NOT NULL CONSTRAINT \"PK___EFMigrationsHistory\" PRIMARY KEY,\n \"ProductVersion\" TEXT NOT NULL\n);\n\nCREATE TABLE \"Aliases\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Aliases\" PRIMARY KEY,\n \"BirthDate\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"Email\" TEXT NULL,\n \"FirstName\" VARCHAR NULL,\n \"Gender\" VARCHAR NULL,\n \"LastName\" VARCHAR NULL,\n \"NickName\" VARCHAR NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0\n);\n\nCREATE TABLE \"Services\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Services\" PRIMARY KEY,\n \"Name\" TEXT NULL,\n \"Url\" TEXT NULL,\n \"Logo\" BLOB NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0\n);\n\nCREATE TABLE \"EncryptionKeys\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_EncryptionKeys\" PRIMARY KEY,\n \"PublicKey\" TEXT NOT NULL,\n \"PrivateKey\" TEXT NOT NULL,\n \"IsPrimary\" INTEGER NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0\n);\n\nCREATE TABLE \"Settings\" (\n \"Key\" TEXT NOT NULL CONSTRAINT \"PK_Settings\" PRIMARY KEY,\n \"Value\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0\n);\n\n-- Tables with foreign keys\nCREATE TABLE \"Credentials\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Credentials\" PRIMARY KEY,\n \"AliasId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"Notes\" TEXT NULL,\n \"ServiceId\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"Username\" TEXT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0,\n CONSTRAINT \"FK_Credentials_Aliases_AliasId\" FOREIGN KEY (\"AliasId\") REFERENCES \"Aliases\" (\"Id\") ON DELETE CASCADE,\n CONSTRAINT \"FK_Credentials_Services_ServiceId\" FOREIGN KEY (\"ServiceId\") REFERENCES \"Services\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"Attachments\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Attachments\" PRIMARY KEY,\n \"Blob\" BLOB NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"Filename\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0,\n \"UpdatedAt\" TEXT NOT NULL,\n CONSTRAINT \"FK_Attachments_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"Passwords\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Passwords\" PRIMARY KEY,\n \"Value\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0,\n CONSTRAINT \"FK_Passwords_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"TotpCodes\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_TotpCodes\" PRIMARY KEY,\n \"Name\" TEXT NOT NULL,\n \"SecretKey\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0,\n CONSTRAINT \"FK_TotpCodes_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\n\n-- Restore data from temp tables\nINSERT INTO \"__EFMigrationsHistory\" SELECT * FROM \"__EFMigrationsHistory_temp\";\nINSERT INTO \"Aliases\" SELECT * FROM \"Aliases_temp\";\nINSERT INTO \"Services\" SELECT * FROM \"Services_temp\";\nINSERT INTO \"EncryptionKeys\" SELECT * FROM \"EncryptionKeys_temp\";\nINSERT INTO \"Settings\" SELECT * FROM \"Settings_temp\";\nINSERT INTO \"Credentials\" SELECT * FROM \"Credentials_temp\";\nINSERT INTO \"Attachments\" SELECT * FROM \"Attachments_temp\";\nINSERT INTO \"Passwords\" SELECT * FROM \"Passwords_temp\";\nINSERT INTO \"TotpCodes\" SELECT * FROM \"TotpCodes_temp\";\n\n-- Recreate indexes\nCREATE INDEX \"IX_Credentials_AliasId\" ON \"Credentials\" (\"AliasId\");\nCREATE INDEX \"IX_Credentials_ServiceId\" ON \"Credentials\" (\"ServiceId\");\nCREATE INDEX \"IX_Attachments_CredentialId\" ON \"Attachments\" (\"CredentialId\");\nCREATE INDEX \"IX_Passwords_CredentialId\" ON \"Passwords\" (\"CredentialId\");\nCREATE INDEX \"IX_TotpCodes_CredentialId\" ON \"TotpCodes\" (\"CredentialId\");\n\n-- Clean up temp tables\nDROP TABLE \"__EFMigrationsHistory_temp\";\nDROP TABLE \"Aliases_temp\";\nDROP TABLE \"Services_temp\";\nDROP TABLE \"EncryptionKeys_temp\";\nDROP TABLE \"Settings_temp\";\nDROP TABLE \"Credentials_temp\";\nDROP TABLE \"Attachments_temp\";\nDROP TABLE \"Passwords_temp\";\nDROP TABLE \"TotpCodes_temp\";\n\nPRAGMA foreign_keys = ON;\n\n\nCREATE TABLE \"Passkeys\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Passkeys\" PRIMARY KEY,\n \"RpId\" TEXT COLLATE NOCASE NOT NULL,\n \"UserHandle\" BLOB NOT NULL,\n \"PublicKey\" TEXT NOT NULL,\n \"PrivateKey\" TEXT NOT NULL,\n \"PrfKey\" BLOB NULL,\n \"DisplayName\" TEXT NOT NULL,\n \"AdditionalData\" BLOB NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL,\n CONSTRAINT \"FK_Passkeys_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE INDEX \"IX_Passkeys_CredentialId\" ON \"Passkeys\" (\"CredentialId\");\n\nCREATE INDEX \"IX_Passkeys_RpId\" ON \"Passkeys\" (\"RpId\");\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20251014122838_1.6.0-AddPasskeys', '9.0.4');\n\nCOMMIT;\n"; /** * Individual migration SQL scripts * Auto-generated from EF Core migrations diff --git a/apps/browser-extension/src/utils/dist/shared/vault-sql/index.d.ts b/apps/browser-extension/src/utils/dist/shared/vault-sql/index.d.ts index ea25cb473..871c1b2f1 100644 --- a/apps/browser-extension/src/utils/dist/shared/vault-sql/index.d.ts +++ b/apps/browser-extension/src/utils/dist/shared/vault-sql/index.d.ts @@ -122,7 +122,7 @@ declare const VAULT_VERSIONS: VaultVersion[]; * Complete database schema SQL (latest version) * Auto-generated from EF Core migrations */ -declare const COMPLETE_SCHEMA_SQL = "\n\uFEFFCREATE TABLE IF NOT EXISTS \"__EFMigrationsHistory\" (\n \"MigrationId\" TEXT NOT NULL CONSTRAINT \"PK___EFMigrationsHistory\" PRIMARY KEY,\n \"ProductVersion\" TEXT NOT NULL\n);\n\nBEGIN TRANSACTION;\nCREATE TABLE \"Aliases\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Aliases\" PRIMARY KEY,\n \"Gender\" VARCHAR NULL,\n \"FirstName\" VARCHAR NULL,\n \"LastName\" VARCHAR NULL,\n \"NickName\" VARCHAR NULL,\n \"BirthDate\" TEXT NOT NULL,\n \"AddressStreet\" VARCHAR NULL,\n \"AddressCity\" VARCHAR NULL,\n \"AddressState\" VARCHAR NULL,\n \"AddressZipCode\" VARCHAR NULL,\n \"AddressCountry\" VARCHAR NULL,\n \"Hobbies\" TEXT NULL,\n \"EmailPrefix\" TEXT NULL,\n \"PhoneMobile\" TEXT NULL,\n \"BankAccountIBAN\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nCREATE TABLE \"Services\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Services\" PRIMARY KEY,\n \"Name\" TEXT NULL,\n \"Url\" TEXT NULL,\n \"Logo\" BLOB NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nCREATE TABLE \"Credentials\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Credentials\" PRIMARY KEY,\n \"AliasId\" TEXT NOT NULL,\n \"Notes\" TEXT NULL,\n \"Username\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"ServiceId\" TEXT NOT NULL,\n CONSTRAINT \"FK_Credentials_Aliases_AliasId\" FOREIGN KEY (\"AliasId\") REFERENCES \"Aliases\" (\"Id\") ON DELETE CASCADE,\n CONSTRAINT \"FK_Credentials_Services_ServiceId\" FOREIGN KEY (\"ServiceId\") REFERENCES \"Services\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"Attachment\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Attachment\" PRIMARY KEY,\n \"Filename\" TEXT NOT NULL,\n \"Blob\" BLOB NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n CONSTRAINT \"FK_Attachment_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"Passwords\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Passwords\" PRIMARY KEY,\n \"Value\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n CONSTRAINT \"FK_Passwords_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE INDEX \"IX_Attachment_CredentialId\" ON \"Attachment\" (\"CredentialId\");\n\nCREATE INDEX \"IX_Credentials_AliasId\" ON \"Credentials\" (\"AliasId\");\n\nCREATE INDEX \"IX_Credentials_ServiceId\" ON \"Credentials\" (\"ServiceId\");\n\nCREATE INDEX \"IX_Passwords_CredentialId\" ON \"Passwords\" (\"CredentialId\");\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240708094944_1.0.0-InitialMigration', '9.0.4');\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240708224522_1.0.1-EmptyTestMigration', '9.0.4');\n\nALTER TABLE \"Aliases\" RENAME COLUMN \"EmailPrefix\" TO \"Email\";\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240711204207_1.0.2-ChangeEmailColumn', '9.0.4');\n\nCREATE TABLE \"EncryptionKeys\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_EncryptionKeys\" PRIMARY KEY,\n \"PublicKey\" TEXT NOT NULL,\n \"PrivateKey\" TEXT NOT NULL,\n \"IsPrimary\" INTEGER NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240729105618_1.1.0-AddPkiTables', '9.0.4');\n\nCREATE TABLE \"Settings\" (\n \"Key\" TEXT NOT NULL CONSTRAINT \"PK_Settings\" PRIMARY KEY,\n \"Value\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240805073413_1.2.0-AddSettingsTable', '9.0.4');\n\nCREATE TABLE \"ef_temp_Aliases\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Aliases\" PRIMARY KEY,\n \"BirthDate\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"Email\" TEXT NULL,\n \"FirstName\" VARCHAR NULL,\n \"Gender\" VARCHAR NULL,\n \"LastName\" VARCHAR NULL,\n \"NickName\" VARCHAR NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nINSERT INTO \"ef_temp_Aliases\" (\"Id\", \"BirthDate\", \"CreatedAt\", \"Email\", \"FirstName\", \"Gender\", \"LastName\", \"NickName\", \"UpdatedAt\")\nSELECT \"Id\", \"BirthDate\", \"CreatedAt\", \"Email\", \"FirstName\", \"Gender\", \"LastName\", \"NickName\", \"UpdatedAt\"\nFROM \"Aliases\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 0;\n\nBEGIN TRANSACTION;\nDROP TABLE \"Aliases\";\n\nALTER TABLE \"ef_temp_Aliases\" RENAME TO \"Aliases\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 1;\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240805122422_1.3.0-UpdateIdentityStructure', '9.0.4');\n\nBEGIN TRANSACTION;\nCREATE TABLE \"ef_temp_Credentials\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Credentials\" PRIMARY KEY,\n \"AliasId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"Notes\" TEXT NULL,\n \"ServiceId\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"Username\" TEXT NULL,\n CONSTRAINT \"FK_Credentials_Aliases_AliasId\" FOREIGN KEY (\"AliasId\") REFERENCES \"Aliases\" (\"Id\") ON DELETE CASCADE,\n CONSTRAINT \"FK_Credentials_Services_ServiceId\" FOREIGN KEY (\"ServiceId\") REFERENCES \"Services\" (\"Id\") ON DELETE CASCADE\n);\n\nINSERT INTO \"ef_temp_Credentials\" (\"Id\", \"AliasId\", \"CreatedAt\", \"Notes\", \"ServiceId\", \"UpdatedAt\", \"Username\")\nSELECT \"Id\", \"AliasId\", \"CreatedAt\", \"Notes\", \"ServiceId\", \"UpdatedAt\", \"Username\"\nFROM \"Credentials\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 0;\n\nBEGIN TRANSACTION;\nDROP TABLE \"Credentials\";\n\nALTER TABLE \"ef_temp_Credentials\" RENAME TO \"Credentials\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 1;\n\nBEGIN TRANSACTION;\nCREATE INDEX \"IX_Credentials_AliasId\" ON \"Credentials\" (\"AliasId\");\n\nCREATE INDEX \"IX_Credentials_ServiceId\" ON \"Credentials\" (\"ServiceId\");\n\nCOMMIT;\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240812141727_1.3.1-MakeUsernameOptional', '9.0.4');\n\nBEGIN TRANSACTION;\nALTER TABLE \"Settings\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Services\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Passwords\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"EncryptionKeys\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Credentials\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Attachment\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Aliases\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240916105320_1.4.0-AddSyncSupport', '9.0.4');\n\nALTER TABLE \"Attachment\" RENAME TO \"Attachments\";\n\nCREATE TABLE \"ef_temp_Attachments\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Attachments\" PRIMARY KEY,\n \"Blob\" BLOB NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"Filename\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n CONSTRAINT \"FK_Attachments_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nINSERT INTO \"ef_temp_Attachments\" (\"Id\", \"Blob\", \"CreatedAt\", \"CredentialId\", \"Filename\", \"IsDeleted\", \"UpdatedAt\")\nSELECT \"Id\", \"Blob\", \"CreatedAt\", \"CredentialId\", \"Filename\", \"IsDeleted\", \"UpdatedAt\"\nFROM \"Attachments\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 0;\n\nBEGIN TRANSACTION;\nDROP TABLE \"Attachments\";\n\nALTER TABLE \"ef_temp_Attachments\" RENAME TO \"Attachments\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 1;\n\nBEGIN TRANSACTION;\nCREATE INDEX \"IX_Attachments_CredentialId\" ON \"Attachments\" (\"CredentialId\");\n\nCOMMIT;\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240917191243_1.4.1-RenameAttachmentsPlural', '9.0.4');\n\nBEGIN TRANSACTION;\nCREATE TABLE \"TotpCodes\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_TotpCodes\" PRIMARY KEY,\n \"Name\" TEXT NOT NULL,\n \"SecretKey\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL,\n CONSTRAINT \"FK_TotpCodes_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE INDEX \"IX_TotpCodes_CredentialId\" ON \"TotpCodes\" (\"CredentialId\");\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20250310131554_1.5.0-AddTotpCodes', '9.0.4');\n\n\nPRAGMA foreign_keys = OFF;\n\n-- Clean up any existing temp tables first\nDROP TABLE IF EXISTS \"__EFMigrationsHistory_temp\";\nDROP TABLE IF EXISTS \"Aliases_temp\";\nDROP TABLE IF EXISTS \"Services_temp\";\nDROP TABLE IF EXISTS \"EncryptionKeys_temp\";\nDROP TABLE IF EXISTS \"Settings_temp\";\nDROP TABLE IF EXISTS \"Credentials_temp\";\nDROP TABLE IF EXISTS \"Attachments_temp\";\nDROP TABLE IF EXISTS \"Passwords_temp\";\nDROP TABLE IF EXISTS \"TotpCodes_temp\";\n\n-- Create backup tables for all data\nCREATE TABLE \"__EFMigrationsHistory_temp\" AS SELECT * FROM \"__EFMigrationsHistory\";\nCREATE TABLE \"Aliases_temp\" AS SELECT * FROM \"Aliases\";\nCREATE TABLE \"Services_temp\" AS SELECT * FROM \"Services\";\nCREATE TABLE \"EncryptionKeys_temp\" AS SELECT * FROM \"EncryptionKeys\";\nCREATE TABLE \"Settings_temp\" AS SELECT * FROM \"Settings\";\nCREATE TABLE \"Credentials_temp\" AS SELECT * FROM \"Credentials\";\nCREATE TABLE \"Attachments_temp\" AS SELECT * FROM \"Attachments\";\nCREATE TABLE \"Passwords_temp\" AS SELECT * FROM \"Passwords\";\nCREATE TABLE \"TotpCodes_temp\" AS SELECT * FROM \"TotpCodes\";\n\n-- Delete orphaned records that do not have a valid FK to the credential object\nDELETE FROM \"Attachments_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\nDELETE FROM \"Passwords_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\nDELETE FROM \"TotpCodes_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\n\n-- Delete orphaned credentials that do not have valid FKs to alias or service objects\nDELETE FROM \"Credentials_temp\" WHERE \"AliasId\" NOT IN (SELECT \"Id\" FROM \"Aliases_temp\");\nDELETE FROM \"Credentials_temp\" WHERE \"ServiceId\" NOT IN (SELECT \"Id\" FROM \"Services_temp\");\n\n-- After cleaning credentials, clean dependent tables again in case we removed credentials\nDELETE FROM \"Attachments_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\nDELETE FROM \"Passwords_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\nDELETE FROM \"TotpCodes_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\n\n-- Drop all existing tables\nDROP TABLE \"TotpCodes\";\nDROP TABLE \"Passwords\";\nDROP TABLE \"Attachments\";\nDROP TABLE \"Credentials\";\nDROP TABLE \"Settings\";\nDROP TABLE \"EncryptionKeys\";\nDROP TABLE \"Services\";\nDROP TABLE \"Aliases\";\nDROP TABLE \"__EFMigrationsHistory\";\n\n-- Recreate tables with proper constraints (no dependencies first)\nCREATE TABLE \"__EFMigrationsHistory\" (\n \"MigrationId\" TEXT NOT NULL CONSTRAINT \"PK___EFMigrationsHistory\" PRIMARY KEY,\n \"ProductVersion\" TEXT NOT NULL\n);\n\nCREATE TABLE \"Aliases\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Aliases\" PRIMARY KEY,\n \"BirthDate\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"Email\" TEXT NULL,\n \"FirstName\" VARCHAR NULL,\n \"Gender\" VARCHAR NULL,\n \"LastName\" VARCHAR NULL,\n \"NickName\" VARCHAR NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0\n);\n\nCREATE TABLE \"Services\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Services\" PRIMARY KEY,\n \"Name\" TEXT NULL,\n \"Url\" TEXT NULL,\n \"Logo\" BLOB NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0\n);\n\nCREATE TABLE \"EncryptionKeys\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_EncryptionKeys\" PRIMARY KEY,\n \"PublicKey\" TEXT NOT NULL,\n \"PrivateKey\" TEXT NOT NULL,\n \"IsPrimary\" INTEGER NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0\n);\n\nCREATE TABLE \"Settings\" (\n \"Key\" TEXT NOT NULL CONSTRAINT \"PK_Settings\" PRIMARY KEY,\n \"Value\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0\n);\n\n-- Tables with foreign keys\nCREATE TABLE \"Credentials\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Credentials\" PRIMARY KEY,\n \"AliasId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"Notes\" TEXT NULL,\n \"ServiceId\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"Username\" TEXT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0,\n CONSTRAINT \"FK_Credentials_Aliases_AliasId\" FOREIGN KEY (\"AliasId\") REFERENCES \"Aliases\" (\"Id\") ON DELETE CASCADE,\n CONSTRAINT \"FK_Credentials_Services_ServiceId\" FOREIGN KEY (\"ServiceId\") REFERENCES \"Services\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"Attachments\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Attachments\" PRIMARY KEY,\n \"Blob\" BLOB NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"Filename\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0,\n \"UpdatedAt\" TEXT NOT NULL,\n CONSTRAINT \"FK_Attachments_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"Passwords\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Passwords\" PRIMARY KEY,\n \"Value\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0,\n CONSTRAINT \"FK_Passwords_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"TotpCodes\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_TotpCodes\" PRIMARY KEY,\n \"Name\" TEXT NOT NULL,\n \"SecretKey\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0,\n CONSTRAINT \"FK_TotpCodes_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\n\n-- Restore data from temp tables\nINSERT INTO \"__EFMigrationsHistory\" SELECT * FROM \"__EFMigrationsHistory_temp\";\nINSERT INTO \"Aliases\" SELECT * FROM \"Aliases_temp\";\nINSERT INTO \"Services\" SELECT * FROM \"Services_temp\";\nINSERT INTO \"EncryptionKeys\" SELECT * FROM \"EncryptionKeys_temp\";\nINSERT INTO \"Settings\" SELECT * FROM \"Settings_temp\";\nINSERT INTO \"Credentials\" SELECT * FROM \"Credentials_temp\";\nINSERT INTO \"Attachments\" SELECT * FROM \"Attachments_temp\";\nINSERT INTO \"Passwords\" SELECT * FROM \"Passwords_temp\";\nINSERT INTO \"TotpCodes\" SELECT * FROM \"TotpCodes_temp\";\n\n-- Recreate indexes\nCREATE INDEX \"IX_Credentials_AliasId\" ON \"Credentials\" (\"AliasId\");\nCREATE INDEX \"IX_Credentials_ServiceId\" ON \"Credentials\" (\"ServiceId\");\nCREATE INDEX \"IX_Attachments_CredentialId\" ON \"Attachments\" (\"CredentialId\");\nCREATE INDEX \"IX_Passwords_CredentialId\" ON \"Passwords\" (\"CredentialId\");\nCREATE INDEX \"IX_TotpCodes_CredentialId\" ON \"TotpCodes\" (\"CredentialId\");\n\n-- Clean up temp tables\nDROP TABLE \"__EFMigrationsHistory_temp\";\nDROP TABLE \"Aliases_temp\";\nDROP TABLE \"Services_temp\";\nDROP TABLE \"EncryptionKeys_temp\";\nDROP TABLE \"Settings_temp\";\nDROP TABLE \"Credentials_temp\";\nDROP TABLE \"Attachments_temp\";\nDROP TABLE \"Passwords_temp\";\nDROP TABLE \"TotpCodes_temp\";\n\nPRAGMA foreign_keys = ON;\n\n\nCREATE TABLE \"Passkeys\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Passkeys\" PRIMARY KEY,\n \"RpId\" TEXT COLLATE NOCASE NOT NULL,\n \"UserId\" TEXT NULL,\n \"PublicKey\" TEXT NOT NULL,\n \"PrivateKey\" TEXT NOT NULL,\n \"PrfKey\" BLOB NULL,\n \"DisplayName\" TEXT NOT NULL,\n \"AdditionalData\" BLOB NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL,\n CONSTRAINT \"FK_Passkeys_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE INDEX \"IX_Passkeys_CredentialId\" ON \"Passkeys\" (\"CredentialId\");\n\nCREATE INDEX \"IX_Passkeys_RpId\" ON \"Passkeys\" (\"RpId\");\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20251007085746_1.6.0-AddPasskeys', '9.0.4');\n\nCOMMIT;\n"; +declare const COMPLETE_SCHEMA_SQL = "\n\uFEFFCREATE TABLE IF NOT EXISTS \"__EFMigrationsHistory\" (\n \"MigrationId\" TEXT NOT NULL CONSTRAINT \"PK___EFMigrationsHistory\" PRIMARY KEY,\n \"ProductVersion\" TEXT NOT NULL\n);\n\nBEGIN TRANSACTION;\nCREATE TABLE \"Aliases\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Aliases\" PRIMARY KEY,\n \"Gender\" VARCHAR NULL,\n \"FirstName\" VARCHAR NULL,\n \"LastName\" VARCHAR NULL,\n \"NickName\" VARCHAR NULL,\n \"BirthDate\" TEXT NOT NULL,\n \"AddressStreet\" VARCHAR NULL,\n \"AddressCity\" VARCHAR NULL,\n \"AddressState\" VARCHAR NULL,\n \"AddressZipCode\" VARCHAR NULL,\n \"AddressCountry\" VARCHAR NULL,\n \"Hobbies\" TEXT NULL,\n \"EmailPrefix\" TEXT NULL,\n \"PhoneMobile\" TEXT NULL,\n \"BankAccountIBAN\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nCREATE TABLE \"Services\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Services\" PRIMARY KEY,\n \"Name\" TEXT NULL,\n \"Url\" TEXT NULL,\n \"Logo\" BLOB NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nCREATE TABLE \"Credentials\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Credentials\" PRIMARY KEY,\n \"AliasId\" TEXT NOT NULL,\n \"Notes\" TEXT NULL,\n \"Username\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"ServiceId\" TEXT NOT NULL,\n CONSTRAINT \"FK_Credentials_Aliases_AliasId\" FOREIGN KEY (\"AliasId\") REFERENCES \"Aliases\" (\"Id\") ON DELETE CASCADE,\n CONSTRAINT \"FK_Credentials_Services_ServiceId\" FOREIGN KEY (\"ServiceId\") REFERENCES \"Services\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"Attachment\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Attachment\" PRIMARY KEY,\n \"Filename\" TEXT NOT NULL,\n \"Blob\" BLOB NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n CONSTRAINT \"FK_Attachment_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"Passwords\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Passwords\" PRIMARY KEY,\n \"Value\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n CONSTRAINT \"FK_Passwords_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE INDEX \"IX_Attachment_CredentialId\" ON \"Attachment\" (\"CredentialId\");\n\nCREATE INDEX \"IX_Credentials_AliasId\" ON \"Credentials\" (\"AliasId\");\n\nCREATE INDEX \"IX_Credentials_ServiceId\" ON \"Credentials\" (\"ServiceId\");\n\nCREATE INDEX \"IX_Passwords_CredentialId\" ON \"Passwords\" (\"CredentialId\");\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240708094944_1.0.0-InitialMigration', '9.0.4');\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240708224522_1.0.1-EmptyTestMigration', '9.0.4');\n\nALTER TABLE \"Aliases\" RENAME COLUMN \"EmailPrefix\" TO \"Email\";\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240711204207_1.0.2-ChangeEmailColumn', '9.0.4');\n\nCREATE TABLE \"EncryptionKeys\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_EncryptionKeys\" PRIMARY KEY,\n \"PublicKey\" TEXT NOT NULL,\n \"PrivateKey\" TEXT NOT NULL,\n \"IsPrimary\" INTEGER NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240729105618_1.1.0-AddPkiTables', '9.0.4');\n\nCREATE TABLE \"Settings\" (\n \"Key\" TEXT NOT NULL CONSTRAINT \"PK_Settings\" PRIMARY KEY,\n \"Value\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240805073413_1.2.0-AddSettingsTable', '9.0.4');\n\nCREATE TABLE \"ef_temp_Aliases\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Aliases\" PRIMARY KEY,\n \"BirthDate\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"Email\" TEXT NULL,\n \"FirstName\" VARCHAR NULL,\n \"Gender\" VARCHAR NULL,\n \"LastName\" VARCHAR NULL,\n \"NickName\" VARCHAR NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nINSERT INTO \"ef_temp_Aliases\" (\"Id\", \"BirthDate\", \"CreatedAt\", \"Email\", \"FirstName\", \"Gender\", \"LastName\", \"NickName\", \"UpdatedAt\")\nSELECT \"Id\", \"BirthDate\", \"CreatedAt\", \"Email\", \"FirstName\", \"Gender\", \"LastName\", \"NickName\", \"UpdatedAt\"\nFROM \"Aliases\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 0;\n\nBEGIN TRANSACTION;\nDROP TABLE \"Aliases\";\n\nALTER TABLE \"ef_temp_Aliases\" RENAME TO \"Aliases\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 1;\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240805122422_1.3.0-UpdateIdentityStructure', '9.0.4');\n\nBEGIN TRANSACTION;\nCREATE TABLE \"ef_temp_Credentials\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Credentials\" PRIMARY KEY,\n \"AliasId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"Notes\" TEXT NULL,\n \"ServiceId\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"Username\" TEXT NULL,\n CONSTRAINT \"FK_Credentials_Aliases_AliasId\" FOREIGN KEY (\"AliasId\") REFERENCES \"Aliases\" (\"Id\") ON DELETE CASCADE,\n CONSTRAINT \"FK_Credentials_Services_ServiceId\" FOREIGN KEY (\"ServiceId\") REFERENCES \"Services\" (\"Id\") ON DELETE CASCADE\n);\n\nINSERT INTO \"ef_temp_Credentials\" (\"Id\", \"AliasId\", \"CreatedAt\", \"Notes\", \"ServiceId\", \"UpdatedAt\", \"Username\")\nSELECT \"Id\", \"AliasId\", \"CreatedAt\", \"Notes\", \"ServiceId\", \"UpdatedAt\", \"Username\"\nFROM \"Credentials\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 0;\n\nBEGIN TRANSACTION;\nDROP TABLE \"Credentials\";\n\nALTER TABLE \"ef_temp_Credentials\" RENAME TO \"Credentials\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 1;\n\nBEGIN TRANSACTION;\nCREATE INDEX \"IX_Credentials_AliasId\" ON \"Credentials\" (\"AliasId\");\n\nCREATE INDEX \"IX_Credentials_ServiceId\" ON \"Credentials\" (\"ServiceId\");\n\nCOMMIT;\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240812141727_1.3.1-MakeUsernameOptional', '9.0.4');\n\nBEGIN TRANSACTION;\nALTER TABLE \"Settings\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Services\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Passwords\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"EncryptionKeys\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Credentials\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Attachment\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Aliases\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240916105320_1.4.0-AddSyncSupport', '9.0.4');\n\nALTER TABLE \"Attachment\" RENAME TO \"Attachments\";\n\nCREATE TABLE \"ef_temp_Attachments\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Attachments\" PRIMARY KEY,\n \"Blob\" BLOB NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"Filename\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n CONSTRAINT \"FK_Attachments_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nINSERT INTO \"ef_temp_Attachments\" (\"Id\", \"Blob\", \"CreatedAt\", \"CredentialId\", \"Filename\", \"IsDeleted\", \"UpdatedAt\")\nSELECT \"Id\", \"Blob\", \"CreatedAt\", \"CredentialId\", \"Filename\", \"IsDeleted\", \"UpdatedAt\"\nFROM \"Attachments\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 0;\n\nBEGIN TRANSACTION;\nDROP TABLE \"Attachments\";\n\nALTER TABLE \"ef_temp_Attachments\" RENAME TO \"Attachments\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 1;\n\nBEGIN TRANSACTION;\nCREATE INDEX \"IX_Attachments_CredentialId\" ON \"Attachments\" (\"CredentialId\");\n\nCOMMIT;\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240917191243_1.4.1-RenameAttachmentsPlural', '9.0.4');\n\nBEGIN TRANSACTION;\nCREATE TABLE \"TotpCodes\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_TotpCodes\" PRIMARY KEY,\n \"Name\" TEXT NOT NULL,\n \"SecretKey\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL,\n CONSTRAINT \"FK_TotpCodes_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE INDEX \"IX_TotpCodes_CredentialId\" ON \"TotpCodes\" (\"CredentialId\");\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20250310131554_1.5.0-AddTotpCodes', '9.0.4');\n\n\nPRAGMA foreign_keys = OFF;\n\n-- Clean up any existing temp tables first\nDROP TABLE IF EXISTS \"__EFMigrationsHistory_temp\";\nDROP TABLE IF EXISTS \"Aliases_temp\";\nDROP TABLE IF EXISTS \"Services_temp\";\nDROP TABLE IF EXISTS \"EncryptionKeys_temp\";\nDROP TABLE IF EXISTS \"Settings_temp\";\nDROP TABLE IF EXISTS \"Credentials_temp\";\nDROP TABLE IF EXISTS \"Attachments_temp\";\nDROP TABLE IF EXISTS \"Passwords_temp\";\nDROP TABLE IF EXISTS \"TotpCodes_temp\";\n\n-- Create backup tables for all data\nCREATE TABLE \"__EFMigrationsHistory_temp\" AS SELECT * FROM \"__EFMigrationsHistory\";\nCREATE TABLE \"Aliases_temp\" AS SELECT * FROM \"Aliases\";\nCREATE TABLE \"Services_temp\" AS SELECT * FROM \"Services\";\nCREATE TABLE \"EncryptionKeys_temp\" AS SELECT * FROM \"EncryptionKeys\";\nCREATE TABLE \"Settings_temp\" AS SELECT * FROM \"Settings\";\nCREATE TABLE \"Credentials_temp\" AS SELECT * FROM \"Credentials\";\nCREATE TABLE \"Attachments_temp\" AS SELECT * FROM \"Attachments\";\nCREATE TABLE \"Passwords_temp\" AS SELECT * FROM \"Passwords\";\nCREATE TABLE \"TotpCodes_temp\" AS SELECT * FROM \"TotpCodes\";\n\n-- Delete orphaned records that do not have a valid FK to the credential object\nDELETE FROM \"Attachments_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\nDELETE FROM \"Passwords_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\nDELETE FROM \"TotpCodes_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\n\n-- Delete orphaned credentials that do not have valid FKs to alias or service objects\nDELETE FROM \"Credentials_temp\" WHERE \"AliasId\" NOT IN (SELECT \"Id\" FROM \"Aliases_temp\");\nDELETE FROM \"Credentials_temp\" WHERE \"ServiceId\" NOT IN (SELECT \"Id\" FROM \"Services_temp\");\n\n-- After cleaning credentials, clean dependent tables again in case we removed credentials\nDELETE FROM \"Attachments_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\nDELETE FROM \"Passwords_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\nDELETE FROM \"TotpCodes_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\n\n-- Drop all existing tables\nDROP TABLE \"TotpCodes\";\nDROP TABLE \"Passwords\";\nDROP TABLE \"Attachments\";\nDROP TABLE \"Credentials\";\nDROP TABLE \"Settings\";\nDROP TABLE \"EncryptionKeys\";\nDROP TABLE \"Services\";\nDROP TABLE \"Aliases\";\nDROP TABLE \"__EFMigrationsHistory\";\n\n-- Recreate tables with proper constraints (no dependencies first)\nCREATE TABLE \"__EFMigrationsHistory\" (\n \"MigrationId\" TEXT NOT NULL CONSTRAINT \"PK___EFMigrationsHistory\" PRIMARY KEY,\n \"ProductVersion\" TEXT NOT NULL\n);\n\nCREATE TABLE \"Aliases\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Aliases\" PRIMARY KEY,\n \"BirthDate\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"Email\" TEXT NULL,\n \"FirstName\" VARCHAR NULL,\n \"Gender\" VARCHAR NULL,\n \"LastName\" VARCHAR NULL,\n \"NickName\" VARCHAR NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0\n);\n\nCREATE TABLE \"Services\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Services\" PRIMARY KEY,\n \"Name\" TEXT NULL,\n \"Url\" TEXT NULL,\n \"Logo\" BLOB NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0\n);\n\nCREATE TABLE \"EncryptionKeys\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_EncryptionKeys\" PRIMARY KEY,\n \"PublicKey\" TEXT NOT NULL,\n \"PrivateKey\" TEXT NOT NULL,\n \"IsPrimary\" INTEGER NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0\n);\n\nCREATE TABLE \"Settings\" (\n \"Key\" TEXT NOT NULL CONSTRAINT \"PK_Settings\" PRIMARY KEY,\n \"Value\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0\n);\n\n-- Tables with foreign keys\nCREATE TABLE \"Credentials\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Credentials\" PRIMARY KEY,\n \"AliasId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"Notes\" TEXT NULL,\n \"ServiceId\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"Username\" TEXT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0,\n CONSTRAINT \"FK_Credentials_Aliases_AliasId\" FOREIGN KEY (\"AliasId\") REFERENCES \"Aliases\" (\"Id\") ON DELETE CASCADE,\n CONSTRAINT \"FK_Credentials_Services_ServiceId\" FOREIGN KEY (\"ServiceId\") REFERENCES \"Services\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"Attachments\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Attachments\" PRIMARY KEY,\n \"Blob\" BLOB NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"Filename\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0,\n \"UpdatedAt\" TEXT NOT NULL,\n CONSTRAINT \"FK_Attachments_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"Passwords\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Passwords\" PRIMARY KEY,\n \"Value\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0,\n CONSTRAINT \"FK_Passwords_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"TotpCodes\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_TotpCodes\" PRIMARY KEY,\n \"Name\" TEXT NOT NULL,\n \"SecretKey\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0,\n CONSTRAINT \"FK_TotpCodes_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\n\n-- Restore data from temp tables\nINSERT INTO \"__EFMigrationsHistory\" SELECT * FROM \"__EFMigrationsHistory_temp\";\nINSERT INTO \"Aliases\" SELECT * FROM \"Aliases_temp\";\nINSERT INTO \"Services\" SELECT * FROM \"Services_temp\";\nINSERT INTO \"EncryptionKeys\" SELECT * FROM \"EncryptionKeys_temp\";\nINSERT INTO \"Settings\" SELECT * FROM \"Settings_temp\";\nINSERT INTO \"Credentials\" SELECT * FROM \"Credentials_temp\";\nINSERT INTO \"Attachments\" SELECT * FROM \"Attachments_temp\";\nINSERT INTO \"Passwords\" SELECT * FROM \"Passwords_temp\";\nINSERT INTO \"TotpCodes\" SELECT * FROM \"TotpCodes_temp\";\n\n-- Recreate indexes\nCREATE INDEX \"IX_Credentials_AliasId\" ON \"Credentials\" (\"AliasId\");\nCREATE INDEX \"IX_Credentials_ServiceId\" ON \"Credentials\" (\"ServiceId\");\nCREATE INDEX \"IX_Attachments_CredentialId\" ON \"Attachments\" (\"CredentialId\");\nCREATE INDEX \"IX_Passwords_CredentialId\" ON \"Passwords\" (\"CredentialId\");\nCREATE INDEX \"IX_TotpCodes_CredentialId\" ON \"TotpCodes\" (\"CredentialId\");\n\n-- Clean up temp tables\nDROP TABLE \"__EFMigrationsHistory_temp\";\nDROP TABLE \"Aliases_temp\";\nDROP TABLE \"Services_temp\";\nDROP TABLE \"EncryptionKeys_temp\";\nDROP TABLE \"Settings_temp\";\nDROP TABLE \"Credentials_temp\";\nDROP TABLE \"Attachments_temp\";\nDROP TABLE \"Passwords_temp\";\nDROP TABLE \"TotpCodes_temp\";\n\nPRAGMA foreign_keys = ON;\n\n\nCREATE TABLE \"Passkeys\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Passkeys\" PRIMARY KEY,\n \"RpId\" TEXT COLLATE NOCASE NOT NULL,\n \"UserHandle\" BLOB NOT NULL,\n \"PublicKey\" TEXT NOT NULL,\n \"PrivateKey\" TEXT NOT NULL,\n \"PrfKey\" BLOB NULL,\n \"DisplayName\" TEXT NOT NULL,\n \"AdditionalData\" BLOB NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL,\n CONSTRAINT \"FK_Passkeys_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE INDEX \"IX_Passkeys_CredentialId\" ON \"Passkeys\" (\"CredentialId\");\n\nCREATE INDEX \"IX_Passkeys_RpId\" ON \"Passkeys\" (\"RpId\");\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20251014122838_1.6.0-AddPasskeys', '9.0.4');\n\nCOMMIT;\n"; /** * Individual migration SQL scripts * Auto-generated from EF Core migrations diff --git a/apps/browser-extension/src/utils/dist/shared/vault-sql/index.js b/apps/browser-extension/src/utils/dist/shared/vault-sql/index.js index 23deaf64d..7872cbecc 100644 --- a/apps/browser-extension/src/utils/dist/shared/vault-sql/index.js +++ b/apps/browser-extension/src/utils/dist/shared/vault-sql/index.js @@ -464,7 +464,7 @@ PRAGMA foreign_keys = ON; CREATE TABLE "Passkeys" ( "Id" TEXT NOT NULL CONSTRAINT "PK_Passkeys" PRIMARY KEY, "RpId" TEXT COLLATE NOCASE NOT NULL, - "UserId" TEXT NULL, + "UserHandle" BLOB NOT NULL, "PublicKey" TEXT NOT NULL, "PrivateKey" TEXT NOT NULL, "PrfKey" BLOB NULL, @@ -482,7 +482,7 @@ CREATE INDEX "IX_Passkeys_CredentialId" ON "Passkeys" ("CredentialId"); CREATE INDEX "IX_Passkeys_RpId" ON "Passkeys" ("RpId"); INSERT INTO "__EFMigrationsHistory" ("MigrationId", "ProductVersion") -VALUES ('20251007085746_1.6.0-AddPasskeys', '9.0.4'); +VALUES ('20251014122838_1.6.0-AddPasskeys', '9.0.4'); COMMIT; `; @@ -851,7 +851,7 @@ PRAGMA foreign_keys = ON; CREATE TABLE "Passkeys" ( "Id" TEXT NOT NULL CONSTRAINT "PK_Passkeys" PRIMARY KEY, "RpId" TEXT COLLATE NOCASE NOT NULL, - "UserId" TEXT NULL, + "UserHandle" BLOB NOT NULL, "PublicKey" TEXT NOT NULL, "PrivateKey" TEXT NOT NULL, "PrfKey" BLOB NULL, @@ -869,7 +869,7 @@ CREATE INDEX "IX_Passkeys_CredentialId" ON "Passkeys" ("CredentialId"); CREATE INDEX "IX_Passkeys_RpId" ON "Passkeys" ("RpId"); INSERT INTO "__EFMigrationsHistory" ("MigrationId", "ProductVersion") -VALUES ('20251007085746_1.6.0-AddPasskeys', '9.0.4'); +VALUES ('20251014122838_1.6.0-AddPasskeys', '9.0.4'); COMMIT;` }; diff --git a/apps/browser-extension/src/utils/dist/shared/vault-sql/index.mjs b/apps/browser-extension/src/utils/dist/shared/vault-sql/index.mjs index 0899a348b..28c6dfc06 100644 --- a/apps/browser-extension/src/utils/dist/shared/vault-sql/index.mjs +++ b/apps/browser-extension/src/utils/dist/shared/vault-sql/index.mjs @@ -435,7 +435,7 @@ PRAGMA foreign_keys = ON; CREATE TABLE "Passkeys" ( "Id" TEXT NOT NULL CONSTRAINT "PK_Passkeys" PRIMARY KEY, "RpId" TEXT COLLATE NOCASE NOT NULL, - "UserId" TEXT NULL, + "UserHandle" BLOB NOT NULL, "PublicKey" TEXT NOT NULL, "PrivateKey" TEXT NOT NULL, "PrfKey" BLOB NULL, @@ -453,7 +453,7 @@ CREATE INDEX "IX_Passkeys_CredentialId" ON "Passkeys" ("CredentialId"); CREATE INDEX "IX_Passkeys_RpId" ON "Passkeys" ("RpId"); INSERT INTO "__EFMigrationsHistory" ("MigrationId", "ProductVersion") -VALUES ('20251007085746_1.6.0-AddPasskeys', '9.0.4'); +VALUES ('20251014122838_1.6.0-AddPasskeys', '9.0.4'); COMMIT; `; @@ -822,7 +822,7 @@ PRAGMA foreign_keys = ON; CREATE TABLE "Passkeys" ( "Id" TEXT NOT NULL CONSTRAINT "PK_Passkeys" PRIMARY KEY, "RpId" TEXT COLLATE NOCASE NOT NULL, - "UserId" TEXT NULL, + "UserHandle" BLOB NOT NULL, "PublicKey" TEXT NOT NULL, "PrivateKey" TEXT NOT NULL, "PrfKey" BLOB NULL, @@ -840,7 +840,7 @@ CREATE INDEX "IX_Passkeys_CredentialId" ON "Passkeys" ("CredentialId"); CREATE INDEX "IX_Passkeys_RpId" ON "Passkeys" ("RpId"); INSERT INTO "__EFMigrationsHistory" ("MigrationId", "ProductVersion") -VALUES ('20251007085746_1.6.0-AddPasskeys', '9.0.4'); +VALUES ('20251014122838_1.6.0-AddPasskeys', '9.0.4'); COMMIT;` }; diff --git a/apps/mobile-app/ios/VaultStoreKit/VaultStore+Passkey.swift b/apps/mobile-app/ios/VaultStoreKit/VaultStore+Passkey.swift index aac250d0b..3bae7d5c8 100644 --- a/apps/mobile-app/ios/VaultStoreKit/VaultStore+Passkey.swift +++ b/apps/mobile-app/ios/VaultStoreKit/VaultStore+Passkey.swift @@ -15,7 +15,7 @@ extension VaultStore { private static let colId = Expression("Id") private static let colCredentialId = Expression("CredentialId") private static let colRpId = Expression("RpId") - private static let colUserId = Expression("UserId") + private static let colUserHandle = Expression("UserHandle") private static let colPublicKey = Expression("PublicKey") private static let colPrivateKey = Expression("PrivateKey") private static let colPrfKey = Expression("PrfKey") @@ -347,7 +347,7 @@ extension VaultStore { let idString = try row.get(Self.colId) let parentCredentialIdString = try row.get(Self.colCredentialId) let rpId = try row.get(Self.colRpId) - let userIdBase64url = try? row.get(Self.colUserId) + let userHandleBlob = try? row.get(Self.colUserHandle) let publicKeyString = try row.get(Self.colPublicKey) let privateKeyString = try row.get(Self.colPrivateKey) let displayName = try row.get(Self.colDisplayName) @@ -376,17 +376,12 @@ extension VaultStore { return nil } - // Parse userId (stored as base64url-encoded string in DB, decode to raw bytes for iOS) - let userId: Data? - if let userIdBase64url = userIdBase64url, !userIdBase64url.isEmpty { - do { - userId = try PasskeyHelper.base64urlToBytes(userIdBase64url) - } catch { - print("VaultStore+Passkey: Failed to decode userId from base64url: \(error)") - userId = nil - } + // Parse userHandle (stored as blob - raw bytes) + let userHandle: Data? + if let userHandleBlob = userHandleBlob { + userHandle = Data(userHandleBlob.bytes) } else { - userId = nil + userHandle = nil } // Parse PrfKey (stored as blob) @@ -403,7 +398,7 @@ extension VaultStore { id: id, parentCredentialId: parentCredentialId, // Parent Credential UUID rpId: rpId, - userHandle: userId, + userHandle: userHandle, userName: nil, // userName not stored in DB, derived from parent credential publicKey: publicKeyData, privateKey: privateKeyData, @@ -520,7 +515,7 @@ extension VaultStore { Self.colId <- passkey.id.uuidString, Self.colCredentialId <- passkey.parentCredentialId.uuidString, Self.colRpId <- passkey.rpId, - Self.colUserId <- passkey.userHandle?.base64EncodedString(), + Self.colUserHandle <- passkey.userHandle.map { Blob(bytes: [UInt8]($0)) }, Self.colPublicKey <- String(data: passkey.publicKey, encoding: .utf8)!, Self.colPrivateKey <- String(data: passkey.privateKey, encoding: .utf8)!, Self.colPrfKey <- passkey.prfKey.map { Blob(bytes: [UInt8]($0)) }, diff --git a/apps/mobile-app/utils/dist/shared/models/vault/index.d.ts b/apps/mobile-app/utils/dist/shared/models/vault/index.d.ts index 815aa0843..a44df8a3b 100644 --- a/apps/mobile-app/utils/dist/shared/models/vault/index.d.ts +++ b/apps/mobile-app/utils/dist/shared/models/vault/index.d.ts @@ -106,8 +106,8 @@ type Passkey = { CredentialId: string; /** The relying party identifier */ RpId: string; - /** The user ID provided by the relying party */ - UserId?: string | null; + /** The user handle (user ID) provided by the relying party - stored as byte array (BLOB) */ + UserHandle?: Uint8Array | number[] | null; /** The public key */ PublicKey: string; /** The private key */ diff --git a/apps/mobile-app/utils/dist/shared/vault-sql/index.d.mts b/apps/mobile-app/utils/dist/shared/vault-sql/index.d.mts index ea25cb473..871c1b2f1 100644 --- a/apps/mobile-app/utils/dist/shared/vault-sql/index.d.mts +++ b/apps/mobile-app/utils/dist/shared/vault-sql/index.d.mts @@ -122,7 +122,7 @@ declare const VAULT_VERSIONS: VaultVersion[]; * Complete database schema SQL (latest version) * Auto-generated from EF Core migrations */ -declare const COMPLETE_SCHEMA_SQL = "\n\uFEFFCREATE TABLE IF NOT EXISTS \"__EFMigrationsHistory\" (\n \"MigrationId\" TEXT NOT NULL CONSTRAINT \"PK___EFMigrationsHistory\" PRIMARY KEY,\n \"ProductVersion\" TEXT NOT NULL\n);\n\nBEGIN TRANSACTION;\nCREATE TABLE \"Aliases\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Aliases\" PRIMARY KEY,\n \"Gender\" VARCHAR NULL,\n \"FirstName\" VARCHAR NULL,\n \"LastName\" VARCHAR NULL,\n \"NickName\" VARCHAR NULL,\n \"BirthDate\" TEXT NOT NULL,\n \"AddressStreet\" VARCHAR NULL,\n \"AddressCity\" VARCHAR NULL,\n \"AddressState\" VARCHAR NULL,\n \"AddressZipCode\" VARCHAR NULL,\n \"AddressCountry\" VARCHAR NULL,\n \"Hobbies\" TEXT NULL,\n \"EmailPrefix\" TEXT NULL,\n \"PhoneMobile\" TEXT NULL,\n \"BankAccountIBAN\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nCREATE TABLE \"Services\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Services\" PRIMARY KEY,\n \"Name\" TEXT NULL,\n \"Url\" TEXT NULL,\n \"Logo\" BLOB NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nCREATE TABLE \"Credentials\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Credentials\" PRIMARY KEY,\n \"AliasId\" TEXT NOT NULL,\n \"Notes\" TEXT NULL,\n \"Username\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"ServiceId\" TEXT NOT NULL,\n CONSTRAINT \"FK_Credentials_Aliases_AliasId\" FOREIGN KEY (\"AliasId\") REFERENCES \"Aliases\" (\"Id\") ON DELETE CASCADE,\n CONSTRAINT \"FK_Credentials_Services_ServiceId\" FOREIGN KEY (\"ServiceId\") REFERENCES \"Services\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"Attachment\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Attachment\" PRIMARY KEY,\n \"Filename\" TEXT NOT NULL,\n \"Blob\" BLOB NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n CONSTRAINT \"FK_Attachment_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"Passwords\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Passwords\" PRIMARY KEY,\n \"Value\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n CONSTRAINT \"FK_Passwords_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE INDEX \"IX_Attachment_CredentialId\" ON \"Attachment\" (\"CredentialId\");\n\nCREATE INDEX \"IX_Credentials_AliasId\" ON \"Credentials\" (\"AliasId\");\n\nCREATE INDEX \"IX_Credentials_ServiceId\" ON \"Credentials\" (\"ServiceId\");\n\nCREATE INDEX \"IX_Passwords_CredentialId\" ON \"Passwords\" (\"CredentialId\");\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240708094944_1.0.0-InitialMigration', '9.0.4');\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240708224522_1.0.1-EmptyTestMigration', '9.0.4');\n\nALTER TABLE \"Aliases\" RENAME COLUMN \"EmailPrefix\" TO \"Email\";\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240711204207_1.0.2-ChangeEmailColumn', '9.0.4');\n\nCREATE TABLE \"EncryptionKeys\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_EncryptionKeys\" PRIMARY KEY,\n \"PublicKey\" TEXT NOT NULL,\n \"PrivateKey\" TEXT NOT NULL,\n \"IsPrimary\" INTEGER NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240729105618_1.1.0-AddPkiTables', '9.0.4');\n\nCREATE TABLE \"Settings\" (\n \"Key\" TEXT NOT NULL CONSTRAINT \"PK_Settings\" PRIMARY KEY,\n \"Value\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240805073413_1.2.0-AddSettingsTable', '9.0.4');\n\nCREATE TABLE \"ef_temp_Aliases\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Aliases\" PRIMARY KEY,\n \"BirthDate\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"Email\" TEXT NULL,\n \"FirstName\" VARCHAR NULL,\n \"Gender\" VARCHAR NULL,\n \"LastName\" VARCHAR NULL,\n \"NickName\" VARCHAR NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nINSERT INTO \"ef_temp_Aliases\" (\"Id\", \"BirthDate\", \"CreatedAt\", \"Email\", \"FirstName\", \"Gender\", \"LastName\", \"NickName\", \"UpdatedAt\")\nSELECT \"Id\", \"BirthDate\", \"CreatedAt\", \"Email\", \"FirstName\", \"Gender\", \"LastName\", \"NickName\", \"UpdatedAt\"\nFROM \"Aliases\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 0;\n\nBEGIN TRANSACTION;\nDROP TABLE \"Aliases\";\n\nALTER TABLE \"ef_temp_Aliases\" RENAME TO \"Aliases\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 1;\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240805122422_1.3.0-UpdateIdentityStructure', '9.0.4');\n\nBEGIN TRANSACTION;\nCREATE TABLE \"ef_temp_Credentials\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Credentials\" PRIMARY KEY,\n \"AliasId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"Notes\" TEXT NULL,\n \"ServiceId\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"Username\" TEXT NULL,\n CONSTRAINT \"FK_Credentials_Aliases_AliasId\" FOREIGN KEY (\"AliasId\") REFERENCES \"Aliases\" (\"Id\") ON DELETE CASCADE,\n CONSTRAINT \"FK_Credentials_Services_ServiceId\" FOREIGN KEY (\"ServiceId\") REFERENCES \"Services\" (\"Id\") ON DELETE CASCADE\n);\n\nINSERT INTO \"ef_temp_Credentials\" (\"Id\", \"AliasId\", \"CreatedAt\", \"Notes\", \"ServiceId\", \"UpdatedAt\", \"Username\")\nSELECT \"Id\", \"AliasId\", \"CreatedAt\", \"Notes\", \"ServiceId\", \"UpdatedAt\", \"Username\"\nFROM \"Credentials\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 0;\n\nBEGIN TRANSACTION;\nDROP TABLE \"Credentials\";\n\nALTER TABLE \"ef_temp_Credentials\" RENAME TO \"Credentials\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 1;\n\nBEGIN TRANSACTION;\nCREATE INDEX \"IX_Credentials_AliasId\" ON \"Credentials\" (\"AliasId\");\n\nCREATE INDEX \"IX_Credentials_ServiceId\" ON \"Credentials\" (\"ServiceId\");\n\nCOMMIT;\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240812141727_1.3.1-MakeUsernameOptional', '9.0.4');\n\nBEGIN TRANSACTION;\nALTER TABLE \"Settings\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Services\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Passwords\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"EncryptionKeys\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Credentials\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Attachment\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Aliases\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240916105320_1.4.0-AddSyncSupport', '9.0.4');\n\nALTER TABLE \"Attachment\" RENAME TO \"Attachments\";\n\nCREATE TABLE \"ef_temp_Attachments\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Attachments\" PRIMARY KEY,\n \"Blob\" BLOB NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"Filename\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n CONSTRAINT \"FK_Attachments_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nINSERT INTO \"ef_temp_Attachments\" (\"Id\", \"Blob\", \"CreatedAt\", \"CredentialId\", \"Filename\", \"IsDeleted\", \"UpdatedAt\")\nSELECT \"Id\", \"Blob\", \"CreatedAt\", \"CredentialId\", \"Filename\", \"IsDeleted\", \"UpdatedAt\"\nFROM \"Attachments\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 0;\n\nBEGIN TRANSACTION;\nDROP TABLE \"Attachments\";\n\nALTER TABLE \"ef_temp_Attachments\" RENAME TO \"Attachments\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 1;\n\nBEGIN TRANSACTION;\nCREATE INDEX \"IX_Attachments_CredentialId\" ON \"Attachments\" (\"CredentialId\");\n\nCOMMIT;\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240917191243_1.4.1-RenameAttachmentsPlural', '9.0.4');\n\nBEGIN TRANSACTION;\nCREATE TABLE \"TotpCodes\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_TotpCodes\" PRIMARY KEY,\n \"Name\" TEXT NOT NULL,\n \"SecretKey\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL,\n CONSTRAINT \"FK_TotpCodes_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE INDEX \"IX_TotpCodes_CredentialId\" ON \"TotpCodes\" (\"CredentialId\");\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20250310131554_1.5.0-AddTotpCodes', '9.0.4');\n\n\nPRAGMA foreign_keys = OFF;\n\n-- Clean up any existing temp tables first\nDROP TABLE IF EXISTS \"__EFMigrationsHistory_temp\";\nDROP TABLE IF EXISTS \"Aliases_temp\";\nDROP TABLE IF EXISTS \"Services_temp\";\nDROP TABLE IF EXISTS \"EncryptionKeys_temp\";\nDROP TABLE IF EXISTS \"Settings_temp\";\nDROP TABLE IF EXISTS \"Credentials_temp\";\nDROP TABLE IF EXISTS \"Attachments_temp\";\nDROP TABLE IF EXISTS \"Passwords_temp\";\nDROP TABLE IF EXISTS \"TotpCodes_temp\";\n\n-- Create backup tables for all data\nCREATE TABLE \"__EFMigrationsHistory_temp\" AS SELECT * FROM \"__EFMigrationsHistory\";\nCREATE TABLE \"Aliases_temp\" AS SELECT * FROM \"Aliases\";\nCREATE TABLE \"Services_temp\" AS SELECT * FROM \"Services\";\nCREATE TABLE \"EncryptionKeys_temp\" AS SELECT * FROM \"EncryptionKeys\";\nCREATE TABLE \"Settings_temp\" AS SELECT * FROM \"Settings\";\nCREATE TABLE \"Credentials_temp\" AS SELECT * FROM \"Credentials\";\nCREATE TABLE \"Attachments_temp\" AS SELECT * FROM \"Attachments\";\nCREATE TABLE \"Passwords_temp\" AS SELECT * FROM \"Passwords\";\nCREATE TABLE \"TotpCodes_temp\" AS SELECT * FROM \"TotpCodes\";\n\n-- Delete orphaned records that do not have a valid FK to the credential object\nDELETE FROM \"Attachments_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\nDELETE FROM \"Passwords_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\nDELETE FROM \"TotpCodes_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\n\n-- Delete orphaned credentials that do not have valid FKs to alias or service objects\nDELETE FROM \"Credentials_temp\" WHERE \"AliasId\" NOT IN (SELECT \"Id\" FROM \"Aliases_temp\");\nDELETE FROM \"Credentials_temp\" WHERE \"ServiceId\" NOT IN (SELECT \"Id\" FROM \"Services_temp\");\n\n-- After cleaning credentials, clean dependent tables again in case we removed credentials\nDELETE FROM \"Attachments_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\nDELETE FROM \"Passwords_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\nDELETE FROM \"TotpCodes_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\n\n-- Drop all existing tables\nDROP TABLE \"TotpCodes\";\nDROP TABLE \"Passwords\";\nDROP TABLE \"Attachments\";\nDROP TABLE \"Credentials\";\nDROP TABLE \"Settings\";\nDROP TABLE \"EncryptionKeys\";\nDROP TABLE \"Services\";\nDROP TABLE \"Aliases\";\nDROP TABLE \"__EFMigrationsHistory\";\n\n-- Recreate tables with proper constraints (no dependencies first)\nCREATE TABLE \"__EFMigrationsHistory\" (\n \"MigrationId\" TEXT NOT NULL CONSTRAINT \"PK___EFMigrationsHistory\" PRIMARY KEY,\n \"ProductVersion\" TEXT NOT NULL\n);\n\nCREATE TABLE \"Aliases\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Aliases\" PRIMARY KEY,\n \"BirthDate\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"Email\" TEXT NULL,\n \"FirstName\" VARCHAR NULL,\n \"Gender\" VARCHAR NULL,\n \"LastName\" VARCHAR NULL,\n \"NickName\" VARCHAR NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0\n);\n\nCREATE TABLE \"Services\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Services\" PRIMARY KEY,\n \"Name\" TEXT NULL,\n \"Url\" TEXT NULL,\n \"Logo\" BLOB NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0\n);\n\nCREATE TABLE \"EncryptionKeys\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_EncryptionKeys\" PRIMARY KEY,\n \"PublicKey\" TEXT NOT NULL,\n \"PrivateKey\" TEXT NOT NULL,\n \"IsPrimary\" INTEGER NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0\n);\n\nCREATE TABLE \"Settings\" (\n \"Key\" TEXT NOT NULL CONSTRAINT \"PK_Settings\" PRIMARY KEY,\n \"Value\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0\n);\n\n-- Tables with foreign keys\nCREATE TABLE \"Credentials\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Credentials\" PRIMARY KEY,\n \"AliasId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"Notes\" TEXT NULL,\n \"ServiceId\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"Username\" TEXT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0,\n CONSTRAINT \"FK_Credentials_Aliases_AliasId\" FOREIGN KEY (\"AliasId\") REFERENCES \"Aliases\" (\"Id\") ON DELETE CASCADE,\n CONSTRAINT \"FK_Credentials_Services_ServiceId\" FOREIGN KEY (\"ServiceId\") REFERENCES \"Services\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"Attachments\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Attachments\" PRIMARY KEY,\n \"Blob\" BLOB NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"Filename\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0,\n \"UpdatedAt\" TEXT NOT NULL,\n CONSTRAINT \"FK_Attachments_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"Passwords\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Passwords\" PRIMARY KEY,\n \"Value\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0,\n CONSTRAINT \"FK_Passwords_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"TotpCodes\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_TotpCodes\" PRIMARY KEY,\n \"Name\" TEXT NOT NULL,\n \"SecretKey\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0,\n CONSTRAINT \"FK_TotpCodes_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\n\n-- Restore data from temp tables\nINSERT INTO \"__EFMigrationsHistory\" SELECT * FROM \"__EFMigrationsHistory_temp\";\nINSERT INTO \"Aliases\" SELECT * FROM \"Aliases_temp\";\nINSERT INTO \"Services\" SELECT * FROM \"Services_temp\";\nINSERT INTO \"EncryptionKeys\" SELECT * FROM \"EncryptionKeys_temp\";\nINSERT INTO \"Settings\" SELECT * FROM \"Settings_temp\";\nINSERT INTO \"Credentials\" SELECT * FROM \"Credentials_temp\";\nINSERT INTO \"Attachments\" SELECT * FROM \"Attachments_temp\";\nINSERT INTO \"Passwords\" SELECT * FROM \"Passwords_temp\";\nINSERT INTO \"TotpCodes\" SELECT * FROM \"TotpCodes_temp\";\n\n-- Recreate indexes\nCREATE INDEX \"IX_Credentials_AliasId\" ON \"Credentials\" (\"AliasId\");\nCREATE INDEX \"IX_Credentials_ServiceId\" ON \"Credentials\" (\"ServiceId\");\nCREATE INDEX \"IX_Attachments_CredentialId\" ON \"Attachments\" (\"CredentialId\");\nCREATE INDEX \"IX_Passwords_CredentialId\" ON \"Passwords\" (\"CredentialId\");\nCREATE INDEX \"IX_TotpCodes_CredentialId\" ON \"TotpCodes\" (\"CredentialId\");\n\n-- Clean up temp tables\nDROP TABLE \"__EFMigrationsHistory_temp\";\nDROP TABLE \"Aliases_temp\";\nDROP TABLE \"Services_temp\";\nDROP TABLE \"EncryptionKeys_temp\";\nDROP TABLE \"Settings_temp\";\nDROP TABLE \"Credentials_temp\";\nDROP TABLE \"Attachments_temp\";\nDROP TABLE \"Passwords_temp\";\nDROP TABLE \"TotpCodes_temp\";\n\nPRAGMA foreign_keys = ON;\n\n\nCREATE TABLE \"Passkeys\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Passkeys\" PRIMARY KEY,\n \"RpId\" TEXT COLLATE NOCASE NOT NULL,\n \"UserId\" TEXT NULL,\n \"PublicKey\" TEXT NOT NULL,\n \"PrivateKey\" TEXT NOT NULL,\n \"PrfKey\" BLOB NULL,\n \"DisplayName\" TEXT NOT NULL,\n \"AdditionalData\" BLOB NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL,\n CONSTRAINT \"FK_Passkeys_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE INDEX \"IX_Passkeys_CredentialId\" ON \"Passkeys\" (\"CredentialId\");\n\nCREATE INDEX \"IX_Passkeys_RpId\" ON \"Passkeys\" (\"RpId\");\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20251007085746_1.6.0-AddPasskeys', '9.0.4');\n\nCOMMIT;\n"; +declare const COMPLETE_SCHEMA_SQL = "\n\uFEFFCREATE TABLE IF NOT EXISTS \"__EFMigrationsHistory\" (\n \"MigrationId\" TEXT NOT NULL CONSTRAINT \"PK___EFMigrationsHistory\" PRIMARY KEY,\n \"ProductVersion\" TEXT NOT NULL\n);\n\nBEGIN TRANSACTION;\nCREATE TABLE \"Aliases\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Aliases\" PRIMARY KEY,\n \"Gender\" VARCHAR NULL,\n \"FirstName\" VARCHAR NULL,\n \"LastName\" VARCHAR NULL,\n \"NickName\" VARCHAR NULL,\n \"BirthDate\" TEXT NOT NULL,\n \"AddressStreet\" VARCHAR NULL,\n \"AddressCity\" VARCHAR NULL,\n \"AddressState\" VARCHAR NULL,\n \"AddressZipCode\" VARCHAR NULL,\n \"AddressCountry\" VARCHAR NULL,\n \"Hobbies\" TEXT NULL,\n \"EmailPrefix\" TEXT NULL,\n \"PhoneMobile\" TEXT NULL,\n \"BankAccountIBAN\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nCREATE TABLE \"Services\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Services\" PRIMARY KEY,\n \"Name\" TEXT NULL,\n \"Url\" TEXT NULL,\n \"Logo\" BLOB NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nCREATE TABLE \"Credentials\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Credentials\" PRIMARY KEY,\n \"AliasId\" TEXT NOT NULL,\n \"Notes\" TEXT NULL,\n \"Username\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"ServiceId\" TEXT NOT NULL,\n CONSTRAINT \"FK_Credentials_Aliases_AliasId\" FOREIGN KEY (\"AliasId\") REFERENCES \"Aliases\" (\"Id\") ON DELETE CASCADE,\n CONSTRAINT \"FK_Credentials_Services_ServiceId\" FOREIGN KEY (\"ServiceId\") REFERENCES \"Services\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"Attachment\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Attachment\" PRIMARY KEY,\n \"Filename\" TEXT NOT NULL,\n \"Blob\" BLOB NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n CONSTRAINT \"FK_Attachment_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"Passwords\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Passwords\" PRIMARY KEY,\n \"Value\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n CONSTRAINT \"FK_Passwords_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE INDEX \"IX_Attachment_CredentialId\" ON \"Attachment\" (\"CredentialId\");\n\nCREATE INDEX \"IX_Credentials_AliasId\" ON \"Credentials\" (\"AliasId\");\n\nCREATE INDEX \"IX_Credentials_ServiceId\" ON \"Credentials\" (\"ServiceId\");\n\nCREATE INDEX \"IX_Passwords_CredentialId\" ON \"Passwords\" (\"CredentialId\");\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240708094944_1.0.0-InitialMigration', '9.0.4');\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240708224522_1.0.1-EmptyTestMigration', '9.0.4');\n\nALTER TABLE \"Aliases\" RENAME COLUMN \"EmailPrefix\" TO \"Email\";\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240711204207_1.0.2-ChangeEmailColumn', '9.0.4');\n\nCREATE TABLE \"EncryptionKeys\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_EncryptionKeys\" PRIMARY KEY,\n \"PublicKey\" TEXT NOT NULL,\n \"PrivateKey\" TEXT NOT NULL,\n \"IsPrimary\" INTEGER NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240729105618_1.1.0-AddPkiTables', '9.0.4');\n\nCREATE TABLE \"Settings\" (\n \"Key\" TEXT NOT NULL CONSTRAINT \"PK_Settings\" PRIMARY KEY,\n \"Value\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240805073413_1.2.0-AddSettingsTable', '9.0.4');\n\nCREATE TABLE \"ef_temp_Aliases\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Aliases\" PRIMARY KEY,\n \"BirthDate\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"Email\" TEXT NULL,\n \"FirstName\" VARCHAR NULL,\n \"Gender\" VARCHAR NULL,\n \"LastName\" VARCHAR NULL,\n \"NickName\" VARCHAR NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nINSERT INTO \"ef_temp_Aliases\" (\"Id\", \"BirthDate\", \"CreatedAt\", \"Email\", \"FirstName\", \"Gender\", \"LastName\", \"NickName\", \"UpdatedAt\")\nSELECT \"Id\", \"BirthDate\", \"CreatedAt\", \"Email\", \"FirstName\", \"Gender\", \"LastName\", \"NickName\", \"UpdatedAt\"\nFROM \"Aliases\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 0;\n\nBEGIN TRANSACTION;\nDROP TABLE \"Aliases\";\n\nALTER TABLE \"ef_temp_Aliases\" RENAME TO \"Aliases\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 1;\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240805122422_1.3.0-UpdateIdentityStructure', '9.0.4');\n\nBEGIN TRANSACTION;\nCREATE TABLE \"ef_temp_Credentials\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Credentials\" PRIMARY KEY,\n \"AliasId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"Notes\" TEXT NULL,\n \"ServiceId\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"Username\" TEXT NULL,\n CONSTRAINT \"FK_Credentials_Aliases_AliasId\" FOREIGN KEY (\"AliasId\") REFERENCES \"Aliases\" (\"Id\") ON DELETE CASCADE,\n CONSTRAINT \"FK_Credentials_Services_ServiceId\" FOREIGN KEY (\"ServiceId\") REFERENCES \"Services\" (\"Id\") ON DELETE CASCADE\n);\n\nINSERT INTO \"ef_temp_Credentials\" (\"Id\", \"AliasId\", \"CreatedAt\", \"Notes\", \"ServiceId\", \"UpdatedAt\", \"Username\")\nSELECT \"Id\", \"AliasId\", \"CreatedAt\", \"Notes\", \"ServiceId\", \"UpdatedAt\", \"Username\"\nFROM \"Credentials\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 0;\n\nBEGIN TRANSACTION;\nDROP TABLE \"Credentials\";\n\nALTER TABLE \"ef_temp_Credentials\" RENAME TO \"Credentials\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 1;\n\nBEGIN TRANSACTION;\nCREATE INDEX \"IX_Credentials_AliasId\" ON \"Credentials\" (\"AliasId\");\n\nCREATE INDEX \"IX_Credentials_ServiceId\" ON \"Credentials\" (\"ServiceId\");\n\nCOMMIT;\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240812141727_1.3.1-MakeUsernameOptional', '9.0.4');\n\nBEGIN TRANSACTION;\nALTER TABLE \"Settings\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Services\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Passwords\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"EncryptionKeys\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Credentials\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Attachment\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Aliases\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240916105320_1.4.0-AddSyncSupport', '9.0.4');\n\nALTER TABLE \"Attachment\" RENAME TO \"Attachments\";\n\nCREATE TABLE \"ef_temp_Attachments\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Attachments\" PRIMARY KEY,\n \"Blob\" BLOB NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"Filename\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n CONSTRAINT \"FK_Attachments_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nINSERT INTO \"ef_temp_Attachments\" (\"Id\", \"Blob\", \"CreatedAt\", \"CredentialId\", \"Filename\", \"IsDeleted\", \"UpdatedAt\")\nSELECT \"Id\", \"Blob\", \"CreatedAt\", \"CredentialId\", \"Filename\", \"IsDeleted\", \"UpdatedAt\"\nFROM \"Attachments\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 0;\n\nBEGIN TRANSACTION;\nDROP TABLE \"Attachments\";\n\nALTER TABLE \"ef_temp_Attachments\" RENAME TO \"Attachments\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 1;\n\nBEGIN TRANSACTION;\nCREATE INDEX \"IX_Attachments_CredentialId\" ON \"Attachments\" (\"CredentialId\");\n\nCOMMIT;\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240917191243_1.4.1-RenameAttachmentsPlural', '9.0.4');\n\nBEGIN TRANSACTION;\nCREATE TABLE \"TotpCodes\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_TotpCodes\" PRIMARY KEY,\n \"Name\" TEXT NOT NULL,\n \"SecretKey\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL,\n CONSTRAINT \"FK_TotpCodes_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE INDEX \"IX_TotpCodes_CredentialId\" ON \"TotpCodes\" (\"CredentialId\");\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20250310131554_1.5.0-AddTotpCodes', '9.0.4');\n\n\nPRAGMA foreign_keys = OFF;\n\n-- Clean up any existing temp tables first\nDROP TABLE IF EXISTS \"__EFMigrationsHistory_temp\";\nDROP TABLE IF EXISTS \"Aliases_temp\";\nDROP TABLE IF EXISTS \"Services_temp\";\nDROP TABLE IF EXISTS \"EncryptionKeys_temp\";\nDROP TABLE IF EXISTS \"Settings_temp\";\nDROP TABLE IF EXISTS \"Credentials_temp\";\nDROP TABLE IF EXISTS \"Attachments_temp\";\nDROP TABLE IF EXISTS \"Passwords_temp\";\nDROP TABLE IF EXISTS \"TotpCodes_temp\";\n\n-- Create backup tables for all data\nCREATE TABLE \"__EFMigrationsHistory_temp\" AS SELECT * FROM \"__EFMigrationsHistory\";\nCREATE TABLE \"Aliases_temp\" AS SELECT * FROM \"Aliases\";\nCREATE TABLE \"Services_temp\" AS SELECT * FROM \"Services\";\nCREATE TABLE \"EncryptionKeys_temp\" AS SELECT * FROM \"EncryptionKeys\";\nCREATE TABLE \"Settings_temp\" AS SELECT * FROM \"Settings\";\nCREATE TABLE \"Credentials_temp\" AS SELECT * FROM \"Credentials\";\nCREATE TABLE \"Attachments_temp\" AS SELECT * FROM \"Attachments\";\nCREATE TABLE \"Passwords_temp\" AS SELECT * FROM \"Passwords\";\nCREATE TABLE \"TotpCodes_temp\" AS SELECT * FROM \"TotpCodes\";\n\n-- Delete orphaned records that do not have a valid FK to the credential object\nDELETE FROM \"Attachments_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\nDELETE FROM \"Passwords_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\nDELETE FROM \"TotpCodes_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\n\n-- Delete orphaned credentials that do not have valid FKs to alias or service objects\nDELETE FROM \"Credentials_temp\" WHERE \"AliasId\" NOT IN (SELECT \"Id\" FROM \"Aliases_temp\");\nDELETE FROM \"Credentials_temp\" WHERE \"ServiceId\" NOT IN (SELECT \"Id\" FROM \"Services_temp\");\n\n-- After cleaning credentials, clean dependent tables again in case we removed credentials\nDELETE FROM \"Attachments_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\nDELETE FROM \"Passwords_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\nDELETE FROM \"TotpCodes_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\n\n-- Drop all existing tables\nDROP TABLE \"TotpCodes\";\nDROP TABLE \"Passwords\";\nDROP TABLE \"Attachments\";\nDROP TABLE \"Credentials\";\nDROP TABLE \"Settings\";\nDROP TABLE \"EncryptionKeys\";\nDROP TABLE \"Services\";\nDROP TABLE \"Aliases\";\nDROP TABLE \"__EFMigrationsHistory\";\n\n-- Recreate tables with proper constraints (no dependencies first)\nCREATE TABLE \"__EFMigrationsHistory\" (\n \"MigrationId\" TEXT NOT NULL CONSTRAINT \"PK___EFMigrationsHistory\" PRIMARY KEY,\n \"ProductVersion\" TEXT NOT NULL\n);\n\nCREATE TABLE \"Aliases\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Aliases\" PRIMARY KEY,\n \"BirthDate\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"Email\" TEXT NULL,\n \"FirstName\" VARCHAR NULL,\n \"Gender\" VARCHAR NULL,\n \"LastName\" VARCHAR NULL,\n \"NickName\" VARCHAR NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0\n);\n\nCREATE TABLE \"Services\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Services\" PRIMARY KEY,\n \"Name\" TEXT NULL,\n \"Url\" TEXT NULL,\n \"Logo\" BLOB NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0\n);\n\nCREATE TABLE \"EncryptionKeys\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_EncryptionKeys\" PRIMARY KEY,\n \"PublicKey\" TEXT NOT NULL,\n \"PrivateKey\" TEXT NOT NULL,\n \"IsPrimary\" INTEGER NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0\n);\n\nCREATE TABLE \"Settings\" (\n \"Key\" TEXT NOT NULL CONSTRAINT \"PK_Settings\" PRIMARY KEY,\n \"Value\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0\n);\n\n-- Tables with foreign keys\nCREATE TABLE \"Credentials\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Credentials\" PRIMARY KEY,\n \"AliasId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"Notes\" TEXT NULL,\n \"ServiceId\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"Username\" TEXT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0,\n CONSTRAINT \"FK_Credentials_Aliases_AliasId\" FOREIGN KEY (\"AliasId\") REFERENCES \"Aliases\" (\"Id\") ON DELETE CASCADE,\n CONSTRAINT \"FK_Credentials_Services_ServiceId\" FOREIGN KEY (\"ServiceId\") REFERENCES \"Services\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"Attachments\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Attachments\" PRIMARY KEY,\n \"Blob\" BLOB NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"Filename\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0,\n \"UpdatedAt\" TEXT NOT NULL,\n CONSTRAINT \"FK_Attachments_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"Passwords\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Passwords\" PRIMARY KEY,\n \"Value\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0,\n CONSTRAINT \"FK_Passwords_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"TotpCodes\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_TotpCodes\" PRIMARY KEY,\n \"Name\" TEXT NOT NULL,\n \"SecretKey\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0,\n CONSTRAINT \"FK_TotpCodes_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\n\n-- Restore data from temp tables\nINSERT INTO \"__EFMigrationsHistory\" SELECT * FROM \"__EFMigrationsHistory_temp\";\nINSERT INTO \"Aliases\" SELECT * FROM \"Aliases_temp\";\nINSERT INTO \"Services\" SELECT * FROM \"Services_temp\";\nINSERT INTO \"EncryptionKeys\" SELECT * FROM \"EncryptionKeys_temp\";\nINSERT INTO \"Settings\" SELECT * FROM \"Settings_temp\";\nINSERT INTO \"Credentials\" SELECT * FROM \"Credentials_temp\";\nINSERT INTO \"Attachments\" SELECT * FROM \"Attachments_temp\";\nINSERT INTO \"Passwords\" SELECT * FROM \"Passwords_temp\";\nINSERT INTO \"TotpCodes\" SELECT * FROM \"TotpCodes_temp\";\n\n-- Recreate indexes\nCREATE INDEX \"IX_Credentials_AliasId\" ON \"Credentials\" (\"AliasId\");\nCREATE INDEX \"IX_Credentials_ServiceId\" ON \"Credentials\" (\"ServiceId\");\nCREATE INDEX \"IX_Attachments_CredentialId\" ON \"Attachments\" (\"CredentialId\");\nCREATE INDEX \"IX_Passwords_CredentialId\" ON \"Passwords\" (\"CredentialId\");\nCREATE INDEX \"IX_TotpCodes_CredentialId\" ON \"TotpCodes\" (\"CredentialId\");\n\n-- Clean up temp tables\nDROP TABLE \"__EFMigrationsHistory_temp\";\nDROP TABLE \"Aliases_temp\";\nDROP TABLE \"Services_temp\";\nDROP TABLE \"EncryptionKeys_temp\";\nDROP TABLE \"Settings_temp\";\nDROP TABLE \"Credentials_temp\";\nDROP TABLE \"Attachments_temp\";\nDROP TABLE \"Passwords_temp\";\nDROP TABLE \"TotpCodes_temp\";\n\nPRAGMA foreign_keys = ON;\n\n\nCREATE TABLE \"Passkeys\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Passkeys\" PRIMARY KEY,\n \"RpId\" TEXT COLLATE NOCASE NOT NULL,\n \"UserHandle\" BLOB NOT NULL,\n \"PublicKey\" TEXT NOT NULL,\n \"PrivateKey\" TEXT NOT NULL,\n \"PrfKey\" BLOB NULL,\n \"DisplayName\" TEXT NOT NULL,\n \"AdditionalData\" BLOB NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL,\n CONSTRAINT \"FK_Passkeys_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE INDEX \"IX_Passkeys_CredentialId\" ON \"Passkeys\" (\"CredentialId\");\n\nCREATE INDEX \"IX_Passkeys_RpId\" ON \"Passkeys\" (\"RpId\");\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20251014122838_1.6.0-AddPasskeys', '9.0.4');\n\nCOMMIT;\n"; /** * Individual migration SQL scripts * Auto-generated from EF Core migrations diff --git a/apps/mobile-app/utils/dist/shared/vault-sql/index.d.ts b/apps/mobile-app/utils/dist/shared/vault-sql/index.d.ts index ea25cb473..871c1b2f1 100644 --- a/apps/mobile-app/utils/dist/shared/vault-sql/index.d.ts +++ b/apps/mobile-app/utils/dist/shared/vault-sql/index.d.ts @@ -122,7 +122,7 @@ declare const VAULT_VERSIONS: VaultVersion[]; * Complete database schema SQL (latest version) * Auto-generated from EF Core migrations */ -declare const COMPLETE_SCHEMA_SQL = "\n\uFEFFCREATE TABLE IF NOT EXISTS \"__EFMigrationsHistory\" (\n \"MigrationId\" TEXT NOT NULL CONSTRAINT \"PK___EFMigrationsHistory\" PRIMARY KEY,\n \"ProductVersion\" TEXT NOT NULL\n);\n\nBEGIN TRANSACTION;\nCREATE TABLE \"Aliases\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Aliases\" PRIMARY KEY,\n \"Gender\" VARCHAR NULL,\n \"FirstName\" VARCHAR NULL,\n \"LastName\" VARCHAR NULL,\n \"NickName\" VARCHAR NULL,\n \"BirthDate\" TEXT NOT NULL,\n \"AddressStreet\" VARCHAR NULL,\n \"AddressCity\" VARCHAR NULL,\n \"AddressState\" VARCHAR NULL,\n \"AddressZipCode\" VARCHAR NULL,\n \"AddressCountry\" VARCHAR NULL,\n \"Hobbies\" TEXT NULL,\n \"EmailPrefix\" TEXT NULL,\n \"PhoneMobile\" TEXT NULL,\n \"BankAccountIBAN\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nCREATE TABLE \"Services\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Services\" PRIMARY KEY,\n \"Name\" TEXT NULL,\n \"Url\" TEXT NULL,\n \"Logo\" BLOB NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nCREATE TABLE \"Credentials\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Credentials\" PRIMARY KEY,\n \"AliasId\" TEXT NOT NULL,\n \"Notes\" TEXT NULL,\n \"Username\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"ServiceId\" TEXT NOT NULL,\n CONSTRAINT \"FK_Credentials_Aliases_AliasId\" FOREIGN KEY (\"AliasId\") REFERENCES \"Aliases\" (\"Id\") ON DELETE CASCADE,\n CONSTRAINT \"FK_Credentials_Services_ServiceId\" FOREIGN KEY (\"ServiceId\") REFERENCES \"Services\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"Attachment\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Attachment\" PRIMARY KEY,\n \"Filename\" TEXT NOT NULL,\n \"Blob\" BLOB NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n CONSTRAINT \"FK_Attachment_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"Passwords\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Passwords\" PRIMARY KEY,\n \"Value\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n CONSTRAINT \"FK_Passwords_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE INDEX \"IX_Attachment_CredentialId\" ON \"Attachment\" (\"CredentialId\");\n\nCREATE INDEX \"IX_Credentials_AliasId\" ON \"Credentials\" (\"AliasId\");\n\nCREATE INDEX \"IX_Credentials_ServiceId\" ON \"Credentials\" (\"ServiceId\");\n\nCREATE INDEX \"IX_Passwords_CredentialId\" ON \"Passwords\" (\"CredentialId\");\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240708094944_1.0.0-InitialMigration', '9.0.4');\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240708224522_1.0.1-EmptyTestMigration', '9.0.4');\n\nALTER TABLE \"Aliases\" RENAME COLUMN \"EmailPrefix\" TO \"Email\";\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240711204207_1.0.2-ChangeEmailColumn', '9.0.4');\n\nCREATE TABLE \"EncryptionKeys\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_EncryptionKeys\" PRIMARY KEY,\n \"PublicKey\" TEXT NOT NULL,\n \"PrivateKey\" TEXT NOT NULL,\n \"IsPrimary\" INTEGER NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240729105618_1.1.0-AddPkiTables', '9.0.4');\n\nCREATE TABLE \"Settings\" (\n \"Key\" TEXT NOT NULL CONSTRAINT \"PK_Settings\" PRIMARY KEY,\n \"Value\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240805073413_1.2.0-AddSettingsTable', '9.0.4');\n\nCREATE TABLE \"ef_temp_Aliases\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Aliases\" PRIMARY KEY,\n \"BirthDate\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"Email\" TEXT NULL,\n \"FirstName\" VARCHAR NULL,\n \"Gender\" VARCHAR NULL,\n \"LastName\" VARCHAR NULL,\n \"NickName\" VARCHAR NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nINSERT INTO \"ef_temp_Aliases\" (\"Id\", \"BirthDate\", \"CreatedAt\", \"Email\", \"FirstName\", \"Gender\", \"LastName\", \"NickName\", \"UpdatedAt\")\nSELECT \"Id\", \"BirthDate\", \"CreatedAt\", \"Email\", \"FirstName\", \"Gender\", \"LastName\", \"NickName\", \"UpdatedAt\"\nFROM \"Aliases\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 0;\n\nBEGIN TRANSACTION;\nDROP TABLE \"Aliases\";\n\nALTER TABLE \"ef_temp_Aliases\" RENAME TO \"Aliases\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 1;\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240805122422_1.3.0-UpdateIdentityStructure', '9.0.4');\n\nBEGIN TRANSACTION;\nCREATE TABLE \"ef_temp_Credentials\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Credentials\" PRIMARY KEY,\n \"AliasId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"Notes\" TEXT NULL,\n \"ServiceId\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"Username\" TEXT NULL,\n CONSTRAINT \"FK_Credentials_Aliases_AliasId\" FOREIGN KEY (\"AliasId\") REFERENCES \"Aliases\" (\"Id\") ON DELETE CASCADE,\n CONSTRAINT \"FK_Credentials_Services_ServiceId\" FOREIGN KEY (\"ServiceId\") REFERENCES \"Services\" (\"Id\") ON DELETE CASCADE\n);\n\nINSERT INTO \"ef_temp_Credentials\" (\"Id\", \"AliasId\", \"CreatedAt\", \"Notes\", \"ServiceId\", \"UpdatedAt\", \"Username\")\nSELECT \"Id\", \"AliasId\", \"CreatedAt\", \"Notes\", \"ServiceId\", \"UpdatedAt\", \"Username\"\nFROM \"Credentials\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 0;\n\nBEGIN TRANSACTION;\nDROP TABLE \"Credentials\";\n\nALTER TABLE \"ef_temp_Credentials\" RENAME TO \"Credentials\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 1;\n\nBEGIN TRANSACTION;\nCREATE INDEX \"IX_Credentials_AliasId\" ON \"Credentials\" (\"AliasId\");\n\nCREATE INDEX \"IX_Credentials_ServiceId\" ON \"Credentials\" (\"ServiceId\");\n\nCOMMIT;\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240812141727_1.3.1-MakeUsernameOptional', '9.0.4');\n\nBEGIN TRANSACTION;\nALTER TABLE \"Settings\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Services\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Passwords\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"EncryptionKeys\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Credentials\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Attachment\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Aliases\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240916105320_1.4.0-AddSyncSupport', '9.0.4');\n\nALTER TABLE \"Attachment\" RENAME TO \"Attachments\";\n\nCREATE TABLE \"ef_temp_Attachments\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Attachments\" PRIMARY KEY,\n \"Blob\" BLOB NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"Filename\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n CONSTRAINT \"FK_Attachments_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nINSERT INTO \"ef_temp_Attachments\" (\"Id\", \"Blob\", \"CreatedAt\", \"CredentialId\", \"Filename\", \"IsDeleted\", \"UpdatedAt\")\nSELECT \"Id\", \"Blob\", \"CreatedAt\", \"CredentialId\", \"Filename\", \"IsDeleted\", \"UpdatedAt\"\nFROM \"Attachments\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 0;\n\nBEGIN TRANSACTION;\nDROP TABLE \"Attachments\";\n\nALTER TABLE \"ef_temp_Attachments\" RENAME TO \"Attachments\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 1;\n\nBEGIN TRANSACTION;\nCREATE INDEX \"IX_Attachments_CredentialId\" ON \"Attachments\" (\"CredentialId\");\n\nCOMMIT;\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240917191243_1.4.1-RenameAttachmentsPlural', '9.0.4');\n\nBEGIN TRANSACTION;\nCREATE TABLE \"TotpCodes\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_TotpCodes\" PRIMARY KEY,\n \"Name\" TEXT NOT NULL,\n \"SecretKey\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL,\n CONSTRAINT \"FK_TotpCodes_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE INDEX \"IX_TotpCodes_CredentialId\" ON \"TotpCodes\" (\"CredentialId\");\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20250310131554_1.5.0-AddTotpCodes', '9.0.4');\n\n\nPRAGMA foreign_keys = OFF;\n\n-- Clean up any existing temp tables first\nDROP TABLE IF EXISTS \"__EFMigrationsHistory_temp\";\nDROP TABLE IF EXISTS \"Aliases_temp\";\nDROP TABLE IF EXISTS \"Services_temp\";\nDROP TABLE IF EXISTS \"EncryptionKeys_temp\";\nDROP TABLE IF EXISTS \"Settings_temp\";\nDROP TABLE IF EXISTS \"Credentials_temp\";\nDROP TABLE IF EXISTS \"Attachments_temp\";\nDROP TABLE IF EXISTS \"Passwords_temp\";\nDROP TABLE IF EXISTS \"TotpCodes_temp\";\n\n-- Create backup tables for all data\nCREATE TABLE \"__EFMigrationsHistory_temp\" AS SELECT * FROM \"__EFMigrationsHistory\";\nCREATE TABLE \"Aliases_temp\" AS SELECT * FROM \"Aliases\";\nCREATE TABLE \"Services_temp\" AS SELECT * FROM \"Services\";\nCREATE TABLE \"EncryptionKeys_temp\" AS SELECT * FROM \"EncryptionKeys\";\nCREATE TABLE \"Settings_temp\" AS SELECT * FROM \"Settings\";\nCREATE TABLE \"Credentials_temp\" AS SELECT * FROM \"Credentials\";\nCREATE TABLE \"Attachments_temp\" AS SELECT * FROM \"Attachments\";\nCREATE TABLE \"Passwords_temp\" AS SELECT * FROM \"Passwords\";\nCREATE TABLE \"TotpCodes_temp\" AS SELECT * FROM \"TotpCodes\";\n\n-- Delete orphaned records that do not have a valid FK to the credential object\nDELETE FROM \"Attachments_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\nDELETE FROM \"Passwords_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\nDELETE FROM \"TotpCodes_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\n\n-- Delete orphaned credentials that do not have valid FKs to alias or service objects\nDELETE FROM \"Credentials_temp\" WHERE \"AliasId\" NOT IN (SELECT \"Id\" FROM \"Aliases_temp\");\nDELETE FROM \"Credentials_temp\" WHERE \"ServiceId\" NOT IN (SELECT \"Id\" FROM \"Services_temp\");\n\n-- After cleaning credentials, clean dependent tables again in case we removed credentials\nDELETE FROM \"Attachments_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\nDELETE FROM \"Passwords_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\nDELETE FROM \"TotpCodes_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\n\n-- Drop all existing tables\nDROP TABLE \"TotpCodes\";\nDROP TABLE \"Passwords\";\nDROP TABLE \"Attachments\";\nDROP TABLE \"Credentials\";\nDROP TABLE \"Settings\";\nDROP TABLE \"EncryptionKeys\";\nDROP TABLE \"Services\";\nDROP TABLE \"Aliases\";\nDROP TABLE \"__EFMigrationsHistory\";\n\n-- Recreate tables with proper constraints (no dependencies first)\nCREATE TABLE \"__EFMigrationsHistory\" (\n \"MigrationId\" TEXT NOT NULL CONSTRAINT \"PK___EFMigrationsHistory\" PRIMARY KEY,\n \"ProductVersion\" TEXT NOT NULL\n);\n\nCREATE TABLE \"Aliases\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Aliases\" PRIMARY KEY,\n \"BirthDate\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"Email\" TEXT NULL,\n \"FirstName\" VARCHAR NULL,\n \"Gender\" VARCHAR NULL,\n \"LastName\" VARCHAR NULL,\n \"NickName\" VARCHAR NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0\n);\n\nCREATE TABLE \"Services\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Services\" PRIMARY KEY,\n \"Name\" TEXT NULL,\n \"Url\" TEXT NULL,\n \"Logo\" BLOB NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0\n);\n\nCREATE TABLE \"EncryptionKeys\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_EncryptionKeys\" PRIMARY KEY,\n \"PublicKey\" TEXT NOT NULL,\n \"PrivateKey\" TEXT NOT NULL,\n \"IsPrimary\" INTEGER NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0\n);\n\nCREATE TABLE \"Settings\" (\n \"Key\" TEXT NOT NULL CONSTRAINT \"PK_Settings\" PRIMARY KEY,\n \"Value\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0\n);\n\n-- Tables with foreign keys\nCREATE TABLE \"Credentials\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Credentials\" PRIMARY KEY,\n \"AliasId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"Notes\" TEXT NULL,\n \"ServiceId\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"Username\" TEXT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0,\n CONSTRAINT \"FK_Credentials_Aliases_AliasId\" FOREIGN KEY (\"AliasId\") REFERENCES \"Aliases\" (\"Id\") ON DELETE CASCADE,\n CONSTRAINT \"FK_Credentials_Services_ServiceId\" FOREIGN KEY (\"ServiceId\") REFERENCES \"Services\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"Attachments\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Attachments\" PRIMARY KEY,\n \"Blob\" BLOB NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"Filename\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0,\n \"UpdatedAt\" TEXT NOT NULL,\n CONSTRAINT \"FK_Attachments_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"Passwords\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Passwords\" PRIMARY KEY,\n \"Value\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0,\n CONSTRAINT \"FK_Passwords_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"TotpCodes\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_TotpCodes\" PRIMARY KEY,\n \"Name\" TEXT NOT NULL,\n \"SecretKey\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0,\n CONSTRAINT \"FK_TotpCodes_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\n\n-- Restore data from temp tables\nINSERT INTO \"__EFMigrationsHistory\" SELECT * FROM \"__EFMigrationsHistory_temp\";\nINSERT INTO \"Aliases\" SELECT * FROM \"Aliases_temp\";\nINSERT INTO \"Services\" SELECT * FROM \"Services_temp\";\nINSERT INTO \"EncryptionKeys\" SELECT * FROM \"EncryptionKeys_temp\";\nINSERT INTO \"Settings\" SELECT * FROM \"Settings_temp\";\nINSERT INTO \"Credentials\" SELECT * FROM \"Credentials_temp\";\nINSERT INTO \"Attachments\" SELECT * FROM \"Attachments_temp\";\nINSERT INTO \"Passwords\" SELECT * FROM \"Passwords_temp\";\nINSERT INTO \"TotpCodes\" SELECT * FROM \"TotpCodes_temp\";\n\n-- Recreate indexes\nCREATE INDEX \"IX_Credentials_AliasId\" ON \"Credentials\" (\"AliasId\");\nCREATE INDEX \"IX_Credentials_ServiceId\" ON \"Credentials\" (\"ServiceId\");\nCREATE INDEX \"IX_Attachments_CredentialId\" ON \"Attachments\" (\"CredentialId\");\nCREATE INDEX \"IX_Passwords_CredentialId\" ON \"Passwords\" (\"CredentialId\");\nCREATE INDEX \"IX_TotpCodes_CredentialId\" ON \"TotpCodes\" (\"CredentialId\");\n\n-- Clean up temp tables\nDROP TABLE \"__EFMigrationsHistory_temp\";\nDROP TABLE \"Aliases_temp\";\nDROP TABLE \"Services_temp\";\nDROP TABLE \"EncryptionKeys_temp\";\nDROP TABLE \"Settings_temp\";\nDROP TABLE \"Credentials_temp\";\nDROP TABLE \"Attachments_temp\";\nDROP TABLE \"Passwords_temp\";\nDROP TABLE \"TotpCodes_temp\";\n\nPRAGMA foreign_keys = ON;\n\n\nCREATE TABLE \"Passkeys\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Passkeys\" PRIMARY KEY,\n \"RpId\" TEXT COLLATE NOCASE NOT NULL,\n \"UserId\" TEXT NULL,\n \"PublicKey\" TEXT NOT NULL,\n \"PrivateKey\" TEXT NOT NULL,\n \"PrfKey\" BLOB NULL,\n \"DisplayName\" TEXT NOT NULL,\n \"AdditionalData\" BLOB NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL,\n CONSTRAINT \"FK_Passkeys_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE INDEX \"IX_Passkeys_CredentialId\" ON \"Passkeys\" (\"CredentialId\");\n\nCREATE INDEX \"IX_Passkeys_RpId\" ON \"Passkeys\" (\"RpId\");\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20251007085746_1.6.0-AddPasskeys', '9.0.4');\n\nCOMMIT;\n"; +declare const COMPLETE_SCHEMA_SQL = "\n\uFEFFCREATE TABLE IF NOT EXISTS \"__EFMigrationsHistory\" (\n \"MigrationId\" TEXT NOT NULL CONSTRAINT \"PK___EFMigrationsHistory\" PRIMARY KEY,\n \"ProductVersion\" TEXT NOT NULL\n);\n\nBEGIN TRANSACTION;\nCREATE TABLE \"Aliases\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Aliases\" PRIMARY KEY,\n \"Gender\" VARCHAR NULL,\n \"FirstName\" VARCHAR NULL,\n \"LastName\" VARCHAR NULL,\n \"NickName\" VARCHAR NULL,\n \"BirthDate\" TEXT NOT NULL,\n \"AddressStreet\" VARCHAR NULL,\n \"AddressCity\" VARCHAR NULL,\n \"AddressState\" VARCHAR NULL,\n \"AddressZipCode\" VARCHAR NULL,\n \"AddressCountry\" VARCHAR NULL,\n \"Hobbies\" TEXT NULL,\n \"EmailPrefix\" TEXT NULL,\n \"PhoneMobile\" TEXT NULL,\n \"BankAccountIBAN\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nCREATE TABLE \"Services\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Services\" PRIMARY KEY,\n \"Name\" TEXT NULL,\n \"Url\" TEXT NULL,\n \"Logo\" BLOB NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nCREATE TABLE \"Credentials\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Credentials\" PRIMARY KEY,\n \"AliasId\" TEXT NOT NULL,\n \"Notes\" TEXT NULL,\n \"Username\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"ServiceId\" TEXT NOT NULL,\n CONSTRAINT \"FK_Credentials_Aliases_AliasId\" FOREIGN KEY (\"AliasId\") REFERENCES \"Aliases\" (\"Id\") ON DELETE CASCADE,\n CONSTRAINT \"FK_Credentials_Services_ServiceId\" FOREIGN KEY (\"ServiceId\") REFERENCES \"Services\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"Attachment\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Attachment\" PRIMARY KEY,\n \"Filename\" TEXT NOT NULL,\n \"Blob\" BLOB NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n CONSTRAINT \"FK_Attachment_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"Passwords\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Passwords\" PRIMARY KEY,\n \"Value\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n CONSTRAINT \"FK_Passwords_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE INDEX \"IX_Attachment_CredentialId\" ON \"Attachment\" (\"CredentialId\");\n\nCREATE INDEX \"IX_Credentials_AliasId\" ON \"Credentials\" (\"AliasId\");\n\nCREATE INDEX \"IX_Credentials_ServiceId\" ON \"Credentials\" (\"ServiceId\");\n\nCREATE INDEX \"IX_Passwords_CredentialId\" ON \"Passwords\" (\"CredentialId\");\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240708094944_1.0.0-InitialMigration', '9.0.4');\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240708224522_1.0.1-EmptyTestMigration', '9.0.4');\n\nALTER TABLE \"Aliases\" RENAME COLUMN \"EmailPrefix\" TO \"Email\";\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240711204207_1.0.2-ChangeEmailColumn', '9.0.4');\n\nCREATE TABLE \"EncryptionKeys\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_EncryptionKeys\" PRIMARY KEY,\n \"PublicKey\" TEXT NOT NULL,\n \"PrivateKey\" TEXT NOT NULL,\n \"IsPrimary\" INTEGER NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240729105618_1.1.0-AddPkiTables', '9.0.4');\n\nCREATE TABLE \"Settings\" (\n \"Key\" TEXT NOT NULL CONSTRAINT \"PK_Settings\" PRIMARY KEY,\n \"Value\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240805073413_1.2.0-AddSettingsTable', '9.0.4');\n\nCREATE TABLE \"ef_temp_Aliases\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Aliases\" PRIMARY KEY,\n \"BirthDate\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"Email\" TEXT NULL,\n \"FirstName\" VARCHAR NULL,\n \"Gender\" VARCHAR NULL,\n \"LastName\" VARCHAR NULL,\n \"NickName\" VARCHAR NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nINSERT INTO \"ef_temp_Aliases\" (\"Id\", \"BirthDate\", \"CreatedAt\", \"Email\", \"FirstName\", \"Gender\", \"LastName\", \"NickName\", \"UpdatedAt\")\nSELECT \"Id\", \"BirthDate\", \"CreatedAt\", \"Email\", \"FirstName\", \"Gender\", \"LastName\", \"NickName\", \"UpdatedAt\"\nFROM \"Aliases\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 0;\n\nBEGIN TRANSACTION;\nDROP TABLE \"Aliases\";\n\nALTER TABLE \"ef_temp_Aliases\" RENAME TO \"Aliases\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 1;\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240805122422_1.3.0-UpdateIdentityStructure', '9.0.4');\n\nBEGIN TRANSACTION;\nCREATE TABLE \"ef_temp_Credentials\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Credentials\" PRIMARY KEY,\n \"AliasId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"Notes\" TEXT NULL,\n \"ServiceId\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"Username\" TEXT NULL,\n CONSTRAINT \"FK_Credentials_Aliases_AliasId\" FOREIGN KEY (\"AliasId\") REFERENCES \"Aliases\" (\"Id\") ON DELETE CASCADE,\n CONSTRAINT \"FK_Credentials_Services_ServiceId\" FOREIGN KEY (\"ServiceId\") REFERENCES \"Services\" (\"Id\") ON DELETE CASCADE\n);\n\nINSERT INTO \"ef_temp_Credentials\" (\"Id\", \"AliasId\", \"CreatedAt\", \"Notes\", \"ServiceId\", \"UpdatedAt\", \"Username\")\nSELECT \"Id\", \"AliasId\", \"CreatedAt\", \"Notes\", \"ServiceId\", \"UpdatedAt\", \"Username\"\nFROM \"Credentials\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 0;\n\nBEGIN TRANSACTION;\nDROP TABLE \"Credentials\";\n\nALTER TABLE \"ef_temp_Credentials\" RENAME TO \"Credentials\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 1;\n\nBEGIN TRANSACTION;\nCREATE INDEX \"IX_Credentials_AliasId\" ON \"Credentials\" (\"AliasId\");\n\nCREATE INDEX \"IX_Credentials_ServiceId\" ON \"Credentials\" (\"ServiceId\");\n\nCOMMIT;\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240812141727_1.3.1-MakeUsernameOptional', '9.0.4');\n\nBEGIN TRANSACTION;\nALTER TABLE \"Settings\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Services\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Passwords\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"EncryptionKeys\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Credentials\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Attachment\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Aliases\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240916105320_1.4.0-AddSyncSupport', '9.0.4');\n\nALTER TABLE \"Attachment\" RENAME TO \"Attachments\";\n\nCREATE TABLE \"ef_temp_Attachments\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Attachments\" PRIMARY KEY,\n \"Blob\" BLOB NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"Filename\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n CONSTRAINT \"FK_Attachments_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nINSERT INTO \"ef_temp_Attachments\" (\"Id\", \"Blob\", \"CreatedAt\", \"CredentialId\", \"Filename\", \"IsDeleted\", \"UpdatedAt\")\nSELECT \"Id\", \"Blob\", \"CreatedAt\", \"CredentialId\", \"Filename\", \"IsDeleted\", \"UpdatedAt\"\nFROM \"Attachments\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 0;\n\nBEGIN TRANSACTION;\nDROP TABLE \"Attachments\";\n\nALTER TABLE \"ef_temp_Attachments\" RENAME TO \"Attachments\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 1;\n\nBEGIN TRANSACTION;\nCREATE INDEX \"IX_Attachments_CredentialId\" ON \"Attachments\" (\"CredentialId\");\n\nCOMMIT;\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240917191243_1.4.1-RenameAttachmentsPlural', '9.0.4');\n\nBEGIN TRANSACTION;\nCREATE TABLE \"TotpCodes\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_TotpCodes\" PRIMARY KEY,\n \"Name\" TEXT NOT NULL,\n \"SecretKey\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL,\n CONSTRAINT \"FK_TotpCodes_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE INDEX \"IX_TotpCodes_CredentialId\" ON \"TotpCodes\" (\"CredentialId\");\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20250310131554_1.5.0-AddTotpCodes', '9.0.4');\n\n\nPRAGMA foreign_keys = OFF;\n\n-- Clean up any existing temp tables first\nDROP TABLE IF EXISTS \"__EFMigrationsHistory_temp\";\nDROP TABLE IF EXISTS \"Aliases_temp\";\nDROP TABLE IF EXISTS \"Services_temp\";\nDROP TABLE IF EXISTS \"EncryptionKeys_temp\";\nDROP TABLE IF EXISTS \"Settings_temp\";\nDROP TABLE IF EXISTS \"Credentials_temp\";\nDROP TABLE IF EXISTS \"Attachments_temp\";\nDROP TABLE IF EXISTS \"Passwords_temp\";\nDROP TABLE IF EXISTS \"TotpCodes_temp\";\n\n-- Create backup tables for all data\nCREATE TABLE \"__EFMigrationsHistory_temp\" AS SELECT * FROM \"__EFMigrationsHistory\";\nCREATE TABLE \"Aliases_temp\" AS SELECT * FROM \"Aliases\";\nCREATE TABLE \"Services_temp\" AS SELECT * FROM \"Services\";\nCREATE TABLE \"EncryptionKeys_temp\" AS SELECT * FROM \"EncryptionKeys\";\nCREATE TABLE \"Settings_temp\" AS SELECT * FROM \"Settings\";\nCREATE TABLE \"Credentials_temp\" AS SELECT * FROM \"Credentials\";\nCREATE TABLE \"Attachments_temp\" AS SELECT * FROM \"Attachments\";\nCREATE TABLE \"Passwords_temp\" AS SELECT * FROM \"Passwords\";\nCREATE TABLE \"TotpCodes_temp\" AS SELECT * FROM \"TotpCodes\";\n\n-- Delete orphaned records that do not have a valid FK to the credential object\nDELETE FROM \"Attachments_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\nDELETE FROM \"Passwords_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\nDELETE FROM \"TotpCodes_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\n\n-- Delete orphaned credentials that do not have valid FKs to alias or service objects\nDELETE FROM \"Credentials_temp\" WHERE \"AliasId\" NOT IN (SELECT \"Id\" FROM \"Aliases_temp\");\nDELETE FROM \"Credentials_temp\" WHERE \"ServiceId\" NOT IN (SELECT \"Id\" FROM \"Services_temp\");\n\n-- After cleaning credentials, clean dependent tables again in case we removed credentials\nDELETE FROM \"Attachments_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\nDELETE FROM \"Passwords_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\nDELETE FROM \"TotpCodes_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\n\n-- Drop all existing tables\nDROP TABLE \"TotpCodes\";\nDROP TABLE \"Passwords\";\nDROP TABLE \"Attachments\";\nDROP TABLE \"Credentials\";\nDROP TABLE \"Settings\";\nDROP TABLE \"EncryptionKeys\";\nDROP TABLE \"Services\";\nDROP TABLE \"Aliases\";\nDROP TABLE \"__EFMigrationsHistory\";\n\n-- Recreate tables with proper constraints (no dependencies first)\nCREATE TABLE \"__EFMigrationsHistory\" (\n \"MigrationId\" TEXT NOT NULL CONSTRAINT \"PK___EFMigrationsHistory\" PRIMARY KEY,\n \"ProductVersion\" TEXT NOT NULL\n);\n\nCREATE TABLE \"Aliases\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Aliases\" PRIMARY KEY,\n \"BirthDate\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"Email\" TEXT NULL,\n \"FirstName\" VARCHAR NULL,\n \"Gender\" VARCHAR NULL,\n \"LastName\" VARCHAR NULL,\n \"NickName\" VARCHAR NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0\n);\n\nCREATE TABLE \"Services\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Services\" PRIMARY KEY,\n \"Name\" TEXT NULL,\n \"Url\" TEXT NULL,\n \"Logo\" BLOB NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0\n);\n\nCREATE TABLE \"EncryptionKeys\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_EncryptionKeys\" PRIMARY KEY,\n \"PublicKey\" TEXT NOT NULL,\n \"PrivateKey\" TEXT NOT NULL,\n \"IsPrimary\" INTEGER NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0\n);\n\nCREATE TABLE \"Settings\" (\n \"Key\" TEXT NOT NULL CONSTRAINT \"PK_Settings\" PRIMARY KEY,\n \"Value\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0\n);\n\n-- Tables with foreign keys\nCREATE TABLE \"Credentials\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Credentials\" PRIMARY KEY,\n \"AliasId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"Notes\" TEXT NULL,\n \"ServiceId\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"Username\" TEXT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0,\n CONSTRAINT \"FK_Credentials_Aliases_AliasId\" FOREIGN KEY (\"AliasId\") REFERENCES \"Aliases\" (\"Id\") ON DELETE CASCADE,\n CONSTRAINT \"FK_Credentials_Services_ServiceId\" FOREIGN KEY (\"ServiceId\") REFERENCES \"Services\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"Attachments\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Attachments\" PRIMARY KEY,\n \"Blob\" BLOB NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"Filename\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0,\n \"UpdatedAt\" TEXT NOT NULL,\n CONSTRAINT \"FK_Attachments_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"Passwords\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Passwords\" PRIMARY KEY,\n \"Value\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0,\n CONSTRAINT \"FK_Passwords_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"TotpCodes\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_TotpCodes\" PRIMARY KEY,\n \"Name\" TEXT NOT NULL,\n \"SecretKey\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0,\n CONSTRAINT \"FK_TotpCodes_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\n\n-- Restore data from temp tables\nINSERT INTO \"__EFMigrationsHistory\" SELECT * FROM \"__EFMigrationsHistory_temp\";\nINSERT INTO \"Aliases\" SELECT * FROM \"Aliases_temp\";\nINSERT INTO \"Services\" SELECT * FROM \"Services_temp\";\nINSERT INTO \"EncryptionKeys\" SELECT * FROM \"EncryptionKeys_temp\";\nINSERT INTO \"Settings\" SELECT * FROM \"Settings_temp\";\nINSERT INTO \"Credentials\" SELECT * FROM \"Credentials_temp\";\nINSERT INTO \"Attachments\" SELECT * FROM \"Attachments_temp\";\nINSERT INTO \"Passwords\" SELECT * FROM \"Passwords_temp\";\nINSERT INTO \"TotpCodes\" SELECT * FROM \"TotpCodes_temp\";\n\n-- Recreate indexes\nCREATE INDEX \"IX_Credentials_AliasId\" ON \"Credentials\" (\"AliasId\");\nCREATE INDEX \"IX_Credentials_ServiceId\" ON \"Credentials\" (\"ServiceId\");\nCREATE INDEX \"IX_Attachments_CredentialId\" ON \"Attachments\" (\"CredentialId\");\nCREATE INDEX \"IX_Passwords_CredentialId\" ON \"Passwords\" (\"CredentialId\");\nCREATE INDEX \"IX_TotpCodes_CredentialId\" ON \"TotpCodes\" (\"CredentialId\");\n\n-- Clean up temp tables\nDROP TABLE \"__EFMigrationsHistory_temp\";\nDROP TABLE \"Aliases_temp\";\nDROP TABLE \"Services_temp\";\nDROP TABLE \"EncryptionKeys_temp\";\nDROP TABLE \"Settings_temp\";\nDROP TABLE \"Credentials_temp\";\nDROP TABLE \"Attachments_temp\";\nDROP TABLE \"Passwords_temp\";\nDROP TABLE \"TotpCodes_temp\";\n\nPRAGMA foreign_keys = ON;\n\n\nCREATE TABLE \"Passkeys\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Passkeys\" PRIMARY KEY,\n \"RpId\" TEXT COLLATE NOCASE NOT NULL,\n \"UserHandle\" BLOB NOT NULL,\n \"PublicKey\" TEXT NOT NULL,\n \"PrivateKey\" TEXT NOT NULL,\n \"PrfKey\" BLOB NULL,\n \"DisplayName\" TEXT NOT NULL,\n \"AdditionalData\" BLOB NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL,\n CONSTRAINT \"FK_Passkeys_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE INDEX \"IX_Passkeys_CredentialId\" ON \"Passkeys\" (\"CredentialId\");\n\nCREATE INDEX \"IX_Passkeys_RpId\" ON \"Passkeys\" (\"RpId\");\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20251014122838_1.6.0-AddPasskeys', '9.0.4');\n\nCOMMIT;\n"; /** * Individual migration SQL scripts * Auto-generated from EF Core migrations diff --git a/apps/mobile-app/utils/dist/shared/vault-sql/index.js b/apps/mobile-app/utils/dist/shared/vault-sql/index.js index 23deaf64d..7872cbecc 100644 --- a/apps/mobile-app/utils/dist/shared/vault-sql/index.js +++ b/apps/mobile-app/utils/dist/shared/vault-sql/index.js @@ -464,7 +464,7 @@ PRAGMA foreign_keys = ON; CREATE TABLE "Passkeys" ( "Id" TEXT NOT NULL CONSTRAINT "PK_Passkeys" PRIMARY KEY, "RpId" TEXT COLLATE NOCASE NOT NULL, - "UserId" TEXT NULL, + "UserHandle" BLOB NOT NULL, "PublicKey" TEXT NOT NULL, "PrivateKey" TEXT NOT NULL, "PrfKey" BLOB NULL, @@ -482,7 +482,7 @@ CREATE INDEX "IX_Passkeys_CredentialId" ON "Passkeys" ("CredentialId"); CREATE INDEX "IX_Passkeys_RpId" ON "Passkeys" ("RpId"); INSERT INTO "__EFMigrationsHistory" ("MigrationId", "ProductVersion") -VALUES ('20251007085746_1.6.0-AddPasskeys', '9.0.4'); +VALUES ('20251014122838_1.6.0-AddPasskeys', '9.0.4'); COMMIT; `; @@ -851,7 +851,7 @@ PRAGMA foreign_keys = ON; CREATE TABLE "Passkeys" ( "Id" TEXT NOT NULL CONSTRAINT "PK_Passkeys" PRIMARY KEY, "RpId" TEXT COLLATE NOCASE NOT NULL, - "UserId" TEXT NULL, + "UserHandle" BLOB NOT NULL, "PublicKey" TEXT NOT NULL, "PrivateKey" TEXT NOT NULL, "PrfKey" BLOB NULL, @@ -869,7 +869,7 @@ CREATE INDEX "IX_Passkeys_CredentialId" ON "Passkeys" ("CredentialId"); CREATE INDEX "IX_Passkeys_RpId" ON "Passkeys" ("RpId"); INSERT INTO "__EFMigrationsHistory" ("MigrationId", "ProductVersion") -VALUES ('20251007085746_1.6.0-AddPasskeys', '9.0.4'); +VALUES ('20251014122838_1.6.0-AddPasskeys', '9.0.4'); COMMIT;` }; diff --git a/apps/mobile-app/utils/dist/shared/vault-sql/index.mjs b/apps/mobile-app/utils/dist/shared/vault-sql/index.mjs index 0899a348b..28c6dfc06 100644 --- a/apps/mobile-app/utils/dist/shared/vault-sql/index.mjs +++ b/apps/mobile-app/utils/dist/shared/vault-sql/index.mjs @@ -435,7 +435,7 @@ PRAGMA foreign_keys = ON; CREATE TABLE "Passkeys" ( "Id" TEXT NOT NULL CONSTRAINT "PK_Passkeys" PRIMARY KEY, "RpId" TEXT COLLATE NOCASE NOT NULL, - "UserId" TEXT NULL, + "UserHandle" BLOB NOT NULL, "PublicKey" TEXT NOT NULL, "PrivateKey" TEXT NOT NULL, "PrfKey" BLOB NULL, @@ -453,7 +453,7 @@ CREATE INDEX "IX_Passkeys_CredentialId" ON "Passkeys" ("CredentialId"); CREATE INDEX "IX_Passkeys_RpId" ON "Passkeys" ("RpId"); INSERT INTO "__EFMigrationsHistory" ("MigrationId", "ProductVersion") -VALUES ('20251007085746_1.6.0-AddPasskeys', '9.0.4'); +VALUES ('20251014122838_1.6.0-AddPasskeys', '9.0.4'); COMMIT; `; @@ -822,7 +822,7 @@ PRAGMA foreign_keys = ON; CREATE TABLE "Passkeys" ( "Id" TEXT NOT NULL CONSTRAINT "PK_Passkeys" PRIMARY KEY, "RpId" TEXT COLLATE NOCASE NOT NULL, - "UserId" TEXT NULL, + "UserHandle" BLOB NOT NULL, "PublicKey" TEXT NOT NULL, "PrivateKey" TEXT NOT NULL, "PrfKey" BLOB NULL, @@ -840,7 +840,7 @@ CREATE INDEX "IX_Passkeys_CredentialId" ON "Passkeys" ("CredentialId"); CREATE INDEX "IX_Passkeys_RpId" ON "Passkeys" ("RpId"); INSERT INTO "__EFMigrationsHistory" ("MigrationId", "ProductVersion") -VALUES ('20251007085746_1.6.0-AddPasskeys', '9.0.4'); +VALUES ('20251014122838_1.6.0-AddPasskeys', '9.0.4'); COMMIT;` }; diff --git a/apps/server/AliasVault.Client/wwwroot/css/tailwind.css b/apps/server/AliasVault.Client/wwwroot/css/tailwind.css index 82dcd040d..30a65222c 100644 --- a/apps/server/AliasVault.Client/wwwroot/css/tailwind.css +++ b/apps/server/AliasVault.Client/wwwroot/css/tailwind.css @@ -1900,6 +1900,10 @@ video { padding-bottom: 7rem; } +.pb-6 { + padding-bottom: 1.5rem; +} + .pb-8 { padding-bottom: 2rem; } @@ -1952,10 +1956,6 @@ video { padding-top: 2rem; } -.pb-6 { - padding-bottom: 1.5rem; -} - .text-left { text-align: left; } diff --git a/apps/server/AliasVault.Client/wwwroot/js/dist/shared/vault-sql/index.d.mts b/apps/server/AliasVault.Client/wwwroot/js/dist/shared/vault-sql/index.d.mts index ea25cb473..871c1b2f1 100644 --- a/apps/server/AliasVault.Client/wwwroot/js/dist/shared/vault-sql/index.d.mts +++ b/apps/server/AliasVault.Client/wwwroot/js/dist/shared/vault-sql/index.d.mts @@ -122,7 +122,7 @@ declare const VAULT_VERSIONS: VaultVersion[]; * Complete database schema SQL (latest version) * Auto-generated from EF Core migrations */ -declare const COMPLETE_SCHEMA_SQL = "\n\uFEFFCREATE TABLE IF NOT EXISTS \"__EFMigrationsHistory\" (\n \"MigrationId\" TEXT NOT NULL CONSTRAINT \"PK___EFMigrationsHistory\" PRIMARY KEY,\n \"ProductVersion\" TEXT NOT NULL\n);\n\nBEGIN TRANSACTION;\nCREATE TABLE \"Aliases\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Aliases\" PRIMARY KEY,\n \"Gender\" VARCHAR NULL,\n \"FirstName\" VARCHAR NULL,\n \"LastName\" VARCHAR NULL,\n \"NickName\" VARCHAR NULL,\n \"BirthDate\" TEXT NOT NULL,\n \"AddressStreet\" VARCHAR NULL,\n \"AddressCity\" VARCHAR NULL,\n \"AddressState\" VARCHAR NULL,\n \"AddressZipCode\" VARCHAR NULL,\n \"AddressCountry\" VARCHAR NULL,\n \"Hobbies\" TEXT NULL,\n \"EmailPrefix\" TEXT NULL,\n \"PhoneMobile\" TEXT NULL,\n \"BankAccountIBAN\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nCREATE TABLE \"Services\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Services\" PRIMARY KEY,\n \"Name\" TEXT NULL,\n \"Url\" TEXT NULL,\n \"Logo\" BLOB NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nCREATE TABLE \"Credentials\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Credentials\" PRIMARY KEY,\n \"AliasId\" TEXT NOT NULL,\n \"Notes\" TEXT NULL,\n \"Username\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"ServiceId\" TEXT NOT NULL,\n CONSTRAINT \"FK_Credentials_Aliases_AliasId\" FOREIGN KEY (\"AliasId\") REFERENCES \"Aliases\" (\"Id\") ON DELETE CASCADE,\n CONSTRAINT \"FK_Credentials_Services_ServiceId\" FOREIGN KEY (\"ServiceId\") REFERENCES \"Services\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"Attachment\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Attachment\" PRIMARY KEY,\n \"Filename\" TEXT NOT NULL,\n \"Blob\" BLOB NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n CONSTRAINT \"FK_Attachment_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"Passwords\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Passwords\" PRIMARY KEY,\n \"Value\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n CONSTRAINT \"FK_Passwords_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE INDEX \"IX_Attachment_CredentialId\" ON \"Attachment\" (\"CredentialId\");\n\nCREATE INDEX \"IX_Credentials_AliasId\" ON \"Credentials\" (\"AliasId\");\n\nCREATE INDEX \"IX_Credentials_ServiceId\" ON \"Credentials\" (\"ServiceId\");\n\nCREATE INDEX \"IX_Passwords_CredentialId\" ON \"Passwords\" (\"CredentialId\");\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240708094944_1.0.0-InitialMigration', '9.0.4');\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240708224522_1.0.1-EmptyTestMigration', '9.0.4');\n\nALTER TABLE \"Aliases\" RENAME COLUMN \"EmailPrefix\" TO \"Email\";\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240711204207_1.0.2-ChangeEmailColumn', '9.0.4');\n\nCREATE TABLE \"EncryptionKeys\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_EncryptionKeys\" PRIMARY KEY,\n \"PublicKey\" TEXT NOT NULL,\n \"PrivateKey\" TEXT NOT NULL,\n \"IsPrimary\" INTEGER NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240729105618_1.1.0-AddPkiTables', '9.0.4');\n\nCREATE TABLE \"Settings\" (\n \"Key\" TEXT NOT NULL CONSTRAINT \"PK_Settings\" PRIMARY KEY,\n \"Value\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240805073413_1.2.0-AddSettingsTable', '9.0.4');\n\nCREATE TABLE \"ef_temp_Aliases\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Aliases\" PRIMARY KEY,\n \"BirthDate\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"Email\" TEXT NULL,\n \"FirstName\" VARCHAR NULL,\n \"Gender\" VARCHAR NULL,\n \"LastName\" VARCHAR NULL,\n \"NickName\" VARCHAR NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nINSERT INTO \"ef_temp_Aliases\" (\"Id\", \"BirthDate\", \"CreatedAt\", \"Email\", \"FirstName\", \"Gender\", \"LastName\", \"NickName\", \"UpdatedAt\")\nSELECT \"Id\", \"BirthDate\", \"CreatedAt\", \"Email\", \"FirstName\", \"Gender\", \"LastName\", \"NickName\", \"UpdatedAt\"\nFROM \"Aliases\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 0;\n\nBEGIN TRANSACTION;\nDROP TABLE \"Aliases\";\n\nALTER TABLE \"ef_temp_Aliases\" RENAME TO \"Aliases\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 1;\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240805122422_1.3.0-UpdateIdentityStructure', '9.0.4');\n\nBEGIN TRANSACTION;\nCREATE TABLE \"ef_temp_Credentials\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Credentials\" PRIMARY KEY,\n \"AliasId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"Notes\" TEXT NULL,\n \"ServiceId\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"Username\" TEXT NULL,\n CONSTRAINT \"FK_Credentials_Aliases_AliasId\" FOREIGN KEY (\"AliasId\") REFERENCES \"Aliases\" (\"Id\") ON DELETE CASCADE,\n CONSTRAINT \"FK_Credentials_Services_ServiceId\" FOREIGN KEY (\"ServiceId\") REFERENCES \"Services\" (\"Id\") ON DELETE CASCADE\n);\n\nINSERT INTO \"ef_temp_Credentials\" (\"Id\", \"AliasId\", \"CreatedAt\", \"Notes\", \"ServiceId\", \"UpdatedAt\", \"Username\")\nSELECT \"Id\", \"AliasId\", \"CreatedAt\", \"Notes\", \"ServiceId\", \"UpdatedAt\", \"Username\"\nFROM \"Credentials\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 0;\n\nBEGIN TRANSACTION;\nDROP TABLE \"Credentials\";\n\nALTER TABLE \"ef_temp_Credentials\" RENAME TO \"Credentials\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 1;\n\nBEGIN TRANSACTION;\nCREATE INDEX \"IX_Credentials_AliasId\" ON \"Credentials\" (\"AliasId\");\n\nCREATE INDEX \"IX_Credentials_ServiceId\" ON \"Credentials\" (\"ServiceId\");\n\nCOMMIT;\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240812141727_1.3.1-MakeUsernameOptional', '9.0.4');\n\nBEGIN TRANSACTION;\nALTER TABLE \"Settings\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Services\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Passwords\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"EncryptionKeys\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Credentials\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Attachment\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Aliases\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240916105320_1.4.0-AddSyncSupport', '9.0.4');\n\nALTER TABLE \"Attachment\" RENAME TO \"Attachments\";\n\nCREATE TABLE \"ef_temp_Attachments\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Attachments\" PRIMARY KEY,\n \"Blob\" BLOB NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"Filename\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n CONSTRAINT \"FK_Attachments_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nINSERT INTO \"ef_temp_Attachments\" (\"Id\", \"Blob\", \"CreatedAt\", \"CredentialId\", \"Filename\", \"IsDeleted\", \"UpdatedAt\")\nSELECT \"Id\", \"Blob\", \"CreatedAt\", \"CredentialId\", \"Filename\", \"IsDeleted\", \"UpdatedAt\"\nFROM \"Attachments\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 0;\n\nBEGIN TRANSACTION;\nDROP TABLE \"Attachments\";\n\nALTER TABLE \"ef_temp_Attachments\" RENAME TO \"Attachments\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 1;\n\nBEGIN TRANSACTION;\nCREATE INDEX \"IX_Attachments_CredentialId\" ON \"Attachments\" (\"CredentialId\");\n\nCOMMIT;\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240917191243_1.4.1-RenameAttachmentsPlural', '9.0.4');\n\nBEGIN TRANSACTION;\nCREATE TABLE \"TotpCodes\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_TotpCodes\" PRIMARY KEY,\n \"Name\" TEXT NOT NULL,\n \"SecretKey\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL,\n CONSTRAINT \"FK_TotpCodes_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE INDEX \"IX_TotpCodes_CredentialId\" ON \"TotpCodes\" (\"CredentialId\");\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20250310131554_1.5.0-AddTotpCodes', '9.0.4');\n\n\nPRAGMA foreign_keys = OFF;\n\n-- Clean up any existing temp tables first\nDROP TABLE IF EXISTS \"__EFMigrationsHistory_temp\";\nDROP TABLE IF EXISTS \"Aliases_temp\";\nDROP TABLE IF EXISTS \"Services_temp\";\nDROP TABLE IF EXISTS \"EncryptionKeys_temp\";\nDROP TABLE IF EXISTS \"Settings_temp\";\nDROP TABLE IF EXISTS \"Credentials_temp\";\nDROP TABLE IF EXISTS \"Attachments_temp\";\nDROP TABLE IF EXISTS \"Passwords_temp\";\nDROP TABLE IF EXISTS \"TotpCodes_temp\";\n\n-- Create backup tables for all data\nCREATE TABLE \"__EFMigrationsHistory_temp\" AS SELECT * FROM \"__EFMigrationsHistory\";\nCREATE TABLE \"Aliases_temp\" AS SELECT * FROM \"Aliases\";\nCREATE TABLE \"Services_temp\" AS SELECT * FROM \"Services\";\nCREATE TABLE \"EncryptionKeys_temp\" AS SELECT * FROM \"EncryptionKeys\";\nCREATE TABLE \"Settings_temp\" AS SELECT * FROM \"Settings\";\nCREATE TABLE \"Credentials_temp\" AS SELECT * FROM \"Credentials\";\nCREATE TABLE \"Attachments_temp\" AS SELECT * FROM \"Attachments\";\nCREATE TABLE \"Passwords_temp\" AS SELECT * FROM \"Passwords\";\nCREATE TABLE \"TotpCodes_temp\" AS SELECT * FROM \"TotpCodes\";\n\n-- Delete orphaned records that do not have a valid FK to the credential object\nDELETE FROM \"Attachments_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\nDELETE FROM \"Passwords_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\nDELETE FROM \"TotpCodes_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\n\n-- Delete orphaned credentials that do not have valid FKs to alias or service objects\nDELETE FROM \"Credentials_temp\" WHERE \"AliasId\" NOT IN (SELECT \"Id\" FROM \"Aliases_temp\");\nDELETE FROM \"Credentials_temp\" WHERE \"ServiceId\" NOT IN (SELECT \"Id\" FROM \"Services_temp\");\n\n-- After cleaning credentials, clean dependent tables again in case we removed credentials\nDELETE FROM \"Attachments_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\nDELETE FROM \"Passwords_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\nDELETE FROM \"TotpCodes_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\n\n-- Drop all existing tables\nDROP TABLE \"TotpCodes\";\nDROP TABLE \"Passwords\";\nDROP TABLE \"Attachments\";\nDROP TABLE \"Credentials\";\nDROP TABLE \"Settings\";\nDROP TABLE \"EncryptionKeys\";\nDROP TABLE \"Services\";\nDROP TABLE \"Aliases\";\nDROP TABLE \"__EFMigrationsHistory\";\n\n-- Recreate tables with proper constraints (no dependencies first)\nCREATE TABLE \"__EFMigrationsHistory\" (\n \"MigrationId\" TEXT NOT NULL CONSTRAINT \"PK___EFMigrationsHistory\" PRIMARY KEY,\n \"ProductVersion\" TEXT NOT NULL\n);\n\nCREATE TABLE \"Aliases\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Aliases\" PRIMARY KEY,\n \"BirthDate\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"Email\" TEXT NULL,\n \"FirstName\" VARCHAR NULL,\n \"Gender\" VARCHAR NULL,\n \"LastName\" VARCHAR NULL,\n \"NickName\" VARCHAR NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0\n);\n\nCREATE TABLE \"Services\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Services\" PRIMARY KEY,\n \"Name\" TEXT NULL,\n \"Url\" TEXT NULL,\n \"Logo\" BLOB NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0\n);\n\nCREATE TABLE \"EncryptionKeys\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_EncryptionKeys\" PRIMARY KEY,\n \"PublicKey\" TEXT NOT NULL,\n \"PrivateKey\" TEXT NOT NULL,\n \"IsPrimary\" INTEGER NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0\n);\n\nCREATE TABLE \"Settings\" (\n \"Key\" TEXT NOT NULL CONSTRAINT \"PK_Settings\" PRIMARY KEY,\n \"Value\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0\n);\n\n-- Tables with foreign keys\nCREATE TABLE \"Credentials\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Credentials\" PRIMARY KEY,\n \"AliasId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"Notes\" TEXT NULL,\n \"ServiceId\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"Username\" TEXT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0,\n CONSTRAINT \"FK_Credentials_Aliases_AliasId\" FOREIGN KEY (\"AliasId\") REFERENCES \"Aliases\" (\"Id\") ON DELETE CASCADE,\n CONSTRAINT \"FK_Credentials_Services_ServiceId\" FOREIGN KEY (\"ServiceId\") REFERENCES \"Services\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"Attachments\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Attachments\" PRIMARY KEY,\n \"Blob\" BLOB NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"Filename\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0,\n \"UpdatedAt\" TEXT NOT NULL,\n CONSTRAINT \"FK_Attachments_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"Passwords\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Passwords\" PRIMARY KEY,\n \"Value\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0,\n CONSTRAINT \"FK_Passwords_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"TotpCodes\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_TotpCodes\" PRIMARY KEY,\n \"Name\" TEXT NOT NULL,\n \"SecretKey\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0,\n CONSTRAINT \"FK_TotpCodes_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\n\n-- Restore data from temp tables\nINSERT INTO \"__EFMigrationsHistory\" SELECT * FROM \"__EFMigrationsHistory_temp\";\nINSERT INTO \"Aliases\" SELECT * FROM \"Aliases_temp\";\nINSERT INTO \"Services\" SELECT * FROM \"Services_temp\";\nINSERT INTO \"EncryptionKeys\" SELECT * FROM \"EncryptionKeys_temp\";\nINSERT INTO \"Settings\" SELECT * FROM \"Settings_temp\";\nINSERT INTO \"Credentials\" SELECT * FROM \"Credentials_temp\";\nINSERT INTO \"Attachments\" SELECT * FROM \"Attachments_temp\";\nINSERT INTO \"Passwords\" SELECT * FROM \"Passwords_temp\";\nINSERT INTO \"TotpCodes\" SELECT * FROM \"TotpCodes_temp\";\n\n-- Recreate indexes\nCREATE INDEX \"IX_Credentials_AliasId\" ON \"Credentials\" (\"AliasId\");\nCREATE INDEX \"IX_Credentials_ServiceId\" ON \"Credentials\" (\"ServiceId\");\nCREATE INDEX \"IX_Attachments_CredentialId\" ON \"Attachments\" (\"CredentialId\");\nCREATE INDEX \"IX_Passwords_CredentialId\" ON \"Passwords\" (\"CredentialId\");\nCREATE INDEX \"IX_TotpCodes_CredentialId\" ON \"TotpCodes\" (\"CredentialId\");\n\n-- Clean up temp tables\nDROP TABLE \"__EFMigrationsHistory_temp\";\nDROP TABLE \"Aliases_temp\";\nDROP TABLE \"Services_temp\";\nDROP TABLE \"EncryptionKeys_temp\";\nDROP TABLE \"Settings_temp\";\nDROP TABLE \"Credentials_temp\";\nDROP TABLE \"Attachments_temp\";\nDROP TABLE \"Passwords_temp\";\nDROP TABLE \"TotpCodes_temp\";\n\nPRAGMA foreign_keys = ON;\n\n\nCREATE TABLE \"Passkeys\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Passkeys\" PRIMARY KEY,\n \"RpId\" TEXT COLLATE NOCASE NOT NULL,\n \"UserId\" TEXT NULL,\n \"PublicKey\" TEXT NOT NULL,\n \"PrivateKey\" TEXT NOT NULL,\n \"PrfKey\" BLOB NULL,\n \"DisplayName\" TEXT NOT NULL,\n \"AdditionalData\" BLOB NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL,\n CONSTRAINT \"FK_Passkeys_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE INDEX \"IX_Passkeys_CredentialId\" ON \"Passkeys\" (\"CredentialId\");\n\nCREATE INDEX \"IX_Passkeys_RpId\" ON \"Passkeys\" (\"RpId\");\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20251007085746_1.6.0-AddPasskeys', '9.0.4');\n\nCOMMIT;\n"; +declare const COMPLETE_SCHEMA_SQL = "\n\uFEFFCREATE TABLE IF NOT EXISTS \"__EFMigrationsHistory\" (\n \"MigrationId\" TEXT NOT NULL CONSTRAINT \"PK___EFMigrationsHistory\" PRIMARY KEY,\n \"ProductVersion\" TEXT NOT NULL\n);\n\nBEGIN TRANSACTION;\nCREATE TABLE \"Aliases\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Aliases\" PRIMARY KEY,\n \"Gender\" VARCHAR NULL,\n \"FirstName\" VARCHAR NULL,\n \"LastName\" VARCHAR NULL,\n \"NickName\" VARCHAR NULL,\n \"BirthDate\" TEXT NOT NULL,\n \"AddressStreet\" VARCHAR NULL,\n \"AddressCity\" VARCHAR NULL,\n \"AddressState\" VARCHAR NULL,\n \"AddressZipCode\" VARCHAR NULL,\n \"AddressCountry\" VARCHAR NULL,\n \"Hobbies\" TEXT NULL,\n \"EmailPrefix\" TEXT NULL,\n \"PhoneMobile\" TEXT NULL,\n \"BankAccountIBAN\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nCREATE TABLE \"Services\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Services\" PRIMARY KEY,\n \"Name\" TEXT NULL,\n \"Url\" TEXT NULL,\n \"Logo\" BLOB NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nCREATE TABLE \"Credentials\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Credentials\" PRIMARY KEY,\n \"AliasId\" TEXT NOT NULL,\n \"Notes\" TEXT NULL,\n \"Username\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"ServiceId\" TEXT NOT NULL,\n CONSTRAINT \"FK_Credentials_Aliases_AliasId\" FOREIGN KEY (\"AliasId\") REFERENCES \"Aliases\" (\"Id\") ON DELETE CASCADE,\n CONSTRAINT \"FK_Credentials_Services_ServiceId\" FOREIGN KEY (\"ServiceId\") REFERENCES \"Services\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"Attachment\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Attachment\" PRIMARY KEY,\n \"Filename\" TEXT NOT NULL,\n \"Blob\" BLOB NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n CONSTRAINT \"FK_Attachment_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"Passwords\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Passwords\" PRIMARY KEY,\n \"Value\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n CONSTRAINT \"FK_Passwords_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE INDEX \"IX_Attachment_CredentialId\" ON \"Attachment\" (\"CredentialId\");\n\nCREATE INDEX \"IX_Credentials_AliasId\" ON \"Credentials\" (\"AliasId\");\n\nCREATE INDEX \"IX_Credentials_ServiceId\" ON \"Credentials\" (\"ServiceId\");\n\nCREATE INDEX \"IX_Passwords_CredentialId\" ON \"Passwords\" (\"CredentialId\");\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240708094944_1.0.0-InitialMigration', '9.0.4');\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240708224522_1.0.1-EmptyTestMigration', '9.0.4');\n\nALTER TABLE \"Aliases\" RENAME COLUMN \"EmailPrefix\" TO \"Email\";\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240711204207_1.0.2-ChangeEmailColumn', '9.0.4');\n\nCREATE TABLE \"EncryptionKeys\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_EncryptionKeys\" PRIMARY KEY,\n \"PublicKey\" TEXT NOT NULL,\n \"PrivateKey\" TEXT NOT NULL,\n \"IsPrimary\" INTEGER NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240729105618_1.1.0-AddPkiTables', '9.0.4');\n\nCREATE TABLE \"Settings\" (\n \"Key\" TEXT NOT NULL CONSTRAINT \"PK_Settings\" PRIMARY KEY,\n \"Value\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240805073413_1.2.0-AddSettingsTable', '9.0.4');\n\nCREATE TABLE \"ef_temp_Aliases\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Aliases\" PRIMARY KEY,\n \"BirthDate\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"Email\" TEXT NULL,\n \"FirstName\" VARCHAR NULL,\n \"Gender\" VARCHAR NULL,\n \"LastName\" VARCHAR NULL,\n \"NickName\" VARCHAR NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nINSERT INTO \"ef_temp_Aliases\" (\"Id\", \"BirthDate\", \"CreatedAt\", \"Email\", \"FirstName\", \"Gender\", \"LastName\", \"NickName\", \"UpdatedAt\")\nSELECT \"Id\", \"BirthDate\", \"CreatedAt\", \"Email\", \"FirstName\", \"Gender\", \"LastName\", \"NickName\", \"UpdatedAt\"\nFROM \"Aliases\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 0;\n\nBEGIN TRANSACTION;\nDROP TABLE \"Aliases\";\n\nALTER TABLE \"ef_temp_Aliases\" RENAME TO \"Aliases\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 1;\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240805122422_1.3.0-UpdateIdentityStructure', '9.0.4');\n\nBEGIN TRANSACTION;\nCREATE TABLE \"ef_temp_Credentials\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Credentials\" PRIMARY KEY,\n \"AliasId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"Notes\" TEXT NULL,\n \"ServiceId\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"Username\" TEXT NULL,\n CONSTRAINT \"FK_Credentials_Aliases_AliasId\" FOREIGN KEY (\"AliasId\") REFERENCES \"Aliases\" (\"Id\") ON DELETE CASCADE,\n CONSTRAINT \"FK_Credentials_Services_ServiceId\" FOREIGN KEY (\"ServiceId\") REFERENCES \"Services\" (\"Id\") ON DELETE CASCADE\n);\n\nINSERT INTO \"ef_temp_Credentials\" (\"Id\", \"AliasId\", \"CreatedAt\", \"Notes\", \"ServiceId\", \"UpdatedAt\", \"Username\")\nSELECT \"Id\", \"AliasId\", \"CreatedAt\", \"Notes\", \"ServiceId\", \"UpdatedAt\", \"Username\"\nFROM \"Credentials\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 0;\n\nBEGIN TRANSACTION;\nDROP TABLE \"Credentials\";\n\nALTER TABLE \"ef_temp_Credentials\" RENAME TO \"Credentials\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 1;\n\nBEGIN TRANSACTION;\nCREATE INDEX \"IX_Credentials_AliasId\" ON \"Credentials\" (\"AliasId\");\n\nCREATE INDEX \"IX_Credentials_ServiceId\" ON \"Credentials\" (\"ServiceId\");\n\nCOMMIT;\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240812141727_1.3.1-MakeUsernameOptional', '9.0.4');\n\nBEGIN TRANSACTION;\nALTER TABLE \"Settings\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Services\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Passwords\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"EncryptionKeys\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Credentials\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Attachment\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Aliases\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240916105320_1.4.0-AddSyncSupport', '9.0.4');\n\nALTER TABLE \"Attachment\" RENAME TO \"Attachments\";\n\nCREATE TABLE \"ef_temp_Attachments\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Attachments\" PRIMARY KEY,\n \"Blob\" BLOB NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"Filename\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n CONSTRAINT \"FK_Attachments_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nINSERT INTO \"ef_temp_Attachments\" (\"Id\", \"Blob\", \"CreatedAt\", \"CredentialId\", \"Filename\", \"IsDeleted\", \"UpdatedAt\")\nSELECT \"Id\", \"Blob\", \"CreatedAt\", \"CredentialId\", \"Filename\", \"IsDeleted\", \"UpdatedAt\"\nFROM \"Attachments\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 0;\n\nBEGIN TRANSACTION;\nDROP TABLE \"Attachments\";\n\nALTER TABLE \"ef_temp_Attachments\" RENAME TO \"Attachments\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 1;\n\nBEGIN TRANSACTION;\nCREATE INDEX \"IX_Attachments_CredentialId\" ON \"Attachments\" (\"CredentialId\");\n\nCOMMIT;\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240917191243_1.4.1-RenameAttachmentsPlural', '9.0.4');\n\nBEGIN TRANSACTION;\nCREATE TABLE \"TotpCodes\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_TotpCodes\" PRIMARY KEY,\n \"Name\" TEXT NOT NULL,\n \"SecretKey\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL,\n CONSTRAINT \"FK_TotpCodes_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE INDEX \"IX_TotpCodes_CredentialId\" ON \"TotpCodes\" (\"CredentialId\");\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20250310131554_1.5.0-AddTotpCodes', '9.0.4');\n\n\nPRAGMA foreign_keys = OFF;\n\n-- Clean up any existing temp tables first\nDROP TABLE IF EXISTS \"__EFMigrationsHistory_temp\";\nDROP TABLE IF EXISTS \"Aliases_temp\";\nDROP TABLE IF EXISTS \"Services_temp\";\nDROP TABLE IF EXISTS \"EncryptionKeys_temp\";\nDROP TABLE IF EXISTS \"Settings_temp\";\nDROP TABLE IF EXISTS \"Credentials_temp\";\nDROP TABLE IF EXISTS \"Attachments_temp\";\nDROP TABLE IF EXISTS \"Passwords_temp\";\nDROP TABLE IF EXISTS \"TotpCodes_temp\";\n\n-- Create backup tables for all data\nCREATE TABLE \"__EFMigrationsHistory_temp\" AS SELECT * FROM \"__EFMigrationsHistory\";\nCREATE TABLE \"Aliases_temp\" AS SELECT * FROM \"Aliases\";\nCREATE TABLE \"Services_temp\" AS SELECT * FROM \"Services\";\nCREATE TABLE \"EncryptionKeys_temp\" AS SELECT * FROM \"EncryptionKeys\";\nCREATE TABLE \"Settings_temp\" AS SELECT * FROM \"Settings\";\nCREATE TABLE \"Credentials_temp\" AS SELECT * FROM \"Credentials\";\nCREATE TABLE \"Attachments_temp\" AS SELECT * FROM \"Attachments\";\nCREATE TABLE \"Passwords_temp\" AS SELECT * FROM \"Passwords\";\nCREATE TABLE \"TotpCodes_temp\" AS SELECT * FROM \"TotpCodes\";\n\n-- Delete orphaned records that do not have a valid FK to the credential object\nDELETE FROM \"Attachments_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\nDELETE FROM \"Passwords_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\nDELETE FROM \"TotpCodes_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\n\n-- Delete orphaned credentials that do not have valid FKs to alias or service objects\nDELETE FROM \"Credentials_temp\" WHERE \"AliasId\" NOT IN (SELECT \"Id\" FROM \"Aliases_temp\");\nDELETE FROM \"Credentials_temp\" WHERE \"ServiceId\" NOT IN (SELECT \"Id\" FROM \"Services_temp\");\n\n-- After cleaning credentials, clean dependent tables again in case we removed credentials\nDELETE FROM \"Attachments_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\nDELETE FROM \"Passwords_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\nDELETE FROM \"TotpCodes_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\n\n-- Drop all existing tables\nDROP TABLE \"TotpCodes\";\nDROP TABLE \"Passwords\";\nDROP TABLE \"Attachments\";\nDROP TABLE \"Credentials\";\nDROP TABLE \"Settings\";\nDROP TABLE \"EncryptionKeys\";\nDROP TABLE \"Services\";\nDROP TABLE \"Aliases\";\nDROP TABLE \"__EFMigrationsHistory\";\n\n-- Recreate tables with proper constraints (no dependencies first)\nCREATE TABLE \"__EFMigrationsHistory\" (\n \"MigrationId\" TEXT NOT NULL CONSTRAINT \"PK___EFMigrationsHistory\" PRIMARY KEY,\n \"ProductVersion\" TEXT NOT NULL\n);\n\nCREATE TABLE \"Aliases\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Aliases\" PRIMARY KEY,\n \"BirthDate\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"Email\" TEXT NULL,\n \"FirstName\" VARCHAR NULL,\n \"Gender\" VARCHAR NULL,\n \"LastName\" VARCHAR NULL,\n \"NickName\" VARCHAR NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0\n);\n\nCREATE TABLE \"Services\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Services\" PRIMARY KEY,\n \"Name\" TEXT NULL,\n \"Url\" TEXT NULL,\n \"Logo\" BLOB NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0\n);\n\nCREATE TABLE \"EncryptionKeys\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_EncryptionKeys\" PRIMARY KEY,\n \"PublicKey\" TEXT NOT NULL,\n \"PrivateKey\" TEXT NOT NULL,\n \"IsPrimary\" INTEGER NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0\n);\n\nCREATE TABLE \"Settings\" (\n \"Key\" TEXT NOT NULL CONSTRAINT \"PK_Settings\" PRIMARY KEY,\n \"Value\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0\n);\n\n-- Tables with foreign keys\nCREATE TABLE \"Credentials\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Credentials\" PRIMARY KEY,\n \"AliasId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"Notes\" TEXT NULL,\n \"ServiceId\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"Username\" TEXT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0,\n CONSTRAINT \"FK_Credentials_Aliases_AliasId\" FOREIGN KEY (\"AliasId\") REFERENCES \"Aliases\" (\"Id\") ON DELETE CASCADE,\n CONSTRAINT \"FK_Credentials_Services_ServiceId\" FOREIGN KEY (\"ServiceId\") REFERENCES \"Services\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"Attachments\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Attachments\" PRIMARY KEY,\n \"Blob\" BLOB NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"Filename\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0,\n \"UpdatedAt\" TEXT NOT NULL,\n CONSTRAINT \"FK_Attachments_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"Passwords\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Passwords\" PRIMARY KEY,\n \"Value\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0,\n CONSTRAINT \"FK_Passwords_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"TotpCodes\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_TotpCodes\" PRIMARY KEY,\n \"Name\" TEXT NOT NULL,\n \"SecretKey\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0,\n CONSTRAINT \"FK_TotpCodes_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\n\n-- Restore data from temp tables\nINSERT INTO \"__EFMigrationsHistory\" SELECT * FROM \"__EFMigrationsHistory_temp\";\nINSERT INTO \"Aliases\" SELECT * FROM \"Aliases_temp\";\nINSERT INTO \"Services\" SELECT * FROM \"Services_temp\";\nINSERT INTO \"EncryptionKeys\" SELECT * FROM \"EncryptionKeys_temp\";\nINSERT INTO \"Settings\" SELECT * FROM \"Settings_temp\";\nINSERT INTO \"Credentials\" SELECT * FROM \"Credentials_temp\";\nINSERT INTO \"Attachments\" SELECT * FROM \"Attachments_temp\";\nINSERT INTO \"Passwords\" SELECT * FROM \"Passwords_temp\";\nINSERT INTO \"TotpCodes\" SELECT * FROM \"TotpCodes_temp\";\n\n-- Recreate indexes\nCREATE INDEX \"IX_Credentials_AliasId\" ON \"Credentials\" (\"AliasId\");\nCREATE INDEX \"IX_Credentials_ServiceId\" ON \"Credentials\" (\"ServiceId\");\nCREATE INDEX \"IX_Attachments_CredentialId\" ON \"Attachments\" (\"CredentialId\");\nCREATE INDEX \"IX_Passwords_CredentialId\" ON \"Passwords\" (\"CredentialId\");\nCREATE INDEX \"IX_TotpCodes_CredentialId\" ON \"TotpCodes\" (\"CredentialId\");\n\n-- Clean up temp tables\nDROP TABLE \"__EFMigrationsHistory_temp\";\nDROP TABLE \"Aliases_temp\";\nDROP TABLE \"Services_temp\";\nDROP TABLE \"EncryptionKeys_temp\";\nDROP TABLE \"Settings_temp\";\nDROP TABLE \"Credentials_temp\";\nDROP TABLE \"Attachments_temp\";\nDROP TABLE \"Passwords_temp\";\nDROP TABLE \"TotpCodes_temp\";\n\nPRAGMA foreign_keys = ON;\n\n\nCREATE TABLE \"Passkeys\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Passkeys\" PRIMARY KEY,\n \"RpId\" TEXT COLLATE NOCASE NOT NULL,\n \"UserHandle\" BLOB NOT NULL,\n \"PublicKey\" TEXT NOT NULL,\n \"PrivateKey\" TEXT NOT NULL,\n \"PrfKey\" BLOB NULL,\n \"DisplayName\" TEXT NOT NULL,\n \"AdditionalData\" BLOB NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL,\n CONSTRAINT \"FK_Passkeys_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE INDEX \"IX_Passkeys_CredentialId\" ON \"Passkeys\" (\"CredentialId\");\n\nCREATE INDEX \"IX_Passkeys_RpId\" ON \"Passkeys\" (\"RpId\");\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20251014122838_1.6.0-AddPasskeys', '9.0.4');\n\nCOMMIT;\n"; /** * Individual migration SQL scripts * Auto-generated from EF Core migrations diff --git a/apps/server/AliasVault.Client/wwwroot/js/dist/shared/vault-sql/index.d.ts b/apps/server/AliasVault.Client/wwwroot/js/dist/shared/vault-sql/index.d.ts index ea25cb473..871c1b2f1 100644 --- a/apps/server/AliasVault.Client/wwwroot/js/dist/shared/vault-sql/index.d.ts +++ b/apps/server/AliasVault.Client/wwwroot/js/dist/shared/vault-sql/index.d.ts @@ -122,7 +122,7 @@ declare const VAULT_VERSIONS: VaultVersion[]; * Complete database schema SQL (latest version) * Auto-generated from EF Core migrations */ -declare const COMPLETE_SCHEMA_SQL = "\n\uFEFFCREATE TABLE IF NOT EXISTS \"__EFMigrationsHistory\" (\n \"MigrationId\" TEXT NOT NULL CONSTRAINT \"PK___EFMigrationsHistory\" PRIMARY KEY,\n \"ProductVersion\" TEXT NOT NULL\n);\n\nBEGIN TRANSACTION;\nCREATE TABLE \"Aliases\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Aliases\" PRIMARY KEY,\n \"Gender\" VARCHAR NULL,\n \"FirstName\" VARCHAR NULL,\n \"LastName\" VARCHAR NULL,\n \"NickName\" VARCHAR NULL,\n \"BirthDate\" TEXT NOT NULL,\n \"AddressStreet\" VARCHAR NULL,\n \"AddressCity\" VARCHAR NULL,\n \"AddressState\" VARCHAR NULL,\n \"AddressZipCode\" VARCHAR NULL,\n \"AddressCountry\" VARCHAR NULL,\n \"Hobbies\" TEXT NULL,\n \"EmailPrefix\" TEXT NULL,\n \"PhoneMobile\" TEXT NULL,\n \"BankAccountIBAN\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nCREATE TABLE \"Services\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Services\" PRIMARY KEY,\n \"Name\" TEXT NULL,\n \"Url\" TEXT NULL,\n \"Logo\" BLOB NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nCREATE TABLE \"Credentials\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Credentials\" PRIMARY KEY,\n \"AliasId\" TEXT NOT NULL,\n \"Notes\" TEXT NULL,\n \"Username\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"ServiceId\" TEXT NOT NULL,\n CONSTRAINT \"FK_Credentials_Aliases_AliasId\" FOREIGN KEY (\"AliasId\") REFERENCES \"Aliases\" (\"Id\") ON DELETE CASCADE,\n CONSTRAINT \"FK_Credentials_Services_ServiceId\" FOREIGN KEY (\"ServiceId\") REFERENCES \"Services\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"Attachment\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Attachment\" PRIMARY KEY,\n \"Filename\" TEXT NOT NULL,\n \"Blob\" BLOB NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n CONSTRAINT \"FK_Attachment_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"Passwords\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Passwords\" PRIMARY KEY,\n \"Value\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n CONSTRAINT \"FK_Passwords_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE INDEX \"IX_Attachment_CredentialId\" ON \"Attachment\" (\"CredentialId\");\n\nCREATE INDEX \"IX_Credentials_AliasId\" ON \"Credentials\" (\"AliasId\");\n\nCREATE INDEX \"IX_Credentials_ServiceId\" ON \"Credentials\" (\"ServiceId\");\n\nCREATE INDEX \"IX_Passwords_CredentialId\" ON \"Passwords\" (\"CredentialId\");\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240708094944_1.0.0-InitialMigration', '9.0.4');\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240708224522_1.0.1-EmptyTestMigration', '9.0.4');\n\nALTER TABLE \"Aliases\" RENAME COLUMN \"EmailPrefix\" TO \"Email\";\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240711204207_1.0.2-ChangeEmailColumn', '9.0.4');\n\nCREATE TABLE \"EncryptionKeys\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_EncryptionKeys\" PRIMARY KEY,\n \"PublicKey\" TEXT NOT NULL,\n \"PrivateKey\" TEXT NOT NULL,\n \"IsPrimary\" INTEGER NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240729105618_1.1.0-AddPkiTables', '9.0.4');\n\nCREATE TABLE \"Settings\" (\n \"Key\" TEXT NOT NULL CONSTRAINT \"PK_Settings\" PRIMARY KEY,\n \"Value\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240805073413_1.2.0-AddSettingsTable', '9.0.4');\n\nCREATE TABLE \"ef_temp_Aliases\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Aliases\" PRIMARY KEY,\n \"BirthDate\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"Email\" TEXT NULL,\n \"FirstName\" VARCHAR NULL,\n \"Gender\" VARCHAR NULL,\n \"LastName\" VARCHAR NULL,\n \"NickName\" VARCHAR NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nINSERT INTO \"ef_temp_Aliases\" (\"Id\", \"BirthDate\", \"CreatedAt\", \"Email\", \"FirstName\", \"Gender\", \"LastName\", \"NickName\", \"UpdatedAt\")\nSELECT \"Id\", \"BirthDate\", \"CreatedAt\", \"Email\", \"FirstName\", \"Gender\", \"LastName\", \"NickName\", \"UpdatedAt\"\nFROM \"Aliases\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 0;\n\nBEGIN TRANSACTION;\nDROP TABLE \"Aliases\";\n\nALTER TABLE \"ef_temp_Aliases\" RENAME TO \"Aliases\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 1;\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240805122422_1.3.0-UpdateIdentityStructure', '9.0.4');\n\nBEGIN TRANSACTION;\nCREATE TABLE \"ef_temp_Credentials\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Credentials\" PRIMARY KEY,\n \"AliasId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"Notes\" TEXT NULL,\n \"ServiceId\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"Username\" TEXT NULL,\n CONSTRAINT \"FK_Credentials_Aliases_AliasId\" FOREIGN KEY (\"AliasId\") REFERENCES \"Aliases\" (\"Id\") ON DELETE CASCADE,\n CONSTRAINT \"FK_Credentials_Services_ServiceId\" FOREIGN KEY (\"ServiceId\") REFERENCES \"Services\" (\"Id\") ON DELETE CASCADE\n);\n\nINSERT INTO \"ef_temp_Credentials\" (\"Id\", \"AliasId\", \"CreatedAt\", \"Notes\", \"ServiceId\", \"UpdatedAt\", \"Username\")\nSELECT \"Id\", \"AliasId\", \"CreatedAt\", \"Notes\", \"ServiceId\", \"UpdatedAt\", \"Username\"\nFROM \"Credentials\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 0;\n\nBEGIN TRANSACTION;\nDROP TABLE \"Credentials\";\n\nALTER TABLE \"ef_temp_Credentials\" RENAME TO \"Credentials\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 1;\n\nBEGIN TRANSACTION;\nCREATE INDEX \"IX_Credentials_AliasId\" ON \"Credentials\" (\"AliasId\");\n\nCREATE INDEX \"IX_Credentials_ServiceId\" ON \"Credentials\" (\"ServiceId\");\n\nCOMMIT;\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240812141727_1.3.1-MakeUsernameOptional', '9.0.4');\n\nBEGIN TRANSACTION;\nALTER TABLE \"Settings\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Services\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Passwords\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"EncryptionKeys\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Credentials\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Attachment\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Aliases\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240916105320_1.4.0-AddSyncSupport', '9.0.4');\n\nALTER TABLE \"Attachment\" RENAME TO \"Attachments\";\n\nCREATE TABLE \"ef_temp_Attachments\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Attachments\" PRIMARY KEY,\n \"Blob\" BLOB NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"Filename\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n CONSTRAINT \"FK_Attachments_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nINSERT INTO \"ef_temp_Attachments\" (\"Id\", \"Blob\", \"CreatedAt\", \"CredentialId\", \"Filename\", \"IsDeleted\", \"UpdatedAt\")\nSELECT \"Id\", \"Blob\", \"CreatedAt\", \"CredentialId\", \"Filename\", \"IsDeleted\", \"UpdatedAt\"\nFROM \"Attachments\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 0;\n\nBEGIN TRANSACTION;\nDROP TABLE \"Attachments\";\n\nALTER TABLE \"ef_temp_Attachments\" RENAME TO \"Attachments\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 1;\n\nBEGIN TRANSACTION;\nCREATE INDEX \"IX_Attachments_CredentialId\" ON \"Attachments\" (\"CredentialId\");\n\nCOMMIT;\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240917191243_1.4.1-RenameAttachmentsPlural', '9.0.4');\n\nBEGIN TRANSACTION;\nCREATE TABLE \"TotpCodes\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_TotpCodes\" PRIMARY KEY,\n \"Name\" TEXT NOT NULL,\n \"SecretKey\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL,\n CONSTRAINT \"FK_TotpCodes_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE INDEX \"IX_TotpCodes_CredentialId\" ON \"TotpCodes\" (\"CredentialId\");\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20250310131554_1.5.0-AddTotpCodes', '9.0.4');\n\n\nPRAGMA foreign_keys = OFF;\n\n-- Clean up any existing temp tables first\nDROP TABLE IF EXISTS \"__EFMigrationsHistory_temp\";\nDROP TABLE IF EXISTS \"Aliases_temp\";\nDROP TABLE IF EXISTS \"Services_temp\";\nDROP TABLE IF EXISTS \"EncryptionKeys_temp\";\nDROP TABLE IF EXISTS \"Settings_temp\";\nDROP TABLE IF EXISTS \"Credentials_temp\";\nDROP TABLE IF EXISTS \"Attachments_temp\";\nDROP TABLE IF EXISTS \"Passwords_temp\";\nDROP TABLE IF EXISTS \"TotpCodes_temp\";\n\n-- Create backup tables for all data\nCREATE TABLE \"__EFMigrationsHistory_temp\" AS SELECT * FROM \"__EFMigrationsHistory\";\nCREATE TABLE \"Aliases_temp\" AS SELECT * FROM \"Aliases\";\nCREATE TABLE \"Services_temp\" AS SELECT * FROM \"Services\";\nCREATE TABLE \"EncryptionKeys_temp\" AS SELECT * FROM \"EncryptionKeys\";\nCREATE TABLE \"Settings_temp\" AS SELECT * FROM \"Settings\";\nCREATE TABLE \"Credentials_temp\" AS SELECT * FROM \"Credentials\";\nCREATE TABLE \"Attachments_temp\" AS SELECT * FROM \"Attachments\";\nCREATE TABLE \"Passwords_temp\" AS SELECT * FROM \"Passwords\";\nCREATE TABLE \"TotpCodes_temp\" AS SELECT * FROM \"TotpCodes\";\n\n-- Delete orphaned records that do not have a valid FK to the credential object\nDELETE FROM \"Attachments_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\nDELETE FROM \"Passwords_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\nDELETE FROM \"TotpCodes_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\n\n-- Delete orphaned credentials that do not have valid FKs to alias or service objects\nDELETE FROM \"Credentials_temp\" WHERE \"AliasId\" NOT IN (SELECT \"Id\" FROM \"Aliases_temp\");\nDELETE FROM \"Credentials_temp\" WHERE \"ServiceId\" NOT IN (SELECT \"Id\" FROM \"Services_temp\");\n\n-- After cleaning credentials, clean dependent tables again in case we removed credentials\nDELETE FROM \"Attachments_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\nDELETE FROM \"Passwords_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\nDELETE FROM \"TotpCodes_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\n\n-- Drop all existing tables\nDROP TABLE \"TotpCodes\";\nDROP TABLE \"Passwords\";\nDROP TABLE \"Attachments\";\nDROP TABLE \"Credentials\";\nDROP TABLE \"Settings\";\nDROP TABLE \"EncryptionKeys\";\nDROP TABLE \"Services\";\nDROP TABLE \"Aliases\";\nDROP TABLE \"__EFMigrationsHistory\";\n\n-- Recreate tables with proper constraints (no dependencies first)\nCREATE TABLE \"__EFMigrationsHistory\" (\n \"MigrationId\" TEXT NOT NULL CONSTRAINT \"PK___EFMigrationsHistory\" PRIMARY KEY,\n \"ProductVersion\" TEXT NOT NULL\n);\n\nCREATE TABLE \"Aliases\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Aliases\" PRIMARY KEY,\n \"BirthDate\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"Email\" TEXT NULL,\n \"FirstName\" VARCHAR NULL,\n \"Gender\" VARCHAR NULL,\n \"LastName\" VARCHAR NULL,\n \"NickName\" VARCHAR NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0\n);\n\nCREATE TABLE \"Services\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Services\" PRIMARY KEY,\n \"Name\" TEXT NULL,\n \"Url\" TEXT NULL,\n \"Logo\" BLOB NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0\n);\n\nCREATE TABLE \"EncryptionKeys\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_EncryptionKeys\" PRIMARY KEY,\n \"PublicKey\" TEXT NOT NULL,\n \"PrivateKey\" TEXT NOT NULL,\n \"IsPrimary\" INTEGER NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0\n);\n\nCREATE TABLE \"Settings\" (\n \"Key\" TEXT NOT NULL CONSTRAINT \"PK_Settings\" PRIMARY KEY,\n \"Value\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0\n);\n\n-- Tables with foreign keys\nCREATE TABLE \"Credentials\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Credentials\" PRIMARY KEY,\n \"AliasId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"Notes\" TEXT NULL,\n \"ServiceId\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"Username\" TEXT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0,\n CONSTRAINT \"FK_Credentials_Aliases_AliasId\" FOREIGN KEY (\"AliasId\") REFERENCES \"Aliases\" (\"Id\") ON DELETE CASCADE,\n CONSTRAINT \"FK_Credentials_Services_ServiceId\" FOREIGN KEY (\"ServiceId\") REFERENCES \"Services\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"Attachments\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Attachments\" PRIMARY KEY,\n \"Blob\" BLOB NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"Filename\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0,\n \"UpdatedAt\" TEXT NOT NULL,\n CONSTRAINT \"FK_Attachments_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"Passwords\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Passwords\" PRIMARY KEY,\n \"Value\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0,\n CONSTRAINT \"FK_Passwords_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"TotpCodes\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_TotpCodes\" PRIMARY KEY,\n \"Name\" TEXT NOT NULL,\n \"SecretKey\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0,\n CONSTRAINT \"FK_TotpCodes_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\n\n-- Restore data from temp tables\nINSERT INTO \"__EFMigrationsHistory\" SELECT * FROM \"__EFMigrationsHistory_temp\";\nINSERT INTO \"Aliases\" SELECT * FROM \"Aliases_temp\";\nINSERT INTO \"Services\" SELECT * FROM \"Services_temp\";\nINSERT INTO \"EncryptionKeys\" SELECT * FROM \"EncryptionKeys_temp\";\nINSERT INTO \"Settings\" SELECT * FROM \"Settings_temp\";\nINSERT INTO \"Credentials\" SELECT * FROM \"Credentials_temp\";\nINSERT INTO \"Attachments\" SELECT * FROM \"Attachments_temp\";\nINSERT INTO \"Passwords\" SELECT * FROM \"Passwords_temp\";\nINSERT INTO \"TotpCodes\" SELECT * FROM \"TotpCodes_temp\";\n\n-- Recreate indexes\nCREATE INDEX \"IX_Credentials_AliasId\" ON \"Credentials\" (\"AliasId\");\nCREATE INDEX \"IX_Credentials_ServiceId\" ON \"Credentials\" (\"ServiceId\");\nCREATE INDEX \"IX_Attachments_CredentialId\" ON \"Attachments\" (\"CredentialId\");\nCREATE INDEX \"IX_Passwords_CredentialId\" ON \"Passwords\" (\"CredentialId\");\nCREATE INDEX \"IX_TotpCodes_CredentialId\" ON \"TotpCodes\" (\"CredentialId\");\n\n-- Clean up temp tables\nDROP TABLE \"__EFMigrationsHistory_temp\";\nDROP TABLE \"Aliases_temp\";\nDROP TABLE \"Services_temp\";\nDROP TABLE \"EncryptionKeys_temp\";\nDROP TABLE \"Settings_temp\";\nDROP TABLE \"Credentials_temp\";\nDROP TABLE \"Attachments_temp\";\nDROP TABLE \"Passwords_temp\";\nDROP TABLE \"TotpCodes_temp\";\n\nPRAGMA foreign_keys = ON;\n\n\nCREATE TABLE \"Passkeys\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Passkeys\" PRIMARY KEY,\n \"RpId\" TEXT COLLATE NOCASE NOT NULL,\n \"UserId\" TEXT NULL,\n \"PublicKey\" TEXT NOT NULL,\n \"PrivateKey\" TEXT NOT NULL,\n \"PrfKey\" BLOB NULL,\n \"DisplayName\" TEXT NOT NULL,\n \"AdditionalData\" BLOB NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL,\n CONSTRAINT \"FK_Passkeys_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE INDEX \"IX_Passkeys_CredentialId\" ON \"Passkeys\" (\"CredentialId\");\n\nCREATE INDEX \"IX_Passkeys_RpId\" ON \"Passkeys\" (\"RpId\");\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20251007085746_1.6.0-AddPasskeys', '9.0.4');\n\nCOMMIT;\n"; +declare const COMPLETE_SCHEMA_SQL = "\n\uFEFFCREATE TABLE IF NOT EXISTS \"__EFMigrationsHistory\" (\n \"MigrationId\" TEXT NOT NULL CONSTRAINT \"PK___EFMigrationsHistory\" PRIMARY KEY,\n \"ProductVersion\" TEXT NOT NULL\n);\n\nBEGIN TRANSACTION;\nCREATE TABLE \"Aliases\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Aliases\" PRIMARY KEY,\n \"Gender\" VARCHAR NULL,\n \"FirstName\" VARCHAR NULL,\n \"LastName\" VARCHAR NULL,\n \"NickName\" VARCHAR NULL,\n \"BirthDate\" TEXT NOT NULL,\n \"AddressStreet\" VARCHAR NULL,\n \"AddressCity\" VARCHAR NULL,\n \"AddressState\" VARCHAR NULL,\n \"AddressZipCode\" VARCHAR NULL,\n \"AddressCountry\" VARCHAR NULL,\n \"Hobbies\" TEXT NULL,\n \"EmailPrefix\" TEXT NULL,\n \"PhoneMobile\" TEXT NULL,\n \"BankAccountIBAN\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nCREATE TABLE \"Services\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Services\" PRIMARY KEY,\n \"Name\" TEXT NULL,\n \"Url\" TEXT NULL,\n \"Logo\" BLOB NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nCREATE TABLE \"Credentials\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Credentials\" PRIMARY KEY,\n \"AliasId\" TEXT NOT NULL,\n \"Notes\" TEXT NULL,\n \"Username\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"ServiceId\" TEXT NOT NULL,\n CONSTRAINT \"FK_Credentials_Aliases_AliasId\" FOREIGN KEY (\"AliasId\") REFERENCES \"Aliases\" (\"Id\") ON DELETE CASCADE,\n CONSTRAINT \"FK_Credentials_Services_ServiceId\" FOREIGN KEY (\"ServiceId\") REFERENCES \"Services\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"Attachment\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Attachment\" PRIMARY KEY,\n \"Filename\" TEXT NOT NULL,\n \"Blob\" BLOB NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n CONSTRAINT \"FK_Attachment_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"Passwords\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Passwords\" PRIMARY KEY,\n \"Value\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n CONSTRAINT \"FK_Passwords_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE INDEX \"IX_Attachment_CredentialId\" ON \"Attachment\" (\"CredentialId\");\n\nCREATE INDEX \"IX_Credentials_AliasId\" ON \"Credentials\" (\"AliasId\");\n\nCREATE INDEX \"IX_Credentials_ServiceId\" ON \"Credentials\" (\"ServiceId\");\n\nCREATE INDEX \"IX_Passwords_CredentialId\" ON \"Passwords\" (\"CredentialId\");\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240708094944_1.0.0-InitialMigration', '9.0.4');\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240708224522_1.0.1-EmptyTestMigration', '9.0.4');\n\nALTER TABLE \"Aliases\" RENAME COLUMN \"EmailPrefix\" TO \"Email\";\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240711204207_1.0.2-ChangeEmailColumn', '9.0.4');\n\nCREATE TABLE \"EncryptionKeys\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_EncryptionKeys\" PRIMARY KEY,\n \"PublicKey\" TEXT NOT NULL,\n \"PrivateKey\" TEXT NOT NULL,\n \"IsPrimary\" INTEGER NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240729105618_1.1.0-AddPkiTables', '9.0.4');\n\nCREATE TABLE \"Settings\" (\n \"Key\" TEXT NOT NULL CONSTRAINT \"PK_Settings\" PRIMARY KEY,\n \"Value\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240805073413_1.2.0-AddSettingsTable', '9.0.4');\n\nCREATE TABLE \"ef_temp_Aliases\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Aliases\" PRIMARY KEY,\n \"BirthDate\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"Email\" TEXT NULL,\n \"FirstName\" VARCHAR NULL,\n \"Gender\" VARCHAR NULL,\n \"LastName\" VARCHAR NULL,\n \"NickName\" VARCHAR NULL,\n \"UpdatedAt\" TEXT NOT NULL\n);\n\nINSERT INTO \"ef_temp_Aliases\" (\"Id\", \"BirthDate\", \"CreatedAt\", \"Email\", \"FirstName\", \"Gender\", \"LastName\", \"NickName\", \"UpdatedAt\")\nSELECT \"Id\", \"BirthDate\", \"CreatedAt\", \"Email\", \"FirstName\", \"Gender\", \"LastName\", \"NickName\", \"UpdatedAt\"\nFROM \"Aliases\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 0;\n\nBEGIN TRANSACTION;\nDROP TABLE \"Aliases\";\n\nALTER TABLE \"ef_temp_Aliases\" RENAME TO \"Aliases\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 1;\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240805122422_1.3.0-UpdateIdentityStructure', '9.0.4');\n\nBEGIN TRANSACTION;\nCREATE TABLE \"ef_temp_Credentials\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Credentials\" PRIMARY KEY,\n \"AliasId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"Notes\" TEXT NULL,\n \"ServiceId\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"Username\" TEXT NULL,\n CONSTRAINT \"FK_Credentials_Aliases_AliasId\" FOREIGN KEY (\"AliasId\") REFERENCES \"Aliases\" (\"Id\") ON DELETE CASCADE,\n CONSTRAINT \"FK_Credentials_Services_ServiceId\" FOREIGN KEY (\"ServiceId\") REFERENCES \"Services\" (\"Id\") ON DELETE CASCADE\n);\n\nINSERT INTO \"ef_temp_Credentials\" (\"Id\", \"AliasId\", \"CreatedAt\", \"Notes\", \"ServiceId\", \"UpdatedAt\", \"Username\")\nSELECT \"Id\", \"AliasId\", \"CreatedAt\", \"Notes\", \"ServiceId\", \"UpdatedAt\", \"Username\"\nFROM \"Credentials\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 0;\n\nBEGIN TRANSACTION;\nDROP TABLE \"Credentials\";\n\nALTER TABLE \"ef_temp_Credentials\" RENAME TO \"Credentials\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 1;\n\nBEGIN TRANSACTION;\nCREATE INDEX \"IX_Credentials_AliasId\" ON \"Credentials\" (\"AliasId\");\n\nCREATE INDEX \"IX_Credentials_ServiceId\" ON \"Credentials\" (\"ServiceId\");\n\nCOMMIT;\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240812141727_1.3.1-MakeUsernameOptional', '9.0.4');\n\nBEGIN TRANSACTION;\nALTER TABLE \"Settings\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Services\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Passwords\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"EncryptionKeys\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Credentials\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Attachment\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nALTER TABLE \"Aliases\" ADD \"IsDeleted\" INTEGER NOT NULL DEFAULT 0;\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240916105320_1.4.0-AddSyncSupport', '9.0.4');\n\nALTER TABLE \"Attachment\" RENAME TO \"Attachments\";\n\nCREATE TABLE \"ef_temp_Attachments\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Attachments\" PRIMARY KEY,\n \"Blob\" BLOB NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"Filename\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n CONSTRAINT \"FK_Attachments_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nINSERT INTO \"ef_temp_Attachments\" (\"Id\", \"Blob\", \"CreatedAt\", \"CredentialId\", \"Filename\", \"IsDeleted\", \"UpdatedAt\")\nSELECT \"Id\", \"Blob\", \"CreatedAt\", \"CredentialId\", \"Filename\", \"IsDeleted\", \"UpdatedAt\"\nFROM \"Attachments\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 0;\n\nBEGIN TRANSACTION;\nDROP TABLE \"Attachments\";\n\nALTER TABLE \"ef_temp_Attachments\" RENAME TO \"Attachments\";\n\nCOMMIT;\n\nPRAGMA foreign_keys = 1;\n\nBEGIN TRANSACTION;\nCREATE INDEX \"IX_Attachments_CredentialId\" ON \"Attachments\" (\"CredentialId\");\n\nCOMMIT;\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20240917191243_1.4.1-RenameAttachmentsPlural', '9.0.4');\n\nBEGIN TRANSACTION;\nCREATE TABLE \"TotpCodes\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_TotpCodes\" PRIMARY KEY,\n \"Name\" TEXT NOT NULL,\n \"SecretKey\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL,\n CONSTRAINT \"FK_TotpCodes_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE INDEX \"IX_TotpCodes_CredentialId\" ON \"TotpCodes\" (\"CredentialId\");\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20250310131554_1.5.0-AddTotpCodes', '9.0.4');\n\n\nPRAGMA foreign_keys = OFF;\n\n-- Clean up any existing temp tables first\nDROP TABLE IF EXISTS \"__EFMigrationsHistory_temp\";\nDROP TABLE IF EXISTS \"Aliases_temp\";\nDROP TABLE IF EXISTS \"Services_temp\";\nDROP TABLE IF EXISTS \"EncryptionKeys_temp\";\nDROP TABLE IF EXISTS \"Settings_temp\";\nDROP TABLE IF EXISTS \"Credentials_temp\";\nDROP TABLE IF EXISTS \"Attachments_temp\";\nDROP TABLE IF EXISTS \"Passwords_temp\";\nDROP TABLE IF EXISTS \"TotpCodes_temp\";\n\n-- Create backup tables for all data\nCREATE TABLE \"__EFMigrationsHistory_temp\" AS SELECT * FROM \"__EFMigrationsHistory\";\nCREATE TABLE \"Aliases_temp\" AS SELECT * FROM \"Aliases\";\nCREATE TABLE \"Services_temp\" AS SELECT * FROM \"Services\";\nCREATE TABLE \"EncryptionKeys_temp\" AS SELECT * FROM \"EncryptionKeys\";\nCREATE TABLE \"Settings_temp\" AS SELECT * FROM \"Settings\";\nCREATE TABLE \"Credentials_temp\" AS SELECT * FROM \"Credentials\";\nCREATE TABLE \"Attachments_temp\" AS SELECT * FROM \"Attachments\";\nCREATE TABLE \"Passwords_temp\" AS SELECT * FROM \"Passwords\";\nCREATE TABLE \"TotpCodes_temp\" AS SELECT * FROM \"TotpCodes\";\n\n-- Delete orphaned records that do not have a valid FK to the credential object\nDELETE FROM \"Attachments_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\nDELETE FROM \"Passwords_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\nDELETE FROM \"TotpCodes_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\n\n-- Delete orphaned credentials that do not have valid FKs to alias or service objects\nDELETE FROM \"Credentials_temp\" WHERE \"AliasId\" NOT IN (SELECT \"Id\" FROM \"Aliases_temp\");\nDELETE FROM \"Credentials_temp\" WHERE \"ServiceId\" NOT IN (SELECT \"Id\" FROM \"Services_temp\");\n\n-- After cleaning credentials, clean dependent tables again in case we removed credentials\nDELETE FROM \"Attachments_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\nDELETE FROM \"Passwords_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\nDELETE FROM \"TotpCodes_temp\" WHERE \"CredentialId\" NOT IN (SELECT \"Id\" FROM \"Credentials_temp\");\n\n-- Drop all existing tables\nDROP TABLE \"TotpCodes\";\nDROP TABLE \"Passwords\";\nDROP TABLE \"Attachments\";\nDROP TABLE \"Credentials\";\nDROP TABLE \"Settings\";\nDROP TABLE \"EncryptionKeys\";\nDROP TABLE \"Services\";\nDROP TABLE \"Aliases\";\nDROP TABLE \"__EFMigrationsHistory\";\n\n-- Recreate tables with proper constraints (no dependencies first)\nCREATE TABLE \"__EFMigrationsHistory\" (\n \"MigrationId\" TEXT NOT NULL CONSTRAINT \"PK___EFMigrationsHistory\" PRIMARY KEY,\n \"ProductVersion\" TEXT NOT NULL\n);\n\nCREATE TABLE \"Aliases\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Aliases\" PRIMARY KEY,\n \"BirthDate\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"Email\" TEXT NULL,\n \"FirstName\" VARCHAR NULL,\n \"Gender\" VARCHAR NULL,\n \"LastName\" VARCHAR NULL,\n \"NickName\" VARCHAR NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0\n);\n\nCREATE TABLE \"Services\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Services\" PRIMARY KEY,\n \"Name\" TEXT NULL,\n \"Url\" TEXT NULL,\n \"Logo\" BLOB NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0\n);\n\nCREATE TABLE \"EncryptionKeys\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_EncryptionKeys\" PRIMARY KEY,\n \"PublicKey\" TEXT NOT NULL,\n \"PrivateKey\" TEXT NOT NULL,\n \"IsPrimary\" INTEGER NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0\n);\n\nCREATE TABLE \"Settings\" (\n \"Key\" TEXT NOT NULL CONSTRAINT \"PK_Settings\" PRIMARY KEY,\n \"Value\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0\n);\n\n-- Tables with foreign keys\nCREATE TABLE \"Credentials\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Credentials\" PRIMARY KEY,\n \"AliasId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"Notes\" TEXT NULL,\n \"ServiceId\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"Username\" TEXT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0,\n CONSTRAINT \"FK_Credentials_Aliases_AliasId\" FOREIGN KEY (\"AliasId\") REFERENCES \"Aliases\" (\"Id\") ON DELETE CASCADE,\n CONSTRAINT \"FK_Credentials_Services_ServiceId\" FOREIGN KEY (\"ServiceId\") REFERENCES \"Services\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"Attachments\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Attachments\" PRIMARY KEY,\n \"Blob\" BLOB NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"Filename\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0,\n \"UpdatedAt\" TEXT NOT NULL,\n CONSTRAINT \"FK_Attachments_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"Passwords\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Passwords\" PRIMARY KEY,\n \"Value\" TEXT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0,\n CONSTRAINT \"FK_Passwords_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE TABLE \"TotpCodes\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_TotpCodes\" PRIMARY KEY,\n \"Name\" TEXT NOT NULL,\n \"SecretKey\" TEXT NOT NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL DEFAULT 0,\n CONSTRAINT \"FK_TotpCodes_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\n\n-- Restore data from temp tables\nINSERT INTO \"__EFMigrationsHistory\" SELECT * FROM \"__EFMigrationsHistory_temp\";\nINSERT INTO \"Aliases\" SELECT * FROM \"Aliases_temp\";\nINSERT INTO \"Services\" SELECT * FROM \"Services_temp\";\nINSERT INTO \"EncryptionKeys\" SELECT * FROM \"EncryptionKeys_temp\";\nINSERT INTO \"Settings\" SELECT * FROM \"Settings_temp\";\nINSERT INTO \"Credentials\" SELECT * FROM \"Credentials_temp\";\nINSERT INTO \"Attachments\" SELECT * FROM \"Attachments_temp\";\nINSERT INTO \"Passwords\" SELECT * FROM \"Passwords_temp\";\nINSERT INTO \"TotpCodes\" SELECT * FROM \"TotpCodes_temp\";\n\n-- Recreate indexes\nCREATE INDEX \"IX_Credentials_AliasId\" ON \"Credentials\" (\"AliasId\");\nCREATE INDEX \"IX_Credentials_ServiceId\" ON \"Credentials\" (\"ServiceId\");\nCREATE INDEX \"IX_Attachments_CredentialId\" ON \"Attachments\" (\"CredentialId\");\nCREATE INDEX \"IX_Passwords_CredentialId\" ON \"Passwords\" (\"CredentialId\");\nCREATE INDEX \"IX_TotpCodes_CredentialId\" ON \"TotpCodes\" (\"CredentialId\");\n\n-- Clean up temp tables\nDROP TABLE \"__EFMigrationsHistory_temp\";\nDROP TABLE \"Aliases_temp\";\nDROP TABLE \"Services_temp\";\nDROP TABLE \"EncryptionKeys_temp\";\nDROP TABLE \"Settings_temp\";\nDROP TABLE \"Credentials_temp\";\nDROP TABLE \"Attachments_temp\";\nDROP TABLE \"Passwords_temp\";\nDROP TABLE \"TotpCodes_temp\";\n\nPRAGMA foreign_keys = ON;\n\n\nCREATE TABLE \"Passkeys\" (\n \"Id\" TEXT NOT NULL CONSTRAINT \"PK_Passkeys\" PRIMARY KEY,\n \"RpId\" TEXT COLLATE NOCASE NOT NULL,\n \"UserHandle\" BLOB NOT NULL,\n \"PublicKey\" TEXT NOT NULL,\n \"PrivateKey\" TEXT NOT NULL,\n \"PrfKey\" BLOB NULL,\n \"DisplayName\" TEXT NOT NULL,\n \"AdditionalData\" BLOB NULL,\n \"CredentialId\" TEXT NOT NULL,\n \"CreatedAt\" TEXT NOT NULL,\n \"UpdatedAt\" TEXT NOT NULL,\n \"IsDeleted\" INTEGER NOT NULL,\n CONSTRAINT \"FK_Passkeys_Credentials_CredentialId\" FOREIGN KEY (\"CredentialId\") REFERENCES \"Credentials\" (\"Id\") ON DELETE CASCADE\n);\n\nCREATE INDEX \"IX_Passkeys_CredentialId\" ON \"Passkeys\" (\"CredentialId\");\n\nCREATE INDEX \"IX_Passkeys_RpId\" ON \"Passkeys\" (\"RpId\");\n\nINSERT INTO \"__EFMigrationsHistory\" (\"MigrationId\", \"ProductVersion\")\nVALUES ('20251014122838_1.6.0-AddPasskeys', '9.0.4');\n\nCOMMIT;\n"; /** * Individual migration SQL scripts * Auto-generated from EF Core migrations diff --git a/apps/server/AliasVault.Client/wwwroot/js/dist/shared/vault-sql/index.js b/apps/server/AliasVault.Client/wwwroot/js/dist/shared/vault-sql/index.js index 23deaf64d..7872cbecc 100644 --- a/apps/server/AliasVault.Client/wwwroot/js/dist/shared/vault-sql/index.js +++ b/apps/server/AliasVault.Client/wwwroot/js/dist/shared/vault-sql/index.js @@ -464,7 +464,7 @@ PRAGMA foreign_keys = ON; CREATE TABLE "Passkeys" ( "Id" TEXT NOT NULL CONSTRAINT "PK_Passkeys" PRIMARY KEY, "RpId" TEXT COLLATE NOCASE NOT NULL, - "UserId" TEXT NULL, + "UserHandle" BLOB NOT NULL, "PublicKey" TEXT NOT NULL, "PrivateKey" TEXT NOT NULL, "PrfKey" BLOB NULL, @@ -482,7 +482,7 @@ CREATE INDEX "IX_Passkeys_CredentialId" ON "Passkeys" ("CredentialId"); CREATE INDEX "IX_Passkeys_RpId" ON "Passkeys" ("RpId"); INSERT INTO "__EFMigrationsHistory" ("MigrationId", "ProductVersion") -VALUES ('20251007085746_1.6.0-AddPasskeys', '9.0.4'); +VALUES ('20251014122838_1.6.0-AddPasskeys', '9.0.4'); COMMIT; `; @@ -851,7 +851,7 @@ PRAGMA foreign_keys = ON; CREATE TABLE "Passkeys" ( "Id" TEXT NOT NULL CONSTRAINT "PK_Passkeys" PRIMARY KEY, "RpId" TEXT COLLATE NOCASE NOT NULL, - "UserId" TEXT NULL, + "UserHandle" BLOB NOT NULL, "PublicKey" TEXT NOT NULL, "PrivateKey" TEXT NOT NULL, "PrfKey" BLOB NULL, @@ -869,7 +869,7 @@ CREATE INDEX "IX_Passkeys_CredentialId" ON "Passkeys" ("CredentialId"); CREATE INDEX "IX_Passkeys_RpId" ON "Passkeys" ("RpId"); INSERT INTO "__EFMigrationsHistory" ("MigrationId", "ProductVersion") -VALUES ('20251007085746_1.6.0-AddPasskeys', '9.0.4'); +VALUES ('20251014122838_1.6.0-AddPasskeys', '9.0.4'); COMMIT;` }; diff --git a/apps/server/AliasVault.Client/wwwroot/js/dist/shared/vault-sql/index.mjs b/apps/server/AliasVault.Client/wwwroot/js/dist/shared/vault-sql/index.mjs index 0899a348b..28c6dfc06 100644 --- a/apps/server/AliasVault.Client/wwwroot/js/dist/shared/vault-sql/index.mjs +++ b/apps/server/AliasVault.Client/wwwroot/js/dist/shared/vault-sql/index.mjs @@ -435,7 +435,7 @@ PRAGMA foreign_keys = ON; CREATE TABLE "Passkeys" ( "Id" TEXT NOT NULL CONSTRAINT "PK_Passkeys" PRIMARY KEY, "RpId" TEXT COLLATE NOCASE NOT NULL, - "UserId" TEXT NULL, + "UserHandle" BLOB NOT NULL, "PublicKey" TEXT NOT NULL, "PrivateKey" TEXT NOT NULL, "PrfKey" BLOB NULL, @@ -453,7 +453,7 @@ CREATE INDEX "IX_Passkeys_CredentialId" ON "Passkeys" ("CredentialId"); CREATE INDEX "IX_Passkeys_RpId" ON "Passkeys" ("RpId"); INSERT INTO "__EFMigrationsHistory" ("MigrationId", "ProductVersion") -VALUES ('20251007085746_1.6.0-AddPasskeys', '9.0.4'); +VALUES ('20251014122838_1.6.0-AddPasskeys', '9.0.4'); COMMIT; `; @@ -822,7 +822,7 @@ PRAGMA foreign_keys = ON; CREATE TABLE "Passkeys" ( "Id" TEXT NOT NULL CONSTRAINT "PK_Passkeys" PRIMARY KEY, "RpId" TEXT COLLATE NOCASE NOT NULL, - "UserId" TEXT NULL, + "UserHandle" BLOB NOT NULL, "PublicKey" TEXT NOT NULL, "PrivateKey" TEXT NOT NULL, "PrfKey" BLOB NULL, @@ -840,7 +840,7 @@ CREATE INDEX "IX_Passkeys_CredentialId" ON "Passkeys" ("CredentialId"); CREATE INDEX "IX_Passkeys_RpId" ON "Passkeys" ("RpId"); INSERT INTO "__EFMigrationsHistory" ("MigrationId", "ProductVersion") -VALUES ('20251007085746_1.6.0-AddPasskeys', '9.0.4'); +VALUES ('20251014122838_1.6.0-AddPasskeys', '9.0.4'); COMMIT;` }; diff --git a/apps/server/Databases/AliasClientDb/Migrations/20251007085746_1.6.0-AddPasskeys.Designer.cs b/apps/server/Databases/AliasClientDb/Migrations/20251014122838_1.6.0-AddPasskeys.Designer.cs similarity index 98% rename from apps/server/Databases/AliasClientDb/Migrations/20251007085746_1.6.0-AddPasskeys.Designer.cs rename to apps/server/Databases/AliasClientDb/Migrations/20251014122838_1.6.0-AddPasskeys.Designer.cs index 8eb5f5a4e..dace3bc2d 100644 --- a/apps/server/Databases/AliasClientDb/Migrations/20251007085746_1.6.0-AddPasskeys.Designer.cs +++ b/apps/server/Databases/AliasClientDb/Migrations/20251014122838_1.6.0-AddPasskeys.Designer.cs @@ -11,7 +11,7 @@ using Microsoft.EntityFrameworkCore.Storage.ValueConversion; namespace AliasClientDb.Migrations { [DbContext(typeof(AliasClientDbContext))] - [Migration("20251007085746_1.6.0-AddPasskeys")] + [Migration("20251014122838_1.6.0-AddPasskeys")] partial class _160AddPasskeys { /// @@ -215,9 +215,9 @@ namespace AliasClientDb.Migrations b.Property("UpdatedAt") .HasColumnType("TEXT"); - b.Property("UserId") - .HasMaxLength(255) - .HasColumnType("TEXT"); + b.Property("UserHandle") + .IsRequired() + .HasColumnType("BLOB"); b.HasKey("Id"); diff --git a/apps/server/Databases/AliasClientDb/Migrations/20251007085746_1.6.0-AddPasskeys.cs b/apps/server/Databases/AliasClientDb/Migrations/20251014122838_1.6.0-AddPasskeys.cs similarity index 98% rename from apps/server/Databases/AliasClientDb/Migrations/20251007085746_1.6.0-AddPasskeys.cs rename to apps/server/Databases/AliasClientDb/Migrations/20251014122838_1.6.0-AddPasskeys.cs index 3134c085a..f26b0a4f5 100644 --- a/apps/server/Databases/AliasClientDb/Migrations/20251007085746_1.6.0-AddPasskeys.cs +++ b/apps/server/Databases/AliasClientDb/Migrations/20251014122838_1.6.0-AddPasskeys.cs @@ -12,7 +12,7 @@ namespace AliasClientDb.Migrations /// protected override void Up(MigrationBuilder migrationBuilder) { - // Simple Database Constraint Repair Script + // Simple Database Constraint Repair Script // Recreates all tables with proper PK/FK constraints while preserving data migrationBuilder.Sql(@" PRAGMA foreign_keys = OFF; @@ -197,7 +197,7 @@ PRAGMA foreign_keys = ON; { Id = table.Column(type: "TEXT", nullable: false), RpId = table.Column(type: "TEXT", maxLength: 255, nullable: false, collation: "NOCASE"), - UserId = table.Column(type: "TEXT", maxLength: 255, nullable: true), + UserHandle = table.Column(type: "BLOB", nullable: false), PublicKey = table.Column(type: "TEXT", nullable: false), PrivateKey = table.Column(type: "TEXT", nullable: false), PrfKey = table.Column(type: "BLOB", maxLength: 64, nullable: true), diff --git a/apps/server/Databases/AliasClientDb/Migrations/AliasClientDbContextModelSnapshot.cs b/apps/server/Databases/AliasClientDb/Migrations/AliasClientDbContextModelSnapshot.cs index b42f2f5cc..777f246cb 100644 --- a/apps/server/Databases/AliasClientDb/Migrations/AliasClientDbContextModelSnapshot.cs +++ b/apps/server/Databases/AliasClientDb/Migrations/AliasClientDbContextModelSnapshot.cs @@ -212,9 +212,9 @@ namespace AliasClientDb.Migrations b.Property("UpdatedAt") .HasColumnType("TEXT"); - b.Property("UserId") - .HasMaxLength(255) - .HasColumnType("TEXT"); + b.Property("UserHandle") + .IsRequired() + .HasColumnType("BLOB"); b.HasKey("Id"); diff --git a/apps/server/Databases/AliasClientDb/Passkey.cs b/apps/server/Databases/AliasClientDb/Passkey.cs index dbb275417..c5744e7e4 100644 --- a/apps/server/Databases/AliasClientDb/Passkey.cs +++ b/apps/server/Databases/AliasClientDb/Passkey.cs @@ -30,10 +30,10 @@ public class Passkey : SyncableEntity public string RpId { get; set; } = string.Empty; /// - /// Gets or sets the user ID provided by the relying party. + /// Gets or sets the user handle which represents the user ID provided by the relying party. /// - [MaxLength(255)] - public string? UserId { get; set; } + [Required] + public byte[] UserHandle { get; set; } = null!; /// /// Gets or sets the public key. diff --git a/apps/server/Databases/AliasClientDb/Scripts/MigrationSql/000_FullSchema.sql b/apps/server/Databases/AliasClientDb/Scripts/MigrationSql/000_FullSchema.sql index b64ec6e3b..b6c7c6544 100644 --- a/apps/server/Databases/AliasClientDb/Scripts/MigrationSql/000_FullSchema.sql +++ b/apps/server/Databases/AliasClientDb/Scripts/MigrationSql/000_FullSchema.sql @@ -429,7 +429,7 @@ PRAGMA foreign_keys = ON; CREATE TABLE "Passkeys" ( "Id" TEXT NOT NULL CONSTRAINT "PK_Passkeys" PRIMARY KEY, "RpId" TEXT COLLATE NOCASE NOT NULL, - "UserId" TEXT NULL, + "UserHandle" BLOB NOT NULL, "PublicKey" TEXT NOT NULL, "PrivateKey" TEXT NOT NULL, "PrfKey" BLOB NULL, @@ -447,7 +447,7 @@ CREATE INDEX "IX_Passkeys_CredentialId" ON "Passkeys" ("CredentialId"); CREATE INDEX "IX_Passkeys_RpId" ON "Passkeys" ("RpId"); INSERT INTO "__EFMigrationsHistory" ("MigrationId", "ProductVersion") -VALUES ('20251007085746_1.6.0-AddPasskeys', '9.0.4'); +VALUES ('20251014122838_1.6.0-AddPasskeys', '9.0.4'); COMMIT; diff --git a/apps/server/Databases/AliasClientDb/Scripts/MigrationSql/010_20250310131554_1.5.0-AddTotpCodes_to_20251007085746_1.6.0-AddPasskeys.sql b/apps/server/Databases/AliasClientDb/Scripts/MigrationSql/010_20250310131554_1.5.0-AddTotpCodes_to_20251014122838_1.6.0-AddPasskeys.sql similarity index 98% rename from apps/server/Databases/AliasClientDb/Scripts/MigrationSql/010_20250310131554_1.5.0-AddTotpCodes_to_20251007085746_1.6.0-AddPasskeys.sql rename to apps/server/Databases/AliasClientDb/Scripts/MigrationSql/010_20250310131554_1.5.0-AddTotpCodes_to_20251014122838_1.6.0-AddPasskeys.sql index 7cdabb097..569159482 100644 --- a/apps/server/Databases/AliasClientDb/Scripts/MigrationSql/010_20250310131554_1.5.0-AddTotpCodes_to_20251007085746_1.6.0-AddPasskeys.sql +++ b/apps/server/Databases/AliasClientDb/Scripts/MigrationSql/010_20250310131554_1.5.0-AddTotpCodes_to_20251014122838_1.6.0-AddPasskeys.sql @@ -178,7 +178,7 @@ PRAGMA foreign_keys = ON; CREATE TABLE "Passkeys" ( "Id" TEXT NOT NULL CONSTRAINT "PK_Passkeys" PRIMARY KEY, "RpId" TEXT COLLATE NOCASE NOT NULL, - "UserId" TEXT NULL, + "UserHandle" BLOB NOT NULL, "PublicKey" TEXT NOT NULL, "PrivateKey" TEXT NOT NULL, "PrfKey" BLOB NULL, @@ -196,7 +196,7 @@ CREATE INDEX "IX_Passkeys_CredentialId" ON "Passkeys" ("CredentialId"); CREATE INDEX "IX_Passkeys_RpId" ON "Passkeys" ("RpId"); INSERT INTO "__EFMigrationsHistory" ("MigrationId", "ProductVersion") -VALUES ('20251007085746_1.6.0-AddPasskeys', '9.0.4'); +VALUES ('20251014122838_1.6.0-AddPasskeys', '9.0.4'); COMMIT; diff --git a/shared/models/src/vault/Passkey.ts b/shared/models/src/vault/Passkey.ts index 4b44b6db6..f2bf76afc 100644 --- a/shared/models/src/vault/Passkey.ts +++ b/shared/models/src/vault/Passkey.ts @@ -11,8 +11,8 @@ export type Passkey = { /** The relying party identifier */ RpId: string; - /** The user ID provided by the relying party */ - UserId?: string | null; + /** The user handle (user ID) provided by the relying party - stored as byte array (BLOB) */ + UserHandle?: Uint8Array | number[] | null; /** The public key */ PublicKey: string; diff --git a/shared/vault-sql/src/sql/SqlConstants.ts b/shared/vault-sql/src/sql/SqlConstants.ts index fa1f16922..ea2981aa8 100644 --- a/shared/vault-sql/src/sql/SqlConstants.ts +++ b/shared/vault-sql/src/sql/SqlConstants.ts @@ -436,7 +436,7 @@ PRAGMA foreign_keys = ON; CREATE TABLE "Passkeys" ( "Id" TEXT NOT NULL CONSTRAINT "PK_Passkeys" PRIMARY KEY, "RpId" TEXT COLLATE NOCASE NOT NULL, - "UserId" TEXT NULL, + "UserHandle" BLOB NOT NULL, "PublicKey" TEXT NOT NULL, "PrivateKey" TEXT NOT NULL, "PrfKey" BLOB NULL, @@ -454,7 +454,7 @@ CREATE INDEX "IX_Passkeys_CredentialId" ON "Passkeys" ("CredentialId"); CREATE INDEX "IX_Passkeys_RpId" ON "Passkeys" ("RpId"); INSERT INTO "__EFMigrationsHistory" ("MigrationId", "ProductVersion") -VALUES ('20251007085746_1.6.0-AddPasskeys', '9.0.4'); +VALUES ('20251014122838_1.6.0-AddPasskeys', '9.0.4'); COMMIT; `; @@ -827,7 +827,7 @@ PRAGMA foreign_keys = ON; CREATE TABLE "Passkeys" ( "Id" TEXT NOT NULL CONSTRAINT "PK_Passkeys" PRIMARY KEY, "RpId" TEXT COLLATE NOCASE NOT NULL, - "UserId" TEXT NULL, + "UserHandle" BLOB NOT NULL, "PublicKey" TEXT NOT NULL, "PrivateKey" TEXT NOT NULL, "PrfKey" BLOB NULL, @@ -845,7 +845,7 @@ CREATE INDEX "IX_Passkeys_CredentialId" ON "Passkeys" ("CredentialId"); CREATE INDEX "IX_Passkeys_RpId" ON "Passkeys" ("RpId"); INSERT INTO "__EFMigrationsHistory" ("MigrationId", "ProductVersion") -VALUES ('20251007085746_1.6.0-AddPasskeys', '9.0.4'); +VALUES ('20251014122838_1.6.0-AddPasskeys', '9.0.4'); COMMIT;`, };