2023-08-07 06:45:02 +00:00
|
|
|
import fs from 'node:fs/promises';
|
|
|
|
import path from 'node:path';
|
|
|
|
|
2023-12-02 01:28:33 +00:00
|
|
|
import { FileMigrationProvider, Kysely, Migrator, PolySqliteDialect } from '@/deps.ts';
|
2023-08-10 18:37:56 +00:00
|
|
|
import { Conf } from '@/config.ts';
|
2023-12-28 02:19:59 +00:00
|
|
|
import { setPragma } from '@/pragma.ts';
|
2023-12-03 20:58:35 +00:00
|
|
|
import SqliteWorker from '@/workers/sqlite.ts';
|
2023-07-09 16:47:19 +00:00
|
|
|
|
2023-08-09 06:53:50 +00:00
|
|
|
interface DittoDB {
|
2023-08-07 05:50:12 +00:00
|
|
|
events: EventRow;
|
2023-08-30 17:04:45 +00:00
|
|
|
events_fts: EventFTSRow;
|
2023-08-07 05:50:12 +00:00
|
|
|
tags: TagRow;
|
2023-08-14 19:11:28 +00:00
|
|
|
relays: RelayRow;
|
2023-09-09 22:41:30 +00:00
|
|
|
unattached_media: UnattachedMediaRow;
|
2023-12-10 22:04:52 +00:00
|
|
|
author_stats: AuthorStatsRow;
|
2023-12-10 17:10:11 +00:00
|
|
|
event_stats: EventStatsRow;
|
2024-03-19 22:45:19 +00:00
|
|
|
pubkey_domains: PubkeyDomainRow;
|
2023-12-10 17:10:11 +00:00
|
|
|
}
|
|
|
|
|
2023-12-10 22:04:52 +00:00
|
|
|
interface AuthorStatsRow {
|
2023-12-10 17:10:11 +00:00
|
|
|
pubkey: string;
|
|
|
|
followers_count: number;
|
|
|
|
following_count: number;
|
|
|
|
notes_count: number;
|
|
|
|
}
|
|
|
|
|
|
|
|
interface EventStatsRow {
|
|
|
|
event_id: string;
|
|
|
|
replies_count: number;
|
|
|
|
reposts_count: number;
|
|
|
|
reactions_count: number;
|
2023-08-07 05:50:12 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
interface EventRow {
|
|
|
|
id: string;
|
|
|
|
kind: number;
|
2023-08-06 17:54:00 +00:00
|
|
|
pubkey: string;
|
2023-08-07 05:50:12 +00:00
|
|
|
content: string;
|
|
|
|
created_at: number;
|
|
|
|
tags: string;
|
|
|
|
sig: string;
|
2024-03-03 03:11:45 +00:00
|
|
|
deleted_at: number | null;
|
2023-08-06 17:54:00 +00:00
|
|
|
}
|
2023-07-09 16:47:19 +00:00
|
|
|
|
2023-08-30 17:04:45 +00:00
|
|
|
interface EventFTSRow {
|
|
|
|
id: string;
|
|
|
|
content: string;
|
|
|
|
}
|
|
|
|
|
2023-08-07 05:50:12 +00:00
|
|
|
interface TagRow {
|
|
|
|
tag: string;
|
2023-09-05 21:11:38 +00:00
|
|
|
value: string;
|
2023-08-07 05:50:12 +00:00
|
|
|
event_id: string;
|
|
|
|
}
|
2023-07-09 16:47:19 +00:00
|
|
|
|
2023-08-14 19:11:28 +00:00
|
|
|
interface RelayRow {
|
|
|
|
url: string;
|
2023-08-16 00:07:26 +00:00
|
|
|
domain: string;
|
|
|
|
active: boolean;
|
2023-08-14 19:11:28 +00:00
|
|
|
}
|
|
|
|
|
2023-09-09 22:41:30 +00:00
|
|
|
interface UnattachedMediaRow {
|
|
|
|
id: string;
|
2023-09-10 01:12:47 +00:00
|
|
|
pubkey: string;
|
2023-09-09 23:12:54 +00:00
|
|
|
url: string;
|
2023-09-09 22:41:30 +00:00
|
|
|
data: string;
|
|
|
|
uploaded_at: Date;
|
|
|
|
}
|
|
|
|
|
2024-03-19 22:45:19 +00:00
|
|
|
interface PubkeyDomainRow {
|
|
|
|
pubkey: string;
|
|
|
|
domain: string;
|
2024-04-06 02:41:55 +00:00
|
|
|
last_updated_at: number;
|
2024-03-19 22:45:19 +00:00
|
|
|
}
|
|
|
|
|
2023-12-03 20:58:35 +00:00
|
|
|
const sqliteWorker = new SqliteWorker();
|
|
|
|
await sqliteWorker.open(Conf.dbPath);
|
2023-12-02 00:15:39 +00:00
|
|
|
|
2023-08-09 06:53:50 +00:00
|
|
|
const db = new Kysely<DittoDB>({
|
2023-12-02 00:15:39 +00:00
|
|
|
dialect: new PolySqliteDialect({
|
|
|
|
database: sqliteWorker,
|
2023-08-07 06:45:02 +00:00
|
|
|
}),
|
|
|
|
});
|
|
|
|
|
2023-10-12 04:44:28 +00:00
|
|
|
// Set PRAGMA values.
|
2023-10-12 04:34:59 +00:00
|
|
|
await Promise.all([
|
|
|
|
setPragma(db, 'synchronous', 'normal'),
|
|
|
|
setPragma(db, 'temp_store', 'memory'),
|
|
|
|
setPragma(db, 'mmap_size', Conf.sqlite.mmapSize),
|
|
|
|
]);
|
|
|
|
|
2023-08-07 06:45:02 +00:00
|
|
|
const migrator = new Migrator({
|
|
|
|
db,
|
|
|
|
provider: new FileMigrationProvider({
|
|
|
|
fs,
|
|
|
|
path,
|
|
|
|
migrationFolder: new URL(import.meta.resolve('./db/migrations')).pathname,
|
2023-08-07 05:50:12 +00:00
|
|
|
}),
|
|
|
|
});
|
2023-08-07 01:14:11 +00:00
|
|
|
|
2023-09-05 21:04:23 +00:00
|
|
|
/** Migrate the database to the latest version. */
|
|
|
|
async function migrate() {
|
2023-12-28 02:19:59 +00:00
|
|
|
console.info('Running migrations...');
|
2023-09-05 21:04:23 +00:00
|
|
|
const results = await migrator.migrateToLatest();
|
|
|
|
|
|
|
|
if (results.error) {
|
|
|
|
console.error(results.error);
|
|
|
|
Deno.exit(1);
|
|
|
|
} else {
|
|
|
|
if (!results.results?.length) {
|
2023-12-28 02:19:59 +00:00
|
|
|
console.info('Everything up-to-date.');
|
2023-09-05 21:04:23 +00:00
|
|
|
} else {
|
2023-12-28 02:19:59 +00:00
|
|
|
console.info('Migrations finished!');
|
2023-12-10 17:10:11 +00:00
|
|
|
for (const { migrationName, status } of results.results!) {
|
2023-12-28 02:19:59 +00:00
|
|
|
console.info(` - ${migrationName}: ${status}`);
|
2023-09-05 21:04:23 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
await migrate();
|
2023-08-07 06:45:02 +00:00
|
|
|
|
2023-12-29 23:01:23 +00:00
|
|
|
export { type AuthorStatsRow, db, type DittoDB, type EventRow, type EventStatsRow, type TagRow };
|