Skip to content

Actions

What the workflow does for you. Each action is a step; you can chain several, put them inside branches or after a wait.

Summary

Action What it does Needs Publisher’s permission
Create a task Adds a follow-up task in Tasks, linked to the event’s quote or invoice. Nothing Quotes, Collections or Clients
Email the team Emails the account owner or the whole team. Nothing None extra
Send a Slack message Posts a message to your Slack channel. Slack connected None extra
Add a note in HubSpot Adds a note to the quote’s Deal or the client’s Company. HubSpot connected None extra
Email the client Sends a branded email to the client’s contact, with the button to view and pay the document. A quote or invoice trigger, and a client with an email Quotes
Expire the quote Marks the quote as expired so the client can no longer approve it. A quote trigger Quotes
Approve the internal request Approves the pending internal approval and sends the quote to the client. A quote trigger and internal approvals in your plan (Scale or higher) Approvals
Void the invoice Voids the invoice if it has no payments applied. An invoice trigger Collections
Send the data to a URL Sends a signed POST with the data you choose to the URL you paste. A public https URL Settings
Send a Teams message Posts a card to your Microsoft Teams channel. Teams connected None extra
Send the client a WhatsApp Sends your approved WhatsApp template to the client’s phone. WhatsApp connected and a client with a phone Quotes
Notify a team member Emails the team member you choose. That they are still active on the team None extra
Remind the client to pay Sends Cord’s payment reminder with what they owe, when it is due and the button to pay. A quote or invoice trigger, and a client with an email Collections
Pause the client’s reminders Pauses or resumes the client’s automatic payment reminders. A trigger with a client Collections
Invoice the quote Issues the invoice for the approved or paid quote, the same as by hand. A quote trigger Quotes
Record a payment promise Records the date the client promises to pay the quote balance. A quote trigger Collections

A workflow acts with the permissions of the person who published it: each action asks for the same permission as doing it by hand in the app. If you lack it, you cannot publish that step, and if the publisher loses it later, the workflow is paused. See Publish, pause and delete.

To add an action, click Add a step › Action or lookup: a finder opens with every action and every lookup, filtered by family (your team, your client, the document, other tools). Pick one and fill in its fields in the panel. Every text field accepts event data like {{cliente}}.

Step error messages appear in your account’s language. This page lists each one with what to do.

Create a task

Adds a task for your team in Tasks, just as if you had created it by hand.

Field Required Detail
Task title Yes Up to 200 characters. Accepts event data. Line breaks become spaces.
Due in (days) No 0 to 365. 0 means due today; 1, tomorrow. Leave empty for a task without a date.
Assignee No An active team member. If they later leave the team, the step fails with “The chosen person is no longer active on the team: choose someone else in the step.”

What it is linked to:

  • If the trigger is about a quote (sent, approved, paid, partial payment, invoiced, etc.), the task is linked to that quote: in Tasks it shows the quote number and client as a link to the quote.
  • If the event carries a related quote, the task is also linked to it: a dispute or refund on a quote, an invoice created from a quote, a payment promise, or a task linked to a quote.
  • On A draft is deleted it is not linked, because the quote no longer exists.
  • If the trigger is about an invoice (issued, sent, paid, payment fails, about to be due, overdue, past due for days, voided, or marked uncollectible), the task is linked to that invoice: in Tasks it shows the invoice number and client as a link to the invoice. If the invoice came from a quote, it’s linked to both.
  • In every other case (clients, products, payouts, scheduled triggers, standalone tasks) the task is standalone.

Assignee: if you choose one, the task is created assigned to that person; if not, unassigned. Either way it is created with normal priority, which you change from Tasks. While it has no assignee, the email reminder goes to the account owner.

When it fails:

  • “The task title came out empty.”: the title only had event data and all of it arrived empty. Add fixed text, for example “Follow-up: {{cliente}}”.
  • “Workflows reached their hourly limit of tasks.”: your workflows created 120 tasks in the last hour. See Limits.
  • “The task could not be created.”: Cord rejected the task, for example because the quote or invoice it was going to be linked to no longer exists.

