admindb 2.2.1 → 2.3.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (89) hide show
  1. package/README.md +368 -364
  2. package/dist/app.js +25 -16
  3. package/dist/auth/config.d.ts +1 -1
  4. package/dist/auth/config.js +18 -30
  5. package/dist/auth/crypto.js +11 -21
  6. package/dist/auth/middleware.js +9 -16
  7. package/dist/auth/routes.js +9 -15
  8. package/dist/cli/args.d.ts +1 -1
  9. package/dist/cli/args.js +20 -29
  10. package/dist/cli/config.d.ts +1 -1
  11. package/dist/cli/config.js +15 -18
  12. package/dist/cli/runner.js +13 -13
  13. package/dist/data/chain.d.ts +1 -1
  14. package/dist/data/chain.js +40 -617
  15. package/dist/data/datasets.d.ts +1 -1
  16. package/dist/data/datasets.js +43 -1
  17. package/dist/data/detector.js +45 -21
  18. package/dist/data/engine.d.ts +1 -1
  19. package/dist/data/engine.js +483 -142
  20. package/dist/data/index.d.ts +1 -1
  21. package/dist/data/index.js +8 -0
  22. package/dist/data/prng.d.ts +1 -0
  23. package/dist/data/prng.js +73 -0
  24. package/dist/data/registry.d.ts +1 -0
  25. package/dist/data/registry.js +805 -0
  26. package/dist/data/schema-graph.d.ts +1 -0
  27. package/dist/data/schema-graph.js +210 -0
  28. package/dist/data/strategies.d.ts +1 -1
  29. package/dist/data/strategies.js +44 -283
  30. package/dist/data/templates.d.ts +1 -0
  31. package/dist/data/templates.js +134 -0
  32. package/dist/data/types.d.ts +1 -1
  33. package/dist/data/validator.d.ts +1 -0
  34. package/dist/data/validator.js +160 -0
  35. package/dist/db/database.js +9 -14
  36. package/dist/db/export.js +32 -55
  37. package/dist/db/filters.d.ts +1 -1
  38. package/dist/db/filters.js +15 -38
  39. package/dist/db/introspection.js +4 -7
  40. package/dist/db/manager.d.ts +1 -1
  41. package/dist/db/manager.js +48 -53
  42. package/dist/db/migrations.js +7 -14
  43. package/dist/db/postgres.js +30 -78
  44. package/dist/index.d.ts +1 -1
  45. package/dist/public/css/app.css +1 -1
  46. package/dist/public/js/browse.js +1 -1
  47. package/dist/public/js/inspector.js +1 -1
  48. package/dist/public/js/query.js +1 -1
  49. package/dist/public/js/seed.js +1 -1
  50. package/dist/routes/api/erd.js +3 -8
  51. package/dist/routes/api/helpers.d.ts +1 -1
  52. package/dist/routes/api/helpers.js +75 -25
  53. package/dist/routes/api/import-export.js +1 -2
  54. package/dist/routes/api/query.js +2 -6
  55. package/dist/routes/api/rows.js +4 -8
  56. package/dist/routes/api/seed.js +35 -21
  57. package/dist/routes/api/tables.js +15 -30
  58. package/dist/routes/databases.js +8 -26
  59. package/dist/routes/pages.js +67 -18
  60. package/dist/serverless.js +31 -44
  61. package/dist/sql/generator.d.ts +1 -1
  62. package/dist/sql/generator.js +35 -109
  63. package/dist/types/api.d.ts +1 -1
  64. package/dist/utils/common.d.ts +1 -1
  65. package/dist/utils/common.js +45 -85
  66. package/dist/utils/csv.d.ts +1 -1
  67. package/dist/utils/csv.js +11 -17
  68. package/dist/utils/datatype.js +46 -60
  69. package/dist/utils/icons.js +8 -8
  70. package/dist/views/layouts/main.hbs +1 -87
  71. package/dist/views/pages/databases.hbs +1 -233
  72. package/dist/views/pages/designer.hbs +1 -89
  73. package/dist/views/pages/erd.hbs +1 -1241
  74. package/dist/views/pages/error.hbs +1 -10
  75. package/dist/views/pages/form.hbs +1 -59
  76. package/dist/views/pages/home.hbs +1 -220
  77. package/dist/views/pages/info.hbs +1 -107
  78. package/dist/views/pages/login.hbs +1 -98
  79. package/dist/views/pages/query.hbs +1 -129
  80. package/dist/views/pages/schema.hbs +1 -298
  81. package/dist/views/pages/seed-select.hbs +251 -0
  82. package/dist/views/pages/seed.hbs +256 -414
  83. package/dist/views/pages/table.hbs +1 -327
  84. package/dist/views/partials/navbar.hbs +1 -83
  85. package/dist/views/partials/sidebar.hbs +1 -129
  86. package/docs/API.md +149 -149
  87. package/docs/EXAMPLES.md +579 -579
  88. package/docs/SECURITY.md +265 -265
  89. package/package.json +80 -79
package/docs/SECURITY.md CHANGED
@@ -1,265 +1,265 @@
1
- # AdminDB Security, Authentication & Protection Guide
2
-
3
- > Comprehensive guide to AdminDB's security architecture, shared responsibility model, native authentication system, filesystem browsing sandboxing, remote PostgreSQL protection, and production deployment safeguards.
4
-
5
- ---
6
-
7
- ## 📑 Table of Contents
8
-
9
- - [🛡️ Security Responsibility Model (Crucial)](#️-security-responsibility-model-crucial)
10
- - [Native Authentication System](#native-authentication-system)
11
- - [Default Credentials & Alerts](#default-credentials--alerts)
12
- - [Cryptographic Password Hashing (`npm run generatehash`)](#cryptographic-password-hashing-npm-run-generatehash)
13
- - [Configuring Credentials](#configuring-credentials)
14
- - [Session Tokens & Cookie Security](#session-tokens--cookie-security)
15
- - [Protecting AdminDB with Your Own Application Auth](#protecting-admindb-with-your-own-application-auth)
16
- - [Custom Express Middleware (Recommended for Production)](#custom-express-middleware-recommended-for-production)
17
- - [Reverse Proxy & Gateway Protection (Nginx, Caddy, Cloudflare Zero Trust)](#reverse-proxy--gateway-protection-nginx-caddy-cloudflare-zero-trust)
18
- - [Manager Mode & Filesystem Browsing Security](#manager-mode--filesystem-browsing-security)
19
- - [Path Sandboxing (`browseRoot`) & Traversal Prevention](#path-sandboxing-browseroot--traversal-prevention)
20
- - [Blocked Files & Secret Exclusion](#blocked-files--secret-exclusion)
21
- - [Disabling File Browsing Completely](#disabling-file-browsing-completely)
22
- - [Remote PostgreSQL Security](#remote-postgresql-security)
23
- - [Credential Masking & Memory Sanitation](#credential-masking--memory-sanitation)
24
- - [Secure JSON Configuration Files (`name.postgres.json`)](#secure-json-configuration-files-namepostgresjson)
25
- - [Per-Database Read-Only Enforcements](#per-database-read-only-enforcements)
26
- - [Production Security Checklist](#production-security-checklist)
27
- - [SQL Safety & Injection Protections](#sql-safety--injection-protections)
28
- - [Universal Destructive Action Safeguards](#universal-destructive-action-safeguards)
29
-
30
- ---
31
-
32
- ## 🛡️ Security Responsibility Model (Crucial)
33
-
34
- > [!WARNING]
35
- > **IMPORTANT: Native Authentication is Basic Security.**
36
- > AdminDB's built-in single-user login screen and HTTP basic authentication are intended as **convenience access controls** for local development, trusted private intranets, or single-operator setups.
37
- >
38
- > **It is the user's sole responsibility to fully protect AdminDB** when exposing it to untrusted networks, shared environments, or the public internet.
39
-
40
- For production or team usage, you should **always**:
41
- 1. **Wrap AdminDB with your application's own authentication**: If embedding via Express/Node.js (`createRouter`), apply your organization's robust authentication middleware (e.g. NextAuth, Passport.js, OAuth2/OIDC, JWT verification, or session guards) before the AdminDB router, and disable native auth (`auth: false`).
42
- 2. **Place behind a secure reverse proxy or VPN**: Terminate TLS/HTTPS and enforce IP allowlisting, Cloudflare Zero Trust / Cloudflare Access, AWS Cognito, or Tailscale/WireGuard.
43
- 3. **Use granular database credentials**: Create dedicated database users with least-privilege permissions instead of root `postgres` superuser accounts.
44
-
45
- ---
46
-
47
- ## Native Authentication System
48
-
49
- ### Default Credentials & Alerts
50
-
51
- Out of the box, AdminDB includes default credentials to ensure a newly launched server is never exposed completely open:
52
-
53
- * **Default Username:** `admin`
54
- * **Default Password:** `admin` *(stored internally via a salted `scrypt` hash)*
55
-
56
- > [!CAUTION]
57
- > When running with default credentials, AdminDB displays a prominent warning in your terminal on startup and an alert badge in the web UI. Always generate a custom password for anything beyond local testing.
58
-
59
- ---
60
-
61
- ### Cryptographic Password Hashing (`npm run generatehash`)
62
-
63
- AdminDB uses Node.js's built-in cryptographic `scrypt` algorithm with a unique 16-byte random salt per hash. To generate a secure hash for your custom password:
64
-
65
- ```bash
66
- npm run generatehash
67
- ```
68
-
69
- The interactive script prompts:
70
- ```text
71
- Enter password to hash: [your-strong-password]
72
- ```
73
-
74
- And outputs a formatted hash:
75
- ```text
76
- ⚡ AdminDB Password Hash Generated
77
-
78
- ➜ Hash: scrypt:8011bcda719a32dd307cbcbad899e963:854657965139a68b14ffb30f6a64a18d8b10197046e720dbf6e2e26fee2c5dcc2b6a8b8aed514c1a2be7d73279481bf780c4cf381b68eea40d4e2a7b58dd24f8
79
- ```
80
-
81
- You can also pass the password as a command-line argument:
82
- ```bash
83
- node scripts/generate-hash.mjs "my_strong_password_123"
84
- ```
85
-
86
- ---
87
-
88
- ### Configuring Credentials
89
-
90
- You can supply the generated hash (or plain-text password) through any of the following methods:
91
-
92
- #### 1. Environment Variables (`.env`)
93
- ```bash
94
- export ADMINDB_USERNAME="ops_admin"
95
- export ADMINDB_PASSWORD="scrypt:8011bcda719a32dd307cbcbad899e963:854657965139a68b14ffb30f6a64a18d8b10197046e720dbf6e2e26fee2c5dcc2b6a8b8aed514c1a2be7d73279481bf780c4cf381b68eea40d4e2a7b58dd24f8"
96
- export ADMINDB_SECRET="a7f8e92c4b1d6e3f8a0b5c7d9e1f2a3b4c5d6e7f8"
97
-
98
- npx admindb
99
- ```
100
-
101
- #### 2. CLI Flags
102
- ```bash
103
- admindb -u ops_admin -P "scrypt:8011bcda719a32dd307cbcbad899e963:854657965139a68b14ffb30f6a64a18d8b10197046e720dbf6e2e26fee2c5dcc2b6a8b8aed514c1a2be7d73279481bf780c4cf381b68eea40d4e2a7b58dd24f8"
104
- ```
105
-
106
- #### 3. JSON Configuration File (`name.postgres.json`)
107
- ```json
108
- {
109
- "production": "postgresql://postgres:secret@localhost:5432/mydb",
110
- "auth": {
111
- "username": "ops_admin",
112
- "password": "scrypt:8011bcda719a32dd307cbcbad899e963:854657965139a68b14ffb30f6a64a18d8b10197046e720dbf6e2e26fee2c5dcc2b6a8b8aed514c1a2be7d73279481bf780c4cf381b68eea40d4e2a7b58dd24f8"
113
- }
114
- }
115
- ```
116
-
117
- ---
118
-
119
- ### Session Tokens & Cookie Security
120
-
121
- When a user logs in through the web UI:
122
- 1. **Token Generation:** A cryptographic timestamped token is created and signed using `HMAC-SHA256` with your configured `ADMINDB_SECRET`.
123
- 2. **Cookie Security Flags:** The session cookie (`admindb_session`) is set with:
124
- - `HttpOnly: true` (prevents client JavaScript access & XSS token theft)
125
- - `SameSite: Lax` (protects against Cross-Site Request Forgery)
126
- - `Path: /` (or your configured `basePath`)
127
- 3. **Constant-Time Verification:** Password matching and token signature verification use constant-time comparisons (`crypto.timingSafeEqual`) to protect against timing attacks.
128
-
129
- ---
130
-
131
- ## Protecting AdminDB with Your Own Application Auth
132
-
133
- ### Custom Express Middleware (Recommended for Production)
134
-
135
- When embedding AdminDB in an existing Express / Next.js backend, turn off built-in auth (`auth: false`) and apply your existing session or JWT middleware:
136
-
137
- ```ts
138
- import express from 'express';
139
- import { createRouter } from 'admindb';
140
-
141
- const app = express();
142
-
143
- // Your enterprise authentication middleware
144
- function requireAdminRole(req: express.Request, res: express.Response, next: express.NextFunction) {
145
- if (req.user && req.user.role === 'SUPERADMIN') {
146
- return next();
147
- }
148
- res.status(403).send('Forbidden: AdminDB requires SUPERADMIN privileges');
149
- }
150
-
151
- app.use('/admin', requireAdminRole, createRouter({
152
- connection: process.env.DATABASE_URL,
153
- basePath: '/admin',
154
- auth: false, // Turn off built-in login form; rely on requireAdminRole
155
- }));
156
-
157
- app.listen(45531);
158
- ```
159
-
160
- ---
161
-
162
- ### Reverse Proxy & Gateway Protection (Nginx, Caddy, Cloudflare Zero Trust)
163
-
164
- If running AdminDB standalone (`npx admindb`), bind to localhost (`HOST=127.0.0.1`) and put a reverse proxy in front:
165
-
166
- ```nginx
167
- # Nginx reverse proxy with IP allowlist and HTTPS termination
168
- server {
169
- listen 443 ssl http2;
170
- server_name db.yourcompany.internal;
171
-
172
- ssl_certificate /etc/ssl/certs/app.crt;
173
- ssl_certificate_key /etc/ssl/certs/app.key;
174
-
175
- # Restrict to VPN / Office IP range
176
- allow 10.0.0.0/8;
177
- allow 192.168.1.0/24;
178
- deny all;
179
-
180
- location / {
181
- proxy_pass http://127.0.0.1:45531;
182
- proxy_set_header Host $host;
183
- proxy_set_header X-Real-IP $remote_addr;
184
- proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
185
- proxy_set_header X-Forwarded-Proto $scheme;
186
- }
187
- }
188
- ```
189
-
190
- ---
191
-
192
- ## Manager Mode & Filesystem Browsing Security
193
-
194
- In Manager Mode, AdminDB provides an interactive filesystem browser to locate and open SQLite databases on the host. Several defensive measures protect host integrity:
195
-
196
- ### Path Sandboxing (`browseRoot`) & Traversal Prevention
197
- - **Sandboxed Root (`browseRoot` / `-d <folder>`):** When started with a specific directory or `--browse-root`, browsing is strictly jailed to that folder. Any attempt to navigate upward returns `403 Forbidden`.
198
- - **Symlink Escape Protection:** All path validations resolve real filesystem symlinks (`realpathSync`), preventing symlink-based jailbreaks.
199
- - **Null-Byte Injection Blocking:** All inputs containing `\0` null-bytes are rejected immediately.
200
-
201
- ### Blocked Files & Secret Exclusion
202
- The file browser automatically ignores and conceals sensitive system folders and secrets:
203
- - Directories: `node_modules`, `.git`, `.svn`, `.hg`, `.aws`, `.ssh`, `System Volume Information`, `$RECYCLE.BIN`.
204
- - Secret Files: Hidden dotfiles (`.*`), `.env`, `.env.local`, `.env.production`.
205
- - File Filter: Only recognized database files (`.db`, `.sqlite`, `.sqlite3`) are displayed for opening.
206
-
207
- ### Disabling File Browsing Completely
208
- When AdminDB is started with explicit database files (`--files`, `name.postgres.json`) or in serverless environments, **filesystem browsing is automatically disabled** (`allowBrowse: false`), eliminating any directory traversal attack surface.
209
-
210
- ---
211
-
212
- ## Remote PostgreSQL Security
213
-
214
- ### Credential Masking & Memory Sanitation
215
- - When PostgreSQL connection URIs (`postgresql://user:password@host:5432/db`) are registered, credentials are sanitised across the UI, responses, and log messages (`postgresql://user:****@host:5432/db`).
216
- - Passwords are encrypted in-memory and are never leaked to client browsers.
217
-
218
- ### Secure JSON Configuration Files (`name.postgres.json`)
219
- To avoid leaking passwords in shell history or process tables (`ps aux`), store database connections in a restricted JSON file:
220
-
221
- ```json
222
- {
223
- "production": "postgresql://postgres:secret@prod.internal:5432/prod_db",
224
- "analytics": "postgresql://postgres:secret@analytics.internal:5432/dw_db"
225
- }
226
- ```
227
-
228
- And start AdminDB using the file:
229
- ```bash
230
- npx admindb name.postgres.json
231
- ```
232
-
233
- ### Per-Database Read-Only Enforcements
234
- - AdminDB allows marking any PostgreSQL or SQLite database as **Read-only** directly from the UI or configuration (`[ ] Open as Read-only`).
235
- - In read-only mode, all write statements (`INSERT`, `UPDATE`, `DELETE`, `DROP`, `ALTER`, `CREATE`) and data-mutating APIs are blocked at the engine layer.
236
-
237
- ---
238
-
239
- ## Production Security Checklist
240
-
241
- - [ ] **Custom Credentials:** Replaced default `admin/admin` with a salted `scrypt` hash (`npm run generatehash`).
242
- - [ ] **Fixed Session Secret:** Configured `ADMINDB_SECRET` to prevent session invalidation on restart.
243
- - [ ] **Private Interface:** Bound to `HOST=127.0.0.1` or private subnet.
244
- - [ ] **HTTPS / TLS:** Terminated SSL via reverse proxy or load balancer.
245
- - [ ] **Custom Auth Wrapper:** Placed behind application auth middleware when embedded in Express.
246
- - [ ] **Least Privilege DB Users:** Connected PostgreSQL using dedicated user roles with appropriate table grants.
247
- - [ ] **Read-Only Where Applicable:** Enabled `--readonly` for auditing and data-viewer personas.
248
- - [ ] **Jailed Browsing:** Specified `-d /path/to/dbs` or disabled browsing with explicit files.
249
-
250
- ---
251
-
252
- ## SQL Safety & Injection Protections
253
-
254
- 1. **Identifier Quoting:** Identifiers (table names, columns, indexes) are safely double-quoted (`"table_name"`).
255
- 2. **Parameterized Queries:** Queries use native driver parameter placeholders (`?` for SQLite, `$1, $2, ...` for PostgreSQL).
256
- 3. **Safe Preview Modes:** Preview endpoints return raw generated SQL strings for visual inspection without executing against the database.
257
- 4. **Internal Table Protection:** Internal AdminDB state tables (`_saved_queries`) are protected from being dropped, renamed, or mutated.
258
-
259
- ---
260
-
261
- ## Universal Destructive Action Safeguards
262
-
263
- 1. **Interactive Confirmation Barriers (`UI.confirm`):** Prompts with primary key details and impact assessments before single/bulk deletions.
264
- 2. **Type-to-Confirm Input Verification:** Dropping tables and deleting database files requires typing the exact name of the item.
265
- 3. **Transactional Isolation:** Bulk operations and CSV imports run in atomic transactions (`BEGIN ... COMMIT/ROLLBACK`), ensuring zero partial corruption on errors.
1
+ # AdminDB Security, Authentication & Protection Guide
2
+
3
+ > Comprehensive guide to AdminDB's security architecture, shared responsibility model, native authentication system, filesystem browsing sandboxing, remote PostgreSQL protection, and production deployment safeguards.
4
+
5
+ ---
6
+
7
+ ## 📑 Table of Contents
8
+
9
+ - [🛡️ Security Responsibility Model (Crucial)](#️-security-responsibility-model-crucial)
10
+ - [Native Authentication System](#native-authentication-system)
11
+ - [Default Credentials & Alerts](#default-credentials--alerts)
12
+ - [Cryptographic Password Hashing (`npm run generatehash`)](#cryptographic-password-hashing-npm-run-generatehash)
13
+ - [Configuring Credentials](#configuring-credentials)
14
+ - [Session Tokens & Cookie Security](#session-tokens--cookie-security)
15
+ - [Protecting AdminDB with Your Own Application Auth](#protecting-admindb-with-your-own-application-auth)
16
+ - [Custom Express Middleware (Recommended for Production)](#custom-express-middleware-recommended-for-production)
17
+ - [Reverse Proxy & Gateway Protection (Nginx, Caddy, Cloudflare Zero Trust)](#reverse-proxy--gateway-protection-nginx-caddy-cloudflare-zero-trust)
18
+ - [Manager Mode & Filesystem Browsing Security](#manager-mode--filesystem-browsing-security)
19
+ - [Path Sandboxing (`browseRoot`) & Traversal Prevention](#path-sandboxing-browseroot--traversal-prevention)
20
+ - [Blocked Files & Secret Exclusion](#blocked-files--secret-exclusion)
21
+ - [Disabling File Browsing Completely](#disabling-file-browsing-completely)
22
+ - [Remote PostgreSQL Security](#remote-postgresql-security)
23
+ - [Credential Masking & Memory Sanitation](#credential-masking--memory-sanitation)
24
+ - [Secure JSON Configuration Files (`name.postgres.json`)](#secure-json-configuration-files-namepostgresjson)
25
+ - [Per-Database Read-Only Enforcements](#per-database-read-only-enforcements)
26
+ - [Production Security Checklist](#production-security-checklist)
27
+ - [SQL Safety & Injection Protections](#sql-safety--injection-protections)
28
+ - [Universal Destructive Action Safeguards](#universal-destructive-action-safeguards)
29
+
30
+ ---
31
+
32
+ ## 🛡️ Security Responsibility Model (Crucial)
33
+
34
+ > [!WARNING]
35
+ > **IMPORTANT: Native Authentication is Basic Security.**
36
+ > AdminDB's built-in single-user login screen and HTTP basic authentication are intended as **convenience access controls** for local development, trusted private intranets, or single-operator setups.
37
+ >
38
+ > **It is the user's sole responsibility to fully protect AdminDB** when exposing it to untrusted networks, shared environments, or the public internet.
39
+
40
+ For production or team usage, you should **always**:
41
+ 1. **Wrap AdminDB with your application's own authentication**: If embedding via Express/Node.js (`createRouter`), apply your organization's robust authentication middleware (e.g. NextAuth, Passport.js, OAuth2/OIDC, JWT verification, or session guards) before the AdminDB router, and disable native auth (`auth: false`).
42
+ 2. **Place behind a secure reverse proxy or VPN**: Terminate TLS/HTTPS and enforce IP allowlisting, Cloudflare Zero Trust / Cloudflare Access, AWS Cognito, or Tailscale/WireGuard.
43
+ 3. **Use granular database credentials**: Create dedicated database users with least-privilege permissions instead of root `postgres` superuser accounts.
44
+
45
+ ---
46
+
47
+ ## Native Authentication System
48
+
49
+ ### Default Credentials & Alerts
50
+
51
+ Out of the box, AdminDB includes default credentials to ensure a newly launched server is never exposed completely open:
52
+
53
+ * **Default Username:** `admin`
54
+ * **Default Password:** `admin` *(stored internally via a salted `scrypt` hash)*
55
+
56
+ > [!CAUTION]
57
+ > When running with default credentials, AdminDB displays a prominent warning in your terminal on startup and an alert badge in the web UI. Always generate a custom password for anything beyond local testing.
58
+
59
+ ---
60
+
61
+ ### Cryptographic Password Hashing (`npm run generatehash`)
62
+
63
+ AdminDB uses Node.js's built-in cryptographic `scrypt` algorithm with a unique 16-byte random salt per hash. To generate a secure hash for your custom password:
64
+
65
+ ```bash
66
+ npm run generatehash
67
+ ```
68
+
69
+ The interactive script prompts:
70
+ ```text
71
+ Enter password to hash: [your-strong-password]
72
+ ```
73
+
74
+ And outputs a formatted hash:
75
+ ```text
76
+ ⚡ AdminDB Password Hash Generated
77
+
78
+ ➜ Hash: scrypt:8011bcda719a32dd307cbcbad899e963:854657965139a68b14ffb30f6a64a18d8b10197046e720dbf6e2e26fee2c5dcc2b6a8b8aed514c1a2be7d73279481bf780c4cf381b68eea40d4e2a7b58dd24f8
79
+ ```
80
+
81
+ You can also pass the password as a command-line argument:
82
+ ```bash
83
+ node scripts/generate-hash.mjs "my_strong_password_123"
84
+ ```
85
+
86
+ ---
87
+
88
+ ### Configuring Credentials
89
+
90
+ You can supply the generated hash (or plain-text password) through any of the following methods:
91
+
92
+ #### 1. Environment Variables (`.env`)
93
+ ```bash
94
+ export ADMINDB_USERNAME="ops_admin"
95
+ export ADMINDB_PASSWORD="scrypt:8011bcda719a32dd307cbcbad899e963:854657965139a68b14ffb30f6a64a18d8b10197046e720dbf6e2e26fee2c5dcc2b6a8b8aed514c1a2be7d73279481bf780c4cf381b68eea40d4e2a7b58dd24f8"
96
+ export ADMINDB_SECRET="a7f8e92c4b1d6e3f8a0b5c7d9e1f2a3b4c5d6e7f8"
97
+
98
+ npx admindb
99
+ ```
100
+
101
+ #### 2. CLI Flags
102
+ ```bash
103
+ admindb -u ops_admin -P "scrypt:8011bcda719a32dd307cbcbad899e963:854657965139a68b14ffb30f6a64a18d8b10197046e720dbf6e2e26fee2c5dcc2b6a8b8aed514c1a2be7d73279481bf780c4cf381b68eea40d4e2a7b58dd24f8"
104
+ ```
105
+
106
+ #### 3. JSON Configuration File (`name.postgres.json`)
107
+ ```json
108
+ {
109
+ "production": "postgresql://postgres:secret@localhost:5432/mydb",
110
+ "auth": {
111
+ "username": "ops_admin",
112
+ "password": "scrypt:8011bcda719a32dd307cbcbad899e963:854657965139a68b14ffb30f6a64a18d8b10197046e720dbf6e2e26fee2c5dcc2b6a8b8aed514c1a2be7d73279481bf780c4cf381b68eea40d4e2a7b58dd24f8"
113
+ }
114
+ }
115
+ ```
116
+
117
+ ---
118
+
119
+ ### Session Tokens & Cookie Security
120
+
121
+ When a user logs in through the web UI:
122
+ 1. **Token Generation:** A cryptographic timestamped token is created and signed using `HMAC-SHA256` with your configured `ADMINDB_SECRET`.
123
+ 2. **Cookie Security Flags:** The session cookie (`admindb_session`) is set with:
124
+ - `HttpOnly: true` (prevents client JavaScript access & XSS token theft)
125
+ - `SameSite: Lax` (protects against Cross-Site Request Forgery)
126
+ - `Path: /` (or your configured `basePath`)
127
+ 3. **Constant-Time Verification:** Password matching and token signature verification use constant-time comparisons (`crypto.timingSafeEqual`) to protect against timing attacks.
128
+
129
+ ---
130
+
131
+ ## Protecting AdminDB with Your Own Application Auth
132
+
133
+ ### Custom Express Middleware (Recommended for Production)
134
+
135
+ When embedding AdminDB in an existing Express / Next.js backend, turn off built-in auth (`auth: false`) and apply your existing session or JWT middleware:
136
+
137
+ ```ts
138
+ import express from 'express';
139
+ import { createRouter } from 'admindb';
140
+
141
+ const app = express();
142
+
143
+ // Your enterprise authentication middleware
144
+ function requireAdminRole(req: express.Request, res: express.Response, next: express.NextFunction) {
145
+ if (req.user && req.user.role === 'SUPERADMIN') {
146
+ return next();
147
+ }
148
+ res.status(403).send('Forbidden: AdminDB requires SUPERADMIN privileges');
149
+ }
150
+
151
+ app.use('/admin', requireAdminRole, createRouter({
152
+ connection: process.env.DATABASE_URL,
153
+ basePath: '/admin',
154
+ auth: false, // Turn off built-in login form; rely on requireAdminRole
155
+ }));
156
+
157
+ app.listen(45531);
158
+ ```
159
+
160
+ ---
161
+
162
+ ### Reverse Proxy & Gateway Protection (Nginx, Caddy, Cloudflare Zero Trust)
163
+
164
+ If running AdminDB standalone (`npx admindb`), bind to localhost (`HOST=127.0.0.1`) and put a reverse proxy in front:
165
+
166
+ ```nginx
167
+ # Nginx reverse proxy with IP allowlist and HTTPS termination
168
+ server {
169
+ listen 443 ssl http2;
170
+ server_name db.yourcompany.internal;
171
+
172
+ ssl_certificate /etc/ssl/certs/app.crt;
173
+ ssl_certificate_key /etc/ssl/certs/app.key;
174
+
175
+ # Restrict to VPN / Office IP range
176
+ allow 10.0.0.0/8;
177
+ allow 192.168.1.0/24;
178
+ deny all;
179
+
180
+ location / {
181
+ proxy_pass http://127.0.0.1:45531;
182
+ proxy_set_header Host $host;
183
+ proxy_set_header X-Real-IP $remote_addr;
184
+ proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
185
+ proxy_set_header X-Forwarded-Proto $scheme;
186
+ }
187
+ }
188
+ ```
189
+
190
+ ---
191
+
192
+ ## Manager Mode & Filesystem Browsing Security
193
+
194
+ In Manager Mode, AdminDB provides an interactive filesystem browser to locate and open SQLite databases on the host. Several defensive measures protect host integrity:
195
+
196
+ ### Path Sandboxing (`browseRoot`) & Traversal Prevention
197
+ - **Sandboxed Root (`browseRoot` / `-d <folder>`):** When started with a specific directory or `--browse-root`, browsing is strictly jailed to that folder. Any attempt to navigate upward returns `403 Forbidden`.
198
+ - **Symlink Escape Protection:** All path validations resolve real filesystem symlinks (`realpathSync`), preventing symlink-based jailbreaks.
199
+ - **Null-Byte Injection Blocking:** All inputs containing `\0` null-bytes are rejected immediately.
200
+
201
+ ### Blocked Files & Secret Exclusion
202
+ The file browser automatically ignores and conceals sensitive system folders and secrets:
203
+ - Directories: `node_modules`, `.git`, `.svn`, `.hg`, `.aws`, `.ssh`, `System Volume Information`, `$RECYCLE.BIN`.
204
+ - Secret Files: Hidden dotfiles (`.*`), `.env`, `.env.local`, `.env.production`.
205
+ - File Filter: Only recognized database files (`.db`, `.sqlite`, `.sqlite3`) are displayed for opening.
206
+
207
+ ### Disabling File Browsing Completely
208
+ When AdminDB is started with explicit database files (`--files`, `name.postgres.json`) or in serverless environments, **filesystem browsing is automatically disabled** (`allowBrowse: false`), eliminating any directory traversal attack surface.
209
+
210
+ ---
211
+
212
+ ## Remote PostgreSQL Security
213
+
214
+ ### Credential Masking & Memory Sanitation
215
+ - When PostgreSQL connection URIs (`postgresql://user:password@host:5432/db`) are registered, credentials are sanitised across the UI, responses, and log messages (`postgresql://user:****@host:5432/db`).
216
+ - Passwords are encrypted in-memory and are never leaked to client browsers.
217
+
218
+ ### Secure JSON Configuration Files (`name.postgres.json`)
219
+ To avoid leaking passwords in shell history or process tables (`ps aux`), store database connections in a restricted JSON file:
220
+
221
+ ```json
222
+ {
223
+ "production": "postgresql://postgres:secret@prod.internal:5432/prod_db",
224
+ "analytics": "postgresql://postgres:secret@analytics.internal:5432/dw_db"
225
+ }
226
+ ```
227
+
228
+ And start AdminDB using the file:
229
+ ```bash
230
+ npx admindb name.postgres.json
231
+ ```
232
+
233
+ ### Per-Database Read-Only Enforcements
234
+ - AdminDB allows marking any PostgreSQL or SQLite database as **Read-only** directly from the UI or configuration (`[ ] Open as Read-only`).
235
+ - In read-only mode, all write statements (`INSERT`, `UPDATE`, `DELETE`, `DROP`, `ALTER`, `CREATE`) and data-mutating APIs are blocked at the engine layer.
236
+
237
+ ---
238
+
239
+ ## Production Security Checklist
240
+
241
+ - [ ] **Custom Credentials:** Replaced default `admin/admin` with a salted `scrypt` hash (`npm run generatehash`).
242
+ - [ ] **Fixed Session Secret:** Configured `ADMINDB_SECRET` to prevent session invalidation on restart.
243
+ - [ ] **Private Interface:** Bound to `HOST=127.0.0.1` or private subnet.
244
+ - [ ] **HTTPS / TLS:** Terminated SSL via reverse proxy or load balancer.
245
+ - [ ] **Custom Auth Wrapper:** Placed behind application auth middleware when embedded in Express.
246
+ - [ ] **Least Privilege DB Users:** Connected PostgreSQL using dedicated user roles with appropriate table grants.
247
+ - [ ] **Read-Only Where Applicable:** Enabled `--readonly` for auditing and data-viewer personas.
248
+ - [ ] **Jailed Browsing:** Specified `-d /path/to/dbs` or disabled browsing with explicit files.
249
+
250
+ ---
251
+
252
+ ## SQL Safety & Injection Protections
253
+
254
+ 1. **Identifier Quoting:** Identifiers (table names, columns, indexes) are safely double-quoted (`"table_name"`).
255
+ 2. **Parameterized Queries:** Queries use native driver parameter placeholders (`?` for SQLite, `$1, $2, ...` for PostgreSQL).
256
+ 3. **Safe Preview Modes:** Preview endpoints return raw generated SQL strings for visual inspection without executing against the database.
257
+ 4. **Internal Table Protection:** Internal AdminDB state tables (`_saved_queries`) are protected from being dropped, renamed, or mutated.
258
+
259
+ ---
260
+
261
+ ## Universal Destructive Action Safeguards
262
+
263
+ 1. **Interactive Confirmation Barriers (`UI.confirm`):** Prompts with primary key details and impact assessments before single/bulk deletions.
264
+ 2. **Type-to-Confirm Input Verification:** Dropping tables and deleting database files requires typing the exact name of the item.
265
+ 3. **Transactional Isolation:** Bulk operations and CSV imports run in atomic transactions (`BEGIN ... COMMIT/ROLLBACK`), ensuring zero partial corruption on errors.