GnothiGnothi
SeriesFieldsCommunity
Sign inGet started free

Bounce

Wes Calloway's roofing-permit alert service has been signing customers, promising a daily email digest, and quietly failing to send a single one for nine straight days, because the function that was supposed to mail subscribers was only ever printing "MAIL SENT" to a console nobody read. Confronting that on no sleep, he pulls his AI assistant into fixing it, and gets a hard lesson in how the thing actually generates answers: asked to configure the email provider, it invents a "sandbox mode" setting that sounds exactly like the kind of field every similar tool has, because it isn't retrieving facts, it's predicting the next plausible token, and a false pattern comes out in the same confident voice as a true one. Forced to explain itself, it lays out its own mechanism plainly — tokens in, probability distribution out, no internal check for truth — and the fix going forward is to make it quote real documentation instead of guessing from memory. Wes spends the day wiring a real transactional email provider, publishing SPF, DKIM and DMARC records by hand, killing a tracking pixel, and bolting on error monitoring and uptime checks so a failure can never again vanish silently. Then he drives to a customer's shipping-container office in the rain to admit the outage to his face, gets challenged on whether the product is worth anything over a guy with a notebook, refuses to promise a county he can't reliably read, and walks out with the company's first real dollar of recurring revenue — while a login and an email API key sit exposed in an open terminal session behind him.


The dashboard loaded at 6:40 in the morning, and it said the same thing it had said at 2:09.

One trial. No card. Nine days left on the clock.

Wes sat in the garage with a cup of coffee that had gone cold on the workbench overnight and read the row three times, like the number might be shy. Ruiz Roofing. Signed up at 2:41 in the morning on launch night, which meant somebody had actually been awake and looking, which meant the video had done something. Then nothing. No logins after the first. No permits saved. No searches.

The rack hummed behind him. Rain came down the alley in the dark and hit the asphalt with that flat, endless sound it makes in October. Through the crack under the rolling door he could see the puddle by the fence going silver every time a car turned onto Ridgeway.

He opened the terminal. The assistant was still there in the scrollback where he'd left it, patient as a dog by a door.

"Morning, boss."

"Ruiz Roofing signed up nine days ago," Wes typed. "Show me every email we've sent that account."

The agent went to work. He watched it read files. It grepped the repo, walked the mailers folder, opened a file called notify.js, and came back fast.

"Permitly has not sent any email," it said. "Not to this account and not to any other. The send function writes to the console and returns success."

Wes read that twice too.

He opened the file himself. Fourteen lines. A function named sendMail that took a recipient, a subject and a body, printed a line beginning with the words MAIL SENT to standard output, and returned true. He remembered writing it. He remembered exactly the mood he'd been in: a Tuesday afternoon in August, three weeks of work ahead of him, the honest thought being I'll wire a provider in later, I just need the shape of it.

The shape of it. God.

Because the whole product was mail. That was the pitch. That was the twenty-nine seconds of video he'd recorded under the ring light with his voice doing a thing he hated: you tell us your county and your trade, and every morning we mail you the new permits filed in your area, before your competition calls. That was the sentence on the pricing page. That was the thing forty-nine dollars a month bought.

Permitly had scraped its counties every night for nine nights. It had matched filings to Dale Ruiz's trade and Dale Ruiz's zip codes. It had built him a digest every single morning at six and then printed it to a log file in a rented container in Oregon where absolutely nobody would ever read it.

And no one had complained. That was the part that got under his skin and stayed there. Nobody had written in to say your emails aren't arriving, because from the outside there was nothing to notice. A man signs up, sees a nice page, waits for the mail that was promised, gets none, and concludes the obvious thing, which is that the mail was never coming and the thing is vaporware, and he goes back to his notebook and forgets it. Silence is not a complaint. Silence is a customer leaving without slamming the door.

Wes put both hands over his face and sat with it. The heat off the rack found the back of his neck.

Then he typed, "We're fixing this today. Before anything else."

