A safety incident logger on AWS for a few dollars a month
Every business with a workshop, a van or a kitchen has a near-miss reporting process, and almost all of them receive about four reports a year. Not because four things happened, but because reporting one means finding a form, filling in eleven fields, and handing it to somebody who might ask what you were doing. So the pallet that nearly fell gets mentioned to a colleague and nowhere else, and six months later it falls on somebody. This post walks through a small system designed around a single number: how many reports you get.

Key takeaways
- One screen, forty seconds: what happened, where, and a photo if there is one.
- Severity is proposed by the system and confirmed by a person, so serious ones route fast.
- Anonymous is the reporter’s choice per report, and the trade-off is stated on the form.
- Actions are tracked separately from reports, because a closed report with an open action is a lie.
- Designed on AWS for about $2 a month.
The whole system on one page
Before any code, here is the shape of what we are designing.
- Machine learning
- Analytics
- Front-end & mobile
- People
Everything is subordinate to the report count
A near-miss system that receives four reports a year is not a system; it is a folder. So every design decision here is checked against one question: does this make reporting faster or slower? A dropdown of incident categories makes triage easier and reporting slower, so there is no dropdown. A required location field makes analysis better and reporting slower, so location is prefilled from the phone and editable.
The target is a report in under a minute from opening the link, and forty seconds is achievable: a sentence, a photo, and send. Everything else — category, severity, root cause, the actions — is done afterwards, by somebody whose job it is, from what was described.
What runs on every report (the inside)
- The intake. One screen. What happened, in your words. Where, prefilled. A photo if there is one. A choice about anonymity. Send. Part 2 is entirely about keeping it that short.
- The triage. Reads the description and proposes a severity and a category. The proposal is not a decision — it routes the report, and a person confirms or changes it. Getting a serious report to somebody in four minutes rather than four hours is the whole reason this step is automated at all.
- Actions. An incident produces zero or more actions, each with an owner and a date, tracked separately from the report. A report is closed when it has been reviewed; an action is closed when the thing is fixed, and conflating those is how businesses end up with tidy incident logs and unchanged workshops.
One report, end to end
- App integration
- Machine learning
- Analytics
- Front-end & mobile
- People
In plain words
A fitter is walking through the yard and a stack of pallets shifts as a forklift passes. Nobody is hurt and nothing falls. Under the old process he would mention it to somebody at lunch. Under this one he stops walking, opens the saved link, types “pallets by the roller door moved when the forklift went past, stack looks too high”, takes one photo, and sends. Thirty-eight seconds.
The triage reads that as a near miss involving stored materials and vehicle movement, proposes medium severity, and routes it to the site manager within the hour. She confirms the severity, looks at the photo, and creates one action: restack and mark a maximum height, owned by the yard supervisor, due Friday. It is done on Thursday.
Four months later the counter notices that this is the third report mentioning the roller door area and the second involving that forklift route. That is a different kind of finding from any individual report — none of the three was serious, and together they describe a place where something is going to happen. Nobody would have spotted it from three pieces of paper in a folder.
Design rules that shaped every decision
- Optimise for the number of reports. Every field added is a report not made.
- Severity is proposed for routing and confirmed by a person. The proposal never closes anything.
- Anonymity is the reporter’s choice, per report, with the trade-off stated before they choose.
- Actions are tracked separately from reports. A reviewed report with an unfixed hazard is not closed.
- Never record fault. The system captures what happened and what was done, and has no field for whose fault it was.
- Count locations and equipment, not people. The pattern that matters is where and what, not who.
Why this shape
Near-miss reporting fails for reasons that are entirely about friction and slightly about fear. The friction is a form; the fear is that reporting something will turn into a conversation about what you were doing at the time. Both are solvable and neither is solved by encouraging people to report more.
So the form is forty seconds, anonymity is genuinely available, and there is no field anywhere in the system for fault. What is left is a description, a place, and a photo — which turns out to be everything you need to fix a stack of pallets, and everything you need to notice that the roller door has come up three times.
The next four posts walk through each piece: how a report gets made in forty seconds, how triage routes it, how actions are tracked, and what the counting finds. One diagram per post, a cost breakdown, and an engineering reference at the end.
All posts