UNPKG

nuxt-surrealdb

Version:

A Nuxt module aimed to simplify the use of SurrealDB

260 lines (259 loc) 5.41 kB
import { useWebSocket } from "@vueuse/core"; import { joinURL } from "ufo"; import { destr } from "destr"; import { computed, reactive, ref, toValue, useRuntimeConfig, useSurrealAuth, watch } from "#imports"; export function useSurrealWS(options) { const { auth: { database: authDatabase }, databases } = useRuntimeConfig().public.surrealdb; const { token: userToken } = useSurrealAuth(); const { database, onDisconnected: _onDisconnected, ...opts } = options || {}; const _database = computed(() => { if (database !== void 0) { if (typeof database !== "string" && typeof database !== "number" && typeof database !== "symbol") { return database; } else { return databases[database]; } } else { return databases["default"]; } }); const useId = 0; const authId = 1; const idCounter = ref(2); const isReady = reactive({ db: false, auth: false }); const queue = []; const isAuthDatabase = !!(options?.auth !== false && _database.value === databases[authDatabase]); const { close, data: _data, open, send: _send, status, ws } = useWebSocket(joinURL(_database.value.ws, "rpc"), { onDisconnected(ws2, event) { idCounter.value = 2; _onDisconnected?.(ws2, event); }, ...opts }); const stopInitWatcher = watch(_data, (newData) => { const _newData = destr(newData); if (_newData && _newData.id === useId) { isReady.db = true; } else if (_newData && _newData.id === authId) { isReady.auth = true; _sendQueue(); stopInitWatcher(); } if (!userToken.value || !isAuthDatabase) { _sendQueue(); stopInitWatcher(); } }); function _init() { _send(JSON.stringify({ id: useId, method: "use", params: [_database.value.NS, _database.value.DB] })); if (userToken.value && isAuthDatabase) { _send(JSON.stringify({ id: authId, method: "query", params: [userToken.value] })); } else if (options?.auth) { _send(JSON.stringify({ id: authId, method: "query", params: [options.auth] })); } } function _sendQueue() { if (!queue.length) return; for (const message of queue) { _send(JSON.stringify(message)); } } const data = computed(() => { const res = destr(_data.value); if (res && !res.error) { return res.result; } else { return res; } }); function send(data2, useBuffer = true) { if (!isReady.db || isAuthDatabase && !isReady.auth) { queue.push(data2); _init(); return false; } else { return _send(JSON.stringify(data2), useBuffer); } } function rpc(req) { return send({ id: idCounter.value++, ...req }); } function authenticate(token) { return rpc({ method: "query", params: [toValue(token)] }); } function create(thing, data2) { return rpc({ method: "create", params: [toValue(thing), toValue(data2)] }); } function info() { return rpc({ method: "info" }); } function insert(thing, data2) { return rpc({ method: "insert", params: [toValue(thing), toValue(data2)] }); } function invalidate() { return rpc({ method: "invalidate" }); } function kill(thing) { return rpc({ method: "kill", params: [toValue(thing)] }); } function set(name, value) { return rpc({ method: "let", params: [toValue(name), toValue(value)] }); } function live(table, diff) { return rpc({ method: "live", params: [toValue(table), toValue(diff)] }); } function merge(thing, data2) { return rpc({ method: "merge", params: [toValue(thing), toValue(data2)] }); } function patch(thing, patches, diff) { return rpc({ method: "patch", params: [toValue(thing), toValue(patches), toValue(diff)] }); } function query(sql, vars) { return rpc({ method: "query", params: [toValue(sql), toValue(vars)] }); } function remove(thing) { return rpc({ method: "delete", params: [toValue(thing)] }); } function select(thing) { return rpc({ method: "select", params: [toValue(thing)] }); } function signin(auth) { return rpc({ method: "signin", params: [toValue(auth)] }); } function signup(auth) { return rpc({ method: "signup", params: [toValue(auth)] }); } function unset(name) { return rpc({ method: "unset", params: [toValue(name)] }); } function update(thing, data2) { return rpc({ method: "update", params: [toValue(thing), toValue(data2)] }); } function use(NS, DB) { if (!NS && !DB) { NS = _database.value.NS; DB = _database.value.DB; } return rpc({ method: "use", params: [toValue(NS), toValue(DB)] }); } return { authenticate, close, create, _data, data, delete: remove, info, insert, invalidate, kill, let: set, live, merge, open, patch, query, remove, rpc, select, _send, send, set, signin, signup, sql: query, status, unset, update, use, ws }; }