Chapter 1 · Session 14
The measures managers act on
A dashboard is not a wall of numbers. Each number on it exists because someone makes a decision with it. This chapter turns the decision in your intent into a short list of measures, each with a formula, a target and an owner.
30 minDecision firstISO 22400 definitionsOEE worked through≈ 6 measures per role
By the end of this chapter you can
- Trace every measure back to a decision in your intent and forward to an action.
- Write a measure sheet: definition, formula, unit, source tables, target, owner and what to do when it is red.
- Calculate OEE and its three factors from a shift's data, and name the loss behind each factor.
- Tell a leading measure from a lagging one, and spot a measure nobody will act on.
Start from the decision, not the data
In Session 2 you wrote your plant's intent: the decision the platform exists to support, who makes it and the data it needs. A dashboard is where that decision gets made. So a dashboard starts from the decision too. If you start from the data instead ("we have downtime, scrap and counts, let's chart them"), you get a screen full of charts that nobody acts on.
Walk the chain for each manager who will use the dashboard. Ask them: what do you decide each day or each shift, and what do you need to know first? Write the answer down in their words. Then turn each answer into a measure.
What a good measure looks like
A measure is more than a name. "Downtime" is not a measure; "minutes a press was stopped during planned production time, per press, per shift, from the downtime events table" is. Write every measure on one line of a measure sheet with these columns:
| Column | Example (Line 3, press shop) | Why it matters |
|---|---|---|
| Decision | Planner: book Press 02 for maintenance this week? | Ties the measure to the intent |
| Definition | Minutes stopped during planned production time | Everyone counts the same way |
| Formula | sum(end − start) of downtime_events, per press, per shift | The agent can build it exactly |
| Unit and period | Minutes per shift | Stops comparing a shift to a week |
| Source tables | downtime_events, lines, shifts | Proves the spine already holds the data |
| Target and limits | Under 30 min a shift; act above 45 | Says when it is red |
| Owner | Maintenance planner | Someone answers for it |
| Action when red | Open a work order for the top cause | If there is no action, drop the measure |
Use the standard definitions
Manufacturing already has agreed definitions for the common measures. ISO 22400-2 defines key performance indicators for manufacturing operations management, including availability, effectiveness, quality ratio, scrap ratio, OEE, mean time between failures and mean time to repair, each with its formula, unit and the times and quantities it is built from [1]. Using them means your OEE means the same as your customer's OEE, and the data elements line up with the ISA-95 model your spine already uses [2].
OEE, worked through
Overall equipment effectiveness multiplies three factors. Each factor catches different losses, so the factor that is lowest tells you where to look [3][4]. Here is one shift on Press 02:
| Quantity | Value | From |
|---|---|---|
| Planned production time | 450 min | shift length minus planned breaks |
| Downtime | 63 min (breakdown 38, die change 25) | downtime_events |
| Run time | 387 min | 450 − 63 |
| Ideal rate | 20 parts a minute (3-second cycle) | the press's standard |
| Total parts | 6,966 | production counts |
| Good parts | 6,757 | total minus rejects from quality_checks |
| Factor | Formula | Result |
|---|---|---|
| Availability | run time ÷ planned time = 387 ÷ 450 | 86.0% |
| Performance | total parts ÷ (run time × ideal rate) = 6,966 ÷ 7,740 | 90.0% |
| Quality | good parts ÷ total parts = 6,757 ÷ 6,966 | 97.0% |
| OEE | 0.860 × 0.900 × 0.970 | 75.1% |
Check it a second way: good parts × ideal cycle time ÷ planned time = 6,757 × 3 s ÷ (450 × 60 s) = 75.1%. Both ways must agree. Put that check in a test, so the agent's code is proven against a number you worked by hand.
Leading and lagging
A lagging measure tells you what already happened: yesterday's OEE, last month's scrap cost. A leading measure moves before the result does: open quality holds, overdue preventive maintenance, a die that is past its stroke count. Managers need both. Lagging measures say whether you are winning; leading measures give them time to act. A good dashboard pairs each lagging measure with at least one leading one.
Measures that mislead
- Averages that hide the spread. A week's OEE of 75% can hide one shift at 40%. Show the shift or the line, not only the plant.
- Percentages without the count. "Scrap 50%" on a two-part trial run is not a crisis. Show the count beside the percentage.
- A target that becomes the goal. When people are judged on one number, they find ways to move the number instead of the work (for example, calling a breakdown a planned stop). Pair each measure with one that would expose gaming: availability with planned-stop minutes.
- Measures from data the spine does not hold. If a measure needs a spreadsheet someone fills in by hand, fix the data first (Session 13's workflow), then build the widget.
You need: Your intent page from Session 2; a spreadsheet or a Markdown table in your repository; one manager for 15 minutes
You will interview one manager and leave with a measure sheet the agent can build from.
Outcome: A measure sheet of up to six measures, each tied to a decision, with one hand-worked number to test against.
Knowledge check
A manager asks for a widget showing 'all the machine data'. What should you ask first?
Knowledge check
Planned time 450 min, run time 387 min, total 6,966 parts at an ideal 20 a minute, 6,757 good. Which factor is lowest?
Knowledge check
Which is a leading measure for scrap cost?
References
- ISO 22400-2:2014, Automation systems and integration: Key performance indicators (KPIs) for manufacturing operations management, Part 2: Definitions and descriptions. https://www.iso.org/standard/54497.html
- ISA: ISA-95 standard, enterprise-control system integration. https://www.isa.org/standards-and-publications/isa-standards/isa-95-standard
- Vorne: Calculating OEE. https://www.oee.com/calculating-oee/
- Vorne: The six big losses. https://www.oee.com/oee-six-big-losses/
Chapter 2 · The Widget Configurator
Widgets: configuration on the spine's data
A widget is not a new program. It is a few lines of configuration (which data, which measure, which target, which picture, how fresh, who may see it) drawn by one component the agent builds once. Adding a widget never opens a new path to the data.
35 minOne renderer, many widgetsViews that respect access rulesThe right visual for the questionReviewed like code
By the end of this chapter you can
- Name the seven parts of a widget's configuration.
- Build a database view that computes a measure and runs with the viewer's rights, so row-level security still applies.
- Choose the visual that answers each kind of question, and say why pies and gauges are poor choices.
- Brief an agent to add a widget, with an acceptance test that a role outside the matrix sees nothing.
Why configuration and not code
You could ask the agent to build each chart as its own page. Ten charts later you would have ten pieces of code, ten ways of fetching data, and ten places an access rule could be forgotten. Instead, the agent builds one widget component once, and every widget is a short entry in a configuration file. The curriculum calls this the Widget Configurator: in your platform it is that file, widgets.json, and the component that draws it.
- One path to the data. The component reads only from approved database views. A new widget cannot reach a table the views do not expose.
- Easy to review. A new widget is a few lines in a pull request. You can read it in a minute; you cannot do that with a new page of code.
- Easy for an agent. "Add a widget for scrap ratio by press" becomes a small, checkable change instead of a new feature.
The source: a view that keeps the access rules
Each measure is computed in the database by a view: a saved query that looks like a table. In PostgreSQL 15 and later, a view created with security_invoker = on runs with the rights of the person asking, so the row-level security policies on the underlying tables still apply [1][2]. A view without it runs with its owner's rights and can show every site's rows to everyone. Supabase's database advisor flags such views as a security problem, so check it after every schema change [3].
-- One measure, computed once, in the database. Runs with the viewer's rights.
create view public.line_shift_oee
with (security_invoker = on) as
select r.site_id, r.line_id, r.shift_date, r.shift,
sum(r.run_min)::numeric / nullif(sum(r.planned_min), 0) as availability,
sum(r.total_count)::numeric / nullif(sum(r.run_min * r.ideal_rate), 0) as performance,
sum(r.good_count)::numeric / nullif(sum(r.total_count), 0) as quality,
sum(r.good_count * 60.0 / r.ideal_rate) / nullif(sum(r.planned_min) * 60, 0) as oee,
max(r.recorded_at) as as_of
from public.production_runs r
group by r.site_id, r.line_id, r.shift_date, r.shift;
-- The view adds no access of its own: a supervisor still sees only their site's rows,
-- because production_runs has row-level security generated from the Role and Exposure Matrix.
grant select on public.line_shift_oee to authenticated;The configuration
Each widget is one entry. The component reads the entry, asks the view for rows (as the signed-in person), and draws the visual. Nothing in the entry is a secret, and nothing in it can widen access: the roles field can only hide a widget from people who could already read its view.
[
{ "id": "oee-now", "title": "OEE this shift", "source": "line_shift_oee", "measure": "oee",
"filter": { "shift_date": "today", "shift": "current" }, "group": "line_id",
"visual": "tile", "format": "percent", "target": 0.80, "red_below": 0.65,
"refresh_s": 60, "stale_after_s": 300, "drill": "/lines/:line_id", "roles": ["supervisor", "manager"] },
{ "id": "oee-trend", "title": "OEE, last 14 days", "source": "line_shift_oee", "measure": "oee",
"filter": { "shift_date": "-14d" }, "visual": "line", "limits": "control", "refresh_s": 900, "roles": ["manager"] },
{ "id": "downtime-pareto", "title": "Downtime by cause, this week", "source": "downtime_by_cause", "measure": "minutes",
"filter": { "week": "current" }, "visual": "pareto", "refresh_s": 300, "roles": ["supervisor", "manager", "planner"] }
]The visual: answer the question that was asked
Each kind of question has a visual that answers it best. In a classic study of how people read charts, Cleveland and McGill found that people judge positions along a common scale (bars, dots on a line) far more accurately than angles, areas or colour shades [4]. That is why pie charts, round gauges and 3-D effects lose to sorted bars and plain lines.
| Visual | Use it for | Avoid it for |
|---|---|---|
| Number tile | One value now, against its target, with a small trend arrow | Comparing many items |
| Line | Change over time; keep the same scale from day to day | Categories with no order |
| Sorted bars (Pareto) | Which causes, products or presses account for most of the loss | Values over time |
| Status grid | Which line or press needs attention now | Showing how big a problem is |
| Control chart | Telling a real change from normal variation (chapter 3) | A single value |
| Table | Lists people act on row by row: open holds, overdue work orders | Spotting a trend |
A Pareto, drawn to scale
Here is one week of downtime on Line 3. Sorting the causes largest first, with a cumulative line, makes the decision obvious: two causes are well over half the minutes, so they get the engineering time this week.
Adding a widget with an agent
Brief the agent the way Session 12 taught: the goal, the limits and the check that proves it is done. For a widget, the check always includes an access test.
Goal: add a widget "Scrap ratio by press, this shift" for supervisors and managers.
Limits: add one view (security_invoker = on) and one entry in widgets.json. Do not change the
widget component, any table, or any row-level security policy.
Done when, from a fresh clone, npm test passes, including the new test that:
1. signs in as the Line 3 supervisor and sees one row per press on Line 3, with the scrap
ratio matching the hand-worked value in docs/measures.md;
2. signs in as a supervisor from another site and gets zero rows;
3. signs in as an operator and does not see the widget at all.You need: Your platform repository; the Supabase SQL editor or a migration file; your AI coding agent; the measure sheet from exercise 1
You will turn three rows of your measure sheet into views and widget entries, built by the agent and checked by you.
Outcome: Three working widgets on the spine's data, each proven to respect the access rules and to compute the number you worked by hand.
Knowledge check
A widget reads a view that was created without security_invoker. What is the risk?
Knowledge check
Which visual best answers 'which causes account for most of our downtime?'
Knowledge check
Why build one widget component driven by configuration, rather than a new page per chart?
References
- PostgreSQL documentation: CREATE VIEW (security_invoker). https://www.postgresql.org/docs/current/sql-createview.html
- Supabase docs: Row Level Security. https://supabase.com/docs/guides/database/postgres/row-level-security
- Supabase docs: Performance and security advisors. https://supabase.com/docs/guides/database/database-advisors
- Cleveland, W. S. and McGill, R. (1984). Graphical perception: theory, experimentation, and application to the development of graphical methods. Journal of the American Statistical Association 79 (387). https://doi.org/10.1080/01621459.1984.10478080
Chapter 3 · Layout, signal and freshness
The dashboard people act on
A good dashboard is read in five seconds, from across a room or on a phone in a glove. It keeps colour for trouble, tells real change from noise, and never shows an old number as if it were live.
30 minFive-second testGrey is normalControl limits, not hunchesEvery widget says 'as of'
By the end of this chapter you can
- Lay out a dashboard for one role so the most important measure is read first, on a wall and on a phone.
- Use colour only for abnormal states, and never colour alone.
- Read an individuals control chart and decide whether a change is a signal or noise.
- Set each widget's refresh and staleness rules, and show the time of its data.
One role, one screen, five seconds
Build one dashboard per role: the supervisor's, the manager's, the planner's. Each answers that role's questions and nobody else's. Then test it the simple way: show it to the person for five seconds, hide it, and ask what they would do next. If they cannot say, the layout is wrong, not the person.
- Most important first. People read a screen top left to bottom right. The measure tied to the main decision goes top left.
- Group by decision. Widgets that feed the same decision sit together.
- Same scale every day. A trend whose axis rescales each morning makes a small wobble look like a cliff.
- Phone first. On a phone the grid becomes one column in the same order, every tile is a tap target of at least 44 px, and text stays at least 15 px, as Session 10 set out [1].
Grey is normal; colour means act
Control-room displays learned this lesson the hard way. ISA-101, the standard for human-machine interfaces in process automation, describes displays where normal states are drawn in muted greys and bright colour is kept for abnormal conditions and alarms, so the eye goes straight to what needs attention [2]. The same applies to a manager's dashboard. A screen where every tile is green or red trains people to ignore colour.
- Normal is grey. A measure inside its limits is drawn in the page's neutral colours.
- One colour for trouble. Amber or red only when a limit is crossed, and the same meaning everywhere.
- Never colour alone. Add a word or a shape ("Below limit", a triangle), so people with colour-blindness and screens in bright sunlight still get the message [3].
- Enough contrast. Text needs a contrast ratio of at least 4.5 to 1 against its background [4].
Signal or noise?
Every process varies. If a manager reacts to every dip, they will change things that were fine and make the process more variable, not less. A control chart draws limits from the process's own normal variation, so you can see which points are real signals [5].
For one value per shift (an individuals chart), the limits are: the mean, plus and minus 2.66 times the average moving range (the average of the differences between one shift and the next). The 2.66 is 3 ÷ 1.128, the factor that turns the average moving range into an estimate of the standard deviation [6].
| Rule (react when…) | What it usually means |
|---|---|
| One point outside a limit | Something specific happened that shift: find it |
| Eight or more points in a row on one side of the mean | The process has shifted: a new die, a new material lot, a new crew |
| Six points in a row steadily rising or falling | A drift: tool wear, a sensor going out of calibration |
The first two are among the Western Electric rules, and the third is one of the Nelson rules, both widely used with control charts [10]. Set the widget's limits to control and have the agent compute the limits in the view, from at least 20 points, never by hand.
Fresh, or honestly stale
A number that looks live but is twenty minutes old is worse than no number: someone will act on it. Every widget therefore carries two settings from its configuration: how often it refreshes, and how old its data may get before it says so.
- Refresh by asking again. The simplest and cheapest way: the page asks the view for new rows every
refresh_sseconds. A minute is enough for most plant measures. - Push for events. For a widget that must change the moment something happens (a new quality hold), Supabase Realtime can push table changes to the page, and it respects row-level security [7]. It streams changes to tables, not to views, so measures computed by views are still refreshed by asking again.
- Show 'as of'. Each view returns the time of its newest row (
as_ofin the example). Afterstale_after_swith nothing newer, the widget goes grey and says "as of 06:03".
Keep it honest over time
Dashboards collect widgets the way garages collect boxes. Record which widgets people open (a simple count per widget per week is enough). Every month, show the manager the list: a widget nobody opened, or whose red never triggered an action, comes off. Fewer, trusted widgets beat many ignored ones [9].
You need: Your platform's preview address; your phone; the three widgets from exercise 2; one manager or supervisor
You will arrange your widgets for one role, make them honest about freshness, and test the result with the person who will use it.
Outcome: A one-role dashboard that passes the five-second test on a phone, shows colour only for trouble, and never shows stale data as live.
Knowledge check
On a supervisor's dashboard, what colour should a measure inside its limits be?
Knowledge check
The Line 3 individuals chart has mean 74.2% and limits 66.2% to 82.2%. Today's shift is 70%. What should the manager do?
Knowledge check
The data feed stops for 10 minutes. What should an OEE tile with stale_after_s = 300 show?
References
- W3C: Understanding WCAG 2.2, Success Criterion 2.5.5 Target Size (Enhanced). https://www.w3.org/WAI/WCAG22/Understanding/target-size-enhanced.html
- ISA: ISA-101, Human-Machine Interfaces for Process Automation Systems. https://www.isa.org/standards-and-publications/isa-standards/isa-101-standards
- W3C: Understanding WCAG 2.2, Success Criterion 1.4.1 Use of Color. https://www.w3.org/WAI/WCAG22/Understanding/use-of-color.html
- W3C: Understanding WCAG 2.2, Success Criterion 1.4.3 Contrast (Minimum). https://www.w3.org/WAI/WCAG22/Understanding/contrast-minimum.html
- NIST/SEMATECH e-Handbook of Statistical Methods: What are control charts?. https://www.itl.nist.gov/div898/handbook/pmc/section3/pmc31.htm
- NIST/SEMATECH e-Handbook of Statistical Methods: Individuals control charts. https://www.itl.nist.gov/div898/handbook/pmc/section3/pmc322.htm
- Supabase docs: Realtime. https://supabase.com/docs/guides/realtime
- Supabase pricing. https://supabase.com/pricing
- Perceptual Edge (Stephen Few): dashboard design articles. https://www.perceptualedge.com/articles.php
- NIST/SEMATECH e-Handbook of Statistical Methods: What are variables control charts? (Western Electric rules). https://www.itl.nist.gov/div898/handbook/pmc/section3/pmc32.htm
Chapter 4 · 12 questions · 80% passes
Final assessment
Twelve questions across the element. Score 80% (10 of 12) to pass. Your LMS records your score and each answer; you can review the chapters and try again.
15 min12 questions≈ 15 minutesRetake allowed
Your result
CivOps AI Academy
Widgets and the Dashboard: Measures Managers Act On
Element F14 complete · Learner
Your LMS records this completion. For the CivOps Foundation certificate, finish the Foundation Course at https://civops.io/learn.