SearchStore works!
This commit is contained in:
parent
9c0a16ebcd
commit
ee7347df10
|
@ -42,6 +42,10 @@ const Conf = {
|
||||||
const { protocol, host } = Conf.url;
|
const { protocol, host } = Conf.url;
|
||||||
return `${protocol === 'https:' ? 'wss:' : 'ws:'}//${host}/relay`;
|
return `${protocol === 'https:' ? 'wss:' : 'ws:'}//${host}/relay`;
|
||||||
},
|
},
|
||||||
|
/** Relay to use for NIP-50 `search` queries. */
|
||||||
|
get searchRelay() {
|
||||||
|
return Deno.env.get('SEARCH_RELAY');
|
||||||
|
},
|
||||||
/** Origin of the Ditto server, including the protocol and port. */
|
/** Origin of the Ditto server, including the protocol and port. */
|
||||||
get localDomain() {
|
get localDomain() {
|
||||||
return Deno.env.get('LOCAL_DOMAIN') || 'http://localhost:8000';
|
return Deno.env.get('LOCAL_DOMAIN') || 'http://localhost:8000';
|
||||||
|
|
|
@ -3,7 +3,7 @@ import { type Event, nip19, z } from '@/deps.ts';
|
||||||
import { type DittoFilter } from '@/filter.ts';
|
import { type DittoFilter } from '@/filter.ts';
|
||||||
import { booleanParamSchema } from '@/schema.ts';
|
import { booleanParamSchema } from '@/schema.ts';
|
||||||
import { nostrIdSchema } from '@/schemas/nostr.ts';
|
import { nostrIdSchema } from '@/schemas/nostr.ts';
|
||||||
import { eventsDB } from '@/storages.ts';
|
import { searchStore } from '@/storages.ts';
|
||||||
import { dedupeEvents } from '@/utils.ts';
|
import { dedupeEvents } from '@/utils.ts';
|
||||||
import { lookupNip05Cached } from '@/utils/nip05.ts';
|
import { lookupNip05Cached } from '@/utils/nip05.ts';
|
||||||
import { renderAccount } from '@/views/mastodon/accounts.ts';
|
import { renderAccount } from '@/views/mastodon/accounts.ts';
|
||||||
|
@ -76,7 +76,7 @@ function searchEvents({ q, type, limit, account_id }: SearchQuery): Promise<Even
|
||||||
filter.authors = [account_id];
|
filter.authors = [account_id];
|
||||||
}
|
}
|
||||||
|
|
||||||
return eventsDB.getEvents([filter]);
|
return searchStore.getEvents([filter]);
|
||||||
}
|
}
|
||||||
|
|
||||||
/** Get event kinds to search from `type` query param. */
|
/** Get event kinds to search from `type` query param. */
|
||||||
|
@ -94,7 +94,7 @@ function typeToKinds(type: SearchQuery['type']): number[] {
|
||||||
/** Resolve a searched value into an event, if applicable. */
|
/** Resolve a searched value into an event, if applicable. */
|
||||||
async function lookupEvent(query: SearchQuery, signal = AbortSignal.timeout(1000)): Promise<Event | undefined> {
|
async function lookupEvent(query: SearchQuery, signal = AbortSignal.timeout(1000)): Promise<Event | undefined> {
|
||||||
const filters = await getLookupFilters(query);
|
const filters = await getLookupFilters(query);
|
||||||
const [event] = await eventsDB.getEvents(filters, { limit: 1, signal });
|
const [event] = await searchStore.getEvents(filters, { limit: 1, signal });
|
||||||
return event;
|
return event;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -1,6 +1,8 @@
|
||||||
|
import { Conf } from '@/config.ts';
|
||||||
import { db } from '@/db.ts';
|
import { db } from '@/db.ts';
|
||||||
import { EventsDB } from '@/storages/events-db.ts';
|
import { EventsDB } from '@/storages/events-db.ts';
|
||||||
import { Memorelay } from '@/storages/memorelay.ts';
|
import { Memorelay } from '@/storages/memorelay.ts';
|
||||||
|
import { SearchStore } from '@/storages/search-store.ts';
|
||||||
|
|
||||||
/** SQLite database to store events this Ditto server cares about. */
|
/** SQLite database to store events this Ditto server cares about. */
|
||||||
const eventsDB = new EventsDB(db);
|
const eventsDB = new EventsDB(db);
|
||||||
|
@ -8,4 +10,10 @@ const eventsDB = new EventsDB(db);
|
||||||
/** In-memory data store for cached events. */
|
/** In-memory data store for cached events. */
|
||||||
const memorelay = new Memorelay({ max: 3000 });
|
const memorelay = new Memorelay({ max: 3000 });
|
||||||
|
|
||||||
export { eventsDB, memorelay };
|
/** Storage to use for remote search. */
|
||||||
|
const searchStore = new SearchStore({
|
||||||
|
relay: Conf.searchRelay,
|
||||||
|
fallback: eventsDB,
|
||||||
|
});
|
||||||
|
|
||||||
|
export { eventsDB, memorelay, searchStore };
|
||||||
|
|
|
@ -0,0 +1,67 @@
|
||||||
|
import { NiceRelay } from 'https://gitlab.com/soapbox-pub/nostr-machina/-/raw/5f4fb59c90c092e5aa59c01e6556a4bec264c167/mod.ts';
|
||||||
|
|
||||||
|
import { Debug, type Event, type Filter } from '@/deps.ts';
|
||||||
|
import { type DittoFilter } from '@/filter.ts';
|
||||||
|
import { type DittoEvent, type EventStore, type GetEventsOpts, type StoreEventOpts } from '@/storages/types.ts';
|
||||||
|
import { EventSet } from '@/utils/event-set.ts';
|
||||||
|
|
||||||
|
interface SearchStoreOpts {
|
||||||
|
relay: string | undefined;
|
||||||
|
fallback: EventStore;
|
||||||
|
}
|
||||||
|
|
||||||
|
class SearchStore implements EventStore {
|
||||||
|
#debug = Debug('ditto:storages:search');
|
||||||
|
|
||||||
|
#fallback: EventStore;
|
||||||
|
#relay: NiceRelay | undefined;
|
||||||
|
|
||||||
|
supportedNips = [50];
|
||||||
|
|
||||||
|
constructor(opts: SearchStoreOpts) {
|
||||||
|
this.#fallback = opts.fallback;
|
||||||
|
|
||||||
|
if (opts.relay) {
|
||||||
|
this.#relay = new NiceRelay(opts.relay);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
storeEvent(_event: Event, _opts?: StoreEventOpts | undefined): Promise<void> {
|
||||||
|
throw new Error('EVENT not implemented.');
|
||||||
|
}
|
||||||
|
|
||||||
|
async getEvents<K extends number>(
|
||||||
|
filters: DittoFilter<K>[],
|
||||||
|
opts?: GetEventsOpts | undefined,
|
||||||
|
): Promise<DittoEvent<K>[]> {
|
||||||
|
this.#debug('REQ', JSON.stringify(filters));
|
||||||
|
|
||||||
|
if (this.#relay) {
|
||||||
|
this.#debug(`Searching for "${filters[0]?.search}" at ${this.#relay.socket.url}...`);
|
||||||
|
|
||||||
|
const sub = this.#relay.req(filters, opts);
|
||||||
|
sub.eoseSignal.onabort = () => sub.close();
|
||||||
|
const events = new EventSet<DittoEvent<K>>();
|
||||||
|
|
||||||
|
for await (const event of sub) {
|
||||||
|
this.#debug('EVENT', JSON.stringify(event));
|
||||||
|
events.add(event);
|
||||||
|
}
|
||||||
|
|
||||||
|
return [...events];
|
||||||
|
} else {
|
||||||
|
this.#debug(`Searching for "${filters[0]?.search}" locally...`);
|
||||||
|
return this.#fallback.getEvents(filters, opts);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
countEvents<K extends number>(_filters: Filter<K>[]): Promise<number> {
|
||||||
|
throw new Error('COUNT not implemented.');
|
||||||
|
}
|
||||||
|
|
||||||
|
deleteEvents<K extends number>(_filters: Filter<K>[]): Promise<void> {
|
||||||
|
throw new Error('DELETE not implemented.');
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
export { SearchStore };
|
Loading…
Reference in New Issue