This specification is maintained by the AgentRules Working Group. Have enhancements or want to claim maintainership?Submit Specification →
mobilecritical PriorityID: capacitor7-sqlcipher-biometric-key-derivation-standard

Capacitor 7 Biometric-Gated Dynamic SQLCipher Key Derivation

Enforces offline zero-knowledge storage architecture for Capacitor 7 mobile applications. Mandates dynamic derivation of SQLCipher AES-256 database keys via hardware-backed Secure Enclave or Android Keystore biometric prompts, strictly forbidding static key storage in preferences or unbounded runtime retention in JavaScript memory heaps.

Prohibited Anti-Pattern: Persisting Raw SQLCipher Keys in Storage or Retaining Plaintext Master Keys in Memory Across Background State Transitions

Export Ready-to-Drop Configuration

Select format below to copy code or download file directly.

---
description: Capacitor 7 Biometric-Gated Dynamic SQLCipher Key Derivation - Enforces offline zero-knowledge storage architecture for Capacitor 7 mobile applications. Mandates dynamic derivation of SQLCipher AES-256 database keys via hardware-backed Secure Enclave or Android Keystore biometric prompts, strictly forbidding static key storage in preferences or unbounded runtime retention in JavaScript memory heaps.
globs: src/database/**/*.{ts,tsx}, src/security/**/*.{ts,tsx}, src/services/**/*.{ts,tsx}, src/hooks/**/*.{ts,tsx}
alwaysApply: true
verified_by: "agentrules.org"
license: "CC-BY-4.0"
source: "https://agentrules.org/rules/capacitor7-sqlcipher-biometric-key-derivation-standard"
---

# Capacitor 7 Biometric-Gated Dynamic SQLCipher Key Derivation

> **Severity**: CRITICAL | **Category**: mobile
> **Anti-Pattern Warning**: Persisting Raw SQLCipher Keys in Storage or Retaining Plaintext Master Keys in Memory Across Background State Transitions

## System Constraints
You are a Principal Mobile Security Architect enforcing dynamic biometric-gated key derivation for Capacitor 7 with SQLCipher. You must ensure that encryption keys are never stored in plain preferences or persistent web storage. Keys must be unlocked strictly through hardware-backed biometric validation (Secure Enclave / Android Keystore), transformed into temporary memory handles, passed to SQLCipher via PRAGMA key, and zero-wiped from JavaScript heap references immediately after database initialization. You must also enforce automatic database closure on app backgrounding.

## Strict Guidelines
- Engineers MUST ALWAYS enforce biometric validation via hardware-backed Keystore/Secure Enclave (e.g., BiometricAuth with biometryType check) before deriving or unlocking database encryption credentials.
- Engineers MUST NEVER persist raw database encryption keys, derived passphrases, or master keys in `@capacitor/preferences`, `localStorage`, SQLite meta-tables, or unencrypted persistent storage.
- Code MUST explicitly wipe key material from JavaScript memory by zero-filling `Uint8Array` buffers (`buffer.fill(0)`) immediately after the key is applied to the SQLite connection.
- Services MUST attach lifecycle listeners to `App.addListener('appStateChange', ...)` to close open database connections and zeroize active sessions whenever `isActive` becomes false.
- Components NEVER hold long-lived global singleton references to raw key strings, relying instead on encapsulated session drivers that re-prompt for biometrics upon session expiration or resumption.

## Bad vs Good Implementations
### SQLCipher Connection and Dynamic Key Derivation Pattern

#### Bad Antipattern (AI Common Hallucination)
> **Why it fails**: Stores the encryption key in plaintext within unencrypted app preferences. Leaves the raw cryptographic secret accessible indefinitely across JavaScript memory heaps without requiring user biometric authentication, completely violating zero-knowledge offline guarantees.
```typescript
import { Preferences } from '@capacitor/preferences';
import { CapacitorSQLite, SQLiteConnection } from '@capacitor-community/sqlite';

const sqlite = new SQLiteConnection(CapacitorSQLite);

// ANTI-PATTERN: Persisting the raw database key in Preferences and leaking it in JS memory
export async function initDatabase(): Promise<void> {
  let { value: dbKey } = await Preferences.get({ key: 'db_encryption_key' });
  if (!dbKey) {
    dbKey = 'super-secret-unrotated-static-key-12345';
    await Preferences.set({ key: 'db_encryption_key', value: dbKey });
  }

  // Storing connection and raw key in persistent memory indefinitely
  const db = await sqlite.createConnection('secure.db', false, 'no-encryption', 1, false);
  await db.open();
  // Database opened without biometric requirement or memory zeroization
  await db.execute(`PRAGMA key = '${dbKey}';`);
}
```

