Skip to content

Commit 4ecf1ef

Browse files
authored
Allow configuring max DB connection pool size via DATABASE_POOL_MAX (#5)
* add env validation utility * make database pool size configurable * rename DB_POOL_MAX to DATABASE_POOL_MAX
1 parent eebfc0c commit 4ecf1ef

7 files changed

Lines changed: 43 additions & 12 deletions

File tree

.env.example

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,3 +2,4 @@ SLACK_BOT_TOKEN=xoxb-
22
SLACK_APP_TOKEN=xapp-
33
GITHUB_TOKEN=github_pat_
44
DATABASE_URL=postgres://root:password@localhost:5432/app
5+
# DATABASE_POOL_MAX=10

installation.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -46,6 +46,7 @@ DATABASE_URL=postgres://user:password@localhost/releases_db
4646
# Optional
4747
# POLL_CRON=0 * * * * # How often to check releases (default: every hour)
4848
# DIGEST_CRON=30 7 * * * # When to send the periodic digest in UTC (default: 07:30 UTC)
49+
# DATABASE_POOL_MAX=10 # Max connections in the DB connection pool (default: 10)
4950
```
5051

5152
All tables are created in the `main` PostgreSQL schema. To use a different schema, change the hardcoded value in `src/db/schema.ts` and `drizzle.config.ts`, then regenerate and re-apply migrations.

src/db/client.ts

Lines changed: 7 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,9 @@
11
import { drizzle } from 'drizzle-orm/bun-sql'
2+
import { positiveInt, requiredString } from '@utils/env'
23

3-
if (!process.env.DATABASE_URL) {
4-
throw new Error('DATABASE_URL is required')
5-
}
6-
7-
export const db = drizzle(process.env.DATABASE_URL)
4+
export const db = drizzle({
5+
connection: {
6+
url: requiredString('DATABASE_URL'),
7+
max: positiveInt('DATABASE_POOL_MAX', 10),
8+
},
9+
})

src/env.d.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,7 @@ declare module 'bun' {
99

1010
// Database
1111
DATABASE_URL: string
12+
DATABASE_POOL_MAX?: string
1213
// Jobs
1314
POLL_CRON?: string
1415
DIGEST_CRON?: string

src/slack/app.ts

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,8 @@
11
import { App } from '@slack/bolt'
2+
import { requiredString } from '@utils/env.ts'
23

34
export const app = new App({
4-
token: process.env.SLACK_BOT_TOKEN,
5-
appToken: process.env.SLACK_APP_TOKEN,
5+
token: requiredString('SLACK_BOT_TOKEN'),
6+
appToken: requiredString('SLACK_APP_TOKEN'),
67
socketMode: true,
78
})

src/utils/env.ts

Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,24 @@
1+
type EnvVarName = keyof typeof process.env
2+
3+
export function requiredString(name: EnvVarName): string {
4+
const value = process.env[name]
5+
if (!value) {
6+
throw new Error(`${name} is required`)
7+
}
8+
9+
return value
10+
}
11+
12+
export function positiveInt(name: EnvVarName, defaultValue: number): number {
13+
const raw = process.env[name]
14+
if (!raw) {
15+
return defaultValue
16+
}
17+
18+
const value = Number(raw)
19+
if (!Number.isInteger(value) || value < 1) {
20+
throw new Error(`${name} must be a positive integer`)
21+
}
22+
23+
return value
24+
}

tsconfig.json

Lines changed: 6 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -13,11 +13,12 @@
1313
"noEmit": true,
1414
"skipLibCheck": true,
1515
"paths": {
16-
"@db/*": ["./src/db/*"],
17-
"@forges/*": ["./src/forges/*"],
18-
"@bot/*": ["./src/slack/*"],
19-
"@jobs/*": ["./src/jobs/*"],
20-
"@classify/*": ["./src/classify/*"]
16+
"@db/*": ["./src/db/*"],
17+
"@forges/*": ["./src/forges/*"],
18+
"@bot/*": ["./src/slack/*"],
19+
"@jobs/*": ["./src/jobs/*"],
20+
"@classify/*": ["./src/classify/*"],
21+
"@utils/*": ["./src/utils/*"]
2122
}
2223
}
2324
}

0 commit comments

Comments
 (0)