# How DBX Performs AI-Driven SQL Generation with Built-in Safety Checks

> Learn how DBX performs AI-driven SQL generation with robust built-in safety checks. Discover how it blocks dangerous keywords and multi-statements for secure database operations.

- Repository: [skyler/dbx](https://github.com/t8y2/dbx)
- Tags: how-to-guide
- Published: 2026-07-05

---

**DBX uses a dedicated AI skill to generate SQL via LLM prompts and enforces read-only safety checks through a centralized `sqlSafetyFromEnv` evaluator that blocks dangerous keywords and multi-statements unless explicitly overridden by environment variables.**

The DBX project (`t8y2/dbx`) implements a secure AI-driven SQL generation system that prevents accidental data destruction while maintaining flexibility for power users. By combining structured prompt engineering with a centralized safety evaluator, DBX ensures that generated SQL never executes destructive operations without explicit user consent.

## The AI Skill Architecture for SQL Generation

DBX ships a dedicated **AI skill** for the `generate` action. When users request query generation through the CLI, desktop UI, or an AI-agent, the system constructs a system prompt that instructs the LLM to return a single fenced SQL code block containing the statement.

### Prompt Engineering and the Generate Skill

In [`apps/desktop/src/lib/ai/aiSkills.ts`](https://github.com/t8y2/dbx/blob/main/apps/desktop/src/lib/ai/aiSkills.ts), the skill definition builds prompts that require the model to output strictly formatted SQL within triple-backtick blocks. This structured approach ensures predictable parsing while the accompanying **risk policy** (`readonly_preferred`) signals the system's security posture to downstream components. The skill can be invoked via `aiSkillForAction('generate')`, which returns the configuration used by `executeAiSkill` to orchestrate the LLM call.

## The SQL Safety Evaluation Pipeline

Before any generated SQL executes, DBX runs the **SQL safety evaluator** (`sqlSafetyFromEnv`) defined in [`packages/node-core/src/sql-safety.ts`](https://github.com/t8y2/dbx/blob/main/packages/node-core/src/sql-safety.ts). This centralized function enforces four critical policies that apply universally across the codebase.

### Read-Only Default Policy

By default, DBX operates in read-only mode. The evaluator returns `"MCP SQL execution is read-only for this session. Set DBX_MCP_ALLOW_WRITES=1 to allow write statements."` whenever a write operation is detected in a session not explicitly authorized for mutations.

### Dangerous Keyword Detection

The system maintains a blocklist of destructive operations. If the generated SQL contains keywords such as `DROP`, `DELETE`, `ALTER`, or `TRUNCATE`, the evaluator immediately returns `"Dangerous SQL keyword \"DROP\" is blocked."` (or the specific keyword detected), halting execution before the query reaches the database.

### Multi-Statement Restrictions

DBX prohibits multiple SQL statements within a single query to prevent injection-style attacks or unintended chained operations. Attempting to submit multiple statements returns `"Only one SQL statement is allowed per query."` unless explicitly overridden.

### Environment-Controlled Overrides

Power users can bypass restrictions using environment variables parsed via `parseBooleanEnv`:

- `DBX_MCP_ALLOW_WRITES=1` — Permits write operations while maintaining other safety checks
- `DBX_MCP_ALLOW_DANGEROUS_SQL=1` — Allows dangerous keywords and multi-statement blocks

When these variables are set, the safety layer relaxes the corresponding checks but continues to surface clear warnings to the user.

## Safety Enforcement Across All Execution Paths

The `sqlSafetyFromEnv` check is invoked **everywhere DBX may execute SQL**, ensuring consistent policy enforcement regardless of the entry point.

### MCP Server Endpoint Protection

In [`packages/mcp-server/src/index.ts`](https://github.com/t8y2/dbx/blob/main/packages/mcp-server/src/index.ts), the `dbx_execute_query` endpoint passes every request through the safety evaluator before execution. If the check returns `allowed: false`, the server responds with a structured error object containing `code: "SQL_BLOCKED"` and the specific safety violation message, preventing the query from reaching the database driver.

### CLI Safety Integration

The CLI implementation in [`packages/cli/src/cli.ts`](https://github.com/t8y2/dbx/blob/main/packages/cli/src/cli.ts) runs the same safety routine before transmitting queries to the backend. When a check fails, the CLI prints a JSON error to stderr with `code: "SQL_BLOCKED"`, allowing scripts to programmatically detect and handle safety violations.

### AI-Agent Auto-Execution Logic

For AI-agent workflows, the runner evaluates safety results before auto-executing generated SQL. As implemented in the test suite at [`packages/app-tests/aiAgentStepPresentation.test.ts`](https://github.com/t8y2/dbx/blob/main/packages/app-tests/aiAgentStepPresentation.test.ts), when `allowed` is `false`, the agent falls back to "show-only" mode, displaying the generated SQL and the safety reason without executing it. Only when `allowed` is `true` does the agent proceed with automatic execution.

## Working with DBX SQL Generation

### Generate SQL from the CLI (Read-Only Default)

```bash
$ dbx generate "show me the top 10 customers by order total"

```

**Result (`stdout`):**

```sql
SELECT c.id, c.name, SUM(o.amount) AS total
FROM customers c
JOIN orders o ON o.customer_id = c.id
GROUP BY c.id, c.name
ORDER BY total DESC
LIMIT 10;

```

### Attempt a Dangerous Write Without Override

```bash
$ dbx generate "delete all rows from users"

```

**Result (`stderr`):**

```json
{
  "error": {
    "code": "SQL_BLOCKED",
    "message": "Dangerous SQL keyword \"DELETE\" is blocked."
  }
}

```

### Enable Dangerous SQL via Environment Variable

```bash
$ DBX_MCP_ALLOW_DANGEROUS_SQL=1 dbx generate "delete all rows from users"

```

With this flag, the SQL is returned and the CLI proceeds to execute it if the `--run` flag is supplied.

### AI-Agent Auto-Execution (Generate Mode)

```typescript
import { executeAiSkill } from '@/lib/ai/ai';

const result = await executeAiSkill('generate', 'show me revenue per region');

if (result.type === 'sql' && result.safety.allowed) {
  // DBX will automatically run the query and display the result.
}

```

The `executeAiSkill` function internally calls `aiSkillForAction('generate')`, builds the prompt, receives the LLM response, then runs `sqlSafetyFromEnv` before any database execution occurs.

## Summary

- DBX generates SQL through a dedicated **AI skill** defined in [`apps/desktop/src/lib/ai/aiSkills.ts`](https://github.com/t8y2/dbx/blob/main/apps/desktop/src/lib/ai/aiSkills.ts) that instructs LLMs to return fenced SQL code blocks.
- The **`sqlSafetyFromEnv`** evaluator in [`packages/node-core/src/sql-safety.ts`](https://github.com/t8y2/dbx/blob/main/packages/node-core/src/sql-safety.ts) enforces read-only defaults and blocks dangerous keywords like `DROP` and `DELETE`.
- **Multi-statement queries** are prohibited unless `DBX_MCP_ALLOW_DANGEROUS_SQL=1` is set.
- Safety checks run in the MCP server ([`packages/mcp-server/src/index.ts`](https://github.com/t8y2/dbx/blob/main/packages/mcp-server/src/index.ts)), CLI ([`packages/cli/src/cli.ts`](https://github.com/t8y2/dbx/blob/main/packages/cli/src/cli.ts)), and AI-agent execution paths, returning structured `SQL_BLOCKED` errors when violated.
- The **risk policy** `readonly_preferred` ensures generated SQL defaults to safe, read-only operations while allowing explicit user overrides.

## Frequently Asked Questions

### What happens if DBX generates a DROP statement?

The safety evaluator detects the dangerous keyword and returns a structured error with code `SQL_BLOCKED`, preventing execution unless `DBX_MCP_ALLOW_DANGEROUS_SQL=1` is explicitly configured in the environment.

### How do I enable write operations in DBX?

Set the environment variable `DBX_MCP_ALLOW_WRITES=1` to allow write statements for the session. To bypass all restrictions including multi-statement blocks, set `DBX_MCP_ALLOW_DANGEROUS_SQL=1`, though this requires explicit acknowledgment of the security risks.

### Can DBX execute multiple SQL statements in one query?

By default, no. The system restricts queries to single statements to prevent injection attacks. Enable multi-statement support by setting `DBX_MCP_ALLOW_DANGEROUS_SQL=1`, though this is strongly discouraged for production environments.

### Where is the safety check implemented in the codebase?

The core logic resides in [`packages/node-core/src/sql-safety.ts`](https://github.com/t8y2/dbx/blob/main/packages/node-core/src/sql-safety.ts) as the `sqlSafetyFromEnv` function. This module is imported and invoked by the MCP server entry point ([`packages/mcp-server/src/index.ts`](https://github.com/t8y2/dbx/blob/main/packages/mcp-server/src/index.ts)), the CLI handler ([`packages/cli/src/cli.ts`](https://github.com/t8y2/dbx/blob/main/packages/cli/src/cli.ts)), and the AI-agent runner components.