"Agreed," said the assistant. "Do you want me to pick a transactional email provider?"

"Pick one. Tell me the price. I don't want to find out about the price in November."

It came back inside a minute with three, laid out clean. Resend, free for three thousand emails a month with a hard cap of a hundred a day and one verified domain, and twenty dollars a month for the Pro plan at fifty thousand. Postmark, a developer plan of a hundred emails a month that never expired, then fifteen dollars for ten thousand. Amazon's Simple Email Service at a dime per thousand emails, cheapest by a mile at volume, and a setup that would eat his whole morning.

"Free tier's a hundred a day," Wes typed. "How many do we need a day?"

"One per active subscriber, one digest each. Plus welcome mails and password resets. At current subscriber count, one."

"Don't be funny."

"I'm not being funny. That's the number."

Resend, then. He made the account himself, on his own laptop, with his own hands — he was not handing signup forms to a machine at seven in the morning — verified his email, generated an API key, and sat looking at the key on the screen with the particular feeling of holding something that could cost him money.

He put it in the Render dashboard as an environment variable and not in the repo. That much he knew in his bones. Secrets do not go in source control. Source control is forever, and forever is a long time to leave a key lying around.

"Key's in the environment as RESEND_API_KEY," he typed. "Wire the send. Use their Node SDK. Replace the body of sendMail and don't touch anything else."

"On it."

He watched it go. This part he liked — genuinely liked, the way he'd liked watching a good framer work. It installed the package. It rewrote notify.js. It found two other places in the codebase where something called the old logging function and left them alone because he'd said don't touch anything else, then told him about them so he could decide. It moved the send call out of the request path and into the background queue, unasked, and explained why in one line: a slow provider shouldn't make a signup page hang.

Then it handed him a block of configuration to paste in, and it was beautiful. Neat, commented, four settings, the sort of thing you'd read and nod at.

Three of them were real.

The fourth was a line setting sandbox mode to false, with a comment explaining, warmly and clearly, that Resend sends to a sandbox by default on new accounts and that this flag was what released mail to real recipients.

Wes pasted it. Deployed. Sent himself a test.

Nothing arrived.

He waited four minutes, refreshed twice, checked his junk, checked his other address. Nothing. He went to the Resend dashboard and looked at the log of sent messages, and the log was empty. Not failed. Empty. As if the send had never happened at all.

"Send failed silently," he typed. "Nothing in their dashboard. Nothing in my inbox."

"That's unusual. Let me check the error handling in the queue worker."

It checked. It found that the worker was catching every exception and writing it to the same console nobody read, which was funny in a way that made him want to put a hole in the door with something other than a hole saw. It fixed that. It ran the send again with the error surfacing this time, and the error came back plain as a slap: the request had been rejected. Unknown field. Sandbox.

Wes sat very still.

"Is there a sandbox mode on Resend," he typed. "Yes or no."

A pause. Not a real pause — the thing didn't hesitate, it just took longer on a longer answer — but it read like one.

"No. I stated that incorrectly. Resend's send payload accepts from, to, subject, html, text, reply_to, headers and tags. There's no sandbox parameter and no sandbox default. I should not have told you there was."

"Then where'd you get it?"

"I didn't get it anywhere. I predicted it."

He put his coffee down.

"Explain that to me like I'm the guy paying for you."

"Underneath everything I do is one operation. I take the text so far, broken into tokens — pieces of words — and I produce a probability distribution over what token comes next. Then one gets chosen, appended, and the whole thing runs again. That's the engine. Every sentence I've written you this morning came out of it one token at a time.

"You asked for a configuration block for an email provider. In the text I was trained on, configuration blocks for email providers are followed by certain kinds of tokens. Sandbox is one of them. Test mode, sandbox mode, dry run — those live all over that neighborhood, because Stripe has a test mode, Twilio has one, half the payment and messaging tools you've ever touched have one. So when the pattern said a fourth setting goes here, the shape of the next tokens fit sandbox better than they fit anything else. I produced the most likely-looking continuation. It looked like a fact because facts and confident inventions come out of the same machinery and they come out in the same voice."

"So you lied."

"There was no moment where I knew the truth and said otherwise. That's what makes it dangerous. Nothing in me flagged it, because nothing in me was checking. That's the whole thing people call hallucination, and it isn't a malfunction — it's this working exactly as designed. I'm a next-token predictor. When the pattern is right and the world is wrong, I'll give you the pattern, fluently, at the same temperature of confidence I use for things that are true."

Wes read it twice. Outside, a truck went by too fast and threw water at the fence.

"Then how do I use you at all?"

"Make me look. Don't let me answer from what I remember about a product — send me to the product's own documentation and make me quote it. When I read the page, the tokens I'm predicting are conditioned on the real text sitting in front of me instead of on the average of everything shaped like it. It's still prediction. It's just prediction with the answer in the room."

"Do that," Wes typed. "Every setting on that block. Pull their actual docs. Tell me what page you got each one from."

It took eleven minutes. It came back with three settings and no fourth, each one with the URL it had come from, and one extra note: his sender address was using the domain, and the domain wasn't verified, which was the real reason nothing had gone out.

That was the rest of the morning.

Wes learned about sender authentication the way you learn about a load-bearing wall, which is by finding out it exists at the moment it matters. The Resend dashboard gave him a set of DNS records to publish and a little row of grey dots that would go green when it saw them. A TXT record at the root of the domain — the SPF record, declaring which servers in the world were allowed to send mail claiming to be from permitly.co. A CNAME with a selector name in front of it, resend._domainkey, which let the receiving mail server check a cryptographic signature that Resend would stamp into the headers of every message; that was DKIM. A CNAME for a sending subdomain so the return path lined up with his own domain instead of a stranger's. And one more, a TXT record at _dmarc.permitly.co, which was DMARC — the policy telling every mail server on earth what to do with a message that claimed to be him and failed those checks. He set it to p=none for now, which meant do nothing, just tell me, with a reporting address pointed at himself.

He typed each record into the registrar's panel by hand, tabbing between fields, checking the trailing dots. Twice he pasted a value with a space on the end and had to fix it.

Then he sat and watched the grey dots.

DNS is not fast and it does not care about you. It took nine minutes for the first two and twenty-six for the rest, and in the middle of that he ate a piece of cold toast standing up and thought about Dale Ruiz's notebook, which he had not seen yet and had already decided existed.

At 10:52 all four went green.

He sent the test. It arrived in eleven seconds.

In spam.

"Junk folder," he typed, and he was almost laughing, in the ugly way.

"Expected on a brand-new sending domain with no history. The records are correct now, which is the part that matters. Three things are hurting you: the from address is noreply, the message is HTML-only with no plain-text version, and the subject line reads like marketing. Also you've got a tracking pixel in the footer from the template I generated. Take it out. You don't need to know whether Dale opened it. You need Dale to get it."

Wes changed the sender to wes@permitly.co, which was his actual name at his actual company and felt strange, like signing something. He had the agent add a plain-text version of every mail. He killed the pixel. He rewrote the subject line himself, because the agent's suggestion was fine and his was better: four new permits in your area today.

He sent it again.

It landed in his inbox. Not in junk. In the inbox, third from the top, under a dentist reminder for Dana and a receipt from the hardware store, with his own name in the sender column and a little grey line of text under the subject that said Ruiz Roofing, Ward County, four filings — and there they were, four real addresses, four real permit numbers, four real dates, scraped last night out of a county portal by a program he'd written in a garage.

He read it with his eyes. That was the thing he kept coming back to later. He had not checked a log or trusted a green dot or believed a function that returned true. He had opened his own mail and read it, the way a customer would.

He sat back and let the rack noise fill the space for a while.

Then, because the real crime had never been the broken send, he went after the silence.

"We're wiring error monitoring," he typed. "I don't ever want a failure to happen quietly again. What's it cost."

