Skip to main content
A flow reaches Hand to a human and nobody on your team is available. Doing nothing means the visitor waits for a person who is not coming. Instead, CallKaro runs your Python, creates a ticket in your system, tells the visitor its reference, and closes the conversation cleanly so they can start again later.

Where To Configure It

Settings → Chat routing, or the same panel from Widgets. It is set once for the whole account, not per agent or per widget. Every field in the panel, in order, is on Chat routing. All three messages can quote anything your code returns, e.g. {{ticket_id}}. Leave one empty and the away message is used for it.

The Three Reasons A Ticket Is Raised

Your code is given a reason, so one function can write a sensible ticket for all three:

The Contract

Your code is one async function called run. Its argument is the conversation:
Whatever you return is available to the away message as {{...}}, is stored on the conversation, and shows up beside the transcript in Contacts. Returning the ticket id is worth it for that alone — otherwise the reference exists only in your other system.

The Smallest One That Works

If you only want to see the wiring, start here:
Set your away message to “We’ve raised ticket {{ticket_id}}” and a visitor asking for a person out of hours reads “We’ve raised ticket T-1234”. Replace the body with a real API call once you can see it working.

What You Can Return, And Where It Goes

Return any dictionary you like. Every key in it becomes a variable on the conversation, which means it is available in four places at once:
We’ve raised ticket {{ticket_id}} with our {{queue}} team and will reply within {{sla_hours}} hours.
Only scalars survive — strings, numbers and booleans. Up to 40 keys, names truncated to 64 characters and values to 500. A nested object is dropped, so flatten anything you want to keep.
Returning the ticket id is worth it even if your message never quotes it. Without it the reference exists only in your other system, and nobody opening that conversation in Contacts can connect the two.

A Real Example

Creating a ticket in Freshdesk, and handing the id back:
With an away message of:
Nobody is available right now. We have raised ticket {{ticket_id}} and will get back to you.
Keep your own HTTP timeout below the 8-second limit — 5 or 6 seconds — so a slow API returns a clear failure rather than being cut off mid-request.

When Your Code Fails

If the code raises, times out, or you have not written any, the visitor is still told that someone will come back to them. Which wording they get depends on your wording:
  • If your message quotes a ticket placeholder ({{ticket_id}} and the like), it is replaced with a generic sentence — promising a reference that does not exist would render as “ticket is open”.
  • If it does not quote one, your own words are used, because they are still true. An account that wrote “Nobody is available right now, we will email you” should not lose that sentence because an integration was down.
Either way the conversation is recorded, and a ticket failed event is written to the timeline in Contacts — so the failure is visible to your team rather than only in a log.
Test with the Run code card on a canvas first — same runner, same contract, same 8-second limit, but you can see the result immediately in Try it.

What Gets Passed In

contactKey is the one to store on your ticket. It identifies the person rather than the conversation, so when they come back you can match the ticket to them.

Next Steps

Human handoff

Availability, assignment and capacity

Card types

The Run code card