Chatra is where a customer conversation happens; email is often where the follow-up needs to continue. This guide shows how to send email from Chatra with Volanea by receiving a Chatra webhook in your server and turning the event into a transactional email through the Volanea REST API.
There is an important architectural detail up front: Volanea does not provide a native Chatra marketplace app or one-click plugin. The supported implementation is a server-side integration. Chatra can send outbound webhook events for conversations, and your middleware can validate, map, deduplicate, and send the appropriate message with Volanea.
The result is more reliable than attempting to put an email API key into a browser widget or an automation step that cannot safely manage retries. You control the business rule, the recipient selection, the copy, the idempotency key, and the audit trail.
What this integration does
The practical workflow is:
- A Chatra conversation reaches the event you choose.
- Chatra sends a webhook to a public HTTPS endpoint you operate.
- Your endpoint checks whether the event contains an email address and whether it should create an email.
- Your endpoint creates a deterministic idempotency key from the Chatra event or conversation ID.
- Your endpoint calls
POST https://api.volanea.com/v1/sendwith the recipient, sender, subject, and HTML or text content. - Volanea accepts the send and processes it through its sending pipeline.
For a post-support follow-up, the best Chatra trigger is generally chatTranscript. Chatra calls this webhook when a conversation is finished, giving your integration the full conversation context rather than firing an email for every message fragment. Chatra also provides chatStarted and chatFragment webhook events, but those need stricter controls because they happen earlier or more often in the conversation lifecycle.
That distinction matters. A chatStarted notification is useful for an internal acknowledgement or routing workflow, but it may arrive before the visitor provides an email address. A chatFragment event can support a real-time escalation rule, yet it can generate many deliveries for one conversation. A chatTranscript event is normally the cleanest trigger for a single “we received your request” or “here is the information we promised” email.
Choose the right Chatra webhook trigger
Chatra’s webhook configuration supports three relevant event types: chatStarted, chatFragment, and chatTranscript. Configure the event based on the customer promise your email is meant to fulfill.
Use chatTranscript for a completed-conversation follow-up
Use chatTranscript when the email is a recap, a support follow-up, a case acknowledgement, or a resource promised by an agent. Because the conversation has ended, the webhook can include the completed transcript and visitor context. It also lets you create one email per conversation instead of one per message.
Typical uses include:
- Sending a follow-up after an offline support request.
- Emailing a link or document that an agent said they would send.
- Acknowledging a sales enquiry after the visitor leaves the site.
- Creating a handoff email when a Chatra conversation needs a longer response.
- Recording an email-friendly summary in a support system before you notify the customer.
Use chatStarted only for carefully scoped acknowledgement
chatStarted fires when a visitor or agent starts a new conversation. It is useful when you want an immediate acknowledgement for visitors who have already identified themselves with an email address. Do not assume it always has a usable recipient: some visitors will start chatting anonymously, and some Chatra setups may collect contact information only after the conversation begins.
A safe chatStarted rule is: send only when client.email is present, the visitor is not an existing authenticated customer whose email notifications are disabled, and your system has not previously sent an acknowledgement for that conversation ID.
Use chatFragment only when the message itself is the trigger
chatFragment is for rules that depend on an individual conversation fragment. For example, you might send a secure support-intake email only when a visitor’s message contains a specific request and the visitor explicitly asks for an emailed response.
Avoid treating every fragment as a reason to send email. A single chat can generate many fragments, and an agent message can also appear in the event stream. Filter by sender type, require a valid email address, and keep a record of processed message IDs. In most support flows, chatTranscript is the lower-risk default.
Configure the Chatra webhook
Chatra’s webhook setup is in the operator dashboard under Settings → Integrations → Webhooks. Add the public HTTPS URL for the event you want to receive, enable the integration, and save the configuration. Chatra can send chatStarted, chatFragment, and chatTranscript data to the corresponding configured webhook URLs.
For this guide, use a dedicated endpoint such as:
https://hooks.example.com/chatra/transcript
Do not reuse a broad, unauthenticated endpoint that accepts arbitrary JSON from the internet. Treat the URL as a secret capability: use a long random path segment, restrict access at your edge where possible, log deliveries without logging unnecessary customer content, and route only Chatra traffic to the handler.
A good production URL is more like:
https://hooks.example.com/inbound/chatra/4f8b0b2a-7d71-4e95-8c7d-9a4f0c9d8c1b/transcript
The hard-to-guess path is not a replacement for authentication, but it reduces accidental and opportunistic requests. If you place the endpoint behind a gateway or reverse proxy, add rate limiting and request-size limits there as well. A transcript can contain personal information, so the handler should accept only the amount of data it needs and should not expose errors back to an untrusted caller.
Confirm the event with a real test conversation
Before writing a mapping that sends a real email, run one test Chatra conversation with a test address. Capture the raw webhook body in a secure development log or a temporary endpoint that you control. This is essential because visitor email, name, custom fields, and message content depend on what the visitor has supplied and how your Chatra account is configured.
Do not build production logic around a synthetic Chatra sample alone. Test at least these cases:
- A visitor supplies both name and email.
- A visitor starts a conversation without an email.
- An agent ends the chat without replying.
- A conversation has multiple visitor and agent messages.
- A visitor’s name contains punctuation or non-Latin characters.
- A visitor supplies a malformed or disposable-looking address.
If your website’s visitor identification is implemented with Chatra’s JavaScript API, remember that browser-supplied identity fields are application data, not proof of identity. Your server should rely on your own authenticated user context for account-sensitive email rather than treating a chat-provided email address as authorization to disclose account details.
Understand the Chatra payload before mapping it
For the chatTranscript webhook, the useful model is a conversation-level payload: visitor data is available as client, and the transcript is represented by messages. Chatra message objects use fields including id, type, text, createdAt, agentId, agentName, isTrigger, isPushed, isMissed, isMissedByClient, receivedFrom, and file where applicable.
A representative chatTranscript webhook body for the fields used by this integration looks like this:
{
"id": "conversation_01JQXK6B5YF8X8T1",
"client": {
"id": "client_01JQXK5WMRP2A3D9",
"name": "Avery Patel",
"email": "avery@example.com"
},
"messages": [
{
"id": "message_01JQXK6CWK6QMX0P",
"type": "client",
"text": "Could you send the implementation guide by email?",
"createdAt": "2026-09-30T16:21:30.000Z"
},
{
"id": "message_01JQXK80YWH6H36S",
"type": "agent",
"text": "Absolutely — I will send it shortly.",
"createdAt": "2026-09-30T16:23:12.000Z",
"agentId": "agent_4",
"agentName": "Morgan"
}
]
}
The exact values are, naturally, unique to your conversation. More importantly, fields can be absent. Anonymous visitors may have no client.email; an unnamed visitor may have no meaningful client.name; file-only messages may have no useful text; and custom intake data should be treated as optional unless you have verified it in a live delivery.
The integration below intentionally uses only fields that are central to the email decision: the conversation id, client.email, client.name, and message text. It refuses to send if no recipient address is available. That is safer than guessing from an identifier, a display name, or an arbitrary custom field.
Build the secure Chatra-to-Volanea endpoint
The following Node.js example receives a Chatra chatTranscript webhook, filters for an email address, creates a clean transcript excerpt, and calls Volanea’s single-send endpoint. It also sends an Idempotency-Key derived from the Chatra conversation ID, so a repeated delivery does not create a second customer email.
Set these environment variables on the server or secret manager that runs the handler:
VOLANEA_API_KEY=sk_...
VOLANEA_FROM_EMAIL=support@example.com
VOLANEA_FROM_NAME=Example Support
CHATRA_WEBHOOK_TOKEN=long-random-value
Use a URL containing CHATRA_WEBHOOK_TOKEN, rather than placing the Volanea key in the Chatra dashboard. For example, configure this Chatra destination:
https://hooks.example.com/inbound/chatra/long-random-value/transcript
Here is the webhook handler. It uses Express and Node’s built-in crypto; install Express with npm install express.
import crypto from "node:crypto";
import express from "express";
const app = express();
app.use(express.json({ limit: "256kb" }));
const {
VOLANEA_API_KEY,
VOLANEA_FROM_EMAIL,
VOLANEA_FROM_NAME = "Support",
CHATRA_WEBHOOK_TOKEN
} = process.env;
if (!VOLANEA_API_KEY || !VOLANEA_FROM_EMAIL || !CHATRA_WEBHOOK_TOKEN) {
throw new Error("Missing required environment variables");
}
function escapeHtml(value = "") {
return String(value)
.replaceAll("&", "&")
.replaceAll("<", "<")
.replaceAll(">", ">")
.replaceAll('"', """)
.replaceAll("'", "'");
}
function isEmail(value) {
return typeof value === "string" &&
/^[^\s@]+@[^\s@]+\.[^\s@]+$/.test(value.trim());
}
function transcriptLines(messages = []) {
return messages
.filter((message) => typeof message?.text === "string" && message.text.trim())
.map((message) => {
const speaker = message.type === "agent"
? (message.agentName || "Support")
: "You";
return `${speaker}: ${message.text.trim()}`;
})
.slice(-12);
}
app.post("/inbound/chatra/:token/transcript", async (req, res) => {
if (req.params.token !== CHATRA_WEBHOOK_TOKEN) {
return res.sendStatus(404);
}
const chatra = req.body;
const conversationId = String(chatra?.id || "");
const recipientEmail = String(chatra?.client?.email || "").trim();
const recipientName = String(chatra?.client?.name || "").trim();
// A transcript without a stable conversation ID or a valid visitor email
// cannot safely create this follow-up email.
if (!conversationId || !isEmail(recipientEmail)) {
return res.status(204).end();
}
const lines = transcriptLines(chatra.messages);
const plainTranscript = lines.length
? lines.join("\n")
: "Your conversation has been received by our support team.";
const htmlTranscript = lines.length
? `<ul>${lines.map((line) => `<li>${escapeHtml(line)}</li>`).join("")}</ul>`
: "<p>Your conversation has been received by our support team.</p>";
const displayName = recipientName || "there";
const idempotencyKey = crypto
.createHash("sha256")
.update(`chatra-transcript:${conversationId}:follow-up-v1`)
.digest("hex");
const volaneaResponse = await fetch("https://api.volanea.com/v1/send", {
method: "POST",
headers: {
"Authorization": `Bearer ${VOLANEA_API_KEY}`,
"Content-Type": "application/json",
"Idempotency-Key": idempotencyKey
},
body: JSON.stringify({
from: {
email: VOLANEA_FROM_EMAIL,
name: VOLANEA_FROM_NAME
},
to: [{
email: recipientEmail,
name: recipientName || undefined
}],
subject: "Following up on your chat",
html: `
<p>Hi ${escapeHtml(displayName)},</p>
<p>Thanks for chatting with us. Here is a record of the recent conversation:</p>
${htmlTranscript}
<p>Reply to this email if you need anything else.</p>
`,
text: `Hi ${displayName},\n\nThanks for chatting with us. Here is a record of the recent conversation:\n\n${plainTranscript}\n\nReply to this email if you need anything else.`
})
});
const responseBody = await volaneaResponse.text();
if (!volaneaResponse.ok) {
console.error("Volanea send failed", {
conversationId,
status: volaneaResponse.status,
responseBody
});
return res.sendStatus(500);
}
console.info("Volanea email accepted", {
conversationId,
recipientEmail,
responseBody
});
return res.status(202).json({ accepted: true });
});
app.listen(3000, () => {
console.log("Chatra webhook handler listening on port 3000");
});
The key mapping is explicit:
| Chatra field | Volanea field | Purpose |
|---|---|---|
client.email | to[0].email | The email recipient. |
client.name | to[0].name | Recipient display name when available. |
id | Idempotency-Key input | Ensures one follow-up per conversation version. |
messages[].text | html and text | Conversation excerpt in the follow-up. |
| server environment variables | from and Authorization | Sender identity and Volanea authentication. |
Before sending production traffic, verify and authenticate the from.email domain in Volanea. Your sending domain needs the appropriate DNS authentication records configured for the domain you use. The Volanea API reference and setup guides cover the send endpoint and sender setup in more detail.
Keep the Volanea API key off the Chatra side
The Volanea secret key belongs only in server-side secret storage. It must not be inserted into the Chatra widget code, a public JavaScript bundle, a browser-accessible environment variable, a Chatra custom field, or a client-visible automation configuration.
A Volanea key authorizes an email-sending action. If it reaches the browser, anyone who can inspect source code, browser network calls, a JavaScript error report, or a deployed configuration can potentially use it. Rotating an exposed key stops future misuse but cannot undo sends already made with it.
The secure arrangement is:
- Chatra stores: only the HTTPS webhook destination, ideally with a random path token.
- Your server stores:
VOLANEA_API_KEYin an encrypted environment variable or secrets manager. - Your server sends: the authenticated API request to Volanea.
- Your logs store: delivery identifiers, status codes, and redacted diagnostic information—not API keys or full transcripts by default.
This separation is also operationally useful. You can rotate the Volanea key without editing Chatra, change sender addresses without touching the chat widget, and test a staging environment with a Volanea test key and a non-production webhook URL.
Do not call Volanea directly from the browser
It can be tempting to use Chatra’s browser-side JavaScript API and then call Volanea from frontend code. Do not do this. Aside from exposing the credential, browser code cannot be trusted to enforce your business rules. A visitor could modify the request, select another recipient, alter the email body, or repeat the call.
The browser can help Chatra identify a signed-in visitor or add context to a conversation. It should not become the authority that decides whether a transactional email is sent. Make that decision in your server after receiving the webhook.
Make the follow-up useful, not automatic noise
A technical connection is easy to make; a customer-useful email workflow takes policy. Decide precisely what the email promises and what condition justifies it.
A helpful default is one email after a completed conversation when all of the following are true:
- The visitor supplied a syntactically valid email address.
- The conversation contains a visitor question or request.
- Your team needs to continue the interaction outside Chatra, or promised an emailed resource.
- The conversation has not already produced this specific follow-up.
- The content is appropriate to send by email.
The fifth condition matters more than it first appears. Chat transcripts can include personal data, account details, order numbers, screenshots, or information a visitor did not expect to be repeated in email. Sending a concise acknowledgement may be safer than copying the complete transcript. If you do include content, strip secrets, limit the excerpt, and avoid exposing internal agent notes or system messages.
A strong alternative is to send a minimal confirmation:
Subject: We received your support request
Hi Avery,
Thanks for contacting Example Support. Our team has received your request and will follow up here if more information is needed.
Reference: CHAT-01JQXK6B5YF8X8T1
Use the conversation ID as an internal reference only if it does not reveal account information. If your support process has a separate ticket identifier, use that instead.
Add idempotency before handling retries
Webhook delivery is not the same thing as an exactly-once business event. A sender can retry because it did not receive a timely success response, because a network connection was interrupted after the recipient accepted the request, or because your infrastructure returned an error after making the downstream API call.
That means this sequence is possible:
- Chatra delivers a
chatTranscriptwebhook. - Your handler sends the email to Volanea.
- The connection closes before Chatra sees your
202response. - Chatra delivers the same event again.
- Without idempotency, the visitor gets a duplicate email.
The handler avoids that outcome by making a deterministic Idempotency-Key from the Chatra conversation ID and the email workflow version. Volanea supports idempotency keys on its send endpoint, so retrying the same logical operation with the same key can be handled safely.
Do not generate a random UUID for every retry. A random key makes each request look like a new email operation and defeats deduplication. The key must be stable for the exact business action you mean to perform.
For a single transcript follow-up, this is a sensible construction:
chatra-transcript:{conversation-id}:follow-up-v1
Hashing it, as the example does, makes a compact header value and avoids placing the raw conversation ID in transit logs. If you later deliberately introduce a materially different follow-up template, increment the version suffix. That lets the new workflow send once while still preventing duplicates within that version.
For higher-volume or regulated workflows, keep your own database record too. Store a unique constraint on a value such as (chatra_conversation_id, email_workflow_name, template_version), write the intended send to an outbox table, and process it asynchronously. Volanea idempotency protects the provider call; an outbox gives your application durable state, observability, and a way to retry after outages.
When this breaks
Every production integration needs a failure plan. The difficult part is usually not a valid POST; it is understanding what happens when the Chatra webhook, your endpoint, and Volanea do not all agree on whether the work finished.
Chatra retries create duplicate-send risk
A webhook sender may resend a delivery when your endpoint returns a non-2xx response or times out. If your application calls Volanea before returning an acknowledgement, a failed connection can leave you unsure whether the email was accepted.
Use the same deterministic Idempotency-Key for the same Chatra conversation and email workflow. Also record the Chatra conversation ID in your own data store. Return a successful response only after you have durably queued the work or received an acceptable Volanea result.
Do not “fix” duplicates by merely shortening the email window or hoping retries do not happen. Deduplication must be a deliberate property of the design.
The webhook times out
Your endpoint should do very little synchronously: validate the request, parse the fields you need, create or find a durable work record, and acknowledge. Rendering a large transcript, calling multiple APIs, generating AI summaries, or querying a slow CRM in the webhook request path increases timeout risk.
For the most resilient implementation, respond with 202 Accepted after placing a job in a queue. A worker then performs the Volanea call using the same idempotency key. This separates Chatra’s delivery deadline from email-provider latency and makes transient failures easier to retry.
If you use the direct example in this guide, keep it fast and measure the response time. Move to a queue as soon as the workflow adds CRM lookups, attachments, enrichment, or high volume.
Payload fields are missing on some conversations or plans
Not every Chatra conversation produces a recipient email. The visitor might never enter it, the chat may start anonymously, a bot flow may not collect it, or a custom field may be unavailable in the payload you expected. A message can also be file-only, leaving text empty.
Handle missing values as normal states, not exceptions. The example returns 204 No Content when client.email is not present or does not pass basic syntax validation. It does not invent a recipient, send to an agent, or attempt to pull an address from text.
If your business process requires email follow-up, collect email explicitly in Chatra and test your actual account configuration. Then build a fallback: create an internal task, keep the response in Chatra, or ask the visitor for an email before promising an external follow-up.
The wrong event triggers the email
If you wire a sending rule to chatFragment, you can accidentally send an email for every visitor message, agent response, bot message, or partial content event. If you wire it to chatStarted, you can send before the visitor says why they contacted you.
Start with chatTranscript for one-conversation, one-email workflows. If you need message-level behavior, filter explicitly by message type, a recognized intent, and a message-level dedupe key. Test both visitor and agent-originated fragments before enabling the route.
The sender is not authenticated or the recipient is suppressed
An API request can be technically correct but still fail to send because the sender domain is not verified, the account does not permit the sender identity, or the recipient is suppressed after a prior bounce or complaint. Inspect Volanea’s API response and delivery events rather than treating every accepted HTTP request as an inbox placement guarantee.
Use a real, monitored sender address, authenticate its domain, and make reply handling clear. If you are evaluating volume or plan requirements before launch, review transactional email pricing alongside the expected number of conversation follow-ups.
Transcript content is unsafe to email
A verbatim transcript can put sensitive information into a mailbox, forwarding chain, search index, or retention system that differs from Chatra. It can also make a short support follow-up look overwhelming on mobile.
Use a concise acknowledgement by default. Add only the last few customer-visible messages when the recipient benefits from context. Never include internal metadata, hidden notes, access tokens, payment details, or full URLs containing credentials.
Use Zapier or Make only when it fits the workflow
Chatra has native webhooks, so you do not need Zapier or Make just to get outbound HTTP. A direct webhook-to-middleware route is usually the best option when you need server-side secret management, idempotency, custom validation, or a reliable audit trail.
Zapier and Make can still be useful in lower-code workflows. Both support Chatra-triggered automations, including conversation and message events. However, use a middleware endpoint when the workflow needs to call Volanea with a secret API key and handle nuanced retry behavior. That endpoint can be your own serverless function, container service, or queue-backed worker.
If an automation platform is required by your operations team, keep the same architecture in spirit:
- Chatra triggers the automation.
- The automation sends a normalized payload to your private webhook endpoint.
- Your endpoint owns validation, persistence, idempotency, and the Volanea API key.
- Your endpoint returns a small, predictable response.
Do not paste a production Volanea secret into a client-facing or broadly shared automation step. Limit who can edit the workflow, rotate secrets if an editor leaves the team, and ensure test runs use test recipients.
A production launch checklist
Before turning the integration on for live Chatra conversations, check each item below.
- The Chatra webhook uses HTTPS and a unique random destination path.
- The chosen event is
chatTranscriptunless a message-level rule is truly required. - A live test confirms the actual payload fields your handler uses.
- Missing
client.emailcauses a safe no-send outcome. - The Volanea key is stored only in server-side secret storage.
- The
fromaddress belongs to an authenticated, verified sending domain. - The handler uses a stable
Idempotency-Keyper Chatra conversation and email workflow. - Logs redact API keys and minimize transcript storage.
- Your email template does not disclose sensitive conversation content.
- A failure creates an alert or durable retry record rather than silently dropping the follow-up.
- Test recipients are used before production activation.
- You have a process for suppression, bounces, and customer replies.
The final point is easy to miss. Transactional email is not complete when it is accepted by an API. Decide who owns a reply, how a bounced support follow-up becomes a task, and whether customer consent or communication preferences limit the email you want to send.
Conclusion
The reliable way to send email from Chatra with Volanea is not a marketplace installation. It is a small, controlled server-side bridge: configure Chatra’s chatTranscript webhook, receive the conversation event at a private endpoint, verify that a usable email address exists, and call Volanea’s POST /v1/send endpoint with a deterministic idempotency key.
This design keeps the Volanea API key out of the browser, prevents retry-driven duplicates, handles incomplete Chatra visitor data safely, and gives your team a place to apply real business rules. Start with one clear follow-up email per completed conversation, test against actual Chatra payloads, and add queue-backed processing when the workflow becomes business-critical.
FAQ
Can I install a native Volanea app in Chatra?
No. Volanea does not ship a native Chatra marketplace app or plugin. Use Chatra’s outbound webhooks with a server-side endpoint that calls the Volanea REST API.
Which Chatra event should send the email?
Use chatTranscript for most follow-up workflows because it runs when the conversation is finished and supports one email per completed chat. Use chatStarted or chatFragment only when an earlier or message-specific action is necessary and carefully deduplicated.
Where should I store the Volanea API key?
Store it only in your server environment or secrets manager. Do not put it in Chatra widget JavaScript, browser configuration, custom fields, or a public frontend build.
What happens if the visitor did not give Chatra an email address?
Do not send. Return a safe no-op response, create an internal follow-up task if needed, or ask the visitor to provide an address in the chat flow. Never infer an email address from a name or message text.
How do I prevent duplicate emails after a webhook retry?
Create a stable Idempotency-Key from the Chatra conversation ID and the specific email workflow, then send that same key on every retry to Volanea. For additional protection, persist a unique record for the conversation and workflow in your own database.