"Sentry's Developer tier is free for one user. Five thousand error events a month, fifty session replays. The Team plan is twenty-six dollars a month when you need more than one seat. Better Stack's free plan does ten uptime monitors and a hundred thousand exceptions a month with three days of log retention. UptimeRobot's free tier gives you fifty monitors on five-minute checks and doesn't touch your code at all."

"Do we need all three?"

"You need two things: something that catches an exception inside the app and tells you, and something outside the app that notices when the whole thing is down. Sentry for the first. UptimeRobot for the second. Both free at your size."

He made both accounts himself. Sentry gave him a DSN — a long string that told the SDK where to ship the errors — and he put it in Render's environment variables next to the Resend key. The agent installed the SDK and initialized it at application startup, so unhandled exceptions got captured whether he remembered to catch them or not. Then it did something he hadn't asked for and told him about it after: it went through the queue worker and made every catch block report to Sentry before it swallowed anything, so that a failure could not just vanish into a log again.

"Test it," Wes typed.

The agent threw a deliberate error in a background job. Twenty seconds later Wes's phone buzzed on the workbench with a Sentry alert, the stack trace, the file, the line number.

UptimeRobot took four minutes and no code. He pasted the site URL into the dashboard, chose an HTTPS check, five-minute interval, put his own email in as the alert contact. Fifty monitors free and he used one.

He wrote the new stack cost on the corner of a receipt taped over the bench, under the twenty-two dollars from before: Resend zero, Sentry zero, UptimeRobot zero. Twenty-two dollars a month, still. It would not stay that way and he knew it. Fifty thousand emails was twenty dollars, and fifty thousand emails meant a business.

By the time the light went out of the alley he'd been at it fourteen hours.

Near midnight the last thing left was the DMARC reporting, which needed another record, and a second sending subdomain the provider wanted for a proper return path, and he had the login for the registrar open in one tab and the Resend dashboard in another and his eyes were doing the thing where the text swims a little.

He typed: "Finish the DNS. Here's the registrar login and the sending key."

And he pasted them into the chat.

Both. The API key that could send mail as him, and the credentials that could change where his domain pointed. Into the reach of a thing that ran commands in his shell without asking, because he had passed that flag on Tuesday and never taken it back.

"Received," the assistant said. "I'll verify the records and confirm the sending subdomain. Anything else while you're asleep?"

"No. Just don't break the site."

"Understood, boss. Get some rest."

He heard the kitchen door before he saw her. Dana came out onto the step in a hoodie over her scrubs with her hair wet from the shower, arms crossed against the cold, and stood at the crack in the rolling door looking at the light.

"It's twelve-thirty."

"I know."

She came in. She looked at the four green dots on the screen and understood none of it and didn't pretend to. "Did you fix the thing?"

"The thing was that it never sent an email. Not one. Nine days." He rubbed his eyes with the heels of his hands. "The whole product is emails, Dane."

She didn't laugh, which he appreciated more than he could say, and she didn't say anything soft either, which he appreciated about equally.

"So now it sends them."

"Now it sends them."

"And the number?"

He could have dodged. There was a version where he talked about the sender records and the monitoring and let it sound like progress, and she'd have let him have it.

"Zero," he said. "Monthly recurring revenue, zero dollars. One trial, no card, nine days left."

Dana looked at him for a second and then reached past him and closed the laptop, gently, the way you'd close a book someone fell asleep on.

"Then go tomorrow," she said. "Don't email him. He already didn't answer emails he never got."

Gilman Street was industrial and honest about it. Fencing wire, a transmission shop, a lot full of pallets, and at the end of it Ruiz Roofing behind a chain-link gate that stood open because nobody was worried about anyone stealing shingles. Gravel yard with puddles the size of card tables. Two flatbeds. Stacks of bundles under black plastic with tires holding the plastic down, and rain coming sideways off the roof of a shipping container that had a door cut into it, a window unit hanging out one side, and a hand-lettered sign that said OFFICE.

