Skip to content

Prefix Matching

In many great literary works (the House of Atreus, One Hundred Years of Solitude, the Old Testament), a curse is placed not only on the protagonist, but also on their progeny. That’s friggin’ awesome.

Tags work the same way. When you invalidate a tag, all “child” tags are also invalidated.

import { QueryCache, at, wild, MemoryAdapter } from '@t87s/core';
const schema = at('users', () =>
wild.at('posts').at('settings')
);
const cache = QueryCache({
schema,
adapter: new MemoryAdapter(),
queries: (tags) => ({
getUser: (id: string) => ({
tags: [tags.users(id)],
fn: () => db.users.findById(id),
}),
getUserPosts: (id: string) => ({
tags: [tags.users(id).posts],
fn: () => db.posts.findByUserId(id),
}),
getUserSettings: (id: string) => ({
tags: [tags.users(id).settings],
fn: () => db.settings.findByUserId(id),
}),
}),
});
// Invalidating cache.tags.users('123') also invalidates:
// - ['users', '123'] ← exact match
// - ['users', '123', 'posts'] ← prefix match
// - ['users', '123', 'settings'] ← prefix match
await cache.invalidate(cache.tags.users('123'));

If you only want to invalidate the exact tag:

// Only invalidates ['users', '123'], not children
await cache.invalidate(cache.tags.users('123'), { exact: true });