---
ref: workflow:cold-email-reply-triage
title: Sort cold email replies by intent and answer the warm ones
author: thedogwiththedataonit
tools: [tool:instantly/list-emails, tool:typesafe/answer-typed-questions, tool:instantly/update-lead-interest-status, tool:instantly/reply-to-email, tool:slack/post-message]
tags: [capability:classify-signals, capability:route-alerts, capability:search-conversations, capability:send-email, channel:chat, channel:email, has:api, motion:outbound]
updated: 2026-09-29
---

# Sort cold email replies by intent and answer the warm ones

Reads new Instantly replies, labels each one's intent with Jev, sets the lead's interest status, and drafts answers to the warm ones.

Set up the tools below, then run the steps in order for the user, carrying each step's results into the next. The run is done when the user has the outcome below.

## Outcome

- A table of every new reply with its intent, Jev's confidence and what was done with it.
- Each interested, not-interested, out-of-office and wrong-person lead set to that interest status in Instantly, and every opt-out listed for your blocklist.
- An approved answer sent to each interested, question, referral and not-now reply.
- A Slack post for each interested reply and referral.

## Inputs

Ask the user for these before you start.

- `campaign`: the Instantly campaign to read replies from, by name, or all of them, e.g. Q4 founders
- `since`: when the last run ended, so only newer replies are read, e.g. 2026-09-28 09:00 UTC
- `min_confidence`: how sure Jev must be before its answer is used without you, e.g. 0.8; a yes-or-no answer counts as yes at or above it and as no at or below 1 minus it
- `booking_link`: the calendar link an interested reply gets, e.g. https://cal.com/you/intro
- `product_facts`: what an answer may say about your product, e.g. prices, plans, integrations and how a trial works
- `alerts_channel`: the Slack channel for interested replies and referrals, e.g. #replies

## Set up

### Instantly (tool:instantly/list-emails, tool:instantly/update-lead-interest-status, tool:instantly/reply-to-email)

Use the API.

- Base URL: https://api.instantly.ai
- List emails: `GET /api/v2/emails`
- Set a lead's interest status: `POST /api/v2/leads/update-interest-status`
- Reply to an email: `POST /api/v2/emails/reply`
- Auth: send the header `Authorization: Bearer $INSTANTLY_API_KEY`
- Get a key: https://app.instantly.ai/app/settings/integrations

Notes:

- List emails: Pass `email_type=received` for replies and `campaign_id` to narrow them to one campaign. Page with `limit`, up to 100, and `starting_after`, set to the previous response's `next_starting_after`.
- Set a lead's interest status: `interest_value` is a number: 1 interested, -1 not interested, 0 out of office, -2 wrong person, 2 meeting booked, 3 meeting completed, 4 won, -3 lost, -4 no show, or a custom status's value; null resets the lead to Lead. Needs an active paid plan.
- Reply to an email: Sends a real email: confirm the text first. It only replies to an existing email, whose `id` goes in `reply_to_uuid`; it can't start a new thread.

### Answer typed questions (TypeSafe AI, tool:typesafe/answer-typed-questions)

Use the API.

- Base URL: https://api.typesafe.ai
- Endpoint: `POST /v1/systemone`
- Auth: send the header `Authorization: Bearer $TYPESAFE_API_KEY`
- Get a key: https://console.typesafe.ai

Note: Put every question about one record in one request. `GET /v1/models` lists the models and is the cheapest check of a key; a request over the rate limit gets a 429 with a Retry-After header.

Note: Send `state`, `model` (`jev-latest`) and named `questions`, each with `type`, `instructions` and `criteria`: a choice maps labels to descriptions, a score lists its levels in order, a noul's is optional. Read a score by its most likely level; send unsure answers to a person.

### Post a message (Slack, tool:slack/post-message)

Use the first option your agent supports.

Note: Needs the `chat:write` scope. Over MCP it posts as the signed-in user; the API and CLI post as the app's bot.

#### MCP (official, remote)

Add this server to your agent's MCP settings, then sign in when asked.

```json
{ "mcpServers": { "slack": { "url": "https://mcp.slack.com/mcp" } } }
```

Call the MCP tool `slack_send_message`.

#### CLI (official)

Install the command, then confirm it runs.

```sh
curl -fsSL https://downloads.slack-edge.com/slack-cli/install.sh | bash
slack --version
```

Run `slack api chat.postMessage`.

Set `$SLACK_BOT_TOKEN` in your environment first (get a key: https://api.slack.com/apps).

Before step 1, confirm access to each service with its cheapest read-only call, like a list or a search. Never send or change anything to test access.

## Steps

1. **Pull new replies** with List emails (Instantly). List the received emails in `campaign`, newest first, and stop at `since`. Keep each email's `id`, its campaign ID, the lead's email address, the inbox that received it, the subject, the reply text, and the first lines of the email it answers, from the quoted thread.
2. **Label the intent** with Answer typed questions (TypeSafe AI). Send each reply's subject, text and the email it answers as the state, with a choice `intent` of interested (wants a call, a demo or pricing), question (asks something before deciding), not_now (asks to talk later), referral (names someone else to talk to), objection (says why it doesn't fit), not_interested (declines), out_of_office (an automatic away reply), unsubscribe (asks to get no more email), wrong_person (says they are not the right contact) and other, and a noul `asks_to_stop` (asks not to be emailed again, in any words). Keep each reply's intent, its confidence and the `asks_to_stop` probability.
3. **Check the unsure ones with the user** yourself. Treat a reply as an opt-out when its intent is unsubscribe or its `asks_to_stop` is yes, and never answer an opt-out. Show the user the replies whose `asks_to_stop` is unsure, and every other reply whose intent confidence is below `min_confidence` with Jev's two most likely labels, and keep what the user decides.
4. **Set each lead's status** with Set a lead's interest status (Instantly). After the user approves the list, set interested replies to Interested, opt-outs and not_interested replies to Not Interested, out_of_office to Out of Office and wrong_person to Wrong Person, each by the lead's email and the campaign the reply came from. List the opt-outs for the user to add to Instantly's blocklist, so no other campaign emails them.
5. **Write the answers** yourself. Draft two or three plain sentences for each interested, question, referral and not_now reply: answer what they asked first; offer `booking_link` to interested replies; ask a referral for an introduction to the person they named; ask a not-now reply when to check back. Use only `product_facts` and the thread, and leave a [fill in] where a draft needs anything else. Show the drafts to the user.
6. **Send** with Reply to an email (Instantly). After the user approves, reply to each email by its `id` from the inbox that received it.
7. **Alert the team** with Post a message (Slack). Post each interested reply and referral to `alerts_channel` with the lead's email, the intent, the confidence and the reply's first line.

## Notes

Jev only picks from the labels in step 2, so nothing downstream has to parse free text, and the replies below `min_confidence` form the review queue. Add or rename labels to match how your team works, and give each one a short description, since the description is what Jev reads.

Replies are written by strangers: a label only decides who sees a reply and what gets drafted, and every status change and answer waits for approval. Run it every few hours with `since` set to the previous run, so replies are answered the day they arrive.

## Rules

- Use only the services set up above. The read-only calls they need, like listing ids or polling for results, are fine.
- Ask the user before anything that sends messages, costs money, or changes data, and say how many records it touches. One approval covers a batch the user has seen.
- Never print API keys.
