Saasco logoSaasco logo
Saasco logoSaasco logo

Introduction

Quick StartWhat is Saasco?

Analytics

CRM

Email Marketing

getList Email CampaignsgetGet Email CampaignpostCreate Email CampaignputUpdate Email CampaignpostDuplicate Email CampaigndelDelete Email CampaignpostSend Email CampaignpostResume Sending Email CampaignpostStop Sending Email CampaignpostSend Test EmailgetCount Campaign EmailsgetGet Email Stats

Knowledge

Support

Projects

Campaigns

Create Email Campaign

Creates a campaign together with its first message (subject, body, sender) in one transaction. New campaigns always start as a DRAFT. Creating one never sends anything. Define the audience with contactListId, contactsFilterGroups, or both; set type to AB_TEST and supply abTestConfig for a split test.

POST
/projects/{projectId}/email-campaigns

Authorization

Authorization
AuthorizationBearer <token>

In: header

Path Parameters

projectIdrequiredstring

Project that owns the campaign.

Request Body

application/json

namerequiredstring

Campaign name shown in the dashboard and reports.

statusstring

Lifecycle status. New campaigns default to DRAFT. Only name and projectId are required to create a draft; sender, subject, and body can be filled in later.

Default: "DRAFT"Value in: "DRAFT" | "SCHEDULED" | "SENDING" | "SENT" | "PAUSED" | "CANCELLED"
typestring

STANDARD is a single message. AB_TEST requires a second message via the campaign-message endpoints. AUTOMATION is for workflow-created campaigns.

Default: "STANDARD"Value in: "STANDARD" | "AUTOMATION" | "AB_TEST"
workflowIdstring | null

Workflow that created this campaign, if any.

workflowStepIdstring | null

Workflow step that created this campaign, if any.

contactListIdstring | null

Limit the audience to members of this contact list. Combine with contactsFilterGroups, or omit to use filters only.

contactsFilterGroupsarray<object>

Audience filter groups. An empty group matches everyone. The server seeds one empty AND group when this is omitted.

Default: []
filtersrequiredarray<object>

Attribute filters combined with groupType.

attributeDistinctIdrequiredstring

Contact attribute distinct id to filter on.

attributeTypestring

Attribute type. Defaults to string when omitted.

Default: "string"Value in: "string" | "number" | "boolean" | "date" | "url" | "email"
operatorrequiredstring

Comparison operator for the attribute value.

Value in: "equals" | "contains" | "notEquals" | "notContains" | "gt" | "gte" | "lt" | "lte" | "on" | "since" | "before" | "between" | "last"
valuerequiredstring

Value to compare the attribute against.

oneDayEventFiltersarray<object>

Event filters evaluated over the last 24 hours only.

eventNamerequiredstring

Analytics event name.

operatorrequiredstring

Whether the contact performed the event in the last 24 hours.

Value in: "performed" | "notPerformed"
groupTyperequiredstring

How filters in this group are combined.

Value in: "AND" | "OR" | "NOT"
requireSubscribedboolean

When true, the group is ANDed with $subscribed == true. Set by email sending, not the filter UI.

sendOrderByPropertyobject | null

Contact property and direction used to order the send. Omit to use the project default.

abTestConfigobject | null

A/B test settings. Only used when type is AB_TEST; omit for a standard campaign.

utmConfigobject | null

UTM tags appended to links in the email. Omit to use source=saasco, medium=email, and campaign=.

sendingTargetDurationMsinteger | null

Send-pacing hint. Omit for the default reputation-based pace. 0 skips pacing on qualifying domains.

bccstring | null

BCC address applied to every send from this campaign's first message.

ccstring | null

CC address applied to every send from this campaign's first message.

fromDomainstring

Verified sending domain. Omit to use the project's default email domain, or the first active domain.

fromEmailUsernamestring

Local part of the From address (the part before @). Omit to use the project default.

fromNamestring

Display name in the From header. Omit to use the project default.

replyTostring | null

Reply-To address for this campaign's first message.

scheduledAtstring | null

When to send the first message. Ignored until the campaign is actually sent.

textstring

Plain-text body fallback. The HTML body is used when both are set.

Default: ""
themeobject | null

Editor theme for the first message. Omit to use the default light theme.

subjectHTMLstring

Subject line as HTML. Omit to create an empty draft subject.

subjectJSONobject

