브로드캐스트
`broadcasts.preview`, `send`, `list`, `listAll`, `iterate`, `get`, `cancel`.
모든 메서드
const draft = { audienceIds: ['aud_4c1b8e2a7d9f05c36b4e8a71'], from: 'Acme <[email protected]>', subject: '{{firstName|Hello}}, the September release is out', html: '<p>Hi {{firstName|there}},</p><p>Here is what changed this month.</p>', text: 'Hi {{firstName|there}}, here is what changed this month. Unsubscribe: {{unsubscribeUrl}}', tags: { campaign: 'release-2026-09' },} const reach = await openemail.broadcasts.preview(draft)console.log(reach.recipients, reach.unsubscribed, reach.suppressed) const broadcast = await openemail.broadcasts.send(draft) let latest = await openemail.broadcasts.get(broadcast.id)while (['scheduled', 'queued', 'sending'].includes(latest.status)) { await new Promise((resolve) => setTimeout(resolve, 5_000)) latest = await openemail.broadcasts.get(broadcast.id)} for await (const copy of openemail.emails.iterate({ broadcastId: broadcast.id })) { console.log(copy.id, copy.status)} const later = await openemail.broadcasts.send({ ...draft, scheduledAt: 'P1D' })await openemail.broadcasts.cancel(later.id) const history = await openemail.broadcasts.list({ audienceId: draft.audienceIds[0] })console.log(latest.status, latest.counts.sent, history.items.length)브로드캐스트는 하나 이상의 오디언스에 있는 모든 사람에게 메시지 하나를 사람마다 별도의 사본으로 보냅니다. 각 사본의 받는 사람은 정확히 한 명이고 cc나 bcc가 없어서 누구도 또 누구에게 갔는지 볼 수 없으며, 각 사본은 자체 msg_ ID, 이벤트, 추적, 웹훅이 있는 일반 이메일입니다. emails.list({ broadcastId })로 나열합니다. 브로드캐스트 자체가 기록이므로 사본은 보낸편지함에 보관되지 않습니다.
send는 곧바로 queued 상태의 브로드캐스트로, scheduledAt을 주면 scheduled로 resolve되며 발송은 백그라운드에서 진행됩니다. send에는 emails:send와 audiences:read, preview에는 audiences:read, list, listAll, iterate, get에는 emails:read, cancel에는 emails:send가 필요합니다.
모든 send에는 Idempotency-Key가 붙습니다. options.idempotencyKey로 준 것이거나 SDK가 만든 것이므로, 네트워크 장애 뒤의 재시도는 두 번 보내는 대신 첫 시도가 만든 브로드캐스트로 응답합니다. preview, get, cancel은 반복해도 안전하며 재시도됩니다.
병합 필드
subject, html, text는 사람마다 그 연락처에서 채워집니다. {{firstName}}은 연락처 이름의 첫 단어, {{lastName}}은 나머지, {{name}}은 전체 이름, {{email}}은 사본이 가는 주소, {{unsubscribeUrl}}은 그 사람의 구독을 해지하는 링크입니다.
각 필드는 막대 뒤에 대체 값을 받아 연락처에 값이 없을 때 쓰므로, 이름 없이 저장된 연락처에서 {{firstName|there}}는 "there"가 됩니다. html에서는 값이 이스케이프되고, 다른 {{…}}는 쓴 그대로 남습니다.
저장된 템플릿을 보내려면 html과 text 대신 template을 넘기세요. 같은 다섯 값이 프롭으로 가지만 템플릿이 선언한 프롭만이므로, firstName을 선언한 템플릿은 그 값을 받고 선언하지 않은 템플릿은 그 때문에 거절되지 않습니다. template.props에 있는 것은 모든 사본에 똑같이 들어갑니다.
구독 해지
모든 사본에 원클릭 구독 해지 헤더가 붙어 메일 클라이언트가 자체 구독 해지 버튼을 보여 줄 수 있으며, 대형 메일함 제공자가 대량 메일에 요구하는 것이 이것입니다. {{unsubscribeUrl}}을 직접 넣지 않은 html이나 text 본문에는 링크가 든 한 줄짜리 바닥글이 붙습니다. 템플릿은 그대로 보내지므로 템플릿에 {{unsubscribeUrl}}을 넣으세요.
구독을 해지하면 그 브로드캐스트가 간 모든 오디언스에서 그 사람이 구독 해지로 표시되고, AudienceContactResource.unsubscribedAt이 audiences.listContacts에서 이를 보여 줍니다. 그 사람은 오디언스와 주소록에 남고, 다른 오디언스는 그대로이며, 한 통씩 보내는 메일은 계속 나갑니다. 오디언스에서 뺐다가 다시 넣으면 새로 구독 상태가 됩니다.
건너뛰는 대상
브로드캐스트는 audienceIds 중 적어도 하나에 있는 모든 연락처에, 몇 개에 있든 한 번 닿습니다. 그 오디언스 중 자신이 속한 모든 곳에서 구독을 해지한 연락처와, 바운스나 신고 때문에 또는 누가 추가해서 차단 목록에 있는 주소는 건너뜁니다. send 뒤 발송이 닿기 전에 오디언스에 추가된 연락처는 받습니다.
preview는 보내지 않고 같은 수, recipients, unsubscribed, suppressed를 돌려줍니다. 아무에게도 닿지 않을 send는 422 no_recipients를 던집니다.
무엇이든 기록하기 전에 발송 전체가 요금제의 월간 발송량과 대조되므로, 할당량이 감당할 수 없는 브로드캐스트는 429 send_quota_exceeded를 던지고 아무것도 남기지 않습니다. 사본 한 통이 한 번의 발송으로 계산됩니다.
상태와 진행
get은 사본에서 counts를 바로 읽으므로 브로드캐스트가 발송되는 동안 폴링하세요. status는 scheduled나 queued에서 sending으로 가고, 넘긴 모든 사본이 나가거나 실패하면 sent에 머뭅니다. completedAt이 마지막 사람에게 닿았다고 알린 뒤에도 사본이 기다리는 동안에는 sending입니다. failed는 브로드캐스트 전체가 멈췄다는 뜻이며, lastError가 이유를 알려 줍니다. from 주소로 더 이상 보낼 수 없거나, 템플릿을 해석할 수 없게 되었거나, 요금제가 중간에 소진되었거나, 발송 자체가 계속 실패했거나, 사본을 한 통도 기록하지 못한 경우입니다.
cancel은 scheduled, queued, sending 상태인 브로드캐스트를 멈춥니다. 더 이상 아무도 추가되지 않고 아직 기다리는 모든 사본이 취소되지만, 나간 사본은 되돌릴 수 없습니다. 모든 사본이 나간 뒤의 cancel은 409 broadcast_not_cancellable을 던지고, 취소된 브로드캐스트를 취소하면 그 상태 그대로 resolve됩니다.
응답: BroadcastResource
send, get, cancel은 각각 이것 하나로 resolve됩니다. list는 이것들의 페이지 { items, hasMore, nextCursor }를 최신순으로 resolve하고, listAll과 iterate는 모든 페이지를 훑습니다. preview는 audienceIds, recipients, unsubscribed, suppressed가 있는 BroadcastPreviewResource로 resolve됩니다.
idstring- 영구 식별자로, `brd_` 뒤에 16진수 24자가 붙습니다.
statusBroadcastStatus- `scheduled`, `queued`, `sending`, `sent`, `cancelled`, `failed` 중 하나. `BROADCAST_STATUSES`가 각각에 이름을 붙입니다.
modeApiKeyMode- 만든 키에 따라 `live` 또는 `test`. 테스트 브로드캐스트의 사본은 보냄으로 표시되고 아무에게도 전달되지 않습니다.
sourceEmailSource- 시작된 곳: 키는 `api`, 연결된 앱은 `oauth`, 앱은 `composer`, 어시스턴트는 `mcp`.
audienceIdsstring[]- 보낸 오디언스, 각각 한 번씩.
fromstring- 모든 사본을 보내는 주소.
subjectstring- 병합 필드까지 쓴 그대로의 제목. 템플릿이 제목을 제공하면 비어 있습니다.
countsBroadcastCounts- `recipients`는 `send` 때 잡은 추정치입니다. `created`는 기록된 사본 수, `skipped`는 그때 주소가 차단되어 있어 건너뛴 사람 수, `failedToQueue`는 사본을 기록하지 못한 사람 수입니다. `queued`, `sending`, `sent`, `failed`, `cancelled`는 각 사본이 지금 있는 상태별 수입니다.
lastErrorstring | null- 브로드캐스트가 실패한 이유, 또는 기록하지 못한 가장 최근 사본과 그 이유. 문제가 없는 동안은 null입니다.
scheduledAtstring | null- ISO-8601 UTC, 발송이 시작될 예정 시각. 바로 보낸 브로드캐스트는 null입니다.
startedAtstring | null- ISO-8601 UTC, 발송이 처음 사람들에게 닿은 시각.
completedAtstring | null- ISO-8601 UTC, 마지막 사람에게 닿은 시각. 그 뒤에도 사본이 나가기를 기다릴 수 있습니다.
cancelledAtstring | null- ISO-8601 UTC, `cancel`이 멈춘 시각.
createdAtstring- ISO-8601 UTC, `send`를 호출한 시각. 목록 순서를 정합니다.
updatedAtstring- ISO-8601 UTC, 발송이 진행되면서 갱신됩니다.