@open-matrix/system-directory (1.1.32)
Installation
@open-matrix:registry=npm install @open-matrix/system-directory@1.1.32"@open-matrix/system-directory": "1.1.32"About this package
system-directory
The directory: objects and edges partitioned by authority root (one home, or a platform root),
plus the projections other services write into it (applications, packages, bindings, principals).
One actor, DirectoryActor, mounted at system.directory; operations are listed in
matrix.package.json accepts and implemented in
src/DirectoryActor.ts.
Storage
| Store | When | Source |
|---|---|---|
Postgres (system_directory schema) |
the package configuration names a databaseUrl |
src/postgres/PostgresDirectoryStore.ts, migrations/ |
| In memory | otherwise (tests, harnesses) | src/InMemoryDirectoryStore.ts |
Both implement IDirectoryStore (src/DirectoryStore.ts).
directory.platform.rows.count reports live object and edge counts grouped by authority root.
The Directory owner performs the count after verifying platform.operator with system.auth;
a refusal names that grant and owner. Operators use this actor operation instead of reading the
Directory schema directly.
How a home reaches it
The shared directory runs in the services account (hivecast-services). A home never calls
system.directory directly:
- The home publishes to
hivecast-services.directory.<home>.$inbox. The broker's import mapping fixes<home>to the caller's own root. - system-platform's fan-in (
HostedNamespaceAuthorityFanIn) answers that subject, andHostedNamespaceForwardingProvidersetsauthorityRootto the home in the subject. - It calls
system.directoryinside the services account, so the actor seesdeliveredAuthorityRoot = hivecast-servicesand the home inpayload.authorityRoot.
The actor's own inbox is hivecast-services.system.directory.$inbox; it never sees the tenant
subject. An operation that must be scoped to the caller's home reads the delivered root, and under
the services root, the home the platform forwarded. Edge upsert/delete and authority purge share
this rule in deliveredScope; object mutations remain strictly own-root.
The services account is a trust boundary, not a caller identity. Its platform owner can publish
directly to this actor. NatsAuthorityFactory.issueCredentialExclusive admits shared-services
credentials against the configured owner/delegates before minting them. The hosted-applications
delegate declared in deploy/images/environment-platform-entrypoint.mjs can publish only to the
Directory/Registry fan-in inboxes, not system.directory directly. Home imports fix the target
home; deriveHostedNamespaceAuthorityContext rejects payload roots that disagree with that
subject, and the forwarder overwrites both roots. Thus tenant publishers cannot choose another
home through this path. A services-account publisher granted the direct actor inbox is trusted
to select a home, as with purge; the delivered services root alone does not identify that publisher.
Deleting a home
directory.authority.purge removes every row one authority holds, in one transaction
(src/postgres/purge-authority.ts). system.auth asks for it when an
account is deleted, as the system.directory owner of the deletion
(docs/platform/accounts.md).
Tests
pnpm test # in this directory; Postgres specs use a PGlite fallback without a database URL
Dependencies
Dependencies
| ID | Version |
|---|---|
| @open-matrix/contracts | 1.1.32 |
| @open-matrix/core | 1.1.32 |
| @open-matrix/credential-plane | 1.1.32 |
| @open-matrix/subjects | 1.1.32 |
| @open-matrix/system-postgres | 1.1.32 |
Development Dependencies
| ID | Version |
|---|---|
| @matrix/test-utils | 1.1.32 |
| @open-matrix/nats-auth | 1.1.32 |
| @types/node | ^20.0.0 |
| esbuild | ^0.25.0 |
| tsx | ^4.0.0 |
| typescript | ^5.3.0 |