Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Use Pglite instead of Sqlite #18

Merged
merged 6 commits into from
Aug 13, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
17 changes: 17 additions & 0 deletions docker-compose.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
version: '3.8'

services:
db:
image: postgres:13
container_name: my_postgres
environment:
POSTGRES_DB: mydb
POSTGRES_USER: myuser
POSTGRES_PASSWORD: mypassword
ports:
- "5434:5432"
volumes:
- postgres_data:/var/lib/postgresql/data

volumes:
postgres_data:
4 changes: 2 additions & 2 deletions drizzle.config.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2,12 +2,12 @@ import "dotenv/config";
import type { Config } from "drizzle-kit";

export default {
dialect: "sqlite",
dialect: "postgresql",
schema: "./src/database/schema.ts",
out: "./src/database/migrations",
verbose: true,
strict: true,
dbCredentials: {
url: "workbench.db",
url: "postgresql://myuser:mypassword@localhost:5434/mydb",
},
} satisfies Config;
8 changes: 4 additions & 4 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -26,13 +26,12 @@
"@tailwindcss/typography": "^0.5.13",
"@testing-library/jest-dom": "^6.4.5",
"@testing-library/svelte": "^5.2.0",
"@types/better-sqlite3": "^7.6.11",
"@types/lodash": "^4.17.1",
"@types/pg": "^8.11.6",
"@vitest/browser": "^1.6.0",
"@vitest/ui": "^1.6.0",
"autoprefixer": "^10.4.19",
"better-sqlite3": "^10.0.0",
"drizzle-kit": "^0.21.2",
"drizzle-kit": "^0.24.0",
"jsdom": "^24.0.0",
"postcss": "^8.4.38",
"prettier": "^3.2.5",
Expand Down Expand Up @@ -60,6 +59,7 @@
"@ai-sdk/mistral": "^0.0.26",
"@ai-sdk/openai": "^0.0.10",
"@ai-sdk/ui-utils": "^0.0.24",
"@electric-sql/pglite": "^0.2.0",
"@fontsource-variable/inter": "^5.0.18",
"@lexical/history": "^0.16.0",
"@lexical/plain-text": "^0.16.0",
Expand All @@ -81,7 +81,7 @@
"marked-katex-extension": "^5.0.1",
"msw": "^2.3.1",
"nanoid": "^5.0.7",
"sqlocal": "^0.9.0",
"pg": "^8.12.0",
"svelte-filepond": "^0.2.2",
"svelte-french-toast": "^1.2.0",
"tailwind-merge": "^2.3.0",
Expand Down
552 changes: 247 additions & 305 deletions pnpm-lock.yaml

Large diffs are not rendered by default.

23 changes: 10 additions & 13 deletions src/database/client.ts
Original file line number Diff line number Diff line change
@@ -1,21 +1,18 @@
import { SQLocalDrizzle } from "sqlocal/drizzle";
import { drizzle, SqliteRemoteDatabase } from "drizzle-orm/sqlite-proxy";
import { drizzle, type PgliteDatabase } from "drizzle-orm/pglite";
import { PGlite } from "@electric-sql/pglite";
import * as schema from "./schema";
import { BaseSQLiteDatabase } from "drizzle-orm/sqlite-core";

export const SQLITE_FILENAME = "workbench.db";
let db: PgliteDatabase<typeof schema> | undefined = undefined;

let db: SqliteRemoteDatabase<typeof schema> | undefined = undefined;

