Skip to main content

Enrichment Orchestrator

The enrichment orchestrator is a staged prompt system for safely moving source rows from untouched data to validated and progressively enriched records. It separates basic data checks, semantic validation, enrichment research, and spreadsheet mutation so that each concern has a clear contract and stop gate.

The orchestrator is the only component allowed to edit the workbook. Stage prompts evaluate rows or company groups and return structured decisions.

Package structure

docs/prompts/enrich_o/
├── intro.md
├── orchestrator.md
└── prompts/
├── 01-stage-1-check.md
├── 02-stage-2-validate.md
└── 03-stage-3-enrich-1-routing.md

Add one prompt for each future enrichment category. Enrichment prompt numbers must be contiguous from 1 through the configured max_enrich_steps.

Architecture

Configuration

The required setting is:

max_enrich_steps: 1 # any integer from 1 through the number of registered enrichment prompts

Optional runtime settings:

input_file: path/to/source.xlsx
output_file: path/to/output.xlsx
source_sheet: null # discover when null
retry_errors: false
resume_existing: true
working_projection: zoominfo_minimum

max_enrich_steps counts enrichment prompts only. The readiness and validation stages always run when their input statuses require them.

Stage 1 compact working file

Stage 1 reads the full source workbook locally, performs the readiness check, and creates output_file as a smaller working workbook. Every original row is retained, but only the minimum source columns needed for identity, validation, and routing are copied. Status and later enrichment fields are appended to this working file.

For a ZoomInfo export, retain these source columns in order:

  1. source_row — generated from the original worksheet row number
  2. ZoomInfo Contact ID
  3. ZoomInfo Company ID
  4. Company Name
  5. Website
  6. Email Domain
  7. Certified Active Company
  8. Company Country
  9. NAICS Code 1
  10. Primary Industry
  11. Primary Sub-Industry
  12. Business Model
  13. Query Name

The source workbook remains unchanged and is the source of record. The compact file preserves source_row and available ZoomInfo IDs so results can be joined back to the full export later without sending personal, dialing, address, social-profile, or redundant industry columns to the model.

Rows that fail readiness remain in the compact file with bad_data; they are not removed. Later stage prompts receive only compact fields, prior stage outputs, and the rows admitted by their status gate.

Row-state model

The canonical workbook column is enrichment_status. Do not reuse a CRM field such as Status or Lead Status.

StatusMeaningTerminal by default
newThe row has never been evaluated by this pipelineNo
readyBasic source data is sufficient for semantic validationNo
validSemantic validation passedSometimes
enriched_1enriched_nEnrichment category 1n completedAt configured maximum
bad_dataBasic source data is missing, malformed, or unusableYes
invalidData was sufficient to inspect, but semantic validation failedYes
errorA technical or unexpected execution failure occurredYes, unless explicitly retried

bad_data is intentionally distinct from new. A processed failure must never look like an untouched row.

Recommended operational columns:

ColumnPurpose
enrichment_statusCurrent state-machine status
enrichment_status_reasonConcise reason for the most recent transition
enrichment_last_completed_step0 before enrichment, otherwise the latest completed enrichment number
enrichment_categoryCategory completed by the latest enrichment prompt
enrichment_attempt_countNumber of stage attempts for the row

Operational columns belong to the orchestrator. Stage prompts may propose their values but may not write them directly.

State transitions

An error row may re-enter the stage that failed only when retry_errors=true and the orchestrator retains or receives the failed-stage identifier.

Gates

Gate 1: readiness

The row must contain enough basic identity data to support validation. This is a structural and syntactic check. It does not browse the web, infer a market, or decide whether the company is a good prospect.

  • Pass: new → ready
  • Fail: new → bad_data
  • Execution failure: new → error

Gate 2: validation

The company or account must resolve to a coherent real-world identity, and the supplied row must not contradict that identity. Validation may determine that the row is not eligible for any configured enrichment category without calling the row malformed.

  • Pass and continue: ready → valid, then run enrichment
  • Pass and stop: ready → valid
  • Semantic failure: ready → invalid
  • Execution failure: ready → error

Gate 3: enrichment step

An enrichment prompt must receive the exact status required for its step and may populate only its owned fields.

  • Success: valid → enriched_1 or enriched_(k-1) → enriched_k
  • Execution failure: current status → error
  • Maximum reached: stop after enriched_<max_enrich_steps>

Prompt interface

Every stage prompt receives a common envelope:

{
"stage": "check | validate | enrich_n",
"expected_input_status": "new | ready | valid | enriched_n",
"rows": [],
"company_context": [],
"configuration": {
"max_enrich_steps": 1
}
}

Every stage prompt returns JSON only:

{
"stage": "check | validate | enrich_n",
"results": [
{
"source_row": 2,
"input_status": "new",
"output_status": "ready",
"status_reason": "Company name and business email domain are present.",
"owned_fields": {}
}
]
}

The orchestrator rejects a result if the input status, output status, or field ownership does not match the registered stage contract.

Axioms

  1. The source workbook is immutable and is never overwritten.
  2. Stage 1 retains every source row but may omit non-projected source columns from the compact working workbook.
  3. Values copied into the compact projection must exactly equal their source cell values.
  4. The orchestrator is the only workbook writer.
  5. A stage prompt performs exactly one concern and returns structured data only.
  6. A stage runs only on rows with its declared input status.
  7. Status transitions are monotonic; stages cannot be skipped or reversed.
  8. new always means untouched.
  9. bad_data means insufficient basic input; invalid means semantic validation failed.
  10. error represents execution failure, never a business classification.
  11. bad_data, invalid, and error stop downstream work immediately.
  12. Each enrichment field has exactly one owning prompt.
  13. A prompt may not overwrite another prompt's fields.
  14. Re-running a completed stage with the same inputs must be idempotent.
  15. Company-level results must be identical across contact rows for the same resolved company.
  16. Every transition must include a concise machine-readable reason.
  17. Unsupported facts remain unknown; they are never fabricated to advance a row.
  18. max_enrich_steps is a hard limit enforced by the orchestrator.
  19. Missing stage prompts are configuration errors detected before workbook mutation.
  20. Internal research artifacts may support execution but must not create hidden or helper tabs in the delivered workbook.
  21. The compact working workbook is the pipeline state store after Stage 1.
  22. Final verification must prove row preservation, projection fidelity, valid transitions, field ownership, and workbook usability.

Adding another enrichment category

To add enrichment step k:

  1. Create prompts/NN-stage-3-enrich-k-<category>.md.
  2. Declare its required input status: valid for step 1 or enriched_(k-1) otherwise.
  3. Declare an exclusive field allowlist.
  4. Declare its success status as enriched_k.
  5. Register the prompt in orchestrator.md.
  6. Add transition, idempotency, and field-ownership tests.

Do not increase max_enrich_steps beyond the highest contiguous registered enrichment prompt.