> ## Documentation Index
> Fetch the complete documentation index at: https://docs.experio.cloud/llms.txt
> Use this file to discover all available pages before exploring further.

# Workshop 8: Enrichment Rules

> Capture the rules the business applies that the documents never state, and run them over the graph.

Some facts the business relies on are written down nowhere. No SOW says "this was a healthcare project", but everyone knows it was, because the client is a hospital system. No resume lists every skill a project used, but the project description makes it obvious. An [enrichment rule](/implementation/key-concepts#enrichment-rule) writes these facts into the graph after ingestion. It reads a node (and, if you want, its neighbours), follows a plain-language instruction, and writes back an attribute, a node, a relationship, or both. This workshop decides which of those business rules are worth automating, and writes each one so it can be tested.

Run it in **Phase 3, after the first pilot ingestion**. Rules written against an empty graph are guesses. With real nodes on screen, the room can see which gaps actually hurt the golden questions.

## At a glance

| | |
| - | - |
| **Purpose** | Identify implicit business rules; decide which become enrichment rules; write, test and schedule them |
| **When** | Phase 3 (Pilot ingest), weeks 5–6, after structured data and a document sample are loaded |
| **Duration** | 90 minutes, plus a 30-minute follow-up to review test results |
| **Attendees** | Experio: FFE (leads), Experio SMEs as needed. Client: PM, super user, the SME for each use case |
| **Inputs** | Pilot graph with real data; golden questions and their current results; taxonomies loaded |
| **Outputs** | Rule worksheet (one row per rule); rules saved and previewed; a Flow that runs them after ingestion |
| **Admin pages** | **Model & Define > Enrichment Rules**, **Process > Flows**, **Process > Flow Executions** |

## Before the workshop

**FFE and Experio SMEs**

* Run the golden questions against the pilot graph. For each partial or failed answer, note whether the missing fact is **in a source but not extracted** (fix extraction) or **not stated anywhere** (enrichment candidate).
* Pick five real nodes per candidate target type to test on during the session.
* Check the taxonomies the rules will use are loaded and their leaf values are active.

**Client homework (SMEs)**

* Bring the "everybody knows" rules for your use case: how you'd tag, group or connect things if you did it by hand in a spreadsheet.
* For each rule, bring two or three examples with the answer you'd expect.

## Which tool for which fact

Ask this for every candidate. Most "rules" turn out to belong somewhere else.

| If the fact is... | Use | Example |
| - | - | - |
| Written in the document text | **Extraction instructions** on the ontology attribute or artifact type | Contract `expiration_date` from the SOW |
| Held in a system of record | **Data mapping** ([Workshop 6](/implementation/ws-data-mapping)) | Client `industry` from Salesforce |
| Not stated anywhere, but derivable from what's in the graph | **Enrichment rule** | Project industry from its client's industry |
| About how to read or phrase an answer at question time | **Assistant instruction** (AI Instructions, Cypher instructions) | "Engagement lead means WORKS\_ON\_PROJECT role 'Engagement Lead'" |
| Relative to today (due soon, expiring, recent) | **Leave it to the question**; Cypher compares dates when asked | "Which SOWs expire in the next 90 days?" |

Prefer the source over a rule. If a system of record holds the fact, map it. A rule is an informed guess by a model; a mapped column is the firm's own record.

## Agenda

| Time | Item |
| - | - |
| 0:00 | Recap pilot results: which golden questions failed and why (15 min) |
| 0:15 | Collect candidate rules from SMEs (15 min) |
| 0:30 | Sort each candidate with the decision table (15 min) |
| 0:45 | Write the surviving rules in the worksheet (25 min) |
| 1:10 | Preview one rule live on real nodes (15 min) |
| 1:25 | Agree how and when rules run (5 min) |

## Running the workshop

For each rule, fill in one row of the worksheet:

| Field | Question to ask the room |
| - | - |
| **Target entity type** | "Which kind of node gets the new fact?" |
| **Target filter** | "All of them, or only some?" For example, only nodes where the output attribute is null |
| **Input mode** | "What would you look at to decide?" Only the node's own attributes (**Selected Attributes**), the whole node (**Full Node**), or the node plus everything one hop away (**Neighborhood**) |
| **Instruction** | "Say the rule as you'd explain it to a new analyst." Write it in plain language |
| **Controlled output** | "Is the answer a free choice or one of a list?" If a list, use `@TaxonomyName` |
| **Output** | "What should change in the graph?" An attribute, a new node, a relationship to an existing node, or a new node and relationship |
| **Expected results** | "For these five nodes, what's the right answer?" |

Notes for writing the prompt:

* **Placeholders.** In Selected Attributes mode, use `{attribute_name}` (for example `{description}`). In Full Node and Neighborhood mode, `{node}` inserts the whole node. In Neighborhood mode, `{related.Label.attr}` inserts an attribute from each related node of that type, such as `{related.Client.industry}`.
* **Taxonomies.** `@Industry` expands to the active leaf values of the Industry taxonomy, so the model chooses from your list rather than inventing labels.
* **Relationship outputs link to existing nodes only.** For a **Relationship** output, Experio looks up the target node by a match attribute (default `name`), either **Exact match only** or **Exact, then vector similarity** (the second needs a vector index on the target type). If no node matches, that link is skipped. Use **Node + relationship** when the target should be created.
* **No "today".** The rule prompt is not given the current date. Rules that depend on today's date go stale the day after they run. Leave those to the question.

### Testing

Open the rule's **Preview Rule** page and run it on a small sample of nodes. The preview makes no changes to the graph. Compare the output with the expected results on the worksheet. Fix the prompt and preview again until the sample is right. Then run the job, and spot-check results through lineage on the node.

### Running

Enrichment rules **do not run automatically per file**. They run when you start them:

* **On demand**: **Run Job** from **Model & Define > Enrichment Rules**. Turn on **Overwrite existing values** only when you want to re-process nodes that already have a result.
* **After ingestion**: add an **Enrichment** step to a Flow in **Process > Flows**, after the scan and ingestion steps, and schedule it. This is the normal setup after go-live, so new documents are enriched on each refresh.

Every write is recorded in [lineage](/implementation/key-concepts#lineage), so users can see which rule and model produced a value.

## Worked example: Northbridge Consulting

The pilot showed golden questions Q1 ("cloud migration projects for healthcare clients") and Q4 ("Azure data platform experience in healthcare") returning partial answers. Projects had no industry, and skills lived only on people. Three rules came out of the session.

### Rule 1: Tag project industry

| Field | Value |
| - | - |
| Target | Project; filter `industry` is null |
| Input mode | Neighborhood |
| Output | Attribute `industry` (the team first added this attribute to Project in the ontology) |

```text theme={null}
You are tagging a consulting project with the industry it served.

Project:
{node}

Industry of the client this project was for:
{related.Client.industry}

Choose exactly one industry from this list: @Industry
Use the client's industry when it is present. If it is missing, decide from
the project name and description. If you cannot tell, return null.
```

### Rule 2: Infer skills used

| Field | Value |
| - | - |
| Target | Project; filter `description` is not null |
| Input mode | Selected Attributes (`name`, `description`) |
| Output | Relationship Project `USED_SKILL` Skill, match on `name`, Exact match only |

The Project `description` is filled from the SOW scope during extraction, so this rule reads the SOW's scope indirectly.

```text theme={null}
Project name: {name}
Project description and scope: {description}

List the skills this project clearly required. Choose only from: @Skills
Return at most 8 skills. Do not include a skill unless the description gives
direct evidence for it.
```

Because this is a **Relationship** output, it links only to Skill nodes that already exist with exactly that name. Skill nodes come from resumes, which are extracted with `@Skills` in their instructions, so names line up. Skills no one at Northbridge lists on a resume are skipped. The room accepted that.

### Rule 3: Obligation due soon flag (not adopted)

Helen Park asked for `due_within_90_days` on Obligation. The team wrote it out:

```text theme={null}
Obligation: {description}
Due date: {due_date}
Is this obligation due within 90 days of today? Answer true or false.
```

It was dropped. The prompt has no reliable "today", and the flag would be wrong a day after each run. Instead, golden question Q7 is answered at question time, where Cypher compares `due_date` with the current date. The rule stayed on the worksheet with the reason, so nobody proposes it again.

### Running at Northbridge

Marcus built a Flow "Nightly refresh": scan SharePoint → ingestion → Enrichment (Rule 1) → Enrichment (Rule 2), scheduled nightly. Both rules keep their "is null" / "is not null" filters so re-runs process only new nodes.

## Accelerate with AI

No AI helper drafts enrichment rules today. **Admin Copilot** (⌘J) can explain input modes, placeholders and output types from these docs while you write a rule. The best accelerator is the Preview Rule page. Iterate on real nodes rather than debating the prompt in the abstract.

## Entering it in Experio

<Steps>
  <Step title="Create the rule">
    **Model & Define > Enrichment Rules > Create Rule**. Enter a name and description, choose the target node label, and add a target filter (attribute, operator, value; combine with AND or OR).
  </Step>

  <Step title="Set input, prompt and output">
    Choose the input mode, write the prompt with placeholders and `@TaxonomyName` tags, then configure the output type. Add per-attribute output instructions if the format matters ("title case", "most specific match").
  </Step>

  <Step title="Preview">
    From the rules list, open **Preview Rule**, set a small limit and run it. Nothing is written.
  </Step>

  <Step title="Run and schedule">
    **Run Job** once, and check results on the rule's **Jobs** tab and in lineage. Then add an **Enrichment** step to a Flow in **Process > Flows** and schedule it.
  </Step>
</Steps>

See [Enrichment Rules](/admin-guide/enrichment-rules) and [Flows](/admin-guide/flows). Rules show a compatibility status. An **invalid** rule (for example, its target label or output attribute was removed from the ontology) cannot run until it is fixed and re-validated.

## Common pitfalls

* **Writing a rule for a fact a system already holds.** Map it instead.
* **Writing a rule for a fact the document states.** Fix the extraction instructions instead.
* **Free-text outputs where a list exists.** Without `@TaxonomyName`, the model invents near-duplicate labels ("Health Care", "Healthcare Providers").
* **Expecting a Relationship output to create targets.** It links to existing nodes only. Use Node + relationship when targets must be created.
* **Rules that depend on today's date.** They go stale. Answer them at question time.
* **No target filter.** Every run re-processes every node, costs more, and can overwrite reviewed values if Overwrite is on.
* **Assuming rules run per file.** They run only on demand or in a Flow. Without a scheduled Flow, new documents are never enriched.

## Exit criteria

* [ ] Every candidate rule is sorted with the decision table, and the reason is recorded.
* [ ] Each adopted rule has a worksheet row: target, filter, input mode, prompt, taxonomy, output, expected results.
* [ ] Each rule is previewed on at least five real nodes and matches the expected results.
* [ ] Each rule has run once, and results are spot-checked in lineage.
* [ ] A scheduled Flow runs the rules after ingestion, in the right order.
* [ ] The affected golden questions are re-run and their results recorded.

## Next

If the firm needs to restrict who sees what, continue to [Workshop 9: Access Control](/implementation/ws-access-control). Otherwise go to [Workshop 10: Assistants & Agent Flows](/implementation/ws-assistants-and-flows).