export function useDb(): BaseSQLiteDatabase<any, any, typeof schema> {
export function useDb(): PgliteDatabase<typeof schema> {
if (!db) {
const { driver, batchDriver } = new SQLocalDrizzle(SQLITE_FILENAME);
db = drizzle(driver, batchDriver, { schema });
const client = new PGlite("idb://workbench-data");
db = drizzle(client, { schema });
}
return db;
}

export function useDbFile() {
const { getDatabaseFile, overwriteDatabaseFile } = new SQLocalDrizzle(SQLITE_FILENAME);
return { getDatabaseFile, overwriteDatabaseFile };
}
// export function useDbFile() {
// const { getDatabaseFile, overwriteDatabaseFile } = new SQLocalDrizzle(SQLITE_FILENAME);
// return { getDatabaseFile, overwriteDatabaseFile };
// }
137 changes: 77 additions & 60 deletions src/database/index.ts
Original file line number Diff line number Diff line change
@@ -1,32 +1,33 @@
import { useDb, useDbFile } from "./client.js";
import { useDb } from "./client.js";
import * as schema from "./schema.js";
import { sql } from "drizzle-orm/sql";
import type { PgliteDatabase } from "drizzle-orm/pglite";

export { registerModel, invalidateModel } from "./model.js";
export * from "./schema.js";

export { schema, useDb };

export async function overwriteDb() {
const { overwriteDatabaseFile } = useDbFile();
}

export async function exportDb() {
const { getDatabaseFile } = useDbFile();
const databaseFile = await getDatabaseFile();
const fileUrl = URL.createObjectURL(databaseFile);

const now = new Date();
const timestamp = now.toISOString().split(".")[0].replace(/\:/g, "-");

const a = document.createElement("a");
a.href = fileUrl;
a.download = `workbench-${timestamp}.db`;
a.click();
a.remove();

URL.revokeObjectURL(fileUrl);
}
// export async function overwriteDb() {
// const { overwriteDatabaseFile } = useDbFile();
// }
//
// export async function exportDb() {
// const { getDatabaseFile } = useDbFile();
// const databaseFile = await getDatabaseFile();
// const fileUrl = URL.createObjectURL(databaseFile);
//
// const now = new Date();
// const timestamp = now.toISOString().split(".")[0].replace(/\:/g, "-");
//
// const a = document.createElement("a");
// a.href = fileUrl;
// a.download = `workbench-${timestamp}.db`;
// a.click();
// a.remove();
//
// URL.revokeObjectURL(fileUrl);
// }

export function exposeDb() {
const db = useDb();
Expand All @@ -36,45 +37,61 @@ export function exposeDb() {
window.sql = sql;
// @ts-expect-error
window.db_destroy = async function () {
const rows = await db.all(sql`SELECT name FROM sqlite_master WHERE type='table';`);
console.log("Dropping all tables", rows);
for (const record of rows) {
// drop table
// @ts-ignore
await db.run(sql.raw(`DROP TABLE ${record[0]};`));
}
};
// @ts-expect-error
window.db_listTables = async function () {
const rows = await db.all(sql`SELECT name FROM sqlite_master WHERE type='table';`);
console.log("Tables", rows);
for (const record of rows) {
// list count of rows
// @ts-ignore
const count = await db.get(sql.raw(`SELECT COUNT(*) FROM ${record[0]};`));
// @ts-ignore
console.log(record[0], count);
}
};
// @ts-expect-error
window.db_download = exportDb;
// @ts-expect-error
window.db_overwrite = function () {
const input = document.createElement("input");
input.type = "file";
input.accept = ".db";
input.onchange = async function (e: any) {
console.log("overwrite", e);
if (!e.target) {
return;
}
const file = e.target.files[0];
if (!file) {
return;
const db = useDb() as PgliteDatabase<any>;

// Get all tables in the public schema
const results = await db.execute<{ tablename: string }>(sql`
SELECT tablename
FROM pg_tables
WHERE schemaname = 'public';
`);

console.log("Dropping all tables", results.rows);

// Drop all tables
for (const record of results.rows) {
try {
await db.execute(sql.raw(`DROP TABLE IF EXISTS "${record.tablename}" CASCADE;`));
console.log(`Dropped table: ${record.tablename}`);
} catch (error) {
console.error(`Error dropping table ${record.tablename}:`, error);
}
const { overwriteDatabaseFile } = useDbFile();
await overwriteDatabaseFile(file);
};
document.body.appendChild(input);
}

console.log("All tables dropped");
};

// // @ts-expect-error
// window.db_listTables = async function () {
// const rows = await db.all(sql`SELECT name FROM sqlite_master WHERE type='table';`);
// console.log("Tables", rows);
// for (const record of rows) {
// // list count of rows
// // @ts-ignore
// const count = await db.get(sql.raw(`SELECT COUNT(*) FROM ${record[0]};`));
// // @ts-ignore
// console.log(record[0], count);
// }
// };
// // @ts-expect-error
// window.db_download = exportDb;
// // @ts-expect-error
// window.db_overwrite = function () {
// const input = document.createElement("input");
// input.type = "file";
// input.accept = ".db";
// input.onchange = async function (e: any) {
// console.log("overwrite", e);
// if (!e.target) {
// return;
// }
// const file = e.target.files[0];
// if (!file) {
// return;
// }
// const { overwriteDatabaseFile } = useDbFile();
// await overwriteDatabaseFile(file);
// };
// document.body.appendChild(input);
// };
}
Loading
Loading