elk/composables/cache.ts

138 lines
4.4 KiB
TypeScript
Raw Permalink Normal View History

2023-04-12 13:35:35 +01:00
import { LRUCache } from 'lru-cache'
2023-01-08 06:21:09 +00:00
import type { mastodon } from 'masto'
2022-11-24 05:47:14 +00:00
2023-04-12 13:35:35 +01:00
const cache = new LRUCache<string, any>({
2022-11-24 05:47:14 +00:00
max: 1000,
})
2024-02-24 16:46:14 +00:00
if (import.meta.dev && import.meta.client)
2022-11-24 05:47:14 +00:00
// eslint-disable-next-line no-console
console.log({ cache })
2022-11-24 07:53:27 +00:00
export function setCached(key: string, value: any, override = false) {
if (override || !cache.has(key))
cache.set(key, value)
2022-11-24 05:47:14 +00:00
}
function removeCached(key: string) {
cache.delete(key)
}
2022-11-24 05:47:14 +00:00
2023-01-08 06:21:09 +00:00
export function fetchStatus(id: string, force = false): Promise<mastodon.v1.Status> {
const server = currentServer.value
2023-01-14 21:56:47 +00:00
const userId = currentUser.value?.account.id
const key = `${server}:${userId}:status:${id}`
2022-11-24 05:47:14 +00:00
const cached = cache.get(key)
2022-12-01 07:24:35 +00:00
if (cached && !force)
return Promise.resolve(cached)
2024-01-09 08:56:15 +00:00
const promise = useMastoClient().v1.statuses.$select(id).fetch()
2022-11-24 05:47:14 +00:00
.then((status) => {
cacheStatus(status)
return status
})
cache.set(key, promise)
return promise
}
2023-01-08 06:21:09 +00:00
export function fetchAccountById(id?: string | null): Promise<mastodon.v1.Account | null> {
2022-12-06 23:38:00 +00:00
if (!id)
return Promise.resolve(null)
const server = currentServer.value
2023-01-14 21:56:47 +00:00
const userId = currentUser.value?.account.id
const key = `${server}:${userId}:account:${id}`
2022-11-24 05:47:14 +00:00
const cached = cache.get(key)
if (cached)
return Promise.resolve(cached)
const domain = getInstanceDomainFromServer(server)
2024-01-09 08:56:15 +00:00
const promise = useMastoClient().v1.accounts.$select(id).fetch()
.then((r) => {
2023-01-08 06:21:09 +00:00
if (r.acct && !r.acct.includes('@') && domain)
r.acct = `${r.acct}@${domain}`
cacheAccount(r, server, true)
return r
2022-11-24 05:47:14 +00:00
})
cache.set(key, promise)
return promise
}
2023-01-08 06:21:09 +00:00
export async function fetchAccountByHandle(acct: string): Promise<mastodon.v1.Account> {
const server = currentServer.value
2023-01-14 21:56:47 +00:00
const userId = currentUser.value?.account.id
const domain = getInstanceDomainFromServer(server)
const userAcct = (domain && acct.endsWith(`@${domain}`)) ? acct.slice(0, -domain.length - 1) : acct
const key = `${server}:${userId}:account:${userAcct}`
2022-11-24 05:47:14 +00:00
const cached = cache.get(key)
if (cached)
return Promise.resolve(cached)
async function lookupAccount() {
const client = useMastoClient()
let account: mastodon.v1.Account
if (!isGotoSocial.value) { // TODO: GoToSocial will support this endpoint from 0.10.0
account = await client.v1.accounts.lookup({ acct: userAcct })
}
else {
const userAcctDomain = userAcct.includes('@') ? userAcct : `${userAcct}@${domain}`
2024-01-09 08:56:15 +00:00
account = (await client.v1.search.fetch({ q: `@${userAcctDomain}`, type: 'accounts' })).accounts[0]
}
if (account.acct && !account.acct.includes('@') && domain)
account.acct = `${account.acct}@${domain}`
return account
}
const promise = lookupAccount()
.then((r) => {
cacheAccount(r, server, true)
2022-11-24 05:47:14 +00:00
return r
})
cache.set(key, promise)
return promise
2022-11-24 05:47:14 +00:00
}
export function fetchTag(tagName: string, force = false): Promise<mastodon.v1.Tag> {
const server = currentServer.value
const userId = currentUser.value?.account.id
const key = `${server}:${userId}:tag:${tagName}`
const cached = cache.get(key)
if (cached && !force)
return Promise.resolve(cached)
const promise = useMastoClient().v1.tags.$select(tagName).fetch()
.then((tag) => {
cacheTag(tag)
return tag
})
cache.set(key, promise)
return promise
}
2022-12-06 23:38:00 +00:00
export function useAccountById(id?: string | null) {
2022-11-30 07:08:10 +00:00
return useAsyncState(() => fetchAccountById(id), null).state
}
2023-01-08 06:21:09 +00:00
export function cacheStatus(status: mastodon.v1.Status, server = currentServer.value, override?: boolean) {
2023-01-14 21:56:47 +00:00
const userId = currentUser.value?.account.id
setCached(`${server}:${userId}:status:${status.id}`, status, override)
2022-11-24 05:47:14 +00:00
}
export function removeCachedStatus(id: string, server = currentServer.value) {
2023-01-14 21:56:47 +00:00
const userId = currentUser.value?.account.id
removeCached(`${server}:${userId}:status:${id}`)
}
2023-01-08 06:21:09 +00:00
export function cacheAccount(account: mastodon.v1.Account, server = currentServer.value, override?: boolean) {
2023-01-14 21:56:47 +00:00
const userId = currentUser.value?.account.id
const userAcct = account.acct.endsWith(`@${server}`) ? account.acct.slice(0, -server.length - 1) : account.acct
2023-01-14 21:56:47 +00:00
setCached(`${server}:${userId}:account:${account.id}`, account, override)
setCached(`${server}:${userId}:account:${userAcct}`, account, override)
2022-11-24 05:47:14 +00:00
}
export function cacheTag(tag: mastodon.v1.Tag, server = currentServer.value, override?: boolean) {
const userId = currentUser.value?.account.id
setCached(`${server}:${userId}:tag:${tag.name}`, tag, override)
}