Avatares de contato
Por que não buscamos automaticamente as fotos de perfil do WhatsApp
A Cloud API do WhatsApp, da Meta, não expõe fotos de perfil dos usuários finais. O webhookmessages entrega um payload contacts[].profile que inclui apenas
name. O campo profile_picture_url existe apenas em
/whatsapp_business_profile — ou seja, o perfil da própria empresa — não o dos
contatos usuários finais que enviam mensagens para você.
Isso é consistente em todos os BSPs da plataforma (360dialog, Twilio, Infobip,
etc.). Não existe API pública, edge do Graph, ou campo de webhook que retorne
o avatar do cliente.
O que renderizamos
- Fallback de iniciais (padrão). Renderizamos as iniciais do contato sobre
um selo de cor determinístico derivado de um hash do
wa_iddo contato (com fallback para o número de telefone, e depois para o nome). O mesmo contato sempre recebe a mesma cor entre sessões e dispositivos. - Substituição enviada pelo operador. Operadores podem enviar um JPG / PNG / WEBP
de até 2 MB pelo painel de detalhes do contato no inbox. A imagem é reconvertida
para um JPG quadrado de 256×256 (com EXIF removido) e armazenada no
object store
workspace-attachments, emcontacts/{workspaceId}/{contactId}/avatar-{hash}.jpg. A URL é persistida empublic.contacts.avatar_urle renderizada em todos os lugares em que o contato aparece (barra lateral do inbox, cabeçalho do inbox, lista de contatos, layouts mobile).
Fluxo de trabalho do operador
- Abra uma conversa → painel de detalhes à direita → seção Profile → botões Upload / Replace / Remove.
- Os uploads acessam
POST /api/contacts/[contactId]/avatar(multipart/form-data, campofile); a remoção acessaDELETE /api/contacts/[contactId]/avatar. - Ambas as rotas exigem uma verificação ativa de acesso ao workspace do operador e confirmam que o contato pertence ao workspace de quem faz a chamada antes de alterar dados.
Modelo de dados
avatar_url é anulável (nullable). Nulo significa “renderizar o fallback de iniciais”.
Componente compartilhado
@repo/design-system/components/contact-avatar expõe <ContactAvatar> com
size de xs, sm, md, lg. Use-o em qualquer lugar em que um contato seja
listado, para manter o comportamento de fallback consistente.