/** * Generated by the Lango developer portal. Do not edit by hand. * Group: messaging (Messaging) * APIs: SMS v1.4.1 * Generated: 2026-09-28T10:59:08.306Z */ export class LangoApiError extends Error { status: number; error: string; requestId?: string; constructor(status: number, error: string, message: string, requestId?: string) { super(message); this.name = "LangoApiError"; this.status = status; this.error = error; this.requestId = requestId; } } export interface SendSmsRequest { /** Your registered alphanumeric sender ID. */ senderId: string; /** Recipient in international format, no plus sign. */ to: string; /** The text to send. Never stored in the request log. */ message: string; callbackUrl?: string; } export class MessagingClient { private consumerKey: string; private consumerSecret: string; private baseUrl: string; private token: string | null = null; private tokenExpiresAt = 0; constructor(consumerKey: string, consumerSecret: string, baseUrl: string) { this.consumerKey = consumerKey; this.consumerSecret = consumerSecret; this.baseUrl = baseUrl.replace(/\/+$/, ""); } private async getToken(): Promise { if (this.token && Date.now() < this.tokenExpiresAt) return this.token; const basic = btoa(`${this.consumerKey}:${this.consumerSecret}`); const res = await fetch(`${this.baseUrl}/oauth/v1/token`, { method: "POST", headers: { authorization: `Basic ${basic}`, "content-type": "application/x-www-form-urlencoded" }, body: "grant_type=client_credentials", }); const data = (await res.json().catch(() => undefined)) as | { access_token?: string; expires_in?: number; error?: string; message?: string; requestId?: string } | undefined; if (!res.ok || !data?.access_token) { throw new LangoApiError(res.status, data?.error ?? "TOKEN_ERROR", data?.message ?? "Could not get a sandbox token.", data?.requestId); } this.token = data.access_token; this.tokenExpiresAt = Date.now() + ((data.expires_in ?? 3600) - 60) * 1000; return this.token; } private async request( method: string, path: string, query: Record | undefined, body: unknown, ): Promise { const token = await this.getToken(); const parts = Object.entries(query ?? {}) .filter(([, v]) => v !== undefined) .map(([k, v]) => `${encodeURIComponent(k)}=${encodeURIComponent(String(v))}`); const url = this.baseUrl + path + (parts.length ? `?${parts.join("&")}` : ""); const res = await fetch(url, { method, headers: { authorization: `Bearer ${token}`, ...(body !== undefined ? { "content-type": "application/json" } : {}), }, body: body !== undefined ? JSON.stringify(body) : undefined, }); const data = await res.json().catch(() => undefined); if (!res.ok) { const d = data as { error?: string; message?: string; requestId?: string } | undefined; throw new LangoApiError(res.status, d?.error ?? "REQUEST_FAILED", d?.message ?? res.statusText, d?.requestId); } return data; } /** Send a text message */ async sendSms(body: SendSmsRequest): Promise { return this.request("POST", `/messaging/v1/sms`, undefined, body); } /** Check a message */ async getSms(params: { messageId: string }): Promise { return this.request("GET", `/messaging/v1/sms/${encodeURIComponent(String(params.messageId))}`, undefined, undefined); } }