Prerequisites
Send to the group
1
Send to a list
A list is a group you curate by hand. Put its
list_id in to and Courier sends to each member.const { requestId } = await client.send.message({
message: {
to: { list_id: 'acme-corp.beta-testers' },
template: 'nt_01kx4h2jdafq8bk9aftxak4b40',
},
});
response = client.send.message(
message={
"to": {"list_id": "acme-corp.beta-testers"},
"template": "nt_01kx4h2jdafq8bk9aftxak4b40",
},
)
curl -X POST https://api.courier.com/send \
-H "Authorization: Bearer $COURIER_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"message": {
"to": { "list_id": "acme-corp.beta-testers" },
"template": "nt_01kx4h2jdafq8bk9aftxak4b40"
}
}'
response = courier.send_.message(
message: {
to: { list_id: "acme-corp.beta-testers" },
template: "nt_01kx4h2jdafq8bk9aftxak4b40"
}
)
response, err := client.Send.Message(context.TODO(), courier.SendMessageParams{
Message: courier.SendMessageParamsMessage{
To: courier.SendMessageParamsMessageToUnion{
OfListRecipient: &shared.ListRecipientParam{
ListID: courier.String("acme-corp.beta-testers"),
},
},
Template: courier.String("nt_01kx4h2jdafq8bk9aftxak4b40"),
},
})
SendMessageParams params = SendMessageParams.builder()
.message(SendMessageParams.Message.builder()
.to(JsonValue.from(java.util.Map.of("list_id", "acme-corp.beta-testers")))
.template("nt_01kx4h2jdafq8bk9aftxak4b40")
.build())
.build();
client.send().message(params);
$response = $client->send->message(
message: [
'to' => ['listID' => 'acme-corp.beta-testers'],
'template' => 'nt_01kx4h2jdafq8bk9aftxak4b40',
],
);
SendMessageParams parameters = new()
{
Message = new()
{
To = new ListRecipient { ListID = "acme-corp.beta-testers" },
Template = "nt_01kx4h2jdafq8bk9aftxak4b40",
},
};
await client.Send.Message(parameters);
courier send message \
--api-key "$COURIER_API_KEY" \
--message '{"to":{"list_id":"acme-corp.beta-testers"},"template":"nt_01kx4h2jdafq8bk9aftxak4b40"}'
With Courier MCP, send my nt_01kx4h2jdafq8bk9aftxak4b40 template to the acme-corp.beta-testers list.
2
Send to an audience
An audience is a group Courier keeps current from rules you write. Put its
audience_id in to and everyone who matches now receives the message.const { requestId } = await client.send.message({
message: {
to: { audience_id: 'active-business-users' },
template: 'nt_01kx4h2jdafq8bk9aftxak4b40',
},
});
response = client.send.message(
message={
"to": {"audience_id": "active-business-users"},
"template": "nt_01kx4h2jdafq8bk9aftxak4b40",
},
)
curl -X POST https://api.courier.com/send \
-H "Authorization: Bearer $COURIER_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"message": {
"to": { "audience_id": "active-business-users" },
"template": "nt_01kx4h2jdafq8bk9aftxak4b40"
}
}'
response = courier.send_.message(
message: {
to: { audience_id: "active-business-users" },
template: "nt_01kx4h2jdafq8bk9aftxak4b40"
}
)
response, err := client.Send.Message(context.TODO(), courier.SendMessageParams{
Message: courier.SendMessageParamsMessage{
To: courier.SendMessageParamsMessageToUnion{
OfAudienceRecipient: &shared.AudienceRecipientParam{
AudienceID: "active-business-users",
},
},
Template: courier.String("nt_01kx4h2jdafq8bk9aftxak4b40"),
},
})
SendMessageParams params = SendMessageParams.builder()
.message(SendMessageParams.Message.builder()
.to(JsonValue.from(java.util.Map.of("audience_id", "active-business-users")))
.template("nt_01kx4h2jdafq8bk9aftxak4b40")
.build())
.build();
client.send().message(params);
$response = $client->send->message(
message: [
'to' => ['audienceID' => 'active-business-users'],
'template' => 'nt_01kx4h2jdafq8bk9aftxak4b40',
],
);
SendMessageParams parameters = new()
{
Message = new()
{
To = new AudienceRecipient { AudienceID = "active-business-users" },
Template = "nt_01kx4h2jdafq8bk9aftxak4b40",
},
};
await client.Send.Message(parameters);
courier send message \
--api-key "$COURIER_API_KEY" \
--message '{"to":{"audience_id":"active-business-users"},"template":"nt_01kx4h2jdafq8bk9aftxak4b40"}'
3
Reach many lists at once
A
list_id is a dotted namespace, so list_pattern targets several lists in one call. Use * for one part of the name, or ** as a trailing wildcard.const { requestId } = await client.send.message({
message: {
to: {
list_pattern: "acme-corp.*.beta-testers",
},
template: "nt_01kx4h2jdafq8bk9aftxak4b40",
},
});
response = client.send.message(
message={
"to": {
"list_pattern": "acme-corp.*.beta-testers",
},
"template": "nt_01kx4h2jdafq8bk9aftxak4b40",
},
)
curl -X POST https://api.courier.com/send \
-H "Authorization: Bearer $COURIER_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"message": {
"to": {
"list_pattern": "acme-corp.*.beta-testers"
},
"template": "nt_01kx4h2jdafq8bk9aftxak4b40"
}
}'
response = courier.send_.message(
message: {
to: {
list_pattern: "acme-corp.*.beta-testers"
},
template: "nt_01kx4h2jdafq8bk9aftxak4b40"
}
)
// This provider addresses the recipient with fields outside the typed
// UserRecipient model, so pass the recipient as raw JSON.
to := param.Override[shared.UserRecipientParam](json.RawMessage(`{
"list_pattern": "acme-corp.*.beta-testers"
}`))
response, err := client.Send.Message(context.TODO(), courier.SendMessageParams{
Message: courier.SendMessageParamsMessage{
To: courier.SendMessageParamsMessageToUnion{OfUserRecipient: &to},
Template: courier.String("nt_01kx4h2jdafq8bk9aftxak4b40"),
},
})
SendMessageParams params = SendMessageParams.builder()
.message(SendMessageParams.Message.builder()
// This provider addresses the recipient with fields outside the
// typed UserRecipient model, so pass them as additional properties.
.to(UserRecipient.builder()
.putAdditionalProperty("list_pattern", JsonValue.from("acme-corp.*.beta-testers"))
.build())
.template("nt_01kx4h2jdafq8bk9aftxak4b40")
.build())
.build();
SendMessageResponse response = client.send().message(params);
$response = $client->send->message(
message: [
'to' => [
'list_pattern' => 'acme-corp.*.beta-testers',
],
'template' => 'nt_01kx4h2jdafq8bk9aftxak4b40',
],
);
SendMessageParams parameters = new()
{
Message = new()
{
// This provider addresses the recipient with fields outside the
// typed UserRecipient model, so build it from raw JSON.
To = UserRecipient.FromRawUnchecked(
JsonSerializer.Deserialize<Dictionary<string, JsonElement>>(
"""
{
"list_pattern": "acme-corp.*.beta-testers"
}
"""
)
),
Template = "nt_01kx4h2jdafq8bk9aftxak4b40",
},
};
var response = await client.Send.Message(parameters);
courier send message \
--api-key "$COURIER_API_KEY" \
--message.to '{"list_pattern": "acme-corp.*.beta-testers"}' \
--message.template nt_01kx4h2jdafq8bk9aftxak4b40
With Courier MCP, send my nt_01kx4h2jdafq8bk9aftxak4b40 template to every beta-testers list under acme-corp.
Verify
1
Count the messages
Open and confirm one message per member.
2
Reconcile a wrong count
Compare the log against the membership from the or API.
3
Check who was filtered out
Members who opted out of the template’s topic show as
UNSUBSCRIBED rather than delivered. That is preferences working, not a failed send.A list or audience must exist first. For a one-off set of recipients, instead.