Skip to content
florisknol.com
NLEN

I asked AI for a WhatsApp client. 82 minutes later it was running

Phone with a WhatsApp conversation next to a laptop with code, label 82 MIN

On 5 October at 20:34 I typed two sentences.

"I want a Wantzel implement of whatsapp-ws. Can we make a pure Wantzel implementation for studio of this."

That was all. A pointer to a small open-source WhatsApp bridge, and the wish to have it in Wantzel, the programming language my own environment runs on. At 21:56 my assistant Ilse sent her first reply over WhatsApp. In between sit 82 minutes, read off the ticket and the raw message log.

Since this morning the video is online in which you can see the whole thing, with the prompt, the timestamps and the tests turning green: https://youtu.be/LAdXqhevjrM

In this article I describe what happened in that hour and a half, and what grew out of it in the weeks after. And why the fast part is not the interesting part.

Two sentences are not a specification

If you read "WhatsApp client in 82 minutes", you picture an AI blindly spitting out code. That is not how it went.

The original is about a thousand lines of Go. The heavy lifting sits in a library underneath: the encryption, the binary message format and the Signal protocol. Pure Wantzel means that library is not there. Whatever it did, the agent had to write itself.

So the agent did not start with code but with a ticket. What is the original? What are we building, in six points? What stays out for now, such as media and groups?

Then the licences. The original is under the GPL, the library under the MPL. My software is closed, so not a single line of code is copied. Those projects serve only as a description of the protocol.

And then the most important heading: done when. The handshake works against WhatsApp's live server. Every layer is tested against an independent reference. A deliberate break turns the test red. And on my phone, pairing, receiving and replying all work, even after a restart without pairing again.

Twelve minutes after my prompt there were six new tickets, one per layer. The connection with its handshake. The binary format. Pairing with a QR code. The Signal sessions. Messages back and forth. The interface of the original.

Along the way the agent noticed that the folder of built programs had grown to seven gigabytes. Not its job. It wrote a ticket for it and went back to WhatsApp. The next day it was cleaned up.

Every layer was checked against something the agent had not written itself. The Go library's decoder, and the Signal library playing the part of the other phone. That is how you test the protocol, and not your own assumptions.

At 21:23 came the first commit: twenty files and almost 6,400 lines, tests included. By then not a single message had been sent. Those tests still exist. Last night they were run again, and they are all green.

Why the firewall is code and not a prompt

A minute after that first commit I came up with an extra wish. Ilse would answer my WhatsApp, the same assistant who already handles all my mail. She was never to follow a link, and never to engage with spam or phishing.

The obvious solution is a rule in her instructions. That is exactly what I did not want.

A rule in a prompt is a request to a language model. A cleverly written message talks its way around it. A rule in code cannot be talked into anything.

So the firewall came in layers. First the hub itself looks, without a language model. There is a blocklist and a limit on how fast someone may write, and links arrive as plain text that cannot be opened. Then comes a quick check for spam and phishing. The last layer is her toolset: in a WhatsApp turn she has no browser. She cannot follow a link, even if a message tries to talk her into it.

At 21:44 I sent: "Hello this is a test." The message came in, was decrypted, and nothing came back. For twelve minutes. Ilse was only allowed to answer once her firewall was in place.

At 21:55 her reply path was in git, behind the firewall. Half a minute later her first reply came: the test had arrived.

Then I asked when my next book comes out. She had no date, said so, and offered to note it down. Asked how she knew who I was, she answered: by your number. Someone who claims to be Floris from another number, she does not treat as Floris.

What honestly belongs with this

An hour and a half sounds fast. So I also want to say what surrounded it.

The cryptographic building blocks went into Wantzel's standard library that same evening, about twenty minutes before the prompt. The 82 minutes are the WhatsApp protocol on top of it.

The big choices were made the day before. I chose the unofficial protocol, with the risk that WhatsApp blocks the number. I took that risk knowingly. Beyond that: one paired device, and Ilse as the first to answer.

The firewall was added along the way and sits within the 82 minutes. It is the twelve minutes of silence between the first message and the first reply.

So the fast part is not the story. The story is that two sentences from me became a plan with a clear list of when something is done. And that every layer was tested against something the AI did not come up with itself. I decide what needs to happen and why. The AI builds it and tests it against that list.

From chat link to assistant

That was day one. Then came daily use, and in four weeks the link grew into an assistant. She got images, documents and videos. Group chats. Polls she can send and read back. Voice messages: she listens, and replies in a voice of her own.

This is how I use her now. In the morning she sets up my day. When a quote request comes in, I hear it from her. When an invoice has been open too long, she reminds me. And she thinks ahead: "You have a workshop in Amsterdam tomorrow. Shall I suggest your usual hotel?"

What she should not decide herself, she passes to me. A booking, a price or a commitment ends up with me, as an ordinary WhatsApp message.

On 2 November she moved out of my studio into a program of her own: Mobile Chat Agent. One program with one data folder, so it can run independently. It has an admin page and an MCP connection. With that I update her knowledge from Claude, or adjust her settings. Scheduled messages come from data: what is going on that day decides what she sends.

Last night: five agents at once on the hardest part

One part was not yet hers: calling. From 7 October Ilse could pick up, but through a helper program in Go, with ffmpeg for sound and picture. It worked. Still, it was the only piece not in Wantzel.

Last night five AI agents worked side by side, each on its own branch. One ported the speech codec WhatsApp uses for calls. Another built the encrypted transport. Others did video, removed ffmpeg from the voice messages and merged everything.

How do you stop agents from breaking each other's work? With two agreements.

The tests come from the old program itself. It records exactly what it sends and receives, and the new code has to reproduce that byte for byte.

The seams are written down in advance. Which routine the call uses to pass on sound, and which for picture. Each branch builds towards such a seam, and one branch joins them.

The speech codec now matches the reference byte for byte on all 152 test packets. A recording of an incoming call is part of that. To get there, even Go's math functions had to be rebuilt exactly. Almost right does not produce the same bytes.

How do you know such a test means anything? By breaking the code on purpose. One shift in one line of the decoder, and nine of the thirteen checks turn red. Back to the original code, and everything is green again. A test you have never seen turn red proves little.

The video is Wantzel now too. The H.264 decoder produces every frame identical to what ffmpeg makes of it. And at a quarter to nine last night, the first voice message made without ffmpeg played on my phone.

What has not happened yet at the time of writing: a phone call through the new Wantzel version. Every part is tested against the reference, on one machine. The live call is the next step. Until that works, the Go helper stays as a fallback.

What is still to come, and what I take from it

Ilse is growing into a colleague who gets things done. On the list are booking hotels and restaurants. After that handling quotes and scheduling appointments with clients. Then automatic invoicing and keeping the books. And buying from web shops, down to the groceries.

What I take from these weeks is not much about speed. An agent builds fast when the work is sharply defined up front. What has to be built, what stays out, and when is it done? It builds reliably when it tests against something it did not write itself, and when it has seen that test turn red once. And it stays safe when the boundaries are in code, not only in a prompt.

The human decides what gets built and why. The agent builds it, tests it, and passes on what it may not decide itself.

I build an agent like this for clients too, in one day. I do that on an Expert Day, at your location. You can find more about it on my profile.

All pieces