关于 d1-drizzle-schema
用于生成适配 Cloudflare D1 特性的 Drizzle ORM 模式的技能,涵盖表结构、关系、配置、迁移脚本和模式文档。
主要功能
- 01生成兼容 D1 的 Drizzle 模式
- 02处理 D1 数据类型与限制
- 03定义关系并导出推断类型
- 04提供 Drizzle 配置模板
- 05添加迁移脚本和模式文档
适用场景
- 01为 Cloudflare D1 数据库设计表结构
- 02规避批量插入的参数数量限制
- 03记录模式结构和迁移流程
安装
复制下面的命令,在终端中运行。
$
npx skills add https:/ / github.com/ jezweb/ claude-skills --skill d1-drizzle-schema安装后在 Claude Code 中输入/d1-drizzle-schema确认已加载。
包含的文件
除 SKILL.md 外,安装时一起下载的参考资料和脚本。
assets/drizzle-config-template.tsschema-template.tsreferences/column-patterns.mdd1-specifics.md详细介绍
D1 Drizzle 架构
为 Cloudflare D1 生成正确的 Drizzle ORM 架构。D1 基于 SQLite,但有一些重要差异;如果使用标准 SQLite 模式,可能会导致细微的错误。本技能可生成符合 D1 限制的架构。
D1 的关键差异
| 特性 | 标准 SQLite | D1 |
|---|---|---|
| 外键 | 默认关闭 | 始终开启(无法关闭) |
| 布尔类型 | 不支持 | 不支持——使用 integer({ mode: 'boolean' }) |
| 日期时间类型 | 不支持 | 不支持——使用 integer({ mode: 'timestamp' }) |
| 绑定参数上限 | 约 999 | 100(影响批量插入) |
| JSON 支持 | 扩展 | 始终可用(json_extract、->、->>) |
| 并发 | 多写入器 | 单线程(一次只能执行一个查询) |
工作流
步骤 1:描述数据模型
收集需求:需要哪些表、表之间有哪些关系、哪些字段需要建立索引。如果已有描述,可直接据此推断架构。
步骤 2:生成 Drizzle 架构
使用符合 D1 要求的列模式创建架构文件:
import { sqliteTable, text, integer, real, index, uniqueIndex } from 'drizzle-orm/sqlite-core'
export const users = sqliteTable('users', {
// UUID primary key (preferred for D1)
id: text('id').primaryKey().$defaultFn(() => crypto.randomUUID()),
// Text fields
name: text('name').notNull(),
email: text('email').notNull(),
// Enum (stored as TEXT, validated at schema level)
role: text('role', { enum: ['admin', 'editor', 'viewer'] }).notNull().default('viewer'),
// Boolean (D1 has no BOOL — stored as INTEGER 0/1)
emailVerified: integer('email_verified', { mode: 'boolean' }).notNull().default(false),
// Timestamp (D1 has no DATETIME — stored as unix seconds)
createdAt: integer('created_at', { mode: 'timestamp' }).notNull().$defaultFn(() => new Date()),
updatedAt: integer('updated_at', { mode: 'timestamp' }).notNull().$defaultFn(() => new Date()),
// Typed JSON (stored as TEXT, Drizzle auto-serialises)
preferences: text('preferences', { mode: 'json' }).$type<UserPreferences>(),
// Foreign key (always enforced in D1)
organisationId: text('organisation_id').references(() => organisations.id, { onDelete: 'cascade' }),
}, (table) => ({
emailIdx: uniqueIndex('users_email_idx').on(table.email),
orgIdx: index('users_org_idx').on(table.organisationId),
}))
完整类型参考请参阅 references/column-patterns.md。
步骤 3:添加关系
Drizzle 关系是查询构建器辅助工具(与外键约束分开):
import { relations } from 'drizzle-orm'
export const usersRelations = relations(users, ({ one, many }) => ({
organisation: one(organisations, {
fields: [users.organisationId],
references: [organisations.id],
}),
posts: many(posts),
}))
步骤 4:导出类型
export type User = typeof users.$inferSelect
export type NewUser = typeof users.$inferInsert
步骤 5:设置 Drizzle 配置
将 assets/drizzle-config-template.ts 复制到 drizzle.config.ts,并更新架构路径。
步骤 6:添加迁移脚本
添加到 package.json:
{
"db:generate": "drizzle-kit generate",
"db:migrate:local": "wrangler d1 migrations apply DB --local",
"db:migrate:remote": "wrangler d1 migrations apply DB --remote"
}
测试前,务必先在本地和远程都运行。
步骤 7:生成 DATABASE_SCHEMA.md
记录架构,供后续会话使用:
- 包含列、类型和约束的表
- 关系和外键
- 索引及其用途
- 迁移工作流
批量插入模式
D1 将绑定参数限制为 100 个。计算批次大小:
const BATCH_SIZE = Math.floor(100 / COLUMNS_PER_ROW)
for (let i = 0; i < rows.length; i += BATCH_SIZE) {
await db.insert(table).values(rows.slice(i, i + BATCH_SIZE))
}
D1 运行时用法
import { drizzle } from 'drizzle-orm/d1'
import * as schema from './schema'
// In Worker fetch handler:
const db = drizzle(env.DB, { schema })
// Query patterns
const all = await db.select().from(schema.users).all() // Array<User>
const one = await db.select().from(schema.users).where(eq(schema.users.id, id)).get() // User | undefined
const count = await db.select({ count: sql`count(*)` }).from(schema.users).get()
参考文件
| 何时 | 阅读 |
|---|---|
| D1 与 SQLite 的差异、JSON 查询、限制 | references/d1-specifics.md |
| Drizzle + D1 的列类型模式 | references/column-patterns.md |
资源
| 文件 | 用途 |
|---|---|
| assets/drizzle-config-template.ts | 用于 D1 的初始 drizzle.config.ts |
| assets/schema-template.ts | 包含所有常见 D1 模式的架构示例 |
评论
支持 Markdown