mirror of
https://gitlab.com/soapbox-pub/ditto.git
synced 2025-12-06 11:29:46 +00:00
Merge branch 'timeouts' into 'main'
Add query timeouts See merge request soapbox-pub/ditto!403
This commit is contained in:
commit
4c257fa529
6 changed files with 31 additions and 19 deletions
|
|
@ -27,7 +27,7 @@
|
|||
"@hono/hono": "jsr:@hono/hono@^4.4.6",
|
||||
"@isaacs/ttlcache": "npm:@isaacs/ttlcache@^1.4.1",
|
||||
"@noble/secp256k1": "npm:@noble/secp256k1@^2.0.0",
|
||||
"@nostrify/nostrify": "jsr:@nostrify/nostrify@^0.23.3",
|
||||
"@nostrify/nostrify": "jsr:@nostrify/nostrify@^0.25.0",
|
||||
"@scure/base": "npm:@scure/base@^1.1.6",
|
||||
"@sentry/deno": "https://deno.land/x/sentry@7.112.2/index.mjs",
|
||||
"@soapbox/kysely-deno-sqlite": "jsr:@soapbox/kysely-deno-sqlite@^2.1.0",
|
||||
|
|
@ -51,7 +51,7 @@
|
|||
"iso-639-1": "npm:iso-639-1@2.1.15",
|
||||
"isomorphic-dompurify": "npm:isomorphic-dompurify@^2.11.0",
|
||||
"kysely": "npm:kysely@^0.27.3",
|
||||
"kysely_deno_postgres": "https://gitlab.com/soapbox-pub/kysely-deno-postgres/-/raw/b4725e74ad6ca359ba0e370b55dbb8bb845a8a83/mod.ts",
|
||||
"kysely_deno_postgres": "https://gitlab.com/soapbox-pub/kysely-deno-postgres/-/raw/c6869b9e12d74af78a846ad503d84493f5db9df4/mod.ts",
|
||||
"light-bolt11-decoder": "npm:light-bolt11-decoder",
|
||||
"linkify-plugin-hashtag": "npm:linkify-plugin-hashtag@^4.1.1",
|
||||
"linkify-string": "npm:linkify-string@^4.1.1",
|
||||
|
|
|
|||
12
deno.lock
generated
12
deno.lock
generated
|
|
@ -12,7 +12,7 @@
|
|||
"jsr:@nostrify/nostrify@^0.22.1": "jsr:@nostrify/nostrify@0.22.5",
|
||||
"jsr:@nostrify/nostrify@^0.22.4": "jsr:@nostrify/nostrify@0.22.4",
|
||||
"jsr:@nostrify/nostrify@^0.22.5": "jsr:@nostrify/nostrify@0.22.5",
|
||||
"jsr:@nostrify/nostrify@^0.23.3": "jsr:@nostrify/nostrify@0.23.3",
|
||||
"jsr:@nostrify/nostrify@^0.25.0": "jsr:@nostrify/nostrify@0.25.0",
|
||||
"jsr:@soapbox/kysely-deno-sqlite@^2.1.0": "jsr:@soapbox/kysely-deno-sqlite@2.2.0",
|
||||
"jsr:@soapbox/stickynotes@^0.4.0": "jsr:@soapbox/stickynotes@0.4.0",
|
||||
"jsr:@std/assert@^0.217.0": "jsr:@std/assert@0.217.0",
|
||||
|
|
@ -136,8 +136,8 @@
|
|||
"npm:zod@^3.23.8"
|
||||
]
|
||||
},
|
||||
"@nostrify/nostrify@0.23.3": {
|
||||
"integrity": "868b10dd094801e28f4982ef9815f0d43f2a807b6f8ad291c78ecb3eb291605a",
|
||||
"@nostrify/nostrify@0.25.0": {
|
||||
"integrity": "98f26f44e95ac87fc91b3f3809d38432e1a7f6aebf10380b2554b6f9526313c6",
|
||||
"dependencies": [
|
||||
"jsr:@std/encoding@^0.224.1",
|
||||
"npm:@scure/base@^1.1.6",
|
||||
|
|
@ -1395,6 +1395,10 @@
|
|||
"https://gitlab.com/soapbox-pub/kysely-deno-postgres/-/raw/b4725e74ad6ca359ba0e370b55dbb8bb845a8a83/mod.ts": "662438fd3909984bb8cbaf3fd44d2121e949d11301baf21d6c3f057ccf9887de",
|
||||
"https://gitlab.com/soapbox-pub/kysely-deno-postgres/-/raw/b4725e74ad6ca359ba0e370b55dbb8bb845a8a83/src/PostgreSQLDriver.ts": "ea5a523bceeed420858b744beeb95d48976cb2b0d3f519a68b65a8229036cf6a",
|
||||
"https://gitlab.com/soapbox-pub/kysely-deno-postgres/-/raw/b4725e74ad6ca359ba0e370b55dbb8bb845a8a83/src/PostgreSQLDriverDatabaseConnection.ts": "11e2fc10a3abb3d0729613c4b7cdb9cb73b597fd77353311bb6707c73a635fc5",
|
||||
"https://gitlab.com/soapbox-pub/kysely-deno-postgres/-/raw/c6869b9e12d74af78a846ad503d84493f5db9df4/deps.ts": "b3dbecae69c30a5f161323b8c8ebd91d9af1eceb98fafab3091c7281a4b64fed",
|
||||
"https://gitlab.com/soapbox-pub/kysely-deno-postgres/-/raw/c6869b9e12d74af78a846ad503d84493f5db9df4/mod.ts": "662438fd3909984bb8cbaf3fd44d2121e949d11301baf21d6c3f057ccf9887de",
|
||||
"https://gitlab.com/soapbox-pub/kysely-deno-postgres/-/raw/c6869b9e12d74af78a846ad503d84493f5db9df4/src/PostgreSQLDriver.ts": "0f5d1bc2b24d4e0052e38ee289fb2f5e8e1470544f61aa2afe65e1059bf35dfb",
|
||||
"https://gitlab.com/soapbox-pub/kysely-deno-postgres/-/raw/c6869b9e12d74af78a846ad503d84493f5db9df4/src/PostgreSQLDriverDatabaseConnection.ts": "e5d4e0fc9737c3ec253e679a51f5b43d2bb9a3386c147b7b1d14f4f5a5f734f1",
|
||||
"https://gitlab.com/soapbox-pub/kysely-deno-postgres/-/raw/f2948b86190a10faa293588775e162b3a8b52e70/deps.ts": "b3dbecae69c30a5f161323b8c8ebd91d9af1eceb98fafab3091c7281a4b64fed",
|
||||
"https://gitlab.com/soapbox-pub/kysely-deno-postgres/-/raw/f2948b86190a10faa293588775e162b3a8b52e70/mod.ts": "662438fd3909984bb8cbaf3fd44d2121e949d11301baf21d6c3f057ccf9887de",
|
||||
"https://gitlab.com/soapbox-pub/kysely-deno-postgres/-/raw/f2948b86190a10faa293588775e162b3a8b52e70/src/PostgreSQLDriver.ts": "ac1a39e86fd676973bce215e19db1f26b82408b8f2bb09a3601802974ea7cec6",
|
||||
|
|
@ -1420,7 +1424,7 @@
|
|||
"jsr:@bradenmacdonald/s3-lite-client@^0.7.4",
|
||||
"jsr:@db/sqlite@^0.11.1",
|
||||
"jsr:@hono/hono@^4.4.6",
|
||||
"jsr:@nostrify/nostrify@^0.23.3",
|
||||
"jsr:@nostrify/nostrify@^0.25.0",
|
||||
"jsr:@soapbox/kysely-deno-sqlite@^2.1.0",
|
||||
"jsr:@soapbox/stickynotes@^0.4.0",
|
||||
"jsr:@std/assert@^0.225.1",
|
||||
|
|
|
|||
|
|
@ -78,7 +78,7 @@ async function renderNotifications(
|
|||
const store = c.get('store');
|
||||
const pubkey = await c.get('signer')?.getPublicKey()!;
|
||||
const { signal } = c.req.raw;
|
||||
const opts = { signal, limit: params.limit };
|
||||
const opts = { signal, limit: params.limit, timeout: 10_000 };
|
||||
|
||||
const events = await store
|
||||
.query(filters, opts)
|
||||
|
|
|
|||
|
|
@ -73,11 +73,15 @@ function connectStream(socket: WebSocket) {
|
|||
const pubsub = await Storages.pubsub();
|
||||
|
||||
try {
|
||||
for (const event of await store.query(filters, { limit: FILTER_LIMIT })) {
|
||||
for (const event of await store.query(filters, { limit: FILTER_LIMIT, timeout: 1000 })) {
|
||||
send(['EVENT', subId, event]);
|
||||
}
|
||||
} catch (e) {
|
||||
send(['CLOSED', subId, e.message]);
|
||||
if (e instanceof RelayError) {
|
||||
send(['CLOSED', subId, e.message]);
|
||||
} else {
|
||||
send(['CLOSED', subId, 'error: something went wrong']);
|
||||
}
|
||||
controllers.delete(subId);
|
||||
return;
|
||||
}
|
||||
|
|
@ -124,7 +128,7 @@ function connectStream(socket: WebSocket) {
|
|||
/** Handle COUNT. Return the number of events matching the filters. */
|
||||
async function handleCount([_, subId, ...filters]: NostrClientCOUNT): Promise<void> {
|
||||
const store = await Storages.db();
|
||||
const { count } = await store.count(filters);
|
||||
const { count } = await store.count(filters, { timeout: 100 });
|
||||
send(['COUNT', subId, { count, approximate: false }]);
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -12,7 +12,7 @@ export class DittoPostgres {
|
|||
|
||||
static getPool(): Pool {
|
||||
if (!this.pool) {
|
||||
this.pool = new Pool(Conf.databaseUrl, Conf.pg.poolSize);
|
||||
this.pool = new Pool(Conf.databaseUrl, Conf.pg.poolSize, true);
|
||||
}
|
||||
return this.pool;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -45,13 +45,14 @@ class EventsDB implements NStore {
|
|||
constructor(private kysely: Kysely<DittoTables>) {
|
||||
this.store = new NDatabase(kysely, {
|
||||
fts: Conf.db.dialect,
|
||||
timeoutStrategy: Conf.db.dialect === 'postgres' ? 'setStatementTimeout' : undefined,
|
||||
indexTags: EventsDB.indexTags,
|
||||
searchText: EventsDB.searchText,
|
||||
});
|
||||
}
|
||||
|
||||
/** Insert an event (and its tags) into the database. */
|
||||
async event(event: NostrEvent, _opts?: { signal?: AbortSignal }): Promise<void> {
|
||||
async event(event: NostrEvent, opts: { signal?: AbortSignal; timeout?: number } = {}): Promise<void> {
|
||||
event = purifyEvent(event);
|
||||
this.console.debug('EVENT', JSON.stringify(event));
|
||||
dbEventCounter.inc({ kind: event.kind });
|
||||
|
|
@ -63,7 +64,7 @@ class EventsDB implements NStore {
|
|||
await this.deleteEventsAdmin(event);
|
||||
|
||||
try {
|
||||
await this.store.event(event);
|
||||
await this.store.event(event, { ...opts, timeout: opts.timeout ?? 1000 });
|
||||
} catch (e) {
|
||||
if (e.message === 'Cannot add a deleted event') {
|
||||
throw new RelayError('blocked', 'event deleted by user');
|
||||
|
|
@ -137,7 +138,10 @@ class EventsDB implements NStore {
|
|||
}
|
||||
|
||||
/** Get events for filters from the database. */
|
||||
async query(filters: NostrFilter[], opts: { signal?: AbortSignal; limit?: number } = {}): Promise<NostrEvent[]> {
|
||||
async query(
|
||||
filters: NostrFilter[],
|
||||
opts: { signal?: AbortSignal; timeout?: number; limit?: number } = {},
|
||||
): Promise<NostrEvent[]> {
|
||||
filters = await this.expandFilters(filters);
|
||||
dbQueryCounter.inc();
|
||||
|
||||
|
|
@ -160,28 +164,28 @@ class EventsDB implements NStore {
|
|||
|
||||
this.console.debug('REQ', JSON.stringify(filters));
|
||||
|
||||
return this.store.query(filters, opts);
|
||||
return this.store.query(filters, { ...opts, timeout: opts.timeout ?? 1000 });
|
||||
}
|
||||
|
||||
/** Delete events based on filters from the database. */
|
||||
async remove(filters: NostrFilter[], _opts?: { signal?: AbortSignal }): Promise<void> {
|
||||
async remove(filters: NostrFilter[], opts: { signal?: AbortSignal; timeout?: number } = {}): Promise<void> {
|
||||
if (!filters.length) return Promise.resolve();
|
||||
this.console.debug('DELETE', JSON.stringify(filters));
|
||||
|
||||
return this.store.remove(filters);
|
||||
return this.store.remove(filters, { ...opts, timeout: opts.timeout ?? 3000 });
|
||||
}
|
||||
|
||||
/** Get number of events that would be returned by filters. */
|
||||
async count(
|
||||
filters: NostrFilter[],
|
||||
opts: { signal?: AbortSignal } = {},
|
||||
opts: { signal?: AbortSignal; timeout?: number } = {},
|
||||
): Promise<{ count: number; approximate: boolean }> {
|
||||
if (opts.signal?.aborted) return Promise.reject(abortError());
|
||||
if (!filters.length) return Promise.resolve({ count: 0, approximate: false });
|
||||
|
||||
this.console.debug('COUNT', JSON.stringify(filters));
|
||||
|
||||
return this.store.count(filters);
|
||||
return this.store.count(filters, { ...opts, timeout: opts.timeout ?? 500 });
|
||||
}
|
||||
|
||||
/** Return only the tags that should be indexed. */
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue