import type { Entity } from "@triplit/client"; import type schema from "#triplit/schema"; import { nanoid } from "nanoid"; import { assert } from "~~/utils/assert"; export type Agent = Readonly & { topics: Readonly>[] }>; export const useAgents = () => { const nuxtApp = useNuxtApp(); const triplit = useTriplitClient(); // dont leaking between different users/requests if (!nuxtApp._agentsState) { nuxtApp._agentsState = { list: ref([]), initPromise: null as Promise | null, }; } const state = nuxtApp._agentsState as { list: Ref; initPromise: Promise | null; }; const init = () => { if (state.initPromise) return; state.initPromise = (async () => { const query = triplit.query('agents') .Include('topics', (rel) => rel('topics').Order('createdAt', 'DESC')) .Order('createdAt', 'ASC'); const { results } = await useQuery('agents', triplit, query) watch(results, (newAgents) => { console.log("newAgents", newAgents); state.list.value = newAgents as unknown as Agent[] || []; }, { immediate: true, flush: 'sync' }); })(); }; const getAgent = (id: MaybeRef) => { return computed(() => state.list.value.find((agent) => agent.id === toRef(id).value) || null); } const createAgent = async () => { const triplit = useTriplitClient(); const { user } = useAuth(); if (!user.value) throw new Error('No user'); const id = nanoid(); await triplit.insert('agents', { id, name: 'New Agent', userId: user.value.id, systemPrompt: 'You are a helpful assistant.', defaultModelId: null, imageUrl: null, createdAt: new Date().toISOString(), }); assert('flush' in triplit); await triplit.flush(); return state.list.value.find((agent) => agent.id === id)!; }; return { init, agents: state.list, getAgent, createAgent }; };