BRD_PolicyCenter_PersonalLines_2026.2.md
The wish list: 57 wishes, each under a heading with a number like REQ-PC-001, agreed with the underwriting and pricing teams.
When a company wants new software, someone writes a wish list: "when a driver is added, the system should look up their driving record". Before anyone builds it, each wish needs test rules: "given this, when that, then this should happen". The Brain reads the wish list and the company's other documents, asks eight questions about every wish, and only then lets a language model write the test rules. A filter deletes anything the model made up. Wishes that cannot be tested, or that mention things the company does not have, go to a person instead.
Imagine a teacher writes "the science fair project should be good". You cannot grade that. A better version says "given a project with a hypothesis, when it is presented, then it must show the data it collected". Software has the same problem. A vague wish becomes a wrong program. The details needed to write good test rules are already in other documents: which fields exist, which error messages the other systems send, how past wishes were tested. Nobody has time to read all of it for every wish.
The wish list, the field-name sheet, the other-systems sheet, and old wishes with their test rules
For every wish: eight signed answers, then a short story and one test rule per required case, or "send to a person" with the reason
Who uses it: the people who turn wishes into work for programmers. How much it may do alone: at first its drafts sit next to a person's own. Later they can be sent to the team's task list as suggestions. What people change is how the Brain learns.

What makes this job about wishes instead of prices is a set of settings: four recipe cards for reading, five kinds of fact, eight questions, and a list of cases each kind of wish must cover.
HomeGrwn is the product the Brain runs inside. Its job is to turn a company's own records into models that belong to that company: rules with versions today, trained helpers per question once there are enough labels. The language model that writes the words is your choice. The tests on this page used a small open model on a laptop; a bigger model with your own API key plugs into the same slot, because the writer never decides anything. Here is where each part of the feature refinement job actually ran.
The test files were made by a generator we wrote so we would know the answers. They look like real project files, but they are not a real company's files.
| File | What it is | Size | Who keeps it in a real company |
|---|---|---|---|
| BRD_PolicyCenter_PersonalLines_2026.2.md | The wish list, 57 wishes | 9 KB | Business analysts, in Confluence |
| PC_Field_Mapping_Legacy_to_PolicyCenter.xlsx | Old field → new field, 16 rows | 6 KB | The data migration team, in Box |
| Integration_Spec_PersonalLines_v3.md | Four outside systems and their error messages | 1 KB | Integration architects, in Confluence |
| jira_export_PC_stories.jsonl | 30 old wishes with test rules and reviewer edit counts | 17 KB | Jira |
The wish list
REQ-PC-001 If PolicyDriver.AccidentCount is over 3 the system applies the high-risk surcharge of 12%.
REQ-PC-002 Premiums must be accurate as expected for all cases, etc.
REQ-PC-008 Approving the quote binds the policy and also sends the welcome email and also schedules the inspection.
REQ-PC-016 On entering a VIN the system calls VINLookup and fills PersonalVehicle.Symbol from the response within 3 seconds.
The field-name sheet old name new name
LEG_POL.MPD_FLAG PolicyPeriod.MultiPolicyDiscount
LEG_POL.TERM_CD PolicyPeriod.TermType
(there is no row for PolicyDriver.AccidentCount, so wish REQ-PC-001 talks about a field the company does not have)
The other-systems sheet
Error codes returned by VINLookup: TIMEOUT, VIN_INVALID, NOT_FOUND.
An old wish from Jira
{"story_id": "PC-900", "title": "When a Personal Auto quote is rated and ...", "status": "done",
"acceptance_criteria": ["Given the rating inputs, when the quote is rated, then the premium equals the worked example to the cent"],
"reviewer_edits": 2}Every file took the same trip: the front door stamped it and guessed what it was; a person said yes; a recipe card cut it into pieces; each piece became facts; each fact passed six checkpoints; the facts were filed in folders. Two of the recipe cards first had the wrong reading shape (a grid instead of rows), and every row from those files was held back; the fix was a settings change, not code.
The wish list: 57 wishes, each under a heading with a number like REQ-PC-001, agreed with the underwriting and pricing teams.
The field-name sheet: the old system’s field on the left, the new PolicyCenter object and field on the right, with a type and a transform. A title row above the header.
The other-systems sheet: four outside systems the software calls (driving records, car lookup, replacement cost, rating engine), each with the error messages it can send back and a 5-second timeout.
Old wishes from the team’s task tool: the story, its test rules, its status, and how many times a reviewer changed it before accepting it.
Totals: 109 pieces, 114 facts, 65 folders, 20 names in the name list (16 fields, 4 systems), 0 facts held back, 0.3 seconds.

