DEV Community

Cover image for Here Lies My Toaster
Nazar Boyko
Nazar Boyko

Posted on Edited on AI-assisted

Here Lies My Toaster

Hacktoberfest Open-Source AI Challenge: Ghost in the Machine Submission 👻🌼

This is a submission for the Hacktoberfest Open-Source AI Challenge Week 4: Ghost in the Machine

What I Built

Every house has a drawer of dead things: the earbuds that play on one side, the charger with the split cable, the phone with the spiderweb screen. Nobody mourns them. Halloween ends tonight and Día de los Muertos begins tomorrow, two days for remembering the departed, so I gave the drawer an obituary page.

Obituary card from The Household Gazette for Silas Gourdington III, three carved pumpkins on a porch, the smallest one collapsed. Cause of death: visible patches of rot.

Here Lies is a small web app that runs on your own laptop. You take a photo of something that died, and Gemma 4, running through Ollama on the same machine, writes it a straight-faced newspaper obituary: a name, a cause of death, a life of service, who it leaves behind, a request in lieu of flowers, an epitaph. You can download the card as a PNG.

The rule: the model may invent a name. It may not invent a scratch. Every physical detail on the card has to point at something the model listed when it looked at the photo, and plain Go code checks that before you see it.

Living things get a notice instead.

Notice from The Household Gazette: Still alive. Give it a treat instead.

In my tests the cat, the dog, the monstera and the person were turned away every time.

Demo

More cards on the landing page: https://nazboyko.github.io/here-lies/

Obituary card for Mr. Chester Golden-Crust, two slices of burnt toast
The toaster survived. Mr. Chester Golden-Crust did not: "In lieu of flowers, please wipe the crumbs from beneath the toaster tray."

Obituary card for Agnes Petalbrook, a rotting succulent in a terracotta pot
Agnes Petalbrook: "Survived by a terracotta shard and the faint smell of potting mix."

Obituary card for Mr. Arthur Glowwick, a scorched light bulb lying in ash
Mr. Arthur Glowwick: "It shone when asked, and dimmed when done."

The app: the toast's obituary card on the left, and on the right the list of details the model saw, each marked with the sentence that used it
The app, on another run of the same toast. On the right: what the model saw, and which sentence used each detail.

Run it yourself. You need Ollama, Go 1.26 and Node 20 or newer.

ollama pull gemma4:e4b
git clone https://github.com/nazboyko/here-lies && cd here-lies
make run
open http://localhost:8787
Enter fullscreen mode Exit fullscreen mode

Code

GitHub logo nazboyko / here-lies

Obituaries for the things that died in your house, written by a local open-weight model.

Here Lies

Obituaries for the things that died in your house, written by a model on your own laptop.

The app with an obituary card for two slices of burnt toast, next to the list of details the model saw

Take a photo of something that died: a cracked phone, burnt toast, shoes with holes, last week's pumpkin. Gemma 4 runs on your computer through Ollama, looks at the photo and writes the thing a straight-faced newspaper obituary. The model may invent a name. It may not invent a scratch: every physical detail on the card has to point at something the model listed when it looked at the photo, and plain Go code checks that before you see it.

Point it at a cat, a person or a healthy plant and it refuses: "Still alive. Give it a treat instead."

Landing page: https://nazboyko.github.io/here-lies/

Run it

You need Ollama, Go 1.26 and Node 20 or newer.

ollama pull gemma4:e4b
git clone https://github.com/nazboyko/here-lies && cd here-lies
make run

Then open http://localhost:8787…

How I Built It

Pipeline: 1 Look, Gemma 4 sees the photo. 2 Gate, plain code. 3 Write, Gemma 4 with text only. 4 Check, plain code.

  • Look. Gemma 4 gets the photo and returns JSON: thing, person, animal, living plant or unclear; what the object is; and what it sees, in three lists: damage, wear, features. Code numbers the details d1, d2, d3.
  • Gate. Plain code. People, animals and healthy plants get the still-alive notice.
  • Write. A second Gemma call, text only. It turns the numbered list into an obituary in JSON, and every sentence about the body carries the ids it uses.
  • Check. Plain Go, no model. The cause of death must cite a real damage or wear id, every life sentence must cite a real id, and everything must fit the column. A failing draft goes back once with the problems listed. If the rewrite fails too, code keeps what passes, rebuilds the rest from the detail texts, and the page says what it repaired.

Why two calls? The writer never sees the photo. It can only describe what the looking step wrote down, and because each reference is an id, my code can verify it. One call doing both would hand me prose I could either trust or not.

To measure it, I ran 17 photos from Wikimedia Commons through the real pipeline: 11 dead things, a cat, a dog, a healthy monstera, one person, an intact mug and a blurry shot. Then I opened every photo next to its details and marked each one true, false or unsure.

