create-kuckit-app 0.3.5 → 0.4.0
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.
- package/dist/bin.js +1 -1
- package/dist/{create-project-CP-h4Ygi.js → create-project-geQBZ0Ru.js} +5 -0
- package/dist/index.js +1 -1
- package/package.json +1 -1
- package/templates/base/.claude/skills/kuckit/SKILL.md +22 -2
- package/templates/base/.claude/skills/kuckit/references/MODULE-DEVELOPMENT.md +39 -28
- package/templates/base/.claude/skills/kuckit/references/PACKAGES.md +94 -74
- package/templates/base/AGENTS.md +44 -18
- package/templates/base/apps/server/AGENTS.md +35 -10
- package/templates/base/apps/server/package.json +7 -7
- package/templates/base/apps/server/src/auth.ts +1 -1
- package/templates/base/apps/server/src/container.ts +3 -1
- package/templates/base/apps/server/src/module-rest-routes.ts +47 -0
- package/templates/base/apps/server/src/rest-router-registry.ts +32 -0
- package/templates/base/apps/server/src/rpc.ts +1 -1
- package/templates/base/apps/server/src/server.ts +2 -0
- package/templates/base/apps/web/package.json +9 -9
- package/templates/base/apps/web/src/services/auth-client.ts +1 -1
- package/templates/base/{packages/db/src/migrations → drizzle}/0000_init.sql +31 -36
- package/templates/base/{packages/db/src/migrations → drizzle}/meta/_journal.json +1 -1
- package/templates/base/drizzle.config.ts +38 -0
- package/templates/base/package.json +14 -9
- package/templates/base/packages/items-module/package.json +7 -7
- package/templates/base/packages/items-module/src/api/items.router.ts +1 -1
- package/templates/base/packages/api/AGENTS.md +0 -66
- package/templates/base/packages/api/package.json +0 -35
- package/templates/base/packages/api/src/context.ts +0 -48
- package/templates/base/packages/api/src/index.ts +0 -22
- package/templates/base/packages/api/tsconfig.json +0 -8
- package/templates/base/packages/auth/AGENTS.md +0 -61
- package/templates/base/packages/auth/package.json +0 -27
- package/templates/base/packages/auth/src/index.ts +0 -22
- package/templates/base/packages/auth/tsconfig.json +0 -8
- package/templates/base/packages/db/AGENTS.md +0 -99
- package/templates/base/packages/db/drizzle.config.ts +0 -23
- package/templates/base/packages/db/package.json +0 -36
- package/templates/base/packages/db/src/connection.ts +0 -40
- package/templates/base/packages/db/src/index.ts +0 -4
- package/templates/base/packages/db/src/schema/auth.ts +0 -51
- package/templates/base/packages/db/tsconfig.json +0 -8
|
@@ -1,99 +0,0 @@
|
|
|
1
|
-
# AGENTS.md - Database Package
|
|
2
|
-
|
|
3
|
-
> See root [AGENTS.md](../../AGENTS.md) for SDK Module System patterns
|
|
4
|
-
|
|
5
|
-
## Purpose
|
|
6
|
-
|
|
7
|
-
Drizzle ORM configuration, database connection, migrations, and shared schema.
|
|
8
|
-
|
|
9
|
-
## Key Files
|
|
10
|
-
|
|
11
|
-
| File | Purpose |
|
|
12
|
-
| ------------------- | ------------------------- |
|
|
13
|
-
| `drizzle.config.ts` | Drizzle Kit configuration |
|
|
14
|
-
| `src/connection.ts` | Database connection pool |
|
|
15
|
-
| `src/schema/` | Shared schema definitions |
|
|
16
|
-
| `src/migrations/` | SQL migration files |
|
|
17
|
-
|
|
18
|
-
## Commands
|
|
19
|
-
|
|
20
|
-
```bash
|
|
21
|
-
# Generate migration from schema changes
|
|
22
|
-
bun run db:generate
|
|
23
|
-
|
|
24
|
-
# Apply pending migrations
|
|
25
|
-
bun run db:migrate
|
|
26
|
-
|
|
27
|
-
# Open Drizzle Studio (database GUI)
|
|
28
|
-
bun run db:studio
|
|
29
|
-
```
|
|
30
|
-
|
|
31
|
-
## Adding a New Table
|
|
32
|
-
|
|
33
|
-
1. Create schema file in `src/schema/` or in your module's `adapters/`:
|
|
34
|
-
|
|
35
|
-
```typescript
|
|
36
|
-
import { pgTable, text, timestamp, uuid } from 'drizzle-orm/pg-core'
|
|
37
|
-
|
|
38
|
-
export const myTable = pgTable('my_table', {
|
|
39
|
-
id: uuid('id').primaryKey().defaultRandom(),
|
|
40
|
-
name: text('name').notNull(),
|
|
41
|
-
createdAt: timestamp('created_at').defaultNow(),
|
|
42
|
-
})
|
|
43
|
-
```
|
|
44
|
-
|
|
45
|
-
2. Export from `src/index.ts` if shared
|
|
46
|
-
|
|
47
|
-
3. Generate and run migration:
|
|
48
|
-
```bash
|
|
49
|
-
bun run db:generate
|
|
50
|
-
bun run db:migrate
|
|
51
|
-
```
|
|
52
|
-
|
|
53
|
-
## Module Schema Pattern
|
|
54
|
-
|
|
55
|
-
Modules can define their own schemas in `adapters/`:
|
|
56
|
-
|
|
57
|
-
```typescript
|
|
58
|
-
// packages/items-module/src/adapters/items.schema.ts
|
|
59
|
-
export const itemsTable = pgTable('items', {
|
|
60
|
-
id: uuid('id').primaryKey().defaultRandom(),
|
|
61
|
-
userId: text('user_id').notNull(),
|
|
62
|
-
name: text('name').notNull(),
|
|
63
|
-
})
|
|
64
|
-
```
|
|
65
|
-
|
|
66
|
-
The schema is imported by `drizzle.config.ts` for migration generation.
|
|
67
|
-
|
|
68
|
-
### ⚠️ Important: Register Module Schemas
|
|
69
|
-
|
|
70
|
-
**Drizzle only discovers schemas listed in `drizzle.config.ts`**. When adding a new module with database tables:
|
|
71
|
-
|
|
72
|
-
1. Add the module's schema path to `drizzle.config.ts`:
|
|
73
|
-
|
|
74
|
-
```typescript
|
|
75
|
-
export default defineConfig({
|
|
76
|
-
schema: [
|
|
77
|
-
resolve(currentDirPath, './src/schema'),
|
|
78
|
-
// Add module schema paths here:
|
|
79
|
-
resolve(currentDirPath, '../your-module/src/adapters/schema.drizzle.ts'),
|
|
80
|
-
],
|
|
81
|
-
// ...
|
|
82
|
-
})
|
|
83
|
-
```
|
|
84
|
-
|
|
85
|
-
2. Generate and apply migration:
|
|
86
|
-
```bash
|
|
87
|
-
bun run db:generate
|
|
88
|
-
bun run db:migrate
|
|
89
|
-
```
|
|
90
|
-
|
|
91
|
-
**Common Issue**: If you see "relation does not exist" errors, the module schema likely isn't registered in `drizzle.config.ts`.
|
|
92
|
-
|
|
93
|
-
## Connection
|
|
94
|
-
|
|
95
|
-
```typescript
|
|
96
|
-
import { db } from '@__APP_NAME_KEBAB__/db'
|
|
97
|
-
|
|
98
|
-
const users = await db.select().from(usersTable)
|
|
99
|
-
```
|
|
@@ -1,23 +0,0 @@
|
|
|
1
|
-
import { defineConfig } from 'drizzle-kit'
|
|
2
|
-
import dotenv from 'dotenv'
|
|
3
|
-
import { dirname, resolve } from 'path'
|
|
4
|
-
import { fileURLToPath } from 'url'
|
|
5
|
-
import { buildDatabaseUrl } from './src/connection'
|
|
6
|
-
|
|
7
|
-
const currentFilePath = fileURLToPath(import.meta.url)
|
|
8
|
-
const currentDirPath = dirname(currentFilePath)
|
|
9
|
-
|
|
10
|
-
dotenv.config({
|
|
11
|
-
path: resolve(currentDirPath, '../../apps/server/.env'),
|
|
12
|
-
})
|
|
13
|
-
|
|
14
|
-
export default defineConfig({
|
|
15
|
-
schema: [
|
|
16
|
-
resolve(currentDirPath, './src/schema'),
|
|
17
|
-
// Module schemas - add new module schema paths here
|
|
18
|
-
resolve(currentDirPath, '../items-module/src/adapters/item.drizzle.ts'),
|
|
19
|
-
],
|
|
20
|
-
out: resolve(currentDirPath, './src/migrations'),
|
|
21
|
-
dialect: 'postgresql',
|
|
22
|
-
dbCredentials: { url: buildDatabaseUrl() },
|
|
23
|
-
})
|
|
@@ -1,36 +0,0 @@
|
|
|
1
|
-
{
|
|
2
|
-
"name": "@__APP_NAME_KEBAB__/db",
|
|
3
|
-
"version": "0.0.1",
|
|
4
|
-
"private": true,
|
|
5
|
-
"type": "module",
|
|
6
|
-
"main": "src/index.ts",
|
|
7
|
-
"types": "src/index.ts",
|
|
8
|
-
"exports": {
|
|
9
|
-
".": {
|
|
10
|
-
"types": "./src/index.ts",
|
|
11
|
-
"default": "./src/index.ts"
|
|
12
|
-
},
|
|
13
|
-
"./*": {
|
|
14
|
-
"types": "./src/*.ts",
|
|
15
|
-
"default": "./src/*.ts"
|
|
16
|
-
}
|
|
17
|
-
},
|
|
18
|
-
"scripts": {
|
|
19
|
-
"db:generate": "drizzle-kit generate",
|
|
20
|
-
"db:migrate": "drizzle-kit migrate",
|
|
21
|
-
"db:studio": "drizzle-kit studio"
|
|
22
|
-
},
|
|
23
|
-
"devDependencies": {
|
|
24
|
-
"drizzle-kit": "^0.31.2",
|
|
25
|
-
"@types/pg": "^8.11.11"
|
|
26
|
-
},
|
|
27
|
-
"peerDependencies": {
|
|
28
|
-
"typescript": "^5"
|
|
29
|
-
},
|
|
30
|
-
"dependencies": {
|
|
31
|
-
"drizzle-orm": "^0.44.2",
|
|
32
|
-
"pg": "^8.14.1",
|
|
33
|
-
"dotenv": "^17.2.2",
|
|
34
|
-
"zod": "^4.1.11"
|
|
35
|
-
}
|
|
36
|
-
}
|
|
@@ -1,40 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* Database connection utilities
|
|
3
|
-
* Single source of truth for DATABASE_URL construction
|
|
4
|
-
*/
|
|
5
|
-
|
|
6
|
-
/**
|
|
7
|
-
* Build DATABASE_URL from environment variables
|
|
8
|
-
*
|
|
9
|
-
* Supports two modes:
|
|
10
|
-
* 1. Direct DATABASE_URL - used in local development
|
|
11
|
-
* 2. Individual DB_* vars - used in Cloud Run with Cloud SQL Auth Proxy
|
|
12
|
-
*
|
|
13
|
-
* @throws Error if neither DATABASE_URL nor complete DB_* vars are provided
|
|
14
|
-
*/
|
|
15
|
-
export function buildDatabaseUrl(): string {
|
|
16
|
-
// Prefer DATABASE_URL if provided directly
|
|
17
|
-
if (process.env.DATABASE_URL) {
|
|
18
|
-
return process.env.DATABASE_URL
|
|
19
|
-
}
|
|
20
|
-
|
|
21
|
-
// Construct from individual components (Cloud Run with Cloud SQL)
|
|
22
|
-
const { DB_HOST, DB_USER, DB_PASSWORD, DB_NAME } = process.env
|
|
23
|
-
if (DB_HOST && DB_USER && DB_PASSWORD && DB_NAME) {
|
|
24
|
-
return `postgresql://${DB_USER}:${encodeURIComponent(DB_PASSWORD)}@/${DB_NAME}?host=${DB_HOST}`
|
|
25
|
-
}
|
|
26
|
-
|
|
27
|
-
throw new Error(
|
|
28
|
-
'Missing database configuration: provide DATABASE_URL or DB_HOST, DB_USER, DB_PASSWORD, DB_NAME'
|
|
29
|
-
)
|
|
30
|
-
}
|
|
31
|
-
|
|
32
|
-
/**
|
|
33
|
-
* Ensure DATABASE_URL is set in process.env
|
|
34
|
-
* Call this early in application startup to set up the environment
|
|
35
|
-
*/
|
|
36
|
-
export function ensureDatabaseUrl(): string {
|
|
37
|
-
const url = buildDatabaseUrl()
|
|
38
|
-
process.env.DATABASE_URL = url
|
|
39
|
-
return url
|
|
40
|
-
}
|
|
@@ -1,51 +0,0 @@
|
|
|
1
|
-
import { pgTable, text, timestamp, boolean } from 'drizzle-orm/pg-core'
|
|
2
|
-
|
|
3
|
-
export const user = pgTable('user', {
|
|
4
|
-
id: text('id').primaryKey(),
|
|
5
|
-
name: text('name').notNull(),
|
|
6
|
-
email: text('email').notNull().unique(),
|
|
7
|
-
emailVerified: boolean('email_verified').notNull(),
|
|
8
|
-
image: text('image'),
|
|
9
|
-
createdAt: timestamp('created_at').notNull(),
|
|
10
|
-
updatedAt: timestamp('updated_at').notNull(),
|
|
11
|
-
})
|
|
12
|
-
|
|
13
|
-
export const session = pgTable('session', {
|
|
14
|
-
id: text('id').primaryKey(),
|
|
15
|
-
expiresAt: timestamp('expires_at').notNull(),
|
|
16
|
-
token: text('token').notNull().unique(),
|
|
17
|
-
createdAt: timestamp('created_at').notNull(),
|
|
18
|
-
updatedAt: timestamp('updated_at').notNull(),
|
|
19
|
-
ipAddress: text('ip_address'),
|
|
20
|
-
userAgent: text('user_agent'),
|
|
21
|
-
userId: text('user_id')
|
|
22
|
-
.notNull()
|
|
23
|
-
.references(() => user.id, { onDelete: 'cascade' }),
|
|
24
|
-
})
|
|
25
|
-
|
|
26
|
-
export const account = pgTable('account', {
|
|
27
|
-
id: text('id').primaryKey(),
|
|
28
|
-
accountId: text('account_id').notNull(),
|
|
29
|
-
providerId: text('provider_id').notNull(),
|
|
30
|
-
userId: text('user_id')
|
|
31
|
-
.notNull()
|
|
32
|
-
.references(() => user.id, { onDelete: 'cascade' }),
|
|
33
|
-
accessToken: text('access_token'),
|
|
34
|
-
refreshToken: text('refresh_token'),
|
|
35
|
-
idToken: text('id_token'),
|
|
36
|
-
accessTokenExpiresAt: timestamp('access_token_expires_at'),
|
|
37
|
-
refreshTokenExpiresAt: timestamp('refresh_token_expires_at'),
|
|
38
|
-
scope: text('scope'),
|
|
39
|
-
password: text('password'),
|
|
40
|
-
createdAt: timestamp('created_at').notNull(),
|
|
41
|
-
updatedAt: timestamp('updated_at').notNull(),
|
|
42
|
-
})
|
|
43
|
-
|
|
44
|
-
export const verification = pgTable('verification', {
|
|
45
|
-
id: text('id').primaryKey(),
|
|
46
|
-
identifier: text('identifier').notNull(),
|
|
47
|
-
value: text('value').notNull(),
|
|
48
|
-
expiresAt: timestamp('expires_at').notNull(),
|
|
49
|
-
createdAt: timestamp('created_at'),
|
|
50
|
-
updatedAt: timestamp('updated_at'),
|
|
51
|
-
})
|