It scores each recipe card against the file ending, the words in the file name ("BRD", "Mapping", "Spec", "jira") and the first row. The wish list scored 3 (only the name helped); the sheet and the Jira export scored 11 (their headers matched the card). It reads the version from the name (2026.2, v3).
The paragraph reader opens a folder for every numbered heading and makes one fact per sentence under it. The row reader makes one fact per row, naming it from the columns the card points at (Target Object and Target Field). Nothing here knows what a "policy" is.
After reading, it walks the field facts and the system facts and builds the name list: 16 field names like PolicyPeriod.TermType and 4 systems with their error messages. This list is what question 6 checks against and what the writer is allowed to mention.
| Checkpoint | What it asks here |
|---|---|
| ingest | Did the piece come from a sealed original with a location? |
| validate | Is the value the right kind? A wish must be text; an old wish must have a status. |
| standardize | Trim, fix casing of Object.Field names. |
| resolve | Does a system name in a wish match a system in the other-systems sheet? |
| test | Job-specific: a field named in a wish should exist in the sheet (if not, it is noted for question 6, not held back); two wishes over 92% alike are shown to a person. |
| publish | Is this fact new, or the same as one already filed? |
| Shelf | What is on it, for this job | This job | Where exactly |
|---|---|---|---|
| Original files | The four files, sealed as they arrived | 4 | disk, write-once |
| Pieces | Paragraphs with their heading, rows with their sheet | 109 | Postgres chunks |
| Facts | Wish sentences, field names, system statements, old wishes | 114 | Postgres facts |
| Folders | 58 wishes, 5 system sections, the sheet, the export | 65 | Postgres items, item_versions |
| Name list | 16 field names, 4 systems with error messages | 20 | Postgres entities |
| The notebook | Eight answers per wish plus the draft; every deleted line with its reason | 513 | Postgres decisions, append-only |
| Vectors | Map pins for old wishes and system sentences, names hidden | as needed | pgvector, chunk_vectors |
| The vault | Real names behind the hidden ones (reporter emails, customer names) | as needed | Postgres vault, encrypted |
| Settings | 6 recipe cards, 10 fact kinds, 8 questions, case lists, never-say words | rows · 1 rule set | Postgres job_config, rule_versions |

