123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117 |
- import { create } from "zustand";
- import { persist } from "zustand/middleware";
- import Fuse from "fuse.js";
- export interface Prompt {
- id?: number;
- title: string;
- content: string;
- }
- export interface PromptStore {
- latestId: number;
- prompts: Map<number, Prompt>;
- add: (prompt: Prompt) => number;
- remove: (id: number) => void;
- search: (text: string) => Prompt[];
- }
- export const PROMPT_KEY = "prompt-store";
- export const SearchService = {
- ready: false,
- engine: new Fuse<Prompt>([], { keys: ["title"] }),
- count: {
- builtin: 0,
- },
- init(prompts: Prompt[]) {
- if (this.ready) {
- return;
- }
- this.engine.setCollection(prompts);
- this.ready = true;
- },
- remove(id: number) {
- this.engine.remove((doc) => doc.id === id);
- },
- add(prompt: Prompt) {
- this.engine.add(prompt);
- },
- search(text: string) {
- const results = this.engine.search(text);
- return results.map((v) => v.item);
- },
- };
- export const usePromptStore = create<PromptStore>()(
- persist(
- (set, get) => ({
- latestId: 0,
- prompts: new Map(),
- add(prompt) {
- const prompts = get().prompts;
- prompt.id = get().latestId + 1;
- prompts.set(prompt.id, prompt);
- set(() => ({
- latestId: prompt.id!,
- prompts: prompts,
- }));
- return prompt.id!;
- },
- remove(id) {
- const prompts = get().prompts;
- prompts.delete(id);
- SearchService.remove(id);
- set(() => ({
- prompts,
- }));
- },
- search(text) {
- return SearchService.search(text) as Prompt[];
- },
- }),
- {
- name: PROMPT_KEY,
- version: 1,
- onRehydrateStorage(state) {
- const PROMPT_URL = "./prompts.json";
- type PromptList = Array<[string, string]>;
- fetch(PROMPT_URL)
- .then((res) => res.json())
- .then((res) => {
- const builtinPrompts = [res.en, res.cn]
- .map((promptList: PromptList) => {
- return promptList.map(
- ([title, content]) =>
- ({
- title,
- content,
- } as Prompt),
- );
- })
- .concat([...(state?.prompts?.values() ?? [])]);
- const allPromptsForSearch = builtinPrompts.reduce(
- (pre, cur) => pre.concat(cur),
- [],
- );
- SearchService.count.builtin = res.en.length + res.cn.length;
- SearchService.init(allPromptsForSearch);
- });
- },
- },
- ),
- );
|