Skip to content
← Public packages

@kody/agent-mail

AgentMail inboxes for agents: create/list inboxes, messages, threads, and Svix webhook ingress.

src/create-webhook.ts

72 lines · 2.4 KB · TypeScript
import {
	agentMailRequest,
	clean,
	requireConfirmOrDryRun,
} from './core.ts'

export type CreateWebhookInput = {
	url: string
	eventTypes: string[]
	clientId?: string
	inboxIds?: string[]
	podIds?: string[]
	headers?: Record<string, string>
	/** Preview the request without calling AgentMail. */
	dryRun?: boolean
	/** Required true for a live create (unless dryRun). */
	confirm?: boolean
}

/**
 * Register an AgentMail-side webhook endpoint.
 * Requires confirm: true for a live POST, or dryRun: true to preview.
 * Uses POST /v0/webhooks. Treat the returned secret as a credential.
 *
 * @param input.url - Public webhook ingress URL (required)
 * @param input.eventTypes - Event types such as message.received (required)
 * @param input.clientId - Optional client_id for idempotency
 * @param input.inboxIds - Optional inbox filter (max 10)
 * @param input.podIds - Optional pod filter (max 10)
 * @param input.dryRun - Preview without creating
 * @param input.confirm - Must be true for a live create
 * @returns Created webhook or dry-run preview
 *
 * @example
 * import createWebhook from 'kody:@kody/agent-mail/create-webhook'
 * const preview = await createWebhook({
 *   url: 'https://example.invalid/inbound',
 *   eventTypes: ['message.received'],
 *   dryRun: true,
 * })
 */
export default async function createWebhook(input: CreateWebhookInput) {
	const mode = requireConfirmOrDryRun(input, 'create a live AgentMail webhook')
	const url = clean(input.url)
	if (!url) throw new Error('url is required')
	const eventTypes = Array.isArray(input.eventTypes)
		? input.eventTypes.map((t) => clean(t)).filter(Boolean)
		: []
	if (eventTypes.length === 0) throw new Error('eventTypes must include at least one type')

	const body: Record<string, unknown> = {
		url,
		event_types: eventTypes,
	}
	if (clean(input.clientId)) body.client_id = clean(input.clientId)
	if (Array.isArray(input.inboxIds)) body.inbox_ids = input.inboxIds.map((id) => clean(id)).filter(Boolean)
	if (Array.isArray(input.podIds)) body.pod_ids = input.podIds.map((id) => clean(id)).filter(Boolean)
	if (input.headers && typeof input.headers === 'object') body.headers = input.headers

	const path = '/v0/webhooks'
	if (mode === 'dryRun') {
		return { dryRun: true as const, path, body }
	}

	const webhook = await agentMailRequest({
		method: 'POST',
		path,
		body,
		label: 'AgentMail create webhook',
	})
	return { dryRun: false as const, webhook }
}