The same rules as the price job, applied to documents.
| Situation | What happens |
|---|---|
| The same wish list is fetched from Confluence again, unchanged | Same bytes, same fingerprint: refused at the front door as a twin. Nothing to read. |
| The wish list is saved again with one sentence changed | New fingerprint, so it is read. 57 of the 58 sentence facts already exist and are skipped. The one changed sentence becomes a new fact that replaces the old one; that wish's folder closes version 1 and opens version 2; the old draft stays in the notebook and a new judgment is written after it. |
| The field sheet gains the missing field next month | A new field fact and a new name in the name list. Wish REQ-PC-001, which was sent to a person for naming a missing field, can be judged again and now passes question 6. Both judgments stay in the notebook, dated. |
| Three wishes repeat the same sentence | Three folders (one per wish number), one shared sentence fact. The test wish list does exactly this on purpose, as real documents do. |
| The case list is improved | A new rule-set version, approved by a person. Every draft names the version it used, so old drafts can be told from new ones. |
The clearest example is question 6, "does it name a field the company lacks?". Wish REQ-PC-001 talks about PolicyDriver.AccidentCount. Memory holds the company's field names. The Brain looks for that name in the list, does not find it, and writes that down, pointing at both the wish and the sheet.
One folder per wish. The wish number is the label. A revised wish list lands as a new drop; a wish whose sentence changed gets a new fact and a new folder version. One whose sentence did not change gets nothing, because that fact already exists.
Every answer has a date. Each draft says which version of the folder and which version of the rules it was written from.
Every answer points home. A person reading a draft can open the sentence it came from, the row that made a field name allowed, and the line that listed an error message.
A vector is a long list of numbers that works like a pin on a map. Two sentences that mean nearly the same thing get pins close to each other. Old wishes and system sentences get pins after their names are hidden. The writer asks for the three old wishes nearest to the new one and sees their test rules as examples of how this team writes.
What gets a pin here. Old wishes and their test rules, system sentences, wish sentences. Field names do not get pins. A name is either in the list or it is not, and that is a lookup.
What the pins are for. Style examples for the writer. Finding the system sentence that lists error messages when the wish calls the system by a slightly different name. Spotting two wishes that are almost the same.
What the pins are not for. None of the eight questions uses a pin. In the test, pins were used for zero answers.
The vault. Old wishes from Jira carry reporter emails and sometimes customer names. They are swapped for code words before a pin is made. The real values are locked in the vault, and every peek is written in the audit log.
the original (sealed on the shelf) "PC-912 · Reported by maria.chen@acme-mutual.example: when the Home policy for customer Dale Okafor was cancelled, the Auto quote kept its multi-policy discount." with names hidden (what gets a pin, what the model sees) "PC-912 · Reported by [[email:9a41c2e07b3d]]: when the Home policy for customer [[name:e2f70c11ab98]] was cancelled, the Auto quote kept its multi-policy discount." the pin (a list of numbers; 768 of them with a real embedding model) [-0.0412, 0.0937, 0.0088, ...]
| Question | Which helper | Rule | Model | Right |
|---|---|---|---|---|
| Q1 · One wish or two? | Looks for "and also", "and then", two triggers. The model is asked when unsure. | 51 | 6 | 57 / 57 |
| Q2 · Can it be tested? | Does it have a trigger, a result, a person, and no vague words? (rules) | 57 | 0 | 57 / 57 |
| Q3 · Which names does it use? | Finds Object.Field words and looks them up in the name list | lookup | feeds Q6 and the filter | |
| Q4 · What kind of wish? | a calculation · a check on input · a change of state · a call to another system · a screen · a speed goal (keyword rules; the model when none fire) | 48 | 9 | 51 / 57 |
| Q5 · Which cases must be covered? | A list per kind of wish (rule set v1), plus one case per error message the other system can send | rule | 89.5% of the answer sheet's cases | |
| Q6 · Does it name a field the company lacks? | Lookup in the name list | lookup | 57 / 57 | |
| Q7 · Are all its parts covered? | Counted from Q1 and Q5 | math | – | |
| Q8 · How likely is a reviewer to accept it? | Starts at 0.9 and drops for each problem found (a rule) | 57 | 0 | needs real reviews to score |
The writer gets the wish, the eight signed answers, the names it may use, and one case to cover. It writes the story once, then one test rule per case. Each line goes through the filter: every field name must be in the name list; every number must appear in the wish or in a fact; the case must be one that was asked for; words from the never-say list are cut. A deleted line is kept in the notebook with its reason, and the writer gets one more try with that reason in front of it.
A line says: which wish, which question, the answer, whether a rule or the model answered, which rule version, which facts were read. The draft line holds the story, every test rule kept, and every line deleted with its reason. The database refuses to change or delete a line, and the seals were verified intact.
Like a spelling quiz: the teacher keeps the answer sheet, the student only gets the quiz. A program we wrote made the four files with 57 wishes. On purpose, 6 of them cram two or three wishes into one sentence, 9 are too vague to test, and 6 mention a field the company does not have. It also wrote a secret answer sheet: for each wish, how many wishes it really is, whether it can be tested, what kind it is, and which cases its test rules must cover. The Brain was given only the files, never the answer sheet. When it finished, we compared its notebook with the answer sheet to score it.
| Planted on purpose | Wishes | Example |
|---|---|---|
| two or three wishes in one sentence | 6 | "…binds the policy and also sends the welcome email and also schedules the inspection" |
| too vague to test | 9 | "Premiums must be accurate as expected for all cases, etc." |
| names a field the company lacks | 6 | PolicyDriver.AccidentCount, which is not on the field sheet |
| calls another system | 9 | the car lookup and driving-record systems, each with its error messages |
| ordinary, well written | 27 | a price formula; a blank licence number; cancelling the home policy |