Creating a task is also an event. If you have a workflow with the A task is created trigger, it will react to tasks created by your other workflows. Use the condition “Who caused it is not Another workflow” if you do not want that.

Email the team

Sends an email to people in your organization. It never writes to the client.

Field Required Detail
To Yes The account owner, or The whole team: the active members of your organization, up to 25. Pending invitations do not receive it.
Subject Yes Up to 150 characters. Accepts event data. If it ends up empty when running, the workflow name is used.
Message Yes Up to 2,000 characters. Accepts event data and line breaks.

What the email looks like: your message exactly as you wrote it, and at the bottom a line “Sent by the Name workflow in Cord.” linking to the workflow. The footer uses your account’s language. Event data is inserted as text: if a client’s name contains symbols or tags, they are shown literally and do not alter the email.

Each person receives their own email; nobody sees the others’ addresses.

When it fails:

  • “There is nobody to send the email to”: you chose The account owner and the account has no owner with an email, or there are no active members.
  • “Email is not available right now”: it could not be delivered to anyone. It is retried automatically.
  • “Hourly email limit for workflows reached”: your workflows sent 30 emails in the last hour.

Email the client

Emails the contact of the client on the event’s document, with the business’s branding and the button to the public link: approve, if the event is about a quote; pay, if it is about an invoice.

Field Required Detail
Subject Yes Up to 150 characters. Accepts event data.
Message Yes Up to 2,000 characters. Accepts event data and line breaks. Your client reads this.

Who receives it: the email of the document’s client, never an address typed into the step. If the client has no email on file, the step fails and says so.

What Cord adds: your logo and brand color, the button to the document, the link in plain text in case the button does not open, and your business footer. In the test environment the subject is marked as a test.

Language: the button and the text Cord adds appear in the document’s language: the one the quote or invoice took when sent or issued or, if it doesn’t have one yet, the client record’s or your account’s. Your subject and message go out exactly as you wrote them: Cord doesn’t translate them.

It counts against your plan: each client email uses one send from your plan’s monthly quota, the same as sending a quote by hand. If the quota is gone, the step fails and nothing is sent.

It never arrives twice: every attempt carries the step’s key. If a send is cut off without a response, Cord retries with the same key and the email service doesn’t send your client a second one; an attempt that didn’t go out returns its send to the quota. If you send from your Gmail, which doesn’t know that key, the step stops so you can check whether it arrived. See Runs and errors.

Cord already sends its own invoice reminders on the schedule set in Settings › Invoicing › Reminders. If you also build a workflow that emails the client, check that two notices do not land on the same day for the same money.

Expire the quote

Marks a quote that is still sent or viewed as Expired. The client can no longer approve or reject it from the link, the event is recorded in its history, and A quote expires fires for the rest of your automations.

It only works with triggers that carry a quote; if the quote was already approved, rejected or expired, the step fails with “The quote is no longer in a state that allows this action”.

Approve the internal request

Approves the quote’s pending internal approval request and sends the quote to the client, exactly as if someone approved it in the app. Use it behind a condition — a total below a certain amount, for example — so small approvals do not wait on a person.

It only works with triggers that carry a quote and requires internal approvals in your plan: they come with Scale or higher.

When it fails:

  • “Your current plan does not include internal approvals.”: your plan has no approvals.
  • “This quote no longer has a pending approval request.”: someone already decided it or it was withdrawn. Nothing changes.

Void the invoice

Voids the event’s invoice. It follows the same rules as voiding by hand from Invoices: an invoice with payments applied is not voided — that is what the credit note is for — and in Mexico canceling a CFDI with the SAT may stay pending a response. When it cannot be voided, the step fails with “This invoice cannot be voided: review it in Invoices.” and the invoice stays as it was.

Field Required Detail
Reason No Up to 200 characters. It is kept in the invoice history.

Send the data to a URL

Sends a signed POST to the address you paste: a Zapier Zap, a Make scenario, an n8n flow or your own server. Only the data you check is sent.

