generated from coulomb/repo-seed
docs: audit financial fabric vnext contract
This commit is contained in:
421
docs/financial-fabric-model-audit.md
Normal file
421
docs/financial-fabric-model-audit.md
Normal file
@@ -0,0 +1,421 @@
|
||||
# Financial Fabric Model Audit
|
||||
|
||||
Date: 2026-05-24
|
||||
|
||||
Workplan: `RAIL-FAB-WP-0017`
|
||||
|
||||
## Purpose
|
||||
|
||||
This audit identifies the current `railiance-fabric` assumptions that must
|
||||
change to implement the financial Fabric architecture in
|
||||
`docs/FabricDiscoveryAndUpdate.md`.
|
||||
|
||||
The current implementation is still centered on repo-owned declarations:
|
||||
|
||||
```text
|
||||
repo -> service -> capability -> interface -> dependency -> binding
|
||||
```
|
||||
|
||||
That model remains useful as legacy evidence and as a self-description layer,
|
||||
but it is no longer the correct top-level source of truth for external fabric
|
||||
relations. The vNext model must start from accountability roots: netkingdom,
|
||||
king, lords, tenants, fabrics, subfabrics, deployment automation, durable
|
||||
infrastructure evidence, and cross-boundary utility interfaces.
|
||||
|
||||
## Current Model Assumptions
|
||||
|
||||
### Repo-Owned Declarations Are The Primary Graph Source
|
||||
|
||||
Affected files:
|
||||
|
||||
- `INTENT.md`
|
||||
- `SCOPE.md`
|
||||
- `docs/declaration-schema.md`
|
||||
- `docs/adoption-guide.md`
|
||||
- `docs/first-rollout.md`
|
||||
- `docs/repo-reality-scanner.md`
|
||||
- `fabric/README.md`
|
||||
- `examples/declarations/**`
|
||||
- `fabric/services/**`
|
||||
- `fabric/capabilities/**`
|
||||
- `fabric/interfaces/**`
|
||||
- `fabric/dependencies/**`
|
||||
- `fabric/bindings/**`
|
||||
|
||||
Current behavior:
|
||||
|
||||
- Repositories are expected to own declarations for services, capabilities,
|
||||
interfaces, dependencies, and binding assertions.
|
||||
- The scanner treats repo-owned Fabric declarations as the highest-trust source
|
||||
for accepted graph data.
|
||||
- Existing examples and docs teach adoption by adding `fabric/` files to
|
||||
participating repositories.
|
||||
|
||||
Required change:
|
||||
|
||||
- Repo-owned declarations should become one evidence source, mostly useful for
|
||||
self-description, not the default authority for external relations.
|
||||
- External relations, tenancy, deployment membership, and cross-boundary utility
|
||||
edges should come from fabric-scoped discovery roots and deployment evidence.
|
||||
|
||||
### Declaration Kinds Encode The Graph Shape
|
||||
|
||||
Affected files:
|
||||
|
||||
- `schemas/service.schema.yaml`
|
||||
- `schemas/capability.schema.yaml`
|
||||
- `schemas/interface.schema.yaml`
|
||||
- `schemas/dependency.schema.yaml`
|
||||
- `schemas/binding.schema.yaml`
|
||||
- `schemas/common.schema.yaml`
|
||||
- `railiance_fabric/model.py`
|
||||
- `railiance_fabric/loader.py`
|
||||
- `railiance_fabric/validation.py`
|
||||
- `railiance_fabric/graph.py`
|
||||
- `railiance_fabric/canon.py`
|
||||
- `tests/test_canon.py`
|
||||
- `tests/test_registry.py`
|
||||
- `tests/test_scanner.py`
|
||||
- `tests/test_discovery.py`
|
||||
- `tests/test_discovery_registry.py`
|
||||
- `tests/test_reconciliation.py`
|
||||
|
||||
Current behavior:
|
||||
|
||||
- `loader.py` hardcodes declaration directories:
|
||||
`services`, `capabilities`, `interfaces`, `dependencies`, and `bindings`.
|
||||
- `validation.py` only accepts the legacy declaration kinds through
|
||||
`SCHEMA_BY_KIND`.
|
||||
- `graph.py` builds provider/consumer/binding behavior directly from those
|
||||
declaration kinds.
|
||||
- `canon.py` maps those declaration kinds into canonical categories, with
|
||||
several partial or gap mappings.
|
||||
- Tests assert the legacy kinds and edge types as the normal graph shape.
|
||||
|
||||
Required change:
|
||||
|
||||
- Add vNext semantic graph concepts for netkingdom, actor, fabric, subfabric,
|
||||
owned node, utility interface, accounting attribution, and provenance.
|
||||
- Keep legacy declaration kinds as a compatibility/evidence layer until they
|
||||
can be migrated or intentionally retired.
|
||||
- Stop treating environment tags as possible fabric boundaries.
|
||||
|
||||
### Metadata Owner Is Not Financial Ownership
|
||||
|
||||
Affected files:
|
||||
|
||||
- `schemas/common.schema.yaml`
|
||||
- `railiance_fabric/graph.py`
|
||||
- `railiance_fabric/scanner.py`
|
||||
- `railiance_fabric/registry.py`
|
||||
- `schemas/state-hub-export.schema.yaml`
|
||||
- existing declaration files under `fabric/**`
|
||||
|
||||
Current behavior:
|
||||
|
||||
- `metadata.owner` is required for declarations, but it is just a string.
|
||||
- Graph exports place owner inside node `attributes.owner`, not as a first-class
|
||||
field.
|
||||
- Discovery candidates can carry owner-like attributes, but there is no
|
||||
enforced owner actor, role, inheritance rule, or unresolved-owner state.
|
||||
- State Hub export nodes require `repo`, `domain`, and `lifecycle`, but not
|
||||
financial owner, fabric, or subfabric.
|
||||
|
||||
Required change:
|
||||
|
||||
- Introduce actor identity and role: king, lord, tenant, and supporting
|
||||
operator/steward where needed.
|
||||
- Every accepted node must resolve to an owner actor, either explicit or
|
||||
inherited from containing fabric/subfabric.
|
||||
- Missing or ambiguous ownership must be represented as review state before
|
||||
promotion.
|
||||
|
||||
### Fabric Membership Is Missing
|
||||
|
||||
Affected files:
|
||||
|
||||
- `schemas/state-hub-export.schema.yaml`
|
||||
- `schemas/discovery-snapshot.schema.yaml`
|
||||
- `railiance_fabric/scanner.py`
|
||||
- `railiance_fabric/registry.py`
|
||||
- `railiance_fabric/graph_explorer.py`
|
||||
- `railiance_fabric/graph_explorer_ui.py`
|
||||
- `docs/graph-explorer-contract.md`
|
||||
- `docs/state-hub-integration.md`
|
||||
|
||||
Current behavior:
|
||||
|
||||
- Accepted graph nodes have repo/domain/lifecycle fields, but no `fabric_id`,
|
||||
`subfabric_id`, containment path, or owning lord/tenant relation.
|
||||
- Discovery snapshots are scoped to one `repo_slug`, one commit, and one scan
|
||||
profile.
|
||||
- Registry snapshots are stored per repository and combined by merging the
|
||||
latest snapshot for each repo.
|
||||
|
||||
Required change:
|
||||
|
||||
- Add first-class fabric/subfabric identity and containment.
|
||||
- Preserve repo scoping for repository evidence, but do not let repo scope
|
||||
define fabric membership.
|
||||
- Add a root netkingdom/fabric baseline for the current one-fabric Railiance
|
||||
setup.
|
||||
|
||||
### Cross-Boundary Utility Is Flattened Into Dependency Edges
|
||||
|
||||
Affected files:
|
||||
|
||||
- `schemas/dependency.schema.yaml`
|
||||
- `schemas/binding.schema.yaml`
|
||||
- `railiance_fabric/graph.py`
|
||||
- `railiance_fabric/registry.py`
|
||||
- `railiance_fabric/canon.py`
|
||||
- `railiance_fabric/graph_explorer.py`
|
||||
- `railiance_fabric/graph_explorer_ui.py`
|
||||
- `tests/test_registry.py`
|
||||
- `tests/test_graph_explorer.py`
|
||||
|
||||
Current behavior:
|
||||
|
||||
- Consumers and providers are expressed as dependencies and binding assertions.
|
||||
- Edges such as `consumes`, `binds:*`, and `uses_interface` map mostly to
|
||||
canonical `depends_on`.
|
||||
- There is no explicit provider-owner/consumer-owner boundary, payment schema,
|
||||
metering basis, or business model on the edge.
|
||||
|
||||
Required change:
|
||||
|
||||
- Add a first-class cross-boundary utility edge concept.
|
||||
- Preserve technical dependency edges, but distinguish them from economic or
|
||||
tenancy value interfaces.
|
||||
- Allow cross-boundary edges across fabric and subfabric boundaries without
|
||||
treating the boundary crossing as an error.
|
||||
|
||||
### Cost/Profit Centers Are Not Represented
|
||||
|
||||
Affected files:
|
||||
|
||||
- all current graph schemas and exports
|
||||
- `railiance_fabric/registry.py`
|
||||
- `railiance_fabric/graph_explorer.py`
|
||||
- `railiance_fabric/graph_explorer_ui.py`
|
||||
- State Hub import contract in `schemas/state-hub-export.schema.yaml`
|
||||
|
||||
Current behavior:
|
||||
|
||||
- There are no node or edge fields for cost center, profit center, allocation
|
||||
model, payment schema, metering basis, or attribution validity.
|
||||
|
||||
Required change:
|
||||
|
||||
- Add optional accounting attribution on nodes and edges.
|
||||
- Ensure accounting attribution can drive views without changing fabric or
|
||||
subfabric membership.
|
||||
|
||||
### Discovery Has Good Mechanics But Wrong Roots
|
||||
|
||||
Affected files:
|
||||
|
||||
- `railiance_fabric/scanner.py`
|
||||
- `railiance_fabric/discovery.py`
|
||||
- `railiance_fabric/reconciliation.py`
|
||||
- `railiance_fabric/connectors.py`
|
||||
- `schemas/discovery-snapshot.schema.yaml`
|
||||
- `docs/repo-reality-scanner.md`
|
||||
- `docs/operational-rescan-loops.md`
|
||||
- `docs/registry-onboarding.md`
|
||||
|
||||
Current behavior:
|
||||
|
||||
- Discovery snapshots are provenance-rich and already separate candidates from
|
||||
accepted graph state.
|
||||
- Replacement scopes, stable keys, tombstones, review states, reconciliation
|
||||
diffs, and connector runs are already present.
|
||||
- Discovery is still repo-scoped and gives `repo_declaration` precedence.
|
||||
- `local-fabric-registry` reads repository onboarding manifests, not
|
||||
accountability roots or deployment responsibility boundaries.
|
||||
|
||||
Required change:
|
||||
|
||||
- Reuse the raw-evidence/candidate/accepted mechanics.
|
||||
- Add accountability-root manifests and adapters for deployment automation,
|
||||
infrastructure evidence, recovery/secrets/backup evidence, and ownership
|
||||
boundaries.
|
||||
- Change precedence so repo declarations can be strong self-description
|
||||
evidence without overriding fabric-scoped deployment evidence.
|
||||
|
||||
### State Hub Export Is Too Thin For The New Model
|
||||
|
||||
Affected files:
|
||||
|
||||
- `schemas/state-hub-export.schema.yaml`
|
||||
- `railiance_fabric/graph.py`
|
||||
- `railiance_fabric/registry.py`
|
||||
- `railiance_fabric/server.py`
|
||||
- `docs/state-hub-integration.md`
|
||||
- `docs/registry-api.md`
|
||||
|
||||
Current behavior:
|
||||
|
||||
- `/exports/state-hub` returns a `FabricGraphExport` with nodes and edges.
|
||||
- Nodes require `id`, `kind`, `name`, `repo`, `domain`, and `lifecycle`.
|
||||
- Edges require `from`, `to`, and `type`.
|
||||
- Canon metadata and evidence state are present, but ownership, containment,
|
||||
accounting, and utility metadata are not first-class.
|
||||
|
||||
Required change:
|
||||
|
||||
- Version the export contract.
|
||||
- Add fabric/subfabric containment, owner actor identity, owner role,
|
||||
cross-boundary utility metadata, and optional cost/profit attribution.
|
||||
- Keep enough compatibility metadata for State Hub to support old imports until
|
||||
`STATE-WP-0051` replaces or migrates the read model.
|
||||
|
||||
## Affected APIs And Commands
|
||||
|
||||
HTTP surfaces:
|
||||
|
||||
- `GET /exports/state-hub`
|
||||
- `GET /exports/graph-explorer`
|
||||
- `GET /exports/backstage`
|
||||
- `GET /exports/xregistry`
|
||||
- `GET /graph/providers`
|
||||
- `GET /graph/consumers`
|
||||
- `GET /graph/unresolved`
|
||||
- `GET /graph/blast-radius`
|
||||
- `GET /graph/dependency-path`
|
||||
- `POST /repositories/{repo_slug}/snapshots`
|
||||
- `POST /repositories/{repo_slug}/discovery-snapshots`
|
||||
- `POST /repositories/{repo_slug}/discovery-snapshots/{id}/accept`
|
||||
- `GET /repositories/{repo_slug}/inventory`
|
||||
|
||||
CLI surfaces:
|
||||
|
||||
- `railiance-fabric validate`
|
||||
- `railiance-fabric export`
|
||||
- `railiance-fabric providers`
|
||||
- `railiance-fabric consumers`
|
||||
- `railiance-fabric dependency-path`
|
||||
- `railiance-fabric unresolved`
|
||||
- `railiance-fabric blast-radius`
|
||||
- `railiance-fabric scan`
|
||||
- `railiance-fabric registry sync`
|
||||
- `railiance-fabric registry sync-manifest`
|
||||
- `railiance-fabric registry scan-manifest`
|
||||
- `railiance-fabric registry ingest-discovery`
|
||||
- `railiance-fabric registry accept-discovery`
|
||||
- `railiance-fabric registry rescan-status`
|
||||
|
||||
Projection surfaces:
|
||||
|
||||
- Graph Explorer payload and manifest.
|
||||
- Backstage projection.
|
||||
- xRegistry projection.
|
||||
- State Hub Fabric read-model import.
|
||||
|
||||
## Compatibility Risks
|
||||
|
||||
1. State Hub import compatibility:
|
||||
`STATE-WP-0050` expects the current `FabricGraphExport` shape. Adding
|
||||
required fields or changing node/edge semantics can break ingest unless the
|
||||
export is versioned or State Hub is updated in lockstep.
|
||||
|
||||
2. Graph Explorer compatibility:
|
||||
Graph Explorer filters and detail panes use current node kinds, layers,
|
||||
dependency chains, unresolved states, and canon metadata. New actor/fabric
|
||||
nodes and utility edges need UI mapping before the explorer remains useful.
|
||||
|
||||
3. Query command compatibility:
|
||||
Provider/consumer/dependency-path commands are built on capability and
|
||||
dependency declarations. They may remain useful as legacy views, but should
|
||||
not be presented as the whole Fabric model.
|
||||
|
||||
4. Registry storage compatibility:
|
||||
The registry stores snapshots as JSON, so schema migration is flexible, but
|
||||
combined graph behavior currently deduplicates by node id across latest
|
||||
per-repo snapshots. Fabric-scoped snapshots may need a root snapshot or
|
||||
scenario/fabric identity instead of only repo latest snapshots.
|
||||
|
||||
5. Test fixture blast radius:
|
||||
Most tests assert legacy declaration kinds, repo-scoped discovery keys, and
|
||||
current export payload shape. The migration should add vNext tests before
|
||||
replacing old assertions.
|
||||
|
||||
6. Canon mapping ambiguity:
|
||||
Current canonical categories do not include financial actors, fabrics,
|
||||
subfabrics, accounting attributions, or utility value interfaces. These
|
||||
either need canonical mappings or explicit `mapping_fit: gap` handling.
|
||||
|
||||
7. Existing accepted graph baseline:
|
||||
The current accepted graph contains 49 nodes and 58 edges from the
|
||||
post-`RAIL-FAB-WP-0016` reset. It should be treated as a legacy baseline
|
||||
and re-exported or archived before a controlled vNext reset.
|
||||
|
||||
## Migration Approach
|
||||
|
||||
1. Preserve legacy declarations as `v1alpha1` evidence.
|
||||
Do not delete `fabric/` declarations or examples immediately. Reclassify
|
||||
them as self-description and bootstrap evidence.
|
||||
|
||||
2. Introduce a vNext contract alongside the current export.
|
||||
Add schema version metadata before making breaking changes. Prefer either
|
||||
`railiance.fabric/v1alpha2` or an explicit export `schema_version`.
|
||||
|
||||
3. Add first-class model concepts before changing scanner roots.
|
||||
Implement netkingdom, actor, fabric, subfabric, ownership, utility edge, and
|
||||
accounting attribution semantics in schemas/tests first.
|
||||
|
||||
4. Extend discovery rather than replacing it.
|
||||
Reuse `FabricDiscoverySnapshot`, replacement scopes, candidates,
|
||||
provenance, reconciliation, and acceptance. Add accountability-root
|
||||
manifest evidence and deployment automation adapters.
|
||||
|
||||
5. Seed the current one-fabric baseline.
|
||||
Create the Railiance netkingdom root, current king, current lord/fabric, and
|
||||
inherited ownership defaults. This lets existing nodes resolve ownership
|
||||
before tenant subfabrics exist.
|
||||
|
||||
6. Version State Hub import.
|
||||
Coordinate with `STATE-WP-0051` so State Hub can ingest both the old and
|
||||
vNext export during the transition, or explicitly perform a read-model reset.
|
||||
|
||||
7. Rebuild and compare.
|
||||
Produce a vNext export from the current baseline, compare it against the
|
||||
legacy 49-node/58-edge export, and document intentional semantic changes.
|
||||
|
||||
## Follow-On Implementation Notes
|
||||
|
||||
For `RAIL-FAB-WP-0017-T02`:
|
||||
|
||||
- Define schema names and versioning for vNext graph exports.
|
||||
- Decide whether netkingdom/fabric/actor are node kinds, top-level export
|
||||
sections, or both.
|
||||
- Define ownership inheritance and unresolved-owner representation.
|
||||
- Define utility edge fields:
|
||||
provider owner, consumer owner, provider boundary, consumer boundary,
|
||||
payment schema, metering basis, and evidence.
|
||||
- Define accounting fields:
|
||||
cost center, profit center, allocation model, attribution validity.
|
||||
|
||||
For `RAIL-FAB-WP-0017-T03`:
|
||||
|
||||
- Add model classes or typed helpers beyond the generic `Declaration` wrapper.
|
||||
- Extend validation to enforce resolvable ownership on accepted nodes.
|
||||
- Update registry projection to preserve ownership, containment, accounting,
|
||||
and utility metadata.
|
||||
- Keep old declaration graph validation available as a legacy command or
|
||||
compatibility path.
|
||||
|
||||
For `RAIL-FAB-WP-0017-T04`:
|
||||
|
||||
- Update `schemas/state-hub-export.schema.yaml`.
|
||||
- Add sample vNext export payloads and tests.
|
||||
- Coordinate the import fields with `STATE-WP-0051`.
|
||||
|
||||
For `RAIL-FAB-WP-0018`:
|
||||
|
||||
- Build an accountability-root manifest instead of extending
|
||||
`registry/local-repos.yaml` into too many meanings.
|
||||
- Treat State Hub attached repos as one discovery root, not as the Fabric
|
||||
boundary itself.
|
||||
- Add deployment automation and infrastructure evidence adapters before trying
|
||||
to infer cross-boundary value edges.
|
||||
Reference in New Issue
Block a user