From the last try with llama3.2:3b. Every line below is in the notebook, with the answers it was written from. Every deleted line is there too, with the reason.
"On entering a VIN the system calls VINLookup and fills PersonalVehicle.Symbol from the response within 3 seconds." Seven cases to cover, three from the error messages the systems sheet lists.
Seven of seven cases covered, nothing deleted. The "too slow" line is weak: it repeats the case name instead of saying what the screen should show. A reviewer would fix it, and that fix is what the Brain learns from.
"The comprehensive premium is the base rate for the vehicle's PersonalVehicle.Symbol and territory multiplied by the deductible factor for PersonalVehicle.CompDeductible, rounded to the cent, and never below 25.00."
The surviving example has no real numbers because the wish has none to give. Real numbers live in the price tables, which are in the other job's Memory. Connecting the two is the next step.
Correct, but still one story for three wishes. The next change splits the sentence into three folders first, so each part gets its own kind and its own cases.
| Try | What changed | Questions right | Rules kept | Deleted | Cases missing | Who wrote | Seconds |
|---|---|---|---|---|---|---|---|
| 1 | first scored run | 100 / 90 / 84 / 100 | 165 | 3 | 3 | mostly a fill-in template | ≈60 |
| 2 | better "testable" rules; the case list per kind of wish | 100 / 100 / 90 / 100 | 189 | 3 | 3 | template 48 · model 9 | ≈70 |
| 3 | the model writes everything; no template | 100 / 100 / 90 / 100 | 132 | 60 | 78 | model 57 | 1,599 |
| 4 | send to a person when untestable or a field is missing; tell the model what was deleted and let it try once more | 100 / 100 / 90 / 100 | 156 | 54 | 54 | model 42 · sent to a person 15 | 68.7 |
Tries 1 and 2 had the best-looking numbers because a template filled in 48 of 57 stories from the case names, so the filter had nothing to delete. Try 3 is the model on its own: 60 lines deleted, 78 cases missing, 27 minutes because one wish kept timing out. Try 4 is the design we keep.
Where the 54 deleted lines came from. 51 made-up numbers (deductibles, licence numbers, "after 30 seconds", "1 or more"). 3 made-up field names ("MVR.Violations" instead of PolicyDriver.Violations).
The six "what kind" misses. Three copies of "Premiums must be accurate…" went to the model, which called them a speed goal. Question 2 had already called them untestable, so they were sent to a person and the miss cost nothing. Three copies of a two-in-one sentence about the car lookup and the driving record were called "a call to another system" where the answer sheet says "a check on input". Splitting first fixes it.
Not proven yet. No reviewer has sent changes back, so question 8 has not been scored. The files are our generator's, not a real company's. The model should write "not specified" instead of inventing an edge case the wish does not define.
The architecture, drawn step by step, and the other job built on it.