1. Purpose and Design Rationale
An NSD contains everything needed to stand up a complete Nexus instance: component configurations and deployment targets, the complete data model (entity classes, BDTs, field definitions), RBAC structure, pipeline flow definitions, rulesets, style tokens, node type registry, and contract versions with conformance requirements.
Why a Single Deployable File?
Traditional multi-service deployments scatter configuration across dozens of files, environment variables, and CI/CD pipelines. When the configuration source-of-truth is fragmented, partial deploys become inevitable — the ruleset updates but the RBAC matrix does not, or the data model changes but the view layer still renders the old schema. The NSD eliminates this entire class of defect by bundling every deployment-relevant fact into one atomic artefact. Deploy the NSD or do not deploy — there is no partial state.
2. File Format
Naming convention:
nexus-descriptor-{org_slug}-{version}.nsd.json
Example: nexus-descriptor-nesto-corp-2.1.0.nsd.json
The file is standard JSON (UTF-8, no BOM). Maximum size: 50 MB (including embedded rulesets and flow graphs).
3. Root Schema
{
"$schema": "https://api.nexus-dev.codezerogroup.com/schemas/nsd/1.0.json",
"nsd_version": "1.0",
"descriptor_id": "nsd-nesto-corp-2026-05-02T14:30:00Z",
"created_at": "2026-05-02T14:30:00Z",
"created_by": "m.lubkowski@ou-uv.com",
"org_slug": "nesto-corp",
"contract_versions": { ... },
"deployment_targets": { ... },
"data_model": { ... },
"rbac": { ... },
"rulesets": { ... },
"flows": { ... },
"node_registry": { ... },
"style": { ... },
"components": { ... },
"checksums": {
"contract_versions": "sha256:a1b2c3...",
"deployment_targets": "sha256:d4e5f6...",
"data_model": "sha256:g7h8i9...",
"rbac": "sha256:j0k1l2...",
"rulesets": "sha256:m3n4o5...",
"flows": "sha256:p6q7r8...",
"node_registry": "sha256:s9t0u1...",
"style": "sha256:v2w3x4...",
"components": "sha256:y5z6a7...",
"root": "sha256:b8c9d0..."
}
}
3.1 Checksum Architecture
Each section checksum is computed as:
SHA-256( JSON.stringify(section, keys_sorted=true, indent=none) )
The root checksum is computed as:
SHA-256( sorted_concat( all_section_checksums ) )
Why Per-Section Checksums?
Deterministic JSON serialisation (sorted keys, no whitespace variance) guarantees the same logical content always produces the same hash. This is the foundation of four capabilities:
- Partial diff: Comparing two NSD versions reveals which sections changed — without parsing any section content. A diff between
checksumsobjects completes in microseconds regardless of NSD size. - Selective deployment: If only
rulesetschanged, the DevOps Service pushes updated rules to the Controller layer without touching the View or Model. This reduces deployment risk and time from minutes to seconds. - Integrity verification: Corruption in transit or at rest is detected before deployment begins. The root checksum is a hash-of-hashes — changing a single character in any section cascades to a root checksum mismatch.
- Audit trail: Every deployed NSD version is immutable. The checksum chain provides a cryptographic proof of what was deployed, when, and whether it was altered.
The alternative — a single file-level checksum — would detect corruption but not identify which section changed, forcing full redeployment on every version bump.
4. Section: contract_versions
Declares which layer contract versions this NSD requires. Any runtime that does not implement the required contract version MUST reject the deployment.
{
"contract_versions": {
"controller": "C-1.0",
"model": "M-1.0",
"view": "V-1.0",
"orchestration": "O-1.0",
"nsd_schema": "1.0"
}
}
Why Contract Versioning?
Nexus separates the what (contract) from the how (implementation). A contract defines input/output formats and determinism guarantees. Any implementation that satisfies C-1.0 can replace any other C-1.0 implementation. Contract versions change only on MAJOR breaks (SemVer). This means a Snowflake Controller and an AWS Lambda Controller are interchangeable if both claim C-1.0 — the NSD does not care which runs, only that the contract is met.
5. Section: deployment_targets
Specifies which implementation of each MVC layer this NSD deploys to. Each target includes its full connection and provisioning configuration.
{
"deployment_targets": {
"controller": {
"implementation": "wormwood-python-fastapi",
"version": "0.2.0",
"contract": "C-1.0",
"target_stack": "aws-lambda",
"config": { ... }
},
"model": {
"implementation": "delta-prism-python-fastapi",
"version": "0.1.0",
"contract": "M-1.0",
"target_stack": "aws-neptune",
"config": { ... }
},
"view": {
"implementation": "chameleonv2-react",
"version": "1.2.2",
"contract": "V-1.0",
"target_stack": "static-cdn",
"config": { ... }
},
"orchestration": {
"implementation": "nexus-runtime-python",
"version": "0.1.0",
"contract": "O-1.0",
"target_stack": "aws-step-functions",
"config": { ... }
}
}
}
5.1 Supported Target Stacks
| Layer | Available target_stack values |
|---|---|
| Controller | python-fastapi, aws-lambda, azure-functions, snowflake-snowpark, databricks-pyspark, ms-office-vba, power-platform, docker-onprem, bare-metal-onprem, mainframe-zos |
| Model | delta-prism-python, postgresql, snowflake, databricks-delta-lake, azure-cosmos-db, aws-neptune, sharepoint-lists, ms-access, excel-worksheets, db2-mainframe |
| View | chameleonv2-react, chameleonv2-umd, power-apps, sharepoint-spfx, excel-forms, cli-terminal, pdf-static |
| Orchestration | nexus-runtime-python, aws-step-functions, azure-logic-apps, power-automate, airflow-prefect, databricks-workflows, jcl-mainframe |
6. Section: data_model
Complete entity class definitions, Business Data Type (BDT) registry, and field-level metadata. This is the single source of truth for what data shapes exist in this deployment.
6.1 BDT Registry
Each BDT entry defines a semantic type with constraints, lifecycle class, and unit. BDTs ensure that the same field type is validated identically across every target stack.
{
"bdt_registry": [
{
"code": "PLN_Amount",
"python_type": "float",
"description": "Polish Zloty monetary amount. Never negative.",
"lifecycle": "MUTABLE_STATE",
"constraints": { "min_value": 0.0, "max_value": 10000000.0 },
"unit": "PLN",
"nullable": false
}
]
}
6.2 Entity Classes
Each entity class declares its fields with BDT references, group assignments, and per-role RBAC visibility.
6.3 Field RBAC
Every field in every entity class carries an rbac map defining visibility and editability per role. This is the schema that the View layer uses to filter fields at render time, and the Model layer uses to enforce write permissions.
| Value | Meaning |
|---|---|
read-write | Field is visible and editable |
read-only | Field is visible but not editable |
hidden | Field is not rendered and not returned in queries |
masked | Field is returned as **** (PII protection) |
6.4 Lifecycle Policy
| Lifecycle Class | Description | Allowed | Denied |
|---|---|---|---|
IMMUTABLE_IDENTITY | Write-once, permanent | create, read | update, delete |
MUTABLE_STATE | Event-driven state changes with audit | create, read, update | delete |
OPERATIONAL_EVENT | High-velocity timestamped events, append-only | create, read | update, delete |
DERIVED_METRIC | Recomputable value, requires provenance | create, read, update | delete |
REFERENCE_CONSTANT | Version-pinned policy values | read | create, update, delete |
Why Lifecycle Classes in the NSD?
Lifecycle classes encode business rules about data mutability at the schema level. A REFERENCE_CONSTANT field cannot be updated by any code path, regardless of RBAC role. This prevents accidental data corruption and provides audit guarantees that are enforced by the Model layer, not by application logic. Every target stack implementation must respect these lifecycle constraints identically.
7. Section: rbac
Complete RBAC structure for the deployment: roles with permission matrices, organisations, teams, and members. The NSD declares the full permission model; the runtime enforces it.
| Role | Description | Key Permissions |
|---|---|---|
owner | Full administrative control | All permissions including org.delete and billing |
admin | Team-level administration | All except org.delete, org.manage |
editor | Create and edit entities, run pipelines | entity CRUD (no delete), pipeline run, gate approve/reject |
viewer | Read-only access | entity.read, pipeline.view_runs only |
8. Section: rulesets
All calculation, validation, and scoring rulesets. Each ruleset is a named, versioned collection of rules with formulas, priorities, and technology scoping.
8.1 Formula Portability
Formulas use the Wormwood formula language. The formula language is the portable contract — every Controller implementation must parse and evaluate the same formula syntax identically.
| Construct | Syntax |
|---|---|
| Arithmetic | +, -, *, /, ^, () |
| Comparison | ==, !=, >, <, >=, <= |
| Logical | &&, ||, !, NOT |
| Ternary | condition ? value_true : value_false |
| Functions | SUM, ROUNDUP, ROUND, MAX, MIN, IF, ABS, SQRT, IN, REGEX_MATCH, TOPK_AVG |
| Dot-path access | entity.tag, budget.amount, scoring.total |
| Literals | 'string', null, TRUE, FALSE |
Why a Custom Formula Language?
The formula language must be deterministic, sandboxed, and portable. Python expressions are not portable to COBOL or Excel VBA. SQL WHERE clauses cannot express ternary logic or function composition. A purpose-built formula language with a defined operator set and function library can be compiled to any target: Python eval, SQL CASE expressions, VBA formulas, COBOL evaluation logic, or Snowpark UDFs. The language is intentionally constrained — no loops, no I/O, no side effects — to guarantee that evaluation is always deterministic and terminates.
9. Section: flows
All pipeline definitions with their complete graph structures, node configurations, edge wiring, and trigger configurations. Each flow is a directed acyclic graph (DAG) of typed nodes connected by edges.
9.1 Graph Determinism
The same graph with the same trigger input and the same Human Gate decisions MUST produce the same run result on every target stack. Node positions are visual metadata for the Canvas editor and have no effect on execution. Execution order is determined by topological sort of the edge graph.
Why Pipeline-as-Data?
Pipelines are JSON, not code. This is the critical distinction. A JSON pipeline graph can be rendered in a visual canvas, compiled to AWS Step Functions ASL, compiled to Power Automate flow definitions, compiled to Airflow DAGs, or compiled to JCL job streams. If pipelines were Python code, they would be locked to Python runtimes. By expressing pipelines as typed graphs with declarative node configs, Nexus achieves the same portability for orchestration that the formula language achieves for rule evaluation.
10. Section: node_registry
Declares all node types available in this deployment. Each node type defines its inputs, outputs, config fields, and implementation status. This is the type system for the pipeline graph — a flow can only use node types declared in this registry.
| Node Type | Category | Status | Purpose |
|---|---|---|---|
FormNode | form | Implemented | User input form from class schema |
ApprovalGate | form | Implemented | Human decision point with RBAC |
ValidateNode | intel | Implemented | Apply compliance rules to a record |
AITransform | intel | Implemented | AI-powered data transformation |
StoreNode | storage | Implemented | Write to deltaPrism graph store |
IngestNode | ingest | Implemented | Ingest data from external sources |
ConditionBranch | logic | Implemented | Conditional routing based on expressions |
MatchNode | intel | Implemented | Invoice matching / record matching |
SentimentNode | scoring | Implemented | Sentiment analysis scoring |
OCRNode | intel | Declared | Atlas Document Intelligence OCR |
ForwardNode | egress | Declared | HTTP forward to external API |
11. Section: style
ChameleonV2 theme tokens and CSS customisation. Applied globally and overridable per-pipeline via flows[].style_tokens.
{
"style": {
"global_tokens": {
"theme": "light",
"accent_color": "#6366f1",
"font_family": "Inter, system-ui, sans-serif",
"border_radius": "8px",
"input_height": "40px",
"label_weight": "500",
"error_color": "#ef4444",
"success_color": "#22c55e",
"warning_color": "#f59e0b"
},
"brand": {
"logo_url": null,
"favicon_url": null,
"product_name": "Nexus"
}
}
}
12. Section: components
Infrastructure-level component definitions. Each component maps to a deployable service, binary, or function with resource requirements, health check endpoints, and inter-component dependencies.
| Component | Service | Port | Health | Dependencies |
|---|---|---|---|---|
| Controller | wormwood-engine | 8010 | /health | model |
| Model | delta-prism | 15000 | /health | none |
| View | nexus-ui | static | n/a | controller |
| Orchestration | nexus-runtime | embedded | n/a | controller, model, view |
| Admin | wormwood-admin | 8011 | /health/ | controller |
| Atlas OCR | atlas-ocr | 9000 | /health | none |
Why Secret References, Not Secrets?
The NSD MUST NOT contain plaintext secrets. All sensitive values use the pattern ${secrets.key_name}. The DevOps Service resolves these at deploy time from the configured secrets backend (AWS Secrets Manager, Azure Key Vault, HashiCorp Vault, or environment variables). This means the NSD file can be stored in version control, shared between teams, and audited without exposing credentials. The same NSD deployed to staging and production resolves different secrets from different backends automatically.
13. Checksum Verification
13.1 Generating Checksums
import hashlib, json
def section_checksum(section_data: dict) -> str:
canonical = json.dumps(section_data, sort_keys=True, separators=(',', ':'))
return "sha256:" + hashlib.sha256(canonical.encode('utf-8')).hexdigest()
def root_checksum(section_checksums: dict) -> str:
parts = [f"{k}={v}" for k, v in sorted(section_checksums.items())]
combined = "|".join(parts)
return "sha256:" + hashlib.sha256(combined.encode('utf-8')).hexdigest()
13.2 Verification at Deploy Time
The Nexus DevOps Service MUST:
- Recompute all section checksums from the NSD content
- Compare against the declared checksums
- Recompute root checksum from section checksums
- Compare against declared
checksums.root - Reject deployment if any checksum mismatches
13.3 Section-Level Diff
Comparing two NSD versions is a comparison of their checksums objects. If a section checksum is identical, the section content has not changed and does not need redeployment. This enables:
- Ruleset-only deploys (Controller hot-reload, no Model/View restart)
- Style-only deploys (View asset rebuild, no backend restart)
- RBAC-only deploys (permission refresh, no data migration)
14. NSD Lifecycle
| State | Description | Deployable |
|---|---|---|
draft | Under construction. Checksums may be absent. | No |
sealed | All sections complete. Checksums computed and locked. | Yes |
deployed | Successfully deployed to target stacks. | Active |
superseded | A newer NSD version has been deployed. | Archived |
revoked | Explicitly revoked. Target stacks deprovisioned. | No |
Why a State Machine for Deployments?
The lifecycle state machine prevents two categories of operational error: (1) deploying an incomplete NSD (only sealed NSDs are deployable), and (2) losing track of which version is live (only one NSD per org can be in deployed state). The revoked state provides a hard stop mechanism — if a deployment is discovered to contain a defect, it can be explicitly revoked rather than simply superseded, which triggers active teardown of resources.
14.1 Deployment Sequence
- Validate NSD — verify checksums, contract versions, schema
- Plan — diff against current deployed NSD, identify changed sections
- Preview — show which components will be redeployed and to which targets
- Execute — deploy changed sections in dependency order: Model → Controller → Orchestration → View → Admin
- Verify — run health checks on all deployed components
- Seal — mark NSD as
deployed, record deployment timestamp
14.2 Rollback
If deployment fails at any step: stop, revert all changed components to previous NSD version, mark new NSD as revoked with failure reason. The previous NSD remains deployed.
15. Security
15.1 Secrets Handling
Secret references use ${secrets.key_name}. Resolved at deploy time from the configured backend. The NSD file never contains plaintext credentials.
15.2 NSD Signing (Future)
When implemented, NSDs will carry an Ed25519 signature with public key fingerprint. The DevOps Service will reject unsigned NSDs in production environments.
15.3 Sensitive Field Protection
Entity class fields with rbac value "masked" for any role MUST be encrypted at rest in the Model layer. The NSD declares which fields require encryption; the target implementation enforces it.
16. DevOps Service Interface
| Operation | Input | Output |
|---|---|---|
validate | NSD JSON | Validation result (pass/fail + errors) |
diff | Old NSD + New NSD | Changed sections with details |
plan | NSD JSON + Current state | Deployment plan (what changes, in what order) |
deploy | NSD JSON + Approved plan | Deployment result per component |
rollback | Deployment ID | Rollback result |
status | Org slug | Current deployed NSD + component health |
export | Org slug | Current state exported as NSD JSON |
seal | Draft NSD | Sealed NSD with computed checksums |
Why Export From Running System?
The export operation reads the current state of a running Nexus instance and produces an NSD. This enables: backing up a deployment configuration as a single file, cloning a deployment to a different target stack (e.g., migrating from on-prem Docker to AWS Lambda), and disaster recovery (rebuild the entire system from one JSON file). The NSD is both the deployment input and the deployment output — the system is fully described by its descriptor at all times.
Technique Summary
| Technique | Problem Solved | Mechanism |
|---|---|---|
| Single-file descriptor | Configuration scatter across environments | Atomic JSON artefact: deploy all or nothing |
| Per-section checksums | Full redeployment on any change | SHA-256 per section enables selective deployment |
| Deterministic serialisation | Whitespace/ordering changes trigger false diffs | Sorted keys, no whitespace in hash input |
| Contract versioning | Implementation lock-in | Contracts define I/O formats, not implementations |
| Secret references | Credentials in config files | ${secrets.*} resolved at deploy time |
| Lifecycle state machine | Incomplete deploys, lost version tracking | 5 states: draft → sealed → deployed → superseded / revoked |
| BDT registry | Inconsistent type validation across stacks | Semantic types with constraints enforced by all implementations |
| Lifecycle classes | Accidental mutation of immutable data | Schema-level operation restrictions per data category |
| Formula language | Rules locked to Python runtime | Portable expression language compilable to any target |
| Pipeline-as-data | Orchestration locked to one execution engine | JSON graph compiled to Step Functions / Logic Apps / Airflow / JCL |
| Export operation | No single source of truth for running system | Running system emits its own NSD at any time |
17. Versioned Document References
| Document | Version | Authority | Link |
|---|---|---|---|
| Rule Registry | RR-1.0 | Tier 3 | NEXUS_RULE_REGISTRY.html |
| Node Registry | NR-1.0 | Tier 3 | NEXUS_NODE_REGISTRY.html |
| BDT Registry | BDT-1.0 | Tier 3 | NEXUS_BDT_REGISTRY.html |
| Component Status | CS-1.0 | Tier 3 | NEXUS_COMPONENT_STATUS.html |
| Validation Registry | VR-1.0 | Tier 3 | NEXUS_VALIDATION_REGISTRY.html |
| Roadmap | RM-1.0 | Tier 2 | NEXUS_ROADMAP.html |
| Use Case Register | UC-1.0 | Tier 2 | NEXUS_USECASE_REGISTER.html |
| Deployment Matrix | DM-1.0 | Tier 1 | NEXUS_DEPLOYMENT_MATRIX.html |
| Use Case Template | UCT-1.0 | Tier 3 | NEXUS_USECASE_TEMPLATE.html |