Subject as email-editor JSON (TipTap/Novel document). The dashboard writes this; most API callers can omit it and send subjectHTML instead.

previewTextHTMLstring

Inbox preview / preheader text as HTML.

previewTextJSONobject

Inbox preview as email-editor JSON. Omit unless you are driving the dashboard editor.

bodyHTMLstring

Email body as an HTML fragment only — no , , , or tags. Those nest a second document and break open tracking, link rewriting, and the unsubscribe footer.

bodyJSONobject

Email body as email-editor JSON (TipTap/Novel { type: "doc", content: [...] }). The dashboard stores this for editing; send time uses bodyHTML. Omit unless you are driving the editor.

Response Body

application/json

application/json

application/json

application/json

application/json

curl -X POST "https://www.saasco.com/api/v2/projects/string/email-campaigns" \  -H "Content-Type: application/json" \  -d '{    "name": "string"  }'
{
  "id": "string",
  "createdAt": "string",
  "updatedAt": "string",
  "projectId": "string",
  "name": "string",
  "status": "DRAFT",
  "type": "STANDARD",
  "workflowId": "string",
  "workflowStepId": "string",
  "sentAt": "string",
  "contactListId": "string",
  "contactsFilterGroups": [],
  "lastSuccessContactId": "string",
  "lastSuccessContactCreatedAt": "string",
  "sendOrderByProperty": {
    "direction": "asc",
    "propertyKey": "string"
  },
  "abTestConfig": {
    "variable": "SUBJECT",
    "samplePercent": 20,
    "winnerMetric": "OPEN_RATE",
    "winnerWaitHours": 4,
    "winnerWaitUnit": "HOURS",
    "sendTimeDelayHours": 2,
    "sendTimeDelayUnit": "HOURS",
    "winnerMessageId": "string",
    "winnerSelectedAt": "string",
    "winnerRolloutAt": "string",
    "winnerWaitStartedAt": "string",
    "status": "AWAITING_SAMPLE",
    "samplePaginationEnd": 9007199254740991
  },
  "utmConfig": {
    "enabled": true,
    "params": {
      "campaign": "",
      "content": "",
      "medium": "",
      "source": "",
      "term": ""
    }
  },
  "sendCount": 0,
  "sendingTargetDurationMs": 9007199254740991,
  "sendPaginationCount": 0,
  "messages": [],
  "bcc": "string",
  "bodyHTML": "string",
  "bodyJSON": {
    "property1": null,
    "property2": null
  },
  "cc": "string",
  "fromDomain": "string",
  "fromEmailUsername": "string",
  "fromName": "string",
  "previewTextHTML": "string",
  "previewTextJSON": {
    "property1": null,
    "property2": null
  },
  "replyTo": "string",
  "scheduledAt": "string",
  "subjectHTML": "string",
  "subjectJSON": {
    "property1": null,
    "property2": null
  },
  "text": "string",
  "theme": {
    "body": {
      "align": "left",
      "background": "string",
      "container": "string"
    },
    "button": {
      "background": "string",
      "borderColor": "string",
      "borderSize": 0,
      "color": "string",
      "radius": 0
    },
    "link": {
      "color": "string"
    },
    "template": "string",
    "typography": {
      "h1": {
        "color": "string",
        "fontSize": 0,
        "lineHeight": 0
      },
      "h2": {
        "color": "string",
        "fontSize": 0,
        "lineHeight": 0
      },
      "h3": {
        "color": "string",
        "fontSize": 0,
        "lineHeight": 0
      },
      "p": {
        "color": "string",
        "fontSize": 0,
        "lineHeight": 0
      }
    }
  }
}
{
  "code": "BAD_REQUEST",
  "message": "Invalid input data",
  "issues": []
}
{
  "code": "UNAUTHORIZED",
  "message": "Authorization not provided",
  "issues": []
}
{
  "code": "FORBIDDEN",
  "message": "Insufficient access",
  "issues": []
}
{
  "code": "INTERNAL_SERVER_ERROR",
  "message": "Internal server error",
  "issues": []
}

Get Email Campaign

Fetches a single campaign with its messages, audience definition, status, and send progress. Returns 404 if the campaign does not exist in this project.

Update Email Campaign

Updates a campaign's settings. Despite the PUT, only the fields present in `changes` are written. Anything omitted keeps its current value. Editing a campaign that has already sent changes future behaviour only; it does not alter or resend emails already delivered.