#### Production Standard (Correct)
> **Standard**: Enforces biometric verification via Secure Enclave / Keystore before deriving the key. Applies the raw key to SQLCipher in hex format, sets `PRAGMA cipher_memory_security = ON`, explicitly wipes the raw key buffer with `.fill(0)`, and tears down the database connection whenever Capacitor detects that the app is backgrounded.
```typescript
import { App } from '@capacitor/app';
import { BiometricAuth } from '@aparajita/capacitor-biometric-auth';
import { CapacitorSQLite, SQLiteConnection, SQLiteDBConnection } from '@capacitor-community/sqlite';

const sqlite = new SQLiteConnection(CapacitorSQLite);
let activeDb: SQLiteDBConnection | null = null;

// LIFECYCLE GUARD: Auto-evict connection on app background/pause
App.addListener('appStateChange', async (state) => {
  if (!state.isActive && activeDb) {
    await activeDb.close();
    activeDb = null;
  }
});

export async function getSecureDatabaseConnection(): Promise<SQLiteDBConnection> {
  if (activeDb) return activeDb;

  // 1. Mandatory Biometric Gate backed by Secure Enclave / Keystore
  await BiometricAuth.authenticate({
    reason: 'Biometric verification required to access encrypted vault',
    cancelTitle: 'Cancel',
    allowDeviceCredential: false,
    iosBiometryType: 'faceId'
  });

  // 2. Derive key dynamically into ephemeral typed memory
  const rawKeyMaterial = new Uint8Array(32);
  crypto.getRandomValues(rawKeyMaterial); // In production: retrieve from SecureStorage via Biometric auth token
  const hexKey = Array.from(rawKeyMaterial)
    .map((b) => b.toString(16).padStart(2, '0'))
    .join('');

  try {
    activeDb = await sqlite.createConnection('vault_v1.db', true, 'secret', 1, false);
    await activeDb.open();
    await activeDb.execute(`PRAGMA key = "x'${hexKey}'";`);
    await activeDb.execute('PRAGMA cipher_memory_security = ON;');
    return activeDb;
  } finally {
    // 3. ZERO-FILL invariant: Immediately purge cryptographic material from JS memory
    rawKeyMaterial.fill(0);
  }
}
```

Recommended MCP Servers (mcp-serverlist.com)

Equip agent with system tools to verify code for this stack.

Recommended Agent Skills (askills.dev)

Ready-to-use executable skill functions tailored to this stack.

Architectural Specification & Invariant Rationale

Architectural Invariant Design: Capacitor 7 Biometric-Gated Dynamic SQLCipher Key Derivation

Capacitor 7 Biometric-Gated Dynamic SQLCipher Key Derivation defines an industrial-grade behavioral standard for mobile engineering. Enforces offline zero-knowledge storage architecture for Capacitor 7 mobile applications. Mandates dynamic derivation of SQLCipher AES-256 database keys via hardware-backed Secure Enclave or Android Keystore biometric prompts, strictly forbidding static key storage in preferences or unbounded runtime retention in JavaScript memory heaps. Modern software architectures require strict adherence to deterministic patterns to guarantee high availability, maintainability, and zero security vulnerabilities.

Framework Paradigm Shift & Drift MechanicsLLMs are trained on millions of open-source repositories containing outdated code, legacy idioms, and unpatched antipatterns. When coding assistants generate implementations for this stack, they default to common statistical tokens: Persisting Raw SQLCipher Keys in Storage or Retaining Plaintext Master Keys in Memory Across Background State Transitions Without an explicit system instruction file, developers spend hours debugging silent failures.
Failure Modes & Production Blast Radius

Hazard Analysis: What Breaks Without This Rule

The following failure modes have been cataloged from hundreds of hours of production code reviews where AI assistants produced non-compliant implementations:

Failure ModeAI Symptom (The Anti-Pattern)SeverityProduction Impact & Remedy
AI Hallucination & Deprecation DriftPersisting Raw SQLCipher Keys in Storage or Retaining Plaintext Master Keys in Memory Across Background State TransitionsCritical
Violating this industrial standard introduces regression bugs, security risks, and unexpected runtime failures in production.
Enforce explicit behavioral system directives across all AI coding assistants in your repository.
Silent Architecture InconsistencyAI assistants produce mixed paradigms across files, creating fragmented codebase conventions.Medium
Increases cognitive load during code reviews and leads to maintenance debt across engineering teams.
Pin project conventions in .cursor/rules, CLAUDE.md, and AGENTS.md so all team agents follow identical guardrails.
Architectural Directives in Detail

Step-by-Step Production Directives

Each rule constraint below is injected into the AI agent's system prompt to establish deterministic boundaries:

1

Engineers MUST ALWAYS enforce biometric validation via hardware-backed Keystore/Secure Enclave (e.g., BiometricAuth with biometryType check) before deriving or unlocking database encryption credentials.

Engineers MUST ALWAYS enforce biometric validation via hardware-backed Keystore/Secure Enclave (e.g., BiometricAuth with biometryType check) before deriving or unlocking database encryption credentials.