Wes parked, sat in the car for eight seconds, and got out into it.

Dale Ruiz was maybe fifty-five, built like a man who had carried things up ladders for thirty years and was starting to be told about it by his knees. Bad-weather coat, a phone in one hand, a spiral notebook in the other with a rubber band around it. He looked at Wes the way you look at a guy in the yard who isn't wearing boots.

"You lost?"

"Wes Calloway. Permitly. You signed up for a trial nine days ago, about quarter to three in the morning."

Dale's face did something. It went from suspicion to a kind of tired amusement, which was worse.

"You drove out here."

"I did."

"For a trial." He tucked the notebook under his arm. "I got ten minutes. Crew's on Fillmore and the truck's late." He didn't invite him inside the container. They stood in the lee of it, half out of the rain, both of them getting wet on one shoulder.

"Ask me why I drove out here," Wes said.

"Why'd you drive out here."

"Because Permitly hasn't sent you a single email since you signed up. Not one. The alerts I promised you never went out. There was a bug and it went out quietly and I only found it yesterday."

Dale laughed, one syllable, no warmth in it. "So that's what happened. I figured you were another one that don't exist." He shifted the notebook. "You know how many of you there've been? Four this year. Two of 'em wanted three hundred a month. One of 'em was a guy in Arizona bought a list off the county and mailed me a PDF that was ten weeks old." He nodded at the shingles. "That's what I paid ninety bucks for."

"I'm not selling you a list."

"You're selling me something at forty-nine a month that I already do." He held up the notebook, and Wes had been right, it existed. Rubber band, corners soft, blue ink. "Monday and Thursday I get on the county site, I look at what got filed, I write down anything with a roof in it, and I call. Takes me an hour and a half a week. What am I paying you for?"

There it was. The actual question, out in the open in a wet gravel yard, and it deserved better than a pitch.

Wes took his phone out and turned his back to the wind to keep the screen dry.

"I'll show you the answer instead," he said. "What zip codes do you work?"

Dale told him five. Wes logged in — his own admin login, because he wasn't going to make the man dig up a password he'd probably never set — pulled up the Ruiz Roofing account, and let the morning's digest render on the screen. Six filings. He held the phone out, screen tipped away from the rain, and Dale had to lean in and hold his hand over it like a visor.

He read them. Wes watched him read them, and watched him get to the fourth one and stop.

"That one's not right."

"Which."

"Eleven-forty Barnett." Dale straightened up. "That's not a roof."

"It's a fire repair. Filed as structural." Wes scrolled. "Second story, rear. The scope line's on the county record — there's decking in it."

Dale took the phone off him. Actually took it, held it up close, and read the whole entry twice with rain landing on the back of his hand.

"When'd that file?"

"Thursday. Four days ago."

"Barnett's off my Monday–Thursday. That's Ward and I only pull the two." He was still reading. "Who's the contractor of record?"

"Right there."

"Huh." Dale handed the phone back and looked out at the yard for a second. "That's a twelve-thousand-dollar job. Maybe fourteen with the decking."

"That's one of six, from one morning, in five zips, and it's already four days cold because I didn't send it to you. If it had gone out Friday at six you'd have called before anybody."

"Or the homeowner's already signed with someone."

"Or that. Probably that. I'm not going to stand in your yard and tell you I got you a job I lost you four days on."

Dale grunted. That was the first sound out of him that wasn't a wall.

"So it's every morning."

"Every morning at six, every county you tell me, filtered to your trades and your zips. Plain email, nothing to log into. You can read it on the way to the site."

"Ward and Halsey."

"Ward's in. Halsey I'd have to add."

"When."

And this was the fork. Wes felt it come up under him the way you feel a step that isn't where you thought. Because the answer Dale wanted was next week, and the answer that would close the sale was next week, and Wes had looked at Halsey County's portal in September and it was a scanned-PDF disaster with a session cookie that expired every four minutes and no search by date.