Field Required Detail
Destination URL Yes It must be https and on a public server. Cord rejects internal addresses both when publishing and when running.
Data to send No Check what your destination needs; anything you leave unchecked never leaves Cord. An amount always travels with its currency, even if you don’t check it.
Message No Up to 1,000 characters. Accepts event data; it travels in the mensaje field.
Response data No Up to 5 data fields Cord takes from the response for the next steps. See Use the response.

The body looks like this:

{
  "workflow": "Large deal alert",
  "workflow_id": "…",
  "evento": "quote.approved",
  "objeto": "quote",
  "objeto_id": "…",
  "enviado_en": "2026-09-20T18:00:00.000Z",
  "mensaje": "ACME approved COT-7",
  "datos": { "folio": "COT-7", "total": 150000, "moneda": "MXN" }
}

The data travels the way a machine reads it: unformatted numbers and codes instead of labels. In the run history, the step shows the URL, the data that was sent and the names of the custom headers, never their values.

Use the response

If your destination replies with JSON (the ID of the order it created, a tracking number, a calculated total), take it in Response data and use it in the next steps like any other data.

Column Detail
Data name How you see it among the variables. The variable is built from it: “Order ID” reads as {{respuesta_order_id}}.
Path in the response Names separated by dots, and the position in a list as a number starting at 0: data.id, items.0.total.
Type Text or Number. A number that arrives as text ("120.5") is converted; if it is not a number, it stays empty.
  • Each step holds up to 5 data fields, and Cord reads up to 64 KB of the response.
  • Anything missing from the response, or a response that is not JSON, stays empty: the request did arrive and the step does not fail.
  • The data exists from the step that brings it: an earlier step that uses it cannot be published, and neither can two data fields that read the same in one workflow.
  • In the run history, the step shows what it read.
  • Test sends nothing, so in a test these data fields are empty.

Request signing

Every request carries two signatures made with the workflow’s secret: Cord’s and the Standard Webhooks one. To see the secret, open the step and click Reveal secret. Only people with the Settings permission can see it, and it is recorded in the audit log.

Header Content
webhook-id The same on every retry of the step; it also travels as Idempotency-Key. Use it to avoid processing the same request twice.
webhook-timestamp When this attempt was signed, in unix seconds.
webhook-signature v1,<base64 signature>. During a roll it carries two, separated by a space.
X-Cord-Signature-V1 t=<unix>,v1=<hmac>, the same format as webhooks.
X-Cord-Workflow-Id and X-Cord-Event The workflow and the event that triggered it.

With any Standard Webhooks library, verifying takes one line. In Node:

import { Webhook } from 'standardwebhooks';

const body = new Webhook(process.env.CORD_WORKFLOW_SECRET!).verify(await req.text(), Object.fromEntries(req.headers));

Verify the raw body exactly as it arrived: if you turn it into an object and serialize it again, the signature no longer matches.

Rolling the secret: click Roll and choose how long the old one keeps signing: 1, 24 or 72 hours, or Revoke the old one now if it leaked. While the overlap lasts, every request carries both signatures and your server accepts either, so you change the secret without losing a single request.

Custom headers

For the key that Zapier, Make or your server asks for, such as Authorization: Bearer …, add it under the step’s Custom headers. A step can have up to 5. The value is stored encrypted and never shown again; to change it, save it again with the same name. You can’t use the names Cord sets: Content-Type, User-Agent, Idempotency-Key and anything starting with X-Cord- or webhook-.

Don’t put a key in the Message: it travels in the body and stays in the run history. Duplicating a workflow doesn’t copy its secret or headers, and deleting it erases them.

When it fails:

  • “The destination URL is not valid or points to an internal server.”: fix the URL; it is not retried.
  • “The destination URL did not accept the request.”: if the destination didn’t respond, or responded with 408, 429 or a 5xx error, it is retried on the schedule in Runs and errors, always with the same webhook-id and Idempotency-Key so your destination recognizes the retry. Any other 4xx is not retried: your destination rejected the request and repeating it changes nothing.
  • “We couldn’t read a saved header on this step. Enter its value again.”: save the header again; the step sends nothing without it.
  • “Workflows reached their hourly limit of posts to a URL.”: 120 posts in the last hour.