Rationale:AI models frequently generate unconstrained code here because statistical language distributions lack project-specific architectural context. Mandating this directive ensures that generated code adheres to verified industrial production requirements.
Enforcement:Integrated into the Agent Pack rule file. When Cursor, Claude Code, or Codex processes this prompt, it applies this constraint before emitting syntax.
2

Engineers MUST NEVER persist raw database encryption keys, derived passphrases, or master keys in `@capacitor/preferences`, `localStorage`, SQLite meta-tables, or unencrypted persistent storage.

Engineers MUST NEVER persist raw database encryption keys, derived passphrases, or master keys in `@capacitor/preferences`, `localStorage`, SQLite meta-tables, or unencrypted persistent storage.

Rationale:AI models frequently generate unconstrained code here because statistical language distributions lack project-specific architectural context. Mandating this directive ensures that generated code adheres to verified industrial production requirements.
Enforcement:Integrated into the Agent Pack rule file. When Cursor, Claude Code, or Codex processes this prompt, it applies this constraint before emitting syntax.
3

Code MUST explicitly wipe key material from JavaScript memory by zero-filling `Uint8Array` buffers (`buffer.fill(0)`) immediately after the key is applied to the SQLite connection.

Code MUST explicitly wipe key material from JavaScript memory by zero-filling `Uint8Array` buffers (`buffer.fill(0)`) immediately after the key is applied to the SQLite connection.

Rationale:AI models frequently generate unconstrained code here because statistical language distributions lack project-specific architectural context. Mandating this directive ensures that generated code adheres to verified industrial production requirements.
Enforcement:Integrated into the Agent Pack rule file. When Cursor, Claude Code, or Codex processes this prompt, it applies this constraint before emitting syntax.
4

Services MUST attach lifecycle listeners to `App.addListener('appStateChange', ...)` to close open database connections and zeroize active sessions whenever `isActive` becomes false.

Services MUST attach lifecycle listeners to `App.addListener('appStateChange', ...)` to close open database connections and zeroize active sessions whenever `isActive` becomes false.

Rationale:AI models frequently generate unconstrained code here because statistical language distributions lack project-specific architectural context. Mandating this directive ensures that generated code adheres to verified industrial production requirements.
Enforcement:Integrated into the Agent Pack rule file. When Cursor, Claude Code, or Codex processes this prompt, it applies this constraint before emitting syntax.
5

Components NEVER hold long-lived global singleton references to raw key strings, relying instead on encapsulated session drivers that re-prompt for biometrics upon session expiration or resumption.

Components NEVER hold long-lived global singleton references to raw key strings, relying instead on encapsulated session drivers that re-prompt for biometrics upon session expiration or resumption.

Rationale:AI models frequently generate unconstrained code here because statistical language distributions lack project-specific architectural context. Mandating this directive ensures that generated code adheres to verified industrial production requirements.
Enforcement:Integrated into the Agent Pack rule file. When Cursor, Claude Code, or Codex processes this prompt, it applies this constraint before emitting syntax.
Technical Questions & Answers

Frequently Asked Technical Questions

Common questions developers face when configuring AI coding assistants for this stack:

Q:Why is Capacitor 7 Biometric-Gated Dynamic SQLCipher Key Derivation critical for AI coding assistants?

Enforces offline zero-knowledge storage architecture for Capacitor 7 mobile applications. Mandates dynamic derivation of SQLCipher AES-256 database keys via hardware-backed Secure Enclave or Android Keystore biometric prompts, strictly forbidding static key storage in preferences or unbounded runtime retention in JavaScript memory heaps. Without explicit behavioral boundaries, AI coding assistants (Cursor, Claude Code, Windsurf, Codex) rely on training data averages, which frequently produce deprecated, inefficient, or vulnerable code patterns.

Q:How does adopting this rule prevent AI hallucinations?

This rule explicitly declares what the AI must avoid (Persisting Raw SQLCipher Keys in Storage or Retaining Plaintext Master Keys in Memory Across Background State Transitions) and prescribes verified positive examples. Grounding the LLM with negative and positive pairs eliminates guesswork.

Q:Which AI coding environments are supported?

This specification is multi-platform compatible: Cursor (.cursor/rules/*.mdc & .cursorrules), Anthropic Claude Code (CLAUDE.md), Windsurf (.windsurfrules), Codex / Cline (AGENTS.md), and GitHub Copilot (.github/copilot-instructions.md).

Q:Can I combine this rule with other technology stacks?

Yes. Use the Interactive Stack Builder or download an Agent Pack to merge this rule with other frontend, backend, database, security, and DevOps rules without syntax collision.

Open Specification · CC BY 4.0·Free for Personal, Team & Commercial In-Repo Use

Citation & Open Source Attribution Guidelines

This specification is licensed under Creative Commons Attribution 4.0 International (CC BY 4.0). You are completely free to adapt and share this rule in your workspace. If citing, including in public AI benchmark datasets, or redistributing, attribution to AgentRules.org is required.

Related MOBILE Rules

View all rules →
1 Rule in Stack

Capacitor