Clear each customer's membership tag and each record tag wherever cached,
and always this namespace's collection tag. keys are exact deletes in this
instance's key space: the only bust a null client honours.
ProtectedinvalidateThe bust every organization write makes, whatever it changed: its record
tag in every namespace projecting it, its customer's pages on both
surfaces, and the writer's own folded get keys.
ProtectedpageTags for a page: the scope it searched, each customer whose name its rows
copy, and the fields of records it may not hold that chose its rows.
ProtectedsearchTags for a page: the scope its query searched (each customer's membership
tag, else the collection tag), so an empty page is bustable too, plus the
records it projects and the fields that chose or ordered its rows.
StaticadminThe exact key OrganizationAdminQueryService.get reads through, for its
includeDeleted: false callers.
The includeDeleted: true variant hashes differently and is reached only by
the collection tag, which every Valkey-backed environment has. That gap is
deliberate and pre-existing: it only matters in memory mode, where no admin
get runs with includeDeleted: true.
StaticconsumerThe exact key OrganizationQueryService.get reads through.
get folds onto search, so these args must stay identical to the ones it
passes ({ customerId, ids: [id], pageSize: 1 }) plus the defaults search
bakes into its own key — includeDeleted: false and page: 1. Every other
filter is undefined there, and serviceCacheKey canonicalizes with JCS,
which drops undefined properties. organizationCache.test.ts pins the
equivalence.
Root of the organization class hierarchy: it owns the one
organization-searchcache both surfaces share and the seam that busts it.Every reader and writer of
organizationextends this class —OrganizationQueryService/OrganizationServiceon the consumer side,OrganizationAdminQueryService/OrganizationAdminServiceon the admin side (whose AiPrise verification callbacks write the table without going throughOrganizationService). See SearchCache for why the cache lives at the root rather than beside each service.Collapsing the two former namespaces buys more than deduplication: the admin search previously tagged every entry with a single collection tag, so any write to any customer evicted every cached admin page. Admin entries now carry the customer ids their filter scoped to, and fall back to the collection tag only when genuinely unscoped.