Software · Own tool
What a spreadsheetcannot do.
zapply! is a tool for my own job search, built to replace the application spreadsheet. It stores not a status but documents every station with its date, works out the conversion rates itself, and shows in a Sankey diagram where the process breaks off.
Problem, solution, outcome
The difference from a spreadsheet comes down to one point: what happens to the previous value when the status changes. Everything else follows from that.
Problem
A spreadsheet overwrites
A cell holds one value. After the rejection there is no record that two interviews happened first. The history is not filed away, it is gone.
Solution
zapply! keeps the history
Every station stays as its own entry with its own date and can be corrected afterwards. Eleven stations from planned to withdrawn.
Outcome
The funnel becomes visible
The analysis falls out of the kept paths by itself: how many applications lead to an interview, how many go further, and at which station they end.
The first two panels show the same three stations. On the left only the last one survives, on the right all three are kept, and only from that can the funnel be worked out.
Four functions
Two of them work out what a spreadsheet only holds between the lines. The other two take work off capturing and finding things again.
- 01
Sankey diagram
The funnel across every application in one picture. End states branch off where they occurred, so a rejection after a first interview does not land in the same bucket as a rejection straight after sending.
- 02
Documentation
Eleven stations from planned to withdrawn, each with its own date. Plus channel, salary by amount, type and period, working hours, application deadline and the address of the posting.
- 03
Application statistics
Conversion per transition, applications by month and location, response time as a median, salary range, channels with their interview rate, and the outcome of every closed process.
- 04
Sorting
Sort by date, status, company or salary in both directions, search across five fields at once, and status filter chips. The choice is remembered per device.
Why not simply a spreadsheet
Almost every job search starts with a spreadsheet, and for a while it carries the load. Point by point, the comparison looks like this.
Status change
SpreadsheetThe cell is overwritten. After the rejection there is no record that two interviews happened first.
zapply!Every station is kept with its own date and can be corrected afterwards.
Analysis
SpreadsheetCount rows, build subtotals, draw a chart by hand. Usually it stops at counting.
zapply!The Sankey diagram, conversion rates, response time, salary range and channels all come out of the data itself.
Capturing
SpreadsheetType every column by hand. After twenty applications the spellings drift apart and search stops finding anything.
zapply!Suggestions for around 300 employers and 175 locations, channels as icons, salary structured by amount, type and period.
Next step
SpreadsheetRecorded nowhere. Where a follow up is due is something you have to hold in your head.
zapply!A button in the same row: schedule an interview, accept, reject, no answer.
Two devices
SpreadsheetSend the file back and forth and hope the newer version wins.
zapply!An account with sync. On simultaneous edits the interface presents both states and asks which one holds.
On a phone
SpreadsheetHorizontal scrolling through twenty columns.
zapply!Readable from 320 pixels, one card per application instead of one row.
On the left, how most job searches are actually run. On the right, what the tool does at the same point.
The interface
Two tabs carry the tool: the overview for the current state, the statistics for the analysis. Plus a dialog for the history of a single application. There is nothing else, and nothing else is needed.
Decisions meant to last
The tool should still start in five years. These four decisions follow from that.
- 01
One file for the interface
No framework, no bundler. The app runs as a static file anywhere: locally by double click, inside a WKWebView, behind a Worker. The price is a large file, the gain is durability.
- 02
Password derivation in the browser
Cloudflare grants ten milliseconds of compute per request on the free tier, too little for proper hashing. So the browser runs PBKDF2 with 400,000 rounds and the server stores only a salted SHA-256 hash of the result.
- 03
Sessions without a database read
A signed cookie over account id and expiry instead of a session table. No read per request, no delay from eventually consistent storage. The trade is a 30 day lifetime.
- 04
Optimistic concurrency
Every record carries a revision. The server rejects a write with a stale revision and returns its own state, and the interface presents both. In a tool holding weeks of work, silent overwriting is the worst possible failure.
Status
The tool is in beta and in daily personal use. It is still being developed, so the interface and the data model may still change.
Until 2026 it was called Bewerbungstracker, and the repository still carries that name. The demo runs without sign in on sample data, none of which is stored, and the source is open.