> ## Documentation Index
> Fetch the complete documentation index at: https://docs.pgconsole.com/llms.txt
> Use this file to discover all available pages before exploring further.

# Audit Log

pgconsole emits audit logs as JSON lines to stdout, allowing you to capture and process them with your existing log infrastructure. It also keeps audit entries in memory so they can be inspected from the `/audit-log` page.

## In-App Audit Log

The `/audit-log` page has two tabs:

* **Connection** — SQL execution and data export entries for the selected connection, newest first. Requires `admin` permission on that connection.
* **System** — instance-level events that aren't tied to a connection (`auth.login` / `auth.logout`), including the auth provider and source IP. Only visible to an instance **owner**, since these events span all users.

Entries are stored in memory only. They are lost when the server restarts. By default, pgconsole retains entries indefinitely while the process is running, so memory usage grows with audit volume. For high-traffic deployments, set `retention_days` to prune older entries:

```toml pgconsole.toml theme={null}
[general.audit]
retention_days = 30
```

See the [configuration reference](/configuration/config#audit-log) for details.

## Events

| Event         | Description                             |
| ------------- | --------------------------------------- |
| `auth.login`  | User login attempt (success or failure) |
| `auth.logout` | User logout                             |
| `sql.execute` | SQL query execution                     |
| `data.export` | Data exported (e.g., CSV download)      |

## Log Format

All audit events are JSON objects with a common structure:

```json theme={null}
{
  "type": "audit",
  "ts": "2024-01-15T10:30:45.123Z",
  "action": "...",
  "actor": "alice@example.com"
}
```

### Common Fields

| Field    | Description        |
| -------- | ------------------ |
| `type`   | Always `"audit"`   |
| `ts`     | ISO 8601 timestamp |
| `action` | Event type         |
| `actor`  | Username or email  |

### auth.login

```json theme={null}
{
  "type": "audit",
  "ts": "2024-01-15T10:30:45.123Z",
  "action": "auth.login",
  "actor": "alice@example.com",
  "provider": "google",
  "ip": "192.168.1.100",
  "success": true,
  "source": "web"
}
```

| Field      | Description                                   |
| ---------- | --------------------------------------------- |
| `provider` | Auth provider (`basic`, `google`, `keycloak`) |
| `ip`       | Client IP address                             |
| `success`  | Whether login succeeded                       |
| `error`    | Error message (if failed)                     |
| `source`   | Event origin: currently `"web"`               |

### auth.logout

```json theme={null}
{
  "type": "audit",
  "ts": "2024-01-15T10:35:00.000Z",
  "action": "auth.logout",
  "actor": "alice@example.com",
  "source": "web"
}
```

| Field    | Description                     |
| -------- | ------------------------------- |
| `actor`  | User who logged out             |
| `source` | Event origin: currently `"web"` |

### sql.execute

```json theme={null}
{
  "type": "audit",
  "ts": "2024-01-15T10:32:15.456Z",
  "action": "sql.execute",
  "actor": "alice@example.com",
  "connection": "prod-db",
  "database": "postgres",
  "sql": "SELECT * FROM users WHERE active = true",
  "success": true,
  "duration_ms": 45,
  "row_count": 150,
  "source": "web"
}
```

| Field         | Description                                                                                                                                                                                              |
| ------------- | -------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| `connection`  | Connection ID                                                                                                                                                                                            |
| `database`    | Database name                                                                                                                                                                                            |
| `sql`         | Full SQL query text                                                                                                                                                                                      |
| `success`     | Whether query succeeded                                                                                                                                                                                  |
| `duration_ms` | Execution time in milliseconds                                                                                                                                                                           |
| `row_count`   | Number of rows returned (optional)                                                                                                                                                                       |
| `error`       | Error message (if failed)                                                                                                                                                                                |
| `source`      | Query origin: `"web"` for the web app, `"mcp"` for the [MCP Server](/features/mcp-server)                                                                                                                |
| `tool`        | MCP tool name that ran the query (only when `source` is `"mcp"`)                                                                                                                                         |
| `agent`       | The [agent](/configuration/config#agents) id that ran the query (only when `source` is `"mcp"`). For a delegated agent the `actor` is the user it acts for; for a pure agent the `actor` is `agent:<id>` |

### data.export

```json theme={null}
{
  "type": "audit",
  "ts": "2024-01-15T10:33:00.000Z",
  "action": "data.export",
  "actor": "alice@example.com",
  "connection": "prod-db",
  "database": "postgres",
  "sql": "SELECT * FROM users WHERE active = true",
  "row_count": 150,
  "format": "csv",
  "source": "web"
}
```

| Field        | Description                                         |
| ------------ | --------------------------------------------------- |
| `connection` | Connection ID                                       |
| `database`   | Database name                                       |
| `sql`        | SQL query that produced the exported data           |
| `row_count`  | Number of rows exported                             |
| `format`     | Export format (`csv`, `tsv`, `json`, or `markdown`) |
| `source`     | Export origin: currently `"web"`                    |

## Capturing Logs

Audit logs are written to stdout alongside other server output. Filter by `"type":"audit"` to capture audit events only:

```bash theme={null}
# Filter and write to file
# --line-buffered: flush output after each line for real-time logging
pgconsole | grep --line-buffered '"type":"audit"' >> audit.log

# Parse and forward to log aggregator
# --unbuffered: disable jq's output buffering for real-time streaming
pgconsole | jq --unbuffered -c 'select(.type == "audit")' | nc logserver 5000
```
