LoginSignup
0
0

D1にDrizzleORMを導入してみる

Last updated at Posted at 2023-12-17

背景

素のD1だとSQLが複雑になったときにしんどいので、ORMを導入したい。
CommunityProjectにも掲載とサンプルがある、drizzle-ormを導入してみる。

参考

下記のサンプルリポジトリをもとに試していきます。

DrizzleORMのインストール

DrizzleORMをインストールします。

npm install drizzle-orm better-sqlite3
## opt-in automatic migrations generator
npm install -D drizzle-kit 

package.jsonにschema.tsファイルを元に、generateするスクリプトを追加しておきます。

package.json
  "scripts": {
+    "generate": "drizzle-kit generate:sqlite --schema=src/schema.ts",
+    "up": "drizzle-kit up:sqlite --schema=src/schema.ts"
  }

drizzle.config.jsonファイルを作成します。

drizzle.config.json
{
    "out": "drizzle",
    "schema": "src/schema.ts"
}

Schemaファイルを作成しgenerateする・

サンプルプロジェクトをもとに、下記のshemaファイルを作成します。

src/schema.ts
import { integer, sqliteTable, text } from 'drizzle-orm/sqlite-core';

export const users = sqliteTable('users', {
	id: integer('id').primaryKey(),
	name: text('name').notNull(),
	email: text('email').notNull(),
});

generateスクリプトを叩くことで、drizzleフォルダが作成されます。

$ npm run generate

generate後、下記のスクリプトを叩いて、ローカルの開発環境にSQLを実行し、テーブルを作成します。

$ wrangler d1 execute <DATABASE_NAME> --local --file=./drizzle/0000_sparkling_post.sql

その後、開発環境を立ち上げると、usersテーブルを持ったローカル開発環境が立ち上がります。

$ npx wrangler dev

データベースをWorkers+ORMで叩いてみる

サンプルのリポジトリではrouterが導入されていたので、routerを外したサンプルコードを書いてみました。

localhostを叩く度に、ダミーデータが1件INSERTされて、テーブルの全件をブラウザへ返すSQLです。

import type { DrizzleD1Database } from 'drizzle-orm/d1';
import { drizzle } from 'drizzle-orm/d1';

import { users } from './schema';


export interface Env {
	DB: D1Database;
}

interface Request {
	db: DrizzleD1Database;
}

export default {
	async fetch(req: Request, env: Env, ctx: ExecutionContext): Promise<Response> {
	const db = drizzle(env.DB);

		const query = db.select().from(users);
		console.log(query.toSQL());
		const name = generateRandomWord()
		const email = `${generateRandomWord()}@${generateRandomWord()}.com`
		const res = await db.insert(users).values({ name, email }).returning().get();

		const result = await query.all();
		return new Response(JSON.stringify(result));
		},
};

function generateRandomLetter() {
  const alphabet = "abcdefghijklmnopqrstuvwxyz";
  return alphabet[Math.floor(Math.random() * alphabet.length)];
}

function generateRandomWord() {
  return generateRandomLetter() + generateRandomLetter() + generateRandomLetter();
}

localhostへアクセスするたびにデータが1つずつ増えていくのが確認できると思います。

image.png

0
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
0