‹ 首页

d1-drizzle-schema

@jezweb · 收录于 1 周前 · 上游提交 2 周前

Generate Drizzle ORM schemas for Cloudflare D1 databases with correct D1-specific patterns. Produces schema files, migration commands, type exports, and DATABASE_SCHEMA.md documentation. Handles D1 quirks: foreign keys always enforced, no native BOOLEAN/DATETIME types, 100 bound parameter limit, JSON stored as TEXT. Use when creating a new database, adding tables, or scaffolding a D1 data layer.

适合你,如果正在用 Cloudflare D1 并需要 Drizzle ORM 模式代码

/ 下载安装
d1-drizzle-schema.skill双击,或拖进 Claude 桌面版 / Cowork,即完成安装↓ .skill↓ .zip
用别的 agent?下载 .zip 解压,把文件夹放进它的技能目录
Claude Code~/.claude/skills/(项目级 .claude/skills/)
Codex CLI~/.codex/skills/
Cursor自动读取上面两处目录
其他工具见其文档的「skills」目录;两个下载是同一份文件,只是名字不同
/ 通过 npx 安装 校验哈希
npx oh-my-skill add jezweb/claude-skills/d1-drizzle-schema
/ 通过 bash 安装
curl -fsSL https://oh-my-skill.com/install.sh | bash -s -- jezweb/claude-skills/d1-drizzle-schema
/ 已经装过?验证本机副本,不用重装
npx oh-my-skill verify jezweb/claude-skills/d1-drizzle-schema
安装目标可用 --agent / --scope 或 --to 明确指定;省略时只会在唯一已存在的 agent 目录上自动选择,零命中或多命中会停止并提示。content_hash 缺失或不一致均拒装。
910GitHub stars
~1.1K最小装载
~3.9K含声明引用
~3.9K文本包总量
镜像托管

怎么用

技能原文 SKILL.md作者撰写 · MIT · e875a6b

D1 Drizzle Schema

Generate correct Drizzle ORM schemas for Cloudflare D1. D1 is SQLite-based but has important differences that cause subtle bugs if you use standard SQLite patterns. This skill produces schemas that work correctly with D1's constraints.

Critical D1 Differences

| Feature | Standard SQLite | D1 | |---------|-----------------|-----| | Foreign keys | OFF by default | Always ON (cannot disable) | | Boolean type | No | No — use integer({ mode: 'boolean' }) | | Datetime type | No | No — use integer({ mode: 'timestamp' }) | | Max bound params | ~999 | 100 (affects bulk inserts) | | JSON support | Extension | Always available (json_extract, ->, ->>) | | Concurrency | Multi-writer | Single-threaded (one query at a time) |

Workflow
Step 1: Describe the Data Model

Gather requirements: what tables, what relationships, what needs indexing. If working from an existing description, infer the schema directly.

Step 2: Generate Drizzle Schema

Create schema files using D1-correct column patterns:

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),
}))

See [references/column-patterns.md](references/column-patterns.md) for the full type reference.

Step 3: Add Relations

Drizzle relations are query builder helpers (separate from FK constraints):

import { relations } from 'drizzle-orm'

export const usersRelations = relations(users, ({ one, many }) => ({
  organisation: one(organisations, {
    fields: [users.organisationId],
    references: [organisations.id],
  }),
  posts: many(posts),
}))
Step 4: Export Types
export type User = typeof users.$inferSelect
export type NewUser = typeof users.$inferInsert
Step 5: Set Up Drizzle Config

Copy [assets/drizzle-config-template.ts](assets/drizzle-config-template.ts) to drizzle.config.ts and update the schema path.

Step 6: Add Migration Scripts

Add to 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"
}

Always run on BOTH local AND remote before testing.

Step 7: Generate DATABASE_SCHEMA.md

Document the schema for future sessions:

  • Tables with columns, types, and constraints
  • Relationships and foreign keys
  • Indexes and their purpose
  • Migration workflow
Bulk Insert Pattern

D1 limits bound parameters to 100. Calculate batch size:

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 Runtime Usage
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()
Reference Files

| When | Read | |------|------| | D1 vs SQLite, JSON queries, limits | [references/d1-specifics.md](references/d1-specifics.md) | | Column type patterns for Drizzle + D1 | [references/column-patterns.md](references/column-patterns.md) |

Assets

| File | Purpose | |------|---------| | [assets/drizzle-config-template.ts](assets/drizzle-config-template.ts) | Starter drizzle.config.ts for D1 | | [assets/schema-template.ts](assets/schema-template.ts) | Example schema with all common D1 patterns |

按 MIT 许可原样转载,未经改动 · 在 GitHub 查看 →

评论

登录即可评论;带「已验证安装」的,是发布者名下有本店的安装或持有记录。