KW Knowledge base

Marketing

The Marketing module sends bulk email campaigns to contacts pulled from the CRM. Each campaign is a one-off HTML email sent to either all contacts or contacts filtered by status.

Mitch Wigham
Updated 24 June 2026 · 5 views

13 · Marketing

The Marketing module sends bulk email campaigns to contacts pulled from the CRM. Each campaign is a one-off HTML email sent to either all contacts or contacts filtered by status.

Where to find it

Sidebar → Marketing or /marketing. Requires the marketing feature and an administrator role.

Concepts

  • Campaign — an email message (subject + HTML/plain-text body) plus an audience. A campaign is sent once.
  • Audience — chosen at campaign level, not saved separately. Either:
    • All contacts — every CRM contact with an email address that has not opted out.
    • By status — contacts whose CRM status is one of a set you pick.

There is no saved-segment, saved-list, or template concept — each campaign carries its own body and audience filter.

Layout

+----------+----------------------------------------------+
| Filters  | Campaigns                          [+ New]   |
| [All   ] |---------------------------------------------|
| [Draft ] | April newsletter   Sent   342  78% open     |
| [Sending]| Q2 product launch  Draft                    |
| [Sent  ] |                                              |
+----------+----------------------------------------------+

📷 Screenshot placeholder: screenshots/marketing-campaigns.png

The list page shows KPI cards (total, drafts, sending, sent with average open rate) and a status-filter pill group.

Creating a campaign

  1. + New campaign.
  2. Basics — campaign name, from name, from email, subject. Name, from email and subject are required.
  3. Body — write an HTML body and a plain text body directly in the two text areas. Liquid-style placeholders such as {{firstName}} are noted in the UI for per-recipient merge.
  4. Recipients — pick All contacts or By status (then tick one or more contact statuses).
  5. Save draft. The campaign is created in DRAFT status.

Campaigns are launched separately from the detail page — saving only creates a draft.

Campaign detail & launch

Open a campaign to see its status badge, audience label, KPI cards (recipients, delivered, failed, opens, open rate), the details block, and a rendered email preview.

While the campaign is in DRAFT you can:

  • Edit — re-open the form. Only draft campaigns are editable; editing a launched campaign returns a 409.
  • Launch campaign — builds the send list and queues delivery.
  • Delete — removes the campaign.

Once SENDING, only a Refresh button is available to poll progress.

How a launch works

On launch the service:

  1. Queries CRM contacts in the org with an email address and marketingOptOut = false, applying the status filter if set.
  2. Creates one MarketingSend row per eligible contact, each with its own unsubscribe token, and moves the campaign to SENDING.
  3. Queues the sends in batches of 100 to a background worker.
  4. The worker emails each contact, increments delivered/failed counts, and flips the campaign to SENT when no queued sends remain.

If no contacts are eligible the campaign goes straight to SENT with a recipient count of 0.

Tracking

Each campaign records:

  • Recipients (total send list size)
  • Delivered / Failed counts
  • Opens — via a 1×1 tracking pixel injected into the HTML body
  • Open rate — opens ÷ delivered

Tracking is campaign-level counters only. There is no per-contact event log, no click tracking, and no bounce hard/soft split. There is no CSV export from the campaign report.

Unsubscribes

Every campaign email has an Unsubscribe link appended to both the HTML and plain-text bodies (HTTP link only — there is no mailto: variant). Clicking it sets marketingOptOut = true on the contact's CRM record and shows a confirmation page.

⚠️ Caution. Opt-out is global — an opted-out contact is excluded from every future campaign. There is no in-product re-subscribe; the flag must be cleared on the CRM contact record.

Sending email

Campaign email is delivered through the shared email service. There is no in-product sender-domain verification screen — the from name and from email are free-text fields on the campaign. Deliverability (SPF/DKIM/DMARC) is handled at the mail-server / integration level.

Scheduling

There is no in-product scheduling or recurring/drip send. A draft is sent immediately when you click Launch campaign. (The data model carries a scheduledAt field, but the UI and launch path do not act on it.)

Permissions

The whole Marketing UI is wrapped in the admin guard.

Action Role
View / create / launch / delete campaigns ADMIN or SUPER_ADMIN

The marketing service itself only checks for a valid access token; the admin restriction is enforced by the portal UI guard.

Common workflows

One-off announcement

  1. + New campaign → fill in basics and body.
  2. Recipients → All contacts (or By status).
  3. Save draft → open the campaign → Launch campaign.

Target a customer segment

  • Create the campaign, set Recipients → By status, and tick the CRM statuses you want (statuses come from CRM settings).

See also

Still need help?

Log a support ticket and the team will pick it up from this page.