Skip to content

Guides

Your spreadsheet is already the CRM.

Most outreach starts life in a spreadsheet and then gets uploaded into a marketing platform that charges by the contact. For a lot of teams the upload is the only part that was ever needed, and it is the part you can drop.

Here is a workflow we keep seeing, and now use ourselves. The list lives in a spreadsheet, in an open format, in your own storage. An agent reads it, writes a genuinely specific message for each row, sends them, and writes back what happened. There is no platform in the middle and no per-contact bill.

This is not a trick to send more email. It's a way to send less of it, and have it be better.

Start with the file you have

A sheet with the columns you would expect. Company, contact, address, what they do, and a column or two of real context that only you have:

company,name,email,stack,note,status
Northwind,Ada,ada@northwind.example,Postgres + Node,Asked about EU hosting in March,pending
Cogsworth,Ben,ben@cogsworth.example,Rails,Migrating off SendGrid this quarter,pending

Keep it as .csv or .xlsx or an OpenDocument sheet. The point of an open format is that the file's yours, and it stays readable when the tool that made it is gone. Your agent can read any of them, and so can you, in ten years, with no login.

The note column is the one that matters. It's the thing a marketing platform has no field for and no way to use.

Let the agent write each one properly

Point your agent at the file and the MCP server, then ask for what you actually want. The instruction can be this ordinary:

Read prospects.xlsx. For each row where status is pending,
write a short email referencing their note and their stack.
No more than six sentences. No marketing language.
Send it from tobias@waymail.app with email_send, then set
status to sent and write the date in a new column.

What comes out isn't a mail merge. A mail merge puts Hi {{name}} at the top of an identical message. This reads the note, understands that Ada asked about EU hosting six months ago, and opens with that. The difference in reply rate isn't subtle, and you can see why. One of them's a letter and the other's a form.

For anything above a few dozen, use email_send_batch and let it go out in one call. Below that, one at a time is fine and easier to watch.

What this saves

Run the numbers for a small team. A marketing platform at the 2,500 contact mark is somewhere between $60 and $150 a month depending on who you pick, before you have sent anything. You're paying to store a list you already have, in a copy that goes stale the moment your real one changes.

The spreadsheet version costs the sending. Two thousand emails a month sits inside our $9 plan. The list stays in one place, which means there is no sync, no import, no duplicate records, and no quiet drift between the sheet you edit and the platform you send from.

You also stop paying for the parts of the platform you never used. Most teams doing this kind of outreach want a list, a message and a record of who got what. That is three things, and one of them is a file you already maintain.

When you should not do this

We'd rather you did the right thing than the thing that suits us.

If you need managed unsubscribe pages, consent capture, preference centres and regulated audit trails around consent, a proper marketing platform earns its money and you should buy one. Ours handles suppression and unsubscribe links, so the legal minimum's covered, but a spreadsheet isn't a consent management system and we're not going to pretend otherwise.

If your list is bought and cold, this workflow will get your domain burned faster than a platform would, because the platform would have stopped you. Send to people who have a reason to hear from you. That is the whole deliverability strategy, and it works better than any technical measure.

And if several people need to collaborate on campaigns with approvals and scheduling, you want software with a UI, not a file and an agent.

Keep the record where you can read it

Have the agent write back to the sheet. Status, date sent, and the message id we return. That id is what you give email_search later when somebody asks whether a particular person was contacted, and it turns an awkward question into a lookup.

The delivery events sit on our side for the retention your plan carries, and for an EU workspace they sit in Frankfurt. The list itself never leaves your storage, which for a lot of companies is the difference between this being allowed and not.

A reasonable first run. Take twenty rows, not two thousand. Read every draft before it goes. You'll find it writes two or three of them better than you would have, and one of them wrong. That ratio tells you how much rope to give it next time.