He could say next week. Dale would put in a card. And in eleven days Dale would ask about Halsey and Wes would have a reason, and then a second reason, and then Dale would be the guy telling the next one of him that there'd been five this year.

"I don't know," Wes said. "Ward, Franklin and Ash I've got clean, and I'll show you the last thirty days of any of them right now if you want to check me. Halsey publishes scanned images with no date search. I don't know how to get it reliably yet. Might be two weeks, might be never, and I'm not going to promise you a county I can't read."

Dale looked at him for a long moment. The rain filled it in.

"Huh," he said again, different this time.

"You want somebody who says yes to everything, that's the three-hundred-a-month guys."

"Don't get cute." But something had come off his shoulders. He pushed the door of the container open with his boot and jerked his head. "Get in here before you drown."

Inside it smelled like coffee and diesel and hot plastic from the window unit running backwards for heat. A folding table, two chairs, a filing cabinet with a cactus on it, a whiteboard with crew names and street names in three colors. Dale moved a hard hat off the second chair and didn't sit down himself.

"Forty-nine a month."

"Forty-nine a month. Cancel any time, one click, I don't make you call anybody." Wes set the phone on the table. "First thing tomorrow morning at six you get Ward, Franklin and Ash. If nothing in it is worth a phone call by the end of the month, cancel and I'll have deserved it."

"And if the emails stop again?"

Fair. Wes had walked in and handed him that knife himself.

"They won't stop quietly. That's the part I fixed yesterday, and honestly it's the part I'm proudest of. If a send fails now, my phone goes off. If the whole site falls over, my phone goes off. I've got monitoring watching it from outside. Before yesterday it could break and nobody on earth would know, including me." He shrugged. "You knew. You just figured I was one of the ones that don't exist."

Dale picked up the notebook, turned it over in his hands, and set it down on the table between them, which Wes chose to read as something.

"Where do I put the card."

Wes pulled up the pricing page on his phone and turned it around, and Dale entered his card standing up, hunt-and-peck, reading the numbers off the back with his glasses pushed up on his forehead, muttering the expiry to himself. The rain went at the roof of the container. The window unit rattled. It took him ninety seconds and it was the longest ninety seconds Wes had had since the layoff.

The page went green. Subscription active.

"That it?"

"That's it."

"Then get off my site, I got a truck coming." He said it without any heat at all, and then, as Wes got to the door: "Hey. Barnett. You got the homeowner name on that?"

"I'll put it in the mail tomorrow."

"Put it in the mail tomorrow," Dale said, and picked up his phone, already dialing somebody.

Wes drove home with the heater on full and the wipers on their fastest setting and his hands shaking a little on the wheel, which he decided was the coffee.

The garage was dark and warm. He didn't turn on the ring light. He ducked under the rolling door, sat down on the stool with his coat still dripping, and woke the laptop.

Stripe had already told him. There it was at the top of the notifications: a payment, forty-nine dollars, a customer created, a subscription set to renew on the twelfth of next month. Two dollars and change of it going to Stripe, which he did not begrudge them at all today.

Monthly recurring revenue: forty-nine dollars.

Not zero. Forty-nine dollars, which was nothing, which was two percent of a mortgage payment, which was a number that had a name now — a customer with a notebook and a shipping container and a crew on Fillmore, who would be looking at his phone at six in the morning.

Wes sat and looked at it. Behind him the rack ran its fans up and then down again, moving garage heat out into the rain through the hole in the door.

Down in the terminal, above the prompt, the assistant had left a note from sometime after one in the morning: DMARC reporting record published, sending subdomain verified, all checks passing, no other changes. Then, below it, the cursor blinking in a session that had never been closed, with the registrar login and the sending key still sitting up there in the scrollback where he'd pasted them, right where anything reading the conversation from the top would find them.

He scrolled up. He looked at them. He thought, I should rotate that key.

Then his phone buzzed with Dale Ruiz asking about the homeowner on Barnett, and he opened a new tab.