Measure Result
Photos 17
Gate decision correct 16 of 17
Obituaries printed 13
Passed the check on the first draft 12 of 13
Rewritten once after the check 1
Repaired by code after the rewrite 0
Details on printed cards 65
Really in the photo, checked by eye 53 true, 4 false, 8 unsure
Causes of death resting on a false detail 2
Median seconds 0.8 to look, 2.4 to write and check

Machine: Apple M5 Max, 64 GB, gemma4:e4b through Ollama 0.35.1. A card takes about 3 seconds. The one rejected draft was the charger's: its third life sentence cited no detail, and the rewrite fixed it.

The honest failure. My first look prompt asked for one list of details, each tagged damage, wear or feature. Gemma tagged almost everything as a feature. Burnt toast came back as "dark brown toasted surfaces", so the check found no injury and printed "Natural causes. It was simply no longer needed." Only 6 of 11 dead things had any damage or wear listed, and a split laptop charger became "white wired earbuds".

So I split the schema into three lists and asked for damage first. On the next run all 11 dead things had an injury. That run had its own bug: the model wrote "no visible damage" as an entry in the damage list, the check accepted it as an injury, and a blurred green glow was buried as Miss Petunia Bloomsworth, who "passed away due to no visible damage." Code now drops entries like that.

The table shows the check's limit. It proves that each sentence points at a listed detail, not that the detail is real. Two causes of death rested on details I could not find in the photo: a cassette adapter "suffered a missing screw hole" while its real injury, heat warping, went unmentioned, and a folded umbrella died of "torn fabric". That is why the card footer prints the model's list: you can hold the obituary up against the photo.

How it was tested:

  • 48 Go unit test cases: the check, the gate, the repair step, the HTTP routes, and the Ollama client against a fake server (bad JSON, missing model, Ollama down, timeout).
  • The live run above, plus two extra passes on three photos. The details barely moved, since the look step runs at temperature 0.2. The names changed each time, except the pumpkins, who were Mr. Josiah Gourdington twice.
  • 10 Playwright tests against the real server and model: upload, card, sentence-to-detail mapping, PNG download, still-alive notices, phone width, keyboard, missing model, Ollama down, the LAN address, and a full run that fails if any request leaves the machine.

Stack: Go 1.26 with net/http serving a React, Vite and TypeScript page; Gemma 4 E4B through Ollama; html-to-image for the PNG; Old Standard TT and UnifrakturMaguntia fonts bundled from Fontsource. The Ollama request pattern (structured JSON output, timeouts, plain-language errors) comes from my earlier project Backpack. The code here is new.

Photo credits, all from Wikimedia Commons: jack-o'-lanterns by Giulia Forsythe (CC BY 2.0), burnt toast by Sheep purple (CC BY 2.0), succulent by stephen boisvert (CC BY 2.0), light bulb by Shixart1985 (CC BY 2.0), and the shoes on the cover by Wolfmann (CC BY 4.0).

Why Does Open Innovation Matter?

These photos show the inside of your home: the kitchen counter, the bathroom shelf, whatever is headed for the trash. With an open-weight model on the laptop they never leave it. No upload, no account, no retention policy. The server holds the photo in memory for one request and never writes it to disk.

It works with Wi-Fi off. The browser test records every request during a full run, and the count going to any host outside the machine is zero. Each obituary costs nothing.

Because the model runs on my machine, I could cut its job into two strict steps and check the output in my own code. The schemas, the temperatures and the check live in my repository, not behind an endpoint that can change or disappear, and HERELIES_MODEL swaps in any other Ollama model.

The limit is the eyesight of a small model. Gemma called the broken mug a "creamer jug" with a spout it does not have, and 4 of 65 details were wrong. I can see those mistakes because the pipeline shows them to me, and I prefer that to a better answer I cannot inspect.

The Spirit of It

The most surprising result was a refusal. In the first run Gemma looked at a rotting succulent, translucent and black at the edges, and decided it was alive: "This plant is still with us. Water it." Once the prompt said that brown, mushy or translucent leaves mean dead, Agnes Petalbrook got her obituary.

Día de los Muertos is about remembering through stories. A dead charger is not a grandmother, but it deserves a better send-off than the trash can: a name, a cause of death, and someone to survive it. In its case, "a set of mismatched plugs and a seldom-used surge protector."

Prize Categories

Best Use of Gemma: Gemma 4 runs locally through Ollama, does both the looking and the writing, and code checks its output against what it saw.

Top comments (1)

Collapse
 
robertpaschal profile image
Odinaka Robert Nnamani •

The rule that the model may invent a name but not a scratch, checked in plain Go, is what keeps Mr. Chester Golden-Crust funny instead of made up.