Webhooks
Um webhook de entrada permite que outro sistema publique em um canal enviando JSON para uma URL secreta. Um webhook de saída faz o oposto: ele envia mensagens para a sua URL, aquelas que começam com uma palavra gatilho ou que as pessoas escolhem no menu de mensagem, e publica o que você responde.
Onde gerenciar webhooks
Abra seu avatar no canto superior direito e depois Integrações. As páginas de integrações da comunidade atual listam Webhooks Entrada e Webhooks Saída. Cada webhook pertence a uma comunidade.
Por padrão, administradores de comunidade e administradores do sistema podem criar webhooks. Um administrador do sistema pode conceder esse direito a outros papéis nas configurações de permissões do Console do Sistema. Um administrador do sistema também pode desativar cada tipo em Console do Sistema › Integrações › Gerenciamento de Integração: Ativar Webhooks Entrada e Ativar Webhooks Saída estão ambos ativados por padrão.

Criar um webhook de entrada
- Em Integrações, escolha Webhooks Entrada e depois Adicionar Webhooks Entrada.
- Preencha um Título e uma Descrição: eles aparecem apenas nas páginas de integrações.
- Escolha o Canal para onde as mensagens vão por padrão. Para um Canal Privado, você deve ser membro dele.
- Marque Travar neste canal se os remetentes não devem poder publicar em outros lugares.
- Opcionalmente, defina uma URL para Usuário e Imagem do Perfil para suas mensagens (veja Nome e ícone).
- Escolha Salvar. Copie a URL exibida:
https://chat.example.com/hooks/<key>.
Com a API: POST /api/v4/hooks/incoming com {"channel_id", "display_name", "description", "username", "icon_url", "channel_locked"}; o id da resposta é a chave. Da linha de comando: amctl webhook create-incoming --channel <channel id> --user <user> --display-name "CI".
Enviar uma mensagem para um webhook de entrada
curl -X POST https://chat.example.com/hooks/xgh5ycrx1jf7mbs9w8z4c8e7ho \
-H 'Content-Type: application/json' \
-d '{"text": "Deploy of **api 2.4.0** finished :white_check_mark:"}'
O servidor responde 200 com o corpo ok. Ele também aceita application/x-www-form-urlencoded com o JSON em um campo payload, como os webhooks do Slack, então as ferramentas feitas para o Slack geralmente funcionam sem alterações.
| Campo | Significado |
|---|---|
text | A mensagem, em Markdown. Obrigatório, a menos que haja attachments. Um texto mais longo que o limite de mensagem do servidor é dividido em várias mensagens. |
channel | Outro canal da comunidade do webhook, pelo nome (ops-alerts ou #ops-alerts), ou @username para uma mensagem direta do proprietário do webhook. Recusado quando o webhook está bloqueado para o seu canal. O nome antigo town-square ainda alcança o canal padrão da comunidade, agora chamado general. |
username, icon_url, icon_emoji | O nome e a imagem a exibir, quando o servidor permite substituições. |
attachments | Anexos da mensagem, exibidos como cartões (abaixo). |
props | Propriedades extras armazenadas na mensagem, para aplicativos que as leem. |
type | Um tipo de mensagem personalizado, como custom_poll, para um aplicativo que o exibe. Tipos que começam com system_ são recusados. |
root_id | O ID da primeira mensagem de um tópico, para responder nesse tópico. |
priority | Prioridade da mensagem, por exemplo {"priority": "urgent"}. |
silent | true envia a mensagem sem notificações push. |
Toda mensagem publicada por um webhook carrega uma tag BOT ao lado do seu nome, mesmo quando exibida sob o nome do seu criador, para que as pessoas possam diferenciá-la de uma mensagem de uma pessoa real. Mensagens de webhook nunca acionam webhooks de saída.
Nome e ícone
Um webhook publica como a pessoa que o criou, a menos que o servidor permita substituições. Duas configurações em Console do Sistema › Integrações › Gerenciamento de Integração, ambas desativadas por padrão, mudam isso:
- Permitir que integrações sobrescrevam o nome do usuário (
ServiceSettings.EnablePostUsernameOverride): o Usuário do webhook ou ousernameda solicitação é exibido; sem nenhum dos dois, o nome éwebhook. - Permitir que integrações sobrescreva o imagem do perfil (
ServiceSettings.EnablePostIconOverride): a Imagem do Perfil do webhook, ou oicon_urlouicon_emojida solicitação, é exibido.
Um valor na solicitação tem prioridade sobre o valor salvo no webhook.
Anexos
Anexos adicionam conteúdo estruturado abaixo do texto. Eles seguem o formato de anexo de mensagem do Slack:
{
"text": "Build failed on `main`",
"attachments": [{
"fallback": "main #1902 failed",
"color": "#d24b4e",
"author_name": "GitHub Actions",
"author_icon": "https://chat.example.com/static/ci.png",
"title": "main #1902 failed",
"title_link": "https://ci.example.com/runs/1902",
"text": "Commit `0f4d8e2` by Jonas Weber",
"fields": [
{"title": "Branch", "value": "zephyr-3.7", "short": true},
{"title": "Duration", "value": "3m 40s", "short": true}
],
"footer": "Lumen CI",
"ts": 1760000000
}]
}
| Campo | Significado |
|---|---|
fallback | Texto simples para locais que não podem exibir o cartão, como notificações. |
color | A barra de cor: uma cor hexadecimal, ou good, warning, danger. |
pretext | Texto acima do cartão. |
author_name, author_link, author_icon | Uma linha de cabeçalho pequena. |
title, title_link | O título do cartão, opcionalmente um link. |
text | O corpo do cartão, em Markdown. |
fields | Uma lista de {"title", "value", "short"}; campos short ficam lado a lado. |
image_url, thumb_url | Uma imagem grande abaixo, ou uma pequena ao lado. |
footer, footer_icon, ts | Uma linha de rodapé e um tempo (segundos Unix). |
actions | Botões e menus: veja Mensagens interativas. |
Cartões: etapas e gráficos
O Antimatter adiciona dois campos aos anexos, exibidos pela interface padrão:
stages: as etapas de um pipeline, exibidas como pílulas, até 20. Cada uma é{"name", "status"}, com statuspassed,failed,running,pending,skippedoucanceled.chart: um pequeno gráfico de linha de valores recentes,{"values": [2 to 200 numbers], "threshold": number, "label": "…"}. O limite é desenhado como uma linha tracejada, para o limite de um alerta.
{
"attachments": [{
"color": "danger",
"title": "main #1902 failed",
"stages": [
{"name": "build", "status": "failed"},
{"name": "unit", "status": "skipped"},
{"name": "publish", "status": "skipped"}
]
}, {
"color": "warning",
"title": "API latency above 400 ms",
"chart": {"values": [210, 230, 260, 390, 450, 470], "threshold": 400, "label": "p95 latency, ms"}
}]
}
A interface clássica e outros clientes ignoram esses dois campos, então inclua também as informações essenciais em text ou fields.
Criar um webhook de saída
Um webhook de saída monitora os canais Público de uma comunidade. Ele envia uma mensagem para a sua URL quando a primeira palavra da mensagem corresponde a uma de suas palavras gatilho, ou quando alguém o seleciona no menu da mensagem (uma ação de mensagem).
- Em Integrações, escolha Webhooks Saída e depois Adicionar Webhooks Saída.
- Preencha o Título e a Descrição.
- Escolha o Tipo de Conteúdo (Content Type) da solicitação:
application/x-www-form-urlencodedouapplication/json. - Escolha um Canal, insira Palavras Gatilho (Uma Por Linha), ou ambos. Com um canal e sem palavras gatilho, todas as mensagens desse canal são enviadas. Com ambos, a mensagem deve corresponder a ambos.
- Em Enviar quando, escolha Primeira palavra deve corresponder exatamente a uma palavra gatilho, Primeira palavra começa com uma palavra gatilho ou Do menu de mensagem. Com Do menu de mensagem, as palavras gatilho desaparecem, o Canal é opcional (sem ele, a ação é oferecida em todos os canais públicos da comunidade) e o Título é obrigatório: é o nome da ação no menu.
- Insira as URLs Callback (Uma Por Linha). Cada URL recebe todas as mensagens correspondentes.
- Opcionalmente, defina o Usuário e a Imagem do Perfil usados para as respostas. Para uma ação do menu de mensagem, o campo Ícone substitui Imagem do Perfil: a URL de uma imagem .png ou .jpg ou, na interface padrão do Antimatter, uma imagem enviada. O menu a exibe em cinza; sem uma, a ação recebe um ícone neutro.
- Escolha Salvar e copie o token exibido. Seu serviço o usa para verificar se as solicitações vêm do seu servidor.
Com a API: POST /api/v4/hooks/outgoing com {"team_id", "channel_id", "trigger_words", "trigger_when", "callback_urls", "content_type", "display_name"} (trigger_when: 0 para correspondência exata, 1 para "começa com", 2 para "do menu da mensagem"). Um webhook com trigger_when 2 não usa palavras de gatilho e requer um display_name. Envie seu ícone com POST /api/v4/hooks/outgoing/{hook_id}/icon (multipart, campo image: PNG, JPEG ou GIF, armazenado como PNG de 128 px); seu icon_url então aponta para GET /api/v4/hooks/outgoing/{hook_id}/icon.
ServiceSettings.AllowedUntrustedInternalConnections). Caso contrário, o servidor não chama endereços privados.A solicitação de saída
O Antimatter envia um POST com esses campos, como JSON ou form-encoded, dependendo do tipo de conteúdo:
{
"token": "6kd1ofo5ojr5zgu5ipfipybgnc",
"team_id": "…",
"team_domain": "lumen-labs",
"channel_id": "…",
"channel_name": "ops-alerts",
"timestamp": 1760010000000,
"user_id": "…",
"user_name": "priya",
"post_id": "…",
"text": "deploy api 2.4.0",
"trigger_word": "deploy",
"file_ids": ""
}
Compare token com o token do webhook antes de fazer qualquer coisa. Na versão codificada em formulário, timestamp está em segundos, não em milissegundos. O servidor aguarda sua resposta pelo tempo permitido por Tempo limite de solicitação de integração (30 segundos por padrão, ServiceSettings.OutgoingIntegrationRequestsTimeout).
Responder a um webhook de saída
Para publicar uma resposta, responda com JSON. Para não publicar nada, responda com um corpo vazio.
{
"text": "Deploying **api 2.4.0** to staging…",
"response_type": "comment",
"username": "deploy-bot",
"icon_url": "https://chat.example.com/static/deploy.png"
}
texteattachments: a resposta. Sem nenhum dos dois, nada é publicado.response_type:commentpublica a resposta no tópico da mensagem que disparou; caso contrário, vai para o canal.username,icon_url: exibidos quando o servidor permite substituições; caso contrário, são usados os próprios valores do webhook.props,type,priority: como nos webhooks de entrada.
A resposta é publicada como o criador do webhook, sob o nome substituído, quando houver. Para qualquer coisa mais longa do que uma resposta rápida, responda imediatamente e publique depois com um webhook de entrada ou a API.
Ações de mensagem
Uma ação de mensagem é um webhook de saída com Enviar quando definido como Do menu da mensagem. Ela nunca é acionada por mensagens publicadas. Em vez disso, as pessoas a veem no menu de uma mensagem: Ações de mensagem (⋯) › Ações, sob o título Integrações, com seu ícone. A interface clássica não exibe ações de mensagem. Ao selecioná-la, aquela mensagem é enviada para as URLs de callback, e uma breve notificação indica Enviado para o nome da ação, ou exibe seu ephemeral_text.
- Onde aparece: no canal do webhook ou, sem um canal, em todos os canais públicos de sua comunidade. Apenas canais públicos têm ações de mensagem.
- Convidados só recebem as ações vinculadas a um canal em que estão, não as de toda a comunidade.
- Canais arquivados e somente leitura: a mensagem ainda pode ser enviada. Arquivar um canal exclui os webhooks vinculados a ele, portanto um canal arquivado mantém apenas as ações de toda a comunidade. Uma resposta que a pessoa não pôde publicar lá é mostrada apenas a ela.
- Limite de taxa: cada pessoa pode executar 10 ações de mensagem por minuto, após um pico de 5. Acima disso, o servidor responde
429. - Redes privadas: como para outros webhooks de saída, endereços internos devem ser permitidos em Permitir conexão interna não confiável.
A solicitação
O payload é enviado como JSON ou codificado em formulário, conforme o tipo de conteúdo do webhook:
{
"token": "6kd1ofo5ojr5zgu5ipfipybgnc",
"trigger": "message_action",
"team_id": "…",
"team_domain": "lumen-labs",
"channel_id": "…",
"channel_name": "ops-alerts",
"timestamp": 1760010000000,
"user_id": "…",
"user_name": "priya",
"post_id": "…",
"post_root_id": "",
"post_create_at": 1760009000000,
"post_user_id": "…",
"post_user_name": "jonas",
"permalink": "https://chat.example.com/lumen-labs/pl/…",
"text": "The staging database is full again",
"files": [{"id": "…", "name": "df.txt", "link": "https://chat.example.com/api/v4/files/…"}],
"priority": "",
"requested_ack": false,
"burn_on_read": false
}
user_ideuser_namesão da pessoa que selecionou a ação;post_user_idepost_user_namesão do autor da mensagem.- Apenas aquela mensagem é enviada, nunca o restante do seu tópico.
fileslista os arquivos da mensagem apenas quando a pessoa que selecionou a ação pode baixá-los. Baixar umlinkrequer uma sessão ou um token, como qualquer arquivo da API.- Uma mensagem que se queima após a leitura é enviada sem seu texto e arquivos, com
burn_on_readdefinido comotrue. - No formato codificado por formulário, os arquivos são enviados como campos repetidos de
file_id,file_nameefile_link, na mesma ordem.
A resposta
Responda como em qualquer webhook de saída (veja Responder a um webhook de saída): text ou attachments publica uma resposta no canal, e "response_type": "comment" publica-a no tópico da mensagem. Você também pode responder com ephemeral_text (limitado a 300 caracteres): ela é exibida apenas para a pessoa que selecionou a ação, na notificação. Um corpo vazio não publica nada.
{"ephemeral_text": "Ticket OPS-412 created"}
Com a API
GET /api/v4/channels/{channel_id}/message_actions: as ações que você pode selecionar em um canal, comid,display_name,descriptioneicon_url. Nem tokens nem URLs de callback são retornados.POST /api/v4/posts/{post_id}/message_actions/{hook_id}: executa uma ação em uma mensagem que você pode ler. Ela responde{"ephemeral_text"}.
Quando um webhook não funciona
- 501 da URL do hook: os webhooks de entrada estão desativados no servidor.
- 400 "Failed to decode the payload…": o JSON é inválido, ou o campo do formulário não se chama
payload. "No text specified." significa que a requisição não tem nemtextnemattachments. - 403: o webhook está vinculado a outro canal, ou seu proprietário não pode mais ler o canal.
- Um webhook de saída nunca é acionado: o canal é privado, o gatilho não é a primeira palavra, a mensagem veio de um webhook, ou o webhook está configurado para acionar A partir do menu da mensagem.
- Uma ação de mensagem não está no menu: o canal é privado, a ação está vinculada a outro canal, a pessoa é um convidado e a ação não tem canal, ou os webhooks de saída estão desativados.
- 404 ao executar uma ação de mensagem: a ação não existe, ou ela não cobre o canal daquela mensagem para aquela pessoa. 429: a pessoa executou mais de 10 ações em um minuto. 502: nenhuma das URLs de callback pôde ser alcançada (o log contém o motivo).
- Logs: com Ativar Debugging Webhook ativado (
LogSettings.EnableWebhookDebugging) e o nível de log emDEBUG, o servidor registra os payloads de solicitações recebidas com falha. As chamadas de saída com falha são registradas comoOutgoing Webhook POST failed.