Create template
Create a WhatsApp template and submit it for WhatsApp approval, which is asynchronous (~24–48h). A template belongs to one WhatsApp account (WABA) and can only be sent from that account’s numbers; if the organization has several accounts, choose one with whatsappAccountId: its WABA ID or the name the team gave it, e.g. “Soporte” (see whatsapp_numbers_list). Example (TEXT): { "name": "order_shipped", "language": "es", "category": "UTILITY", "contentType": "TEXT", "content": { "body": "Hola {{1}}, tu pedido ya salió." }, "variables": { "1": "Ana" } }. Example with buttons (CALL_TO_ACTION): { "name": "order_shipped_cta", "language": "es", "category": "UTILITY", "contentType": "CALL_TO_ACTION", "content": { "body": "Hola {{1}}, tu pedido ya salió.", "actions": [{ "type": "URL", "title": "Ver pedido", "url": "https://example.com/orders/{{2}}" }] }, "variables": { "1": "Ana", "2": "12345" } }. Example with reply buttons (QUICK_REPLY): { "name": "order_feedback", "language": "es", "category": "UTILITY", "contentType": "QUICK_REPLY", "content": { "body": "¿Te gustó tu compra?", "actions": [{ "title": "Sí", "id": "yes" }, { "title": "No", "id": "no" }] } }. Example with a header and image (CARD): { "name": "order_shipped_card", "language": "es", "category": "UTILITY", "contentType": "CARD", "content": { "headerType": "media", "mediaUrl": "https://example.com/banner.jpg", "body": "Hola {{1}}, tu pedido ya salió.", "footer": "Gracias por tu compra", "actions": [{ "type": "URL", "title": "Ver pedido", "url": "https://example.com/orders/{{2}}" }] }, "variables": { "1": "Ana", "2": "12345" } }. Example that is only an image (MEDIA): the image URL goes in content.media (an array), NOT in a variable — { "name": "promo_verano", "language": "es", "category": "MARKETING", "contentType": "MEDIA", "content": { "media": ["https://example.com/promo.png"], "body": "¡Hola {{1}}! Aprovecha nuestra promo de verano." }, "variables": { "1": "Ana" } }.
curl --request POST \
--url https://www.useboom.ai/api/v1/templates \
--header 'Authorization: Bearer <token>' \
--header 'Content-Type: application/json' \
--data '
{
"name": "<string>",
"language": "<string>",
"content": {},
"variables": {},
"whatsappAccountId": "<string>",
"phoneNumbers": [
"<string>"
]
}
'import requests
url = "https://www.useboom.ai/api/v1/templates"
payload = {
"name": "<string>",
"language": "<string>",
"content": {},
"variables": {},
"whatsappAccountId": "<string>",
"phoneNumbers": ["<string>"]
}
headers = {
"Authorization": "Bearer <token>",
"Content-Type": "application/json"
}
response = requests.post(url, json=payload, headers=headers)
print(response.text)const options = {
method: 'POST',
headers: {Authorization: 'Bearer <token>', 'Content-Type': 'application/json'},
body: JSON.stringify({
name: '<string>',
language: '<string>',
content: {},
variables: {},
whatsappAccountId: '<string>',
phoneNumbers: ['<string>']
})
};
fetch('https://www.useboom.ai/api/v1/templates', options)
.then(res => res.json())
.then(res => console.log(res))
.catch(err => console.error(err));<?php
$curl = curl_init();
curl_setopt_array($curl, [
CURLOPT_URL => "https://www.useboom.ai/api/v1/templates",
CURLOPT_RETURNTRANSFER => true,
CURLOPT_ENCODING => "",
CURLOPT_MAXREDIRS => 10,
CURLOPT_TIMEOUT => 30,
CURLOPT_HTTP_VERSION => CURL_HTTP_VERSION_1_1,
CURLOPT_CUSTOMREQUEST => "POST",
CURLOPT_POSTFIELDS => json_encode([
'name' => '<string>',
'language' => '<string>',
'content' => [
],
'variables' => [
],
'whatsappAccountId' => '<string>',
'phoneNumbers' => [
'<string>'
]
]),
CURLOPT_HTTPHEADER => [
"Authorization: Bearer <token>",
"Content-Type: application/json"
],
]);
$response = curl_exec($curl);
$err = curl_error($curl);
curl_close($curl);
if ($err) {
echo "cURL Error #:" . $err;
} else {
echo $response;
}package main
import (
"fmt"
"strings"
"net/http"
"io"
)
func main() {
url := "https://www.useboom.ai/api/v1/templates"
payload := strings.NewReader("{\n \"name\": \"<string>\",\n \"language\": \"<string>\",\n \"content\": {},\n \"variables\": {},\n \"whatsappAccountId\": \"<string>\",\n \"phoneNumbers\": [\n \"<string>\"\n ]\n}")
req, _ := http.NewRequest("POST", url, payload)
req.Header.Add("Authorization", "Bearer <token>")
req.Header.Add("Content-Type", "application/json")
res, _ := http.DefaultClient.Do(req)
defer res.Body.Close()
body, _ := io.ReadAll(res.Body)
fmt.Println(string(body))
}HttpResponse<String> response = Unirest.post("https://www.useboom.ai/api/v1/templates")
.header("Authorization", "Bearer <token>")
.header("Content-Type", "application/json")
.body("{\n \"name\": \"<string>\",\n \"language\": \"<string>\",\n \"content\": {},\n \"variables\": {},\n \"whatsappAccountId\": \"<string>\",\n \"phoneNumbers\": [\n \"<string>\"\n ]\n}")
.asString();require 'uri'
require 'net/http'
url = URI("https://www.useboom.ai/api/v1/templates")
http = Net::HTTP.new(url.host, url.port)
http.use_ssl = true
request = Net::HTTP::Post.new(url)
request["Authorization"] = 'Bearer <token>'
request["Content-Type"] = 'application/json'
request.body = "{\n \"name\": \"<string>\",\n \"language\": \"<string>\",\n \"content\": {},\n \"variables\": {},\n \"whatsappAccountId\": \"<string>\",\n \"phoneNumbers\": [\n \"<string>\"\n ]\n}"
response = http.request(request)
puts response.read_body{
"data": [
{
"id": "<string>",
"name": "<string>",
"language": "<string>",
"category": "UTILITY",
"contentType": "TEXT",
"content": "<unknown>",
"variables": {},
"phoneNumbers": [
"<string>"
],
"whatsappAccount": {
"id": "<string>",
"name": "<string>",
"alias": "<string>",
"phoneNumbers": [
"<string>"
]
},
"status": "DRAFT",
"rejectionReason": "<string>",
"createdAt": "<string>",
"updatedAt": "<string>"
}
]
}{
"error": {
"code": "<string>",
"message": "<string>"
}
}{
"error": {
"code": "<string>",
"message": "<string>"
}
}{
"error": {
"code": "<string>",
"message": "<string>"
}
}{
"error": {
"code": "<string>",
"message": "<string>"
}
}{
"error": {
"code": "<string>",
"message": "<string>"
}
}{
"error": {
"code": "<string>",
"message": "<string>"
}
}{
"error": {
"code": "<string>",
"message": "<string>"
}
}{
"error": {
"code": "<string>",
"message": "<string>"
}
}Authorizations
Organization API key, sent as Authorization: Bearer boom_org_....
Body
Template name, unique per WhatsApp account (shared by all its numbers).
1 - 255WhatsApp language code, e.g. es, en. A regional variant like es_MX or en_US is normalized to its base code.
2 - 10UTILITY, MARKETING, AUTHENTICATION TEXT, MEDIA, QUICK_REPLY, CALL_TO_ACTION, CARD Message content. Shape depends on contentType: TEXT { body }; MEDIA { body?, media: [url] }; QUICK_REPLY { body, actions: [{ title, id }] }; CALL_TO_ACTION { body, actions: [{ type: URL|PHONE_NUMBER, title, url|phone }] }; CARD { headerType, headerText|mediaUrl, body, footer?, actions? }. Use {{1}}, {{2}}… for variables. Example (TEXT): { "body": "Hola {{1}}, tu pedido está en camino" }. Example (CALL_TO_ACTION, adds a button): { "body": "Hola {{1}}, tu pedido está en camino", "actions": [{ "type": "URL", "title": "Ver pedido", "url": "https://example.com/orders/{{2}}" }] }. Example (QUICK_REPLY, adds reply buttons): { "body": "¿Te gustó tu compra?", "actions": [{ "title": "Sí", "id": "yes" }, { "title": "No", "id": "no" }] }. Example (CARD, header + optional footer/button): { "headerType": "text", "headerText": "Pedido en camino", "body": "Hola {{1}}, tu pedido ya salió.", "footer": "Gracias por tu compra", "actions": [{ "type": "URL", "title": "Ver pedido", "url": "https://example.com/orders/{{2}}" }] }.
Show child attributes
Show child attributes
Example values for placeholders, e.g. { "1": "Ana" } for {{1}}. Required for every placeholder used.
Show child attributes
Show child attributes
WABA ID of the WhatsApp account to create the template on (whatsappAccount.id from whatsapp_numbers_list), or the account's alias, matched case-insensitively (whatsappAccount.alias, e.g. "Soporte"). The template belongs to that account: every number on it can send it, and numbers on other accounts can't. Works for an account with no active numbers yet. Omit when the organization has a single WhatsApp account; with several, pass this or phoneNumbers.
1Alternative to whatsappAccountId: any WhatsApp number (E.164) on the account to create the template on. One number per account is enough. Numbers on several accounts create one template per account. Omit when the organization has a single WhatsApp account.
11Response
Success
The created template(s) — one per WhatsApp account backing the chosen numbers.
Show child attributes
Show child attributes
Was this page helpful?
curl --request POST \
--url https://www.useboom.ai/api/v1/templates \
--header 'Authorization: Bearer <token>' \
--header 'Content-Type: application/json' \
--data '
{
"name": "<string>",
"language": "<string>",
"content": {},
"variables": {},
"whatsappAccountId": "<string>",
"phoneNumbers": [
"<string>"
]
}
'import requests
url = "https://www.useboom.ai/api/v1/templates"
payload = {
"name": "<string>",
"language": "<string>",
"content": {},
"variables": {},
"whatsappAccountId": "<string>",
"phoneNumbers": ["<string>"]
}
headers = {
"Authorization": "Bearer <token>",
"Content-Type": "application/json"
}
response = requests.post(url, json=payload, headers=headers)
print(response.text)const options = {
method: 'POST',
headers: {Authorization: 'Bearer <token>', 'Content-Type': 'application/json'},
body: JSON.stringify({
name: '<string>',
language: '<string>',
content: {},
variables: {},
whatsappAccountId: '<string>',
phoneNumbers: ['<string>']
})
};
fetch('https://www.useboom.ai/api/v1/templates', options)
.then(res => res.json())
.then(res => console.log(res))
.catch(err => console.error(err));<?php
$curl = curl_init();
curl_setopt_array($curl, [
CURLOPT_URL => "https://www.useboom.ai/api/v1/templates",
CURLOPT_RETURNTRANSFER => true,
CURLOPT_ENCODING => "",
CURLOPT_MAXREDIRS => 10,
CURLOPT_TIMEOUT => 30,
CURLOPT_HTTP_VERSION => CURL_HTTP_VERSION_1_1,
CURLOPT_CUSTOMREQUEST => "POST",
CURLOPT_POSTFIELDS => json_encode([
'name' => '<string>',
'language' => '<string>',
'content' => [
],
'variables' => [
],
'whatsappAccountId' => '<string>',
'phoneNumbers' => [
'<string>'
]
]),
CURLOPT_HTTPHEADER => [
"Authorization: Bearer <token>",
"Content-Type: application/json"
],
]);
$response = curl_exec($curl);
$err = curl_error($curl);
curl_close($curl);
if ($err) {
echo "cURL Error #:" . $err;
} else {
echo $response;
}package main
import (
"fmt"
"strings"
"net/http"
"io"
)
func main() {
url := "https://www.useboom.ai/api/v1/templates"
payload := strings.NewReader("{\n \"name\": \"<string>\",\n \"language\": \"<string>\",\n \"content\": {},\n \"variables\": {},\n \"whatsappAccountId\": \"<string>\",\n \"phoneNumbers\": [\n \"<string>\"\n ]\n}")
req, _ := http.NewRequest("POST", url, payload)
req.Header.Add("Authorization", "Bearer <token>")
req.Header.Add("Content-Type", "application/json")
res, _ := http.DefaultClient.Do(req)
defer res.Body.Close()
body, _ := io.ReadAll(res.Body)
fmt.Println(string(body))
}HttpResponse<String> response = Unirest.post("https://www.useboom.ai/api/v1/templates")
.header("Authorization", "Bearer <token>")
.header("Content-Type", "application/json")
.body("{\n \"name\": \"<string>\",\n \"language\": \"<string>\",\n \"content\": {},\n \"variables\": {},\n \"whatsappAccountId\": \"<string>\",\n \"phoneNumbers\": [\n \"<string>\"\n ]\n}")
.asString();require 'uri'
require 'net/http'
url = URI("https://www.useboom.ai/api/v1/templates")
http = Net::HTTP.new(url.host, url.port)
http.use_ssl = true
request = Net::HTTP::Post.new(url)
request["Authorization"] = 'Bearer <token>'
request["Content-Type"] = 'application/json'
request.body = "{\n \"name\": \"<string>\",\n \"language\": \"<string>\",\n \"content\": {},\n \"variables\": {},\n \"whatsappAccountId\": \"<string>\",\n \"phoneNumbers\": [\n \"<string>\"\n ]\n}"
response = http.request(request)
puts response.read_body{
"data": [
{
"id": "<string>",
"name": "<string>",
"language": "<string>",
"category": "UTILITY",
"contentType": "TEXT",
"content": "<unknown>",
"variables": {},
"phoneNumbers": [
"<string>"
],
"whatsappAccount": {
"id": "<string>",
"name": "<string>",
"alias": "<string>",
"phoneNumbers": [
"<string>"
]
},
"status": "DRAFT",
"rejectionReason": "<string>",
"createdAt": "<string>",
"updatedAt": "<string>"
}
]
}{
"error": {
"code": "<string>",
"message": "<string>"
}
}{
"error": {
"code": "<string>",
"message": "<string>"
}
}{
"error": {
"code": "<string>",
"message": "<string>"
}
}{
"error": {
"code": "<string>",
"message": "<string>"
}
}{
"error": {
"code": "<string>",
"message": "<string>"
}
}{
"error": {
"code": "<string>",
"message": "<string>"
}
}{
"error": {
"code": "<string>",
"message": "<string>"
}
}{
"error": {
"code": "<string>",
"message": "<string>"
}
}