The app is the test run. The factory is the deliverable.
Mise OS routes physical work to whoever should execute it: an agent, a robot, or a human.
Mise OS routes food between restaurant branches, and every routing decision is arithmetic over scraped menu and supplier data. The dataset it inherited was assembled by an earlier scraping pipeline (search, then a generic page scrape, then LLM extraction) which failed silently on prices and left a measurable hole.
Each tool does a job the other two cannot. Observability is not a dashboard bolted on at the end. An alert is what starts the factory.
scraper heal is what fixes it.Traces every stage, endpoint and background job. Its alerts start the factory rather than merely reporting on it.
Holds goals, decisions, risks and services. Records the plan and release gates, with a trace id on every entity.
The supplier feed is what breaks, and scraper heal is what mends it.
Across 22 upstream status pages the collector's null-rate on
overall_status was 63.16%. One healed selector took it to 26.32%
with zero regressions on the four control sites.
So the factory demonstrably builds, not just repairs. Every stage is
one OTel span under a single factory.run root, and one Port entity carrying
that run's trace_id, so any node in the Port graph jumps straight to its
trace. If it is not traced, it did not happen.
# a human asks node factory/run.js --brief "Route the Downtown tomato shortage" # a signal asks node factory/run.js --incident data_source_broken brief → plan → build → verify → approve → release → audit
Surplus moves before anything is bought. A branch below its own par cannot donate. Nearest-expiry stock goes first. Only the net shortage reaches procurement.
The app generates a simulation from the dispatch the factory just
produced: this donor branch, this crate, this expiry window, this path, this
handoff. A different shortage draws a different simulation. The human watches what the
robot will do and approves that; the click writes approval_status
back to Port.
node app/server.js # http://localhost:3000
Change the branch numbers in
factory/mise.js, re-run the factory, reload. The simulation must show a
different donor and quantity. If it does not, it is a hardcoded demo.
The rehearsal is what a human approves against. The same approved plan is what would deploy to a physical robot. The simulation is the gate, not a decoration.
The supplier page's prices stop being text inside .price and
become an attribute on a renamed element, the kind of change a site redesign makes.
GitHub Pages republishes, and the contract catches it.
./scripts/break-mirror.sh # a real commit that restructures the price markup node factory/run.js --incident data_source_broken node factory/heal.js # detect → human gate → repair → re-verify supplier null-rate 100.0% (threshold 5%) -> FAIL failing fields: name, price release SKIPPED (contract failed)
Detection is ours, not the CLI's. Bright
Data never decides a scraper is broken. verify computes the null-rate, and
heal.js passes the concrete failing field names into
brightdata scraper heal. It never heals blind.