Send a Slack message

Posts a message to the channel you connected in Settings › Integrations › Slack.

Field Required Detail
Message Yes Up to 1,000 characters. Accepts event data and line breaks.

What it looks like: the text appears in the channel with the name and icon of the webhook’s Slack app. Event data is inserted as plain text; a < or & in a client’s name does not break the message formatting.

This message is independent from the Settings › Notifications alerts: a workflow posts even if those alerts are off, and with the text you write.

When it fails:

  • “Connect Slack in Settings › Integrations to use this action”: no Slack URL is saved.
  • “Slack did not accept the message. Check the connection in Settings › Integrations”: Slack rejected it, usually because the webhook was deleted or the app was removed from the channel. Create a new webhook and paste the URL. Meanwhile, Cord retries.
  • “The message ended up empty”: the message only had event data and it arrived empty.
  • “Hourly message limit for workflows reached”: 120 messages in the last hour.

How to connect Slack: Slack.

Send a Teams message

Posts a card to the channel you connected in Settings › Integrations › Microsoft Teams, through either connection method:

  • Connect with Microsoft: the card goes to the team and channel you picked, in the name of whoever connected.
  • Power Automate flow: the card goes through the flow whose URL you pasted.
Field Required Detail
Message Yes Up to 1,000 characters. Accepts event data and line breaks.

How it looks: a card with your text in the channel. Teams does not use Slack’s formatting, so asterisks and <url|text> links show up literally; write plain text.

It is independent from Settings › Notifications: the workflow posts even when those notices are off.

When it fails:

  • “Connect Microsoft Teams in Settings › Integrations to use this action.”: Teams is not connected either way.
  • “Microsoft no longer accepts the Teams connection. Reconnect it in Settings › Integrations.”: with Connect with Microsoft, access expired or was revoked. Click Reconnect on the card.
  • “Teams did not accept the message. Check that the channel or the flow is still active.”: the channel no longer exists or you lost access to it, or the Power Automate flow was turned off or deleted. Pick another channel, or create a new flow and paste the new URL. Meanwhile, Cord retries.
  • “The message came out empty.”: the message only had event data and it came out empty.
  • “Workflows reached their hourly limit of Teams messages.”: 120 messages in the last hour.

How to connect Teams: Microsoft Teams.

Send the client a WhatsApp

Sends the template you set up in Settings › Integrations › WhatsApp Business to the phone of the document’s client.

Field Required Detail
Variable 1 to 4 No Fill {{1}}, {{2}}… of your template, in order. They accept event data.

Why variables and not a message: Meta does not allow starting a conversation with free text, only with an approved template. A free-text field here would promise something the provider rejects.

The phone comes from the client, never from a field in the step, and it must carry a country code. Cord does not guess the country: the same number exists in several.

Language: your template’s, the one Meta approved, the same for all your clients; it doesn’t follow each client’s document language.

When it fails:

  • “The client has no phone with a country code on file.”: edit the client and save the number with +.
  • “Connect WhatsApp in Settings › Integrations to use this action.”: WhatsApp is not connected.
  • “WhatsApp did not accept your template. Check it in Settings › Integrations: it must be approved and have the same number of variables.”: it is not approved, the name does not match, or the number of variables differs.
  • “WhatsApp did not accept the message. It retries on its own.”: a temporary rejection; Cord retries.
  • “Workflows reached their hourly limit of WhatsApp messages.”: 60 messages in the last hour.

How to connect it: WhatsApp Business.

Add a note in HubSpot

Adds a note in HubSpot so your sales team sees what happened in Cord.

Field Required Detail
Note Yes Up to 2,000 characters. Accepts event data and line breaks.

Where the note goes:

  1. On the Deal of the event’s quote, if that quote is already in HubSpot.
  2. If there is no Deal, on the client’s Company, if the client is already in HubSpot.
  3. If neither is in HubSpot yet, the step waits and retries: usually the sync finishes within moments.

The note is timestamped when created and appears on the record’s timeline in HubSpot.

Which triggers have somewhere to put the note: quote triggers, quote payments, disputes, refunds and client triggers. On triggers without a quote or client (for example A payout is paid to your bank or A product is created) the note has no record to attach to: the step retries and the run ends as Failed with “HubSpot did not accept this step’s data. Check the setup in Settings › Integrations.” Use this action only with triggers that have a quote or client.

When it fails:

  • “HubSpot needs to be reconnected in Settings › Integrations.”: the connection lost its authorization.
  • “HubSpot did not accept this step’s data. Check the setup in Settings › Integrations.”: HubSpot is not connected or needs reconnecting; the record is not in HubSpot yet (see point 3 above; if it persists, check that the pipeline and stages are complete, because quotes in a status without a stage are not sent to HubSpot); or the Deal or Company was deleted in HubSpot.
  • “HubSpot did not respond. It retries on its own.”: a temporary HubSpot failure.
  • “The note came out empty.”: the note only had event data and it came out empty.
  • “Workflows reached their hourly limit of HubSpot notes.”: 120 notes in the last hour.

How to connect HubSpot: HubSpot.

Notify a team member

Emails the team member you choose, with the link to the workflow at the bottom. Use it so the notice reaches whoever handles the account or the project, not the whole team.

Field Required Details
To Yes An active team member. If they later leave the team, the step fails with “The chosen person is no longer active on the team: choose someone else in the step.”
Subject Yes Up to 150 characters. Accepts event data. If it ends up empty when running, the workflow name is used.
Message Yes Up to 2,000 characters. Accepts event data and line breaks.

It shares the hourly email limit with Email the team.

Remind the client to pay

Sends the same payment reminder as the automatic reminders in Settings › Invoicing › Reminders: what they owe, when it is due and the button to pay. If the event carries an invoice, it reminds about the invoice; otherwise, the quote. It also works inside a For each, with each item’s document.

  • It does not send it if the document has no balance left or if the reminders for the client or that document are paused. The step does not fail: Runs says why it was not sent.
  • With a milestone plan, it only reminds what is payable today: the milestones due today or earlier, with the oldest one’s date. If none is due yet, it does not send it. The invoice of a plan is reminded with the quote link, where it is paid milestone by milestone.
  • On an invoice, the reminder stays in its history.
  • It shares the hourly limit of client emails with Email the client.

When it fails: “The reminder was not sent: the document is no longer open or the client has no email.”

Pause the client’s reminders

Pauses or resumes the automatic payment reminders for the event’s client, the same as from Settings › Invoicing › Reminders. While they are paused, Remind the client to pay does not send either.

Field Required Details
What to do Yes Pause or Resume. Resuming removes any pause on the client, including the ones set by AI collections.

It only works with triggers that carry a client.

Invoice the quote

Issues the invoice for the event’s quote, the same as the Invoice action on the quote’s detail: with your country’s tax rules and, in Mexico, stamped with the SAT. It counts as an invoice issued on your plan.

  • It only invoices an approved or paid quote. If it is already invoiced, it does not issue another one: the step fails with “The quote is no longer in a state that allows this action.”
  • If issuing does not respond, Cord tries again without duplicating it: a quote has a single invoice.

When it fails:

  • “Your plan does not include issuing this invoice.”
  • “Data is missing to issue the invoice: check the business and client tax details.”

Record a payment promise

Records that the client promises to pay the quote balance within the days you choose, the same as recording it in Collections, where it shows up like one entered by hand.

Field Required Details
Promises to pay within (days) Yes Between 0 and 90, counted from today in your business’s time zone.
Note No Up to 400 characters. Accepts event data.

It only works with quote triggers. If it is unknown whether the promise was saved, the run goes to Needs attention instead of recording it twice.

Several actions in a row

Actions at the same level run in order, one after another. If one fails, the following ones do not run until it is resolved: the run is retried from the step that failed, without repeating the ones already done. So a task is not created twice because the Slack message after it failed.

Next