Fixed search results not being cached

fixes #215
This commit is contained in:
hzrd149 2024-09-04 08:54:50 -05:00
parent 7e8855d94c
commit 331ec5d5d0
5 changed files with 40 additions and 11 deletions

View File

@ -0,0 +1,5 @@
---
"nostrudel": patch
---
Fixed search results not being cached

View File

@ -93,6 +93,7 @@
"three": "^0.160.0",
"three-spritetext": "^1.8.2",
"three-stdlib": "^2.29.11",
"tiny-lru": "^11.2.11",
"webln": "^0.3.2",
"workbox-core": "7.0.0",
"workbox-precaching": "7.0.0",

View File

@ -2,6 +2,7 @@ import { useEffect, useMemo, useState } from "react";
import { Filter, kinds, NostrEvent } from "nostr-tools";
import { AbstractRelay, Subscription, SubscriptionParams } from "nostr-tools/abstract-relay";
import { Alert, AlertDescription, AlertIcon, AlertTitle, Heading, Spinner, Text } from "@chakra-ui/react";
import { LRU } from "tiny-lru";
import relayPoolService from "../../../services/relay-pool";
import ProfileSearchResults from "./profile-results";
@ -35,6 +36,8 @@ function createSearchAction(url: string | AbstractRelay) {
return { search, cancel };
}
const searchCache = new LRU<NostrEvent[]>(10);
export default function SearchResults({ query, relay }: { query: string; relay: string | AbstractRelay }) {
const [results, setResults] = useState<NostrEvent[]>([]);
@ -44,17 +47,32 @@ export default function SearchResults({ query, relay }: { query: string; relay:
useEffect(() => {
if (query.length < 3) return;
setResults([]);
setError(undefined);
setSearching(true);
search
.search([{ search: query, kinds: [kinds.Metadata, kinds.ShortTextNote, kinds.LongFormArticle], limit: 200 }], {
onevent: (event) => setResults((arr) => [...arr, event]),
oneose: () => setSearching(false),
})
.catch((err) => setError(err));
return () => search.cancel();
setError(undefined);
if (searchCache.has(query + relay)) {
// restore search from cache
const events = searchCache.get(query + relay)!;
setResults(events);
setSearching(false);
} else {
// run a new search
setResults([]);
setSearching(true);
search
.search([{ search: query, kinds: [kinds.Metadata, kinds.ShortTextNote, kinds.LongFormArticle], limit: 200 }], {
onevent: (event) => {
setResults((arr) => {
const newArr = [...arr, event];
searchCache.set(query + relay, newArr);
return newArr;
});
},
oneose: () => setSearching(false),
})
.catch((err) => setError(err));
return () => search.cancel();
}
}, [query, search]);
const profiles = results.filter((e) => e.kind === kinds.Metadata);

View File

@ -1,6 +1,7 @@
import { useCallback, useEffect } from "react";
import { ButtonGroup, Flex, IconButton, Input, Select } from "@chakra-ui/react";
import { useNavigate, useSearchParams, Link as RouterLink } from "react-router-dom";
import { useForm } from "react-hook-form";
import { safeDecode } from "../../helpers/nip19";
import { getMatchHashtag } from "../../helpers/regexp";
@ -9,7 +10,6 @@ import VerticalPageLayout from "../../components/vertical-page-layout";
import PeopleListProvider from "../../providers/local/people-list-provider";
import { useBreakpointValue } from "../../providers/global/breakpoint-provider";
import QRCodeScannerButton from "../../components/qr-code/qr-code-scanner-button";
import { useForm } from "react-hook-form";
import SearchResults from "./components/search-results";
import useSearchRelays from "../../hooks/use-search-relays";

View File

@ -7640,6 +7640,11 @@ tiny-invariant@^1.0.6:
resolved "https://registry.yarnpkg.com/tiny-invariant/-/tiny-invariant-1.3.1.tgz#8560808c916ef02ecfd55e66090df23a4b7aa642"
integrity sha512-AD5ih2NlSssTCwsMznbvwMZpJ1cbhkGd2uueNxzv2jDlEeZdU04JQfRnggJQ8DrcVBGjAsCKwFBbDlVNtEMlzw==
tiny-lru@^11.2.11:
version "11.2.11"
resolved "https://registry.yarnpkg.com/tiny-lru/-/tiny-lru-11.2.11.tgz#5089a6a4a157f5a97b82aa930b44d550ac5c4778"
integrity sha512-27BIW0dIWTYYoWNnqSmoNMKe5WIbkXsc0xaCQHd3/3xT2XMuMJrzHdrO9QBFR14emBz1Bu0dOAs2sCBBrvgPQA==
tinycolor2@1, tinycolor2@^1.6.0:
version "1.6.0"
resolved "https://registry.yarnpkg.com/tinycolor2/-/tinycolor2-1.6.0.tgz#f98007460169b0263b97072c5ae92484ce02d09e"