Appearance
Instance claims
An instance claim is a registry entry for a mount that allows multiple providers. Unlike singletons, several runtimes can register simultaneously under the same logicalMount, each as a distinct provider keyed by providerRuntimeId.
When to use multiple providers
| Scenario | Why multiple providers makes sense |
|---|---|
Inference providers (system.inference.openai, system.inference.anthropic) | Different backends; caller selects by intent or by name |
| Per-conversation chat actors | One actor per conversation; the mount is parameterized |
| Worker pools | Several runtime processes ready to do the same work |
| Replicated read-only services | Same answer from any replica; load distribution |
Multi-provider mounts are the default — the registry does not impose a unique-provider constraint. Singleton invariants are policy applied on top, not enforced by the registry.
How instance claims look in the registry
Two providers for the same logical mount:
json
[
{
"logicalMount": "system.inference",
"providerRuntimeId": "rt-inference-openai",
"runtimeWireRoot": "COM.NIMBLETEC.RICHARD-SANTOMAURO",
"localMount": "system.inference.openai",
"componentType": "OpenAIInferenceActor",
"packageName": "@open-matrix/driver-openai",
"metadata": { "providerKind": "openai", "models": ["gpt-4o"] },
"status": "live",
"expiresAt": 1714862073221
},
{
"logicalMount": "system.inference",
"providerRuntimeId": "rt-inference-anthropic",
"runtimeWireRoot": "COM.NIMBLETEC.RICHARD-SANTOMAURO",
"localMount": "system.inference.anthropic",
"componentType": "AnthropicInferenceActor",
"packageName": "@open-matrix/driver-anthropic",
"metadata": { "providerKind": "anthropic", "models": ["claude-opus-4-7"] },
"status": "live",
"expiresAt": 1714862071009
}
]registry.resolve { logicalMount: 'system.inference' } returns both. registry.providers { logicalMount: 'system.inference' } returns both. The caller picks based on whatever policy the calling actor implements.
Resolution policy is caller-side
The protocol does not pick a provider for you. Real production policies seen in code:
| Pattern | Used by |
|---|---|
| First live provider wins | most simple resolves |
| Workspace-pinned default | system.inference reads serviceBindings from the Host config |
Match by metadata (providerKind) | inference catalog UI |
| Round-robin / random | not used today; would be a load-balancing feature |
| Closest by Lamport / latency | not used today |
The pi-style serviceBindings model from MASTER-PLAN.md Part 4:
json
{
"serviceBindings": {
"system.inference": {
"order": ["workspace", "home", "platform"],
"pinned": null
}
}
}This is a target shape; today most callers just take the first provider or look up by localMount directly.
Per-instance metadata
Instance claims carry a free-form metadata field that providers use to distinguish themselves. Conventions:
| Key | Meaning |
|---|---|
providerKind | High-level provider identifier (openai, anthropic, local) |
models | List of supported model names (for inference) |
priority | Caller-visible priority hint |
region | Geographic region for routed providers |
tags | Free-form tags consumed by catalog.search |
The catalog reads metadata and exposes it through catalog.list / catalog.search so consumers can filter without knowing every provider's internal mount path.
Instance vs deployment
The discovery metadata spec (WORKSTREAMS/core-and-packaging/MATRIX-DISCOVERY-METADATA-SPEC.md) draws a distinction between DeploymentInstance (a configured run of a package) and MountedInstance (a live actor at a mount). An instance claim in system.registry corresponds to a MountedInstance — specifically the registry-side projection of one. The DeploymentInstance is owned by the runtime-environment workstream and lives in <host-home>/runtimes/<runtimeId>.json.
A single DeploymentInstance can produce many MountedInstances (one runtime serves many mounts, each registering a claim). Conversely, a logical mount can have providers from many DeploymentInstances.
Failure semantics
When one provider fails (e.g., the OpenAI driver crashes), its claim goes stale after heartbeatTtlMs. Subsequent registry.resolve calls return only the still-live providers (Anthropic, in the example above). Callers do not see "provider degraded" — they see "provider is no longer in the live list". This is the same mechanism that drives failover in multi-provider deployments.
Idempotent registration
A runtime that re-registers a claim with the same (logicalMount, providerRuntimeId) overwrites the previous entry. This is intentional: it lets a runtime refresh its metadata or update its runtimeWireRoot without going through unregister/register.
A runtime that crashes and restarts under the same runtimeId will re-register; the registry treats this as an update, not a duplicate.
See also
- Mount claims (registry) — full op surface.
- Singleton claims — when only one provider is allowed.
- Consumer groups — multiple subscribers sharing work.
- Discovery projections — how the catalog surfaces multi-provider mounts.