Raphael Serafim· Publicado em 28 de setembro de 2026· 9 min de leitura

Como gerenciar centenas de grupos de WhatsApp pela API (em lote)

Inventário, padronização em lote, auditoria de admins e limpeza de grupos mortos: como gerenciar centenas de grupos de WhatsApp com a API não oficial.

Ver como Markdown

Para gerenciar centenas de grupos de WhatsApp pela API não oficial, trate os grupos como um inventário: liste tudo com GET /{key}/groups, guarde no seu banco, audite quem é admin em cada um com GET /{key}/groups/{id}/members, aplique padronizações em lote por uma fila com espaçamento e limpe os grupos mortos com DELETE /{key}/groups/{id}. O WhatsApp no celular não foi feito para isso; um script de cinquenta linhas foi.

Agência que cuida de grupos de clientes, rede de franquias com um grupo por loja, escola com grupo por turma, infoprodutor com grupos de várias campanhas. A partir de algumas dezenas de grupos, a pergunta deixa de ser "como criar um grupo" e vira "quais grupos eu tenho, em quais ainda sou admin e quais já morreram". Este guia responde essa pergunta.

A camada não oficial da WAME é independente e não é afiliada, endossada ou suportada pelo WhatsApp ou pela Meta. O uso é de responsabilidade de quem envia.

Passo 1: o inventário

Tudo começa com uma foto do estado atual. GET /{key}/groups devolve os grupos em que a instância é membro, com metadados:

bash
curl "https://us.api-wa.me/SUA_KEY/groups"

Grave isso numa tabela sua. O WhatsApp é a fonte da verdade sobre o grupo; o seu banco é a fonte da verdade sobre por que o grupo existe:

ColunaDe onde vem
id (termina em @g.us)API
nome, descricaoAPI
membros, admins/groups/{id}/members
somos_adminauditoria (abaixo)
cliente, projeto, responsavelvocê
status (ativo, arquivar, sair)você
ultima_atividadewebhook (abaixo)

As colunas "suas" são as que fazem a diferença. Um grupo sem dono no seu cadastro é o primeiro candidato a virar grupo órfão.

javascript
const BASE = 'https://us.api-wa.me/SUA_KEY';
const esperar = (ms) => new Promise((r) => setTimeout(r, ms));
const get = (c) => fetch(`${BASE}${c}`).then((r) => r.json());

async function sincronizarInventario() {
  const r = await get('/groups');
  // A lista vem em `groups`; cada item traz id, subject, desc, announce,
  // restrict e size (quantidade de participantes).
  const grupos = r.groups ?? [];

  for (const g of grupos) {
    await db.grupos.upsert({ id: g.id, nome: g.subject, membros: g.size, vistoEm: new Date() });
  }
  // Grupo no banco que não veio na lista: a instância saiu ou foi removida.
  await db.grupos.marcarAusentes(new Date());
}

Rode a sincronização uma vez por dia. Ela é leitura pura e barata.

Passo 2: auditoria de admins

Quase toda operação de gestão exige que o número seja admin: mudar nome e foto, trocar configurações, adicionar e remover gente, aprovar pedidos. Com o tempo, admins saem, alguém rebaixa o número por engano, o grupo muda de mãos. A auditoria descobre isso antes da operação falhar:

javascript
const MEU_NUMERO = '5511999990000';

async function auditar() {
  const grupos = await db.grupos.ativos();
  for (const g of grupos) {
    const r = await get(`/groups/${g.id}/members`);
    // A lista vem em `data`. Cada participante tem `id` e, se for admin,
    // `admin: "admin"` ou `admin: "superadmin"`. Em grupos com LID, o `id` é o LID
    // e o telefone real vem em `phoneNumber`.
    const membros = r.data ?? [];
    const admins = membros.filter((m) => m.admin);

    await db.grupos.atualizar(g.id, {
      membros: membros.length,
      admins: admins.map((a) => a.id),
      somosAdmin: admins.some((a) => String(a.id).startsWith(MEU_NUMERO)),
    });
    await esperar(3000);
  }
}

O relatório que sai daqui responde três perguntas úteis:

  • Em quais grupos perdemos admin? Precisam que alguém do time promova o número de volta.
  • Quais grupos não têm nenhum admin do nosso time? Risco de perder o controle.
  • Quem é admin em grupos demais? Ex-funcionário que continua admin em quarenta grupos de clientes é problema de segurança.

Para promover e rebaixar, use PATCH /{key}/groups/{id}/role?action=promote ou demote com a lista de participantes. Alguns participantes podem aparecer como LID; veja como tratar LID.

Passo 3: padronização em lote

Com o inventário e a auditoria em mãos, as mudanças em massa ficam seguras. Exemplos comuns: padronizar nomes ("Cliente X | Suporte"), atualizar a descrição com o novo horário de atendimento, trocar a foto pela nova marca.

javascript
async function padronizar(grupos, gerarNome, descricao, fotoUrl) {
  for (const g of grupos.filter((g) => g.somosAdmin)) {
    await fetch(`${BASE}/groups/${g.id}`, {
      method: 'PUT',
      headers: { 'Content-Type': 'application/json' },
      body: JSON.stringify({ name: gerarNome(g), description: descricao }),
    });

    if (fotoUrl) {
      await fetch(`${BASE}/groups/${g.id}/picture`, {
        method: 'PUT',
        headers: { 'Content-Type': 'application/json' },
        body: JSON.stringify({ url: fotoUrl }),
      });
    }
    await esperar(10000 + Math.random() * 10000); // 10 a 20s por grupo
  }
}

O PUT /groups/{id} espera name e description juntos, então mande os dois mesmo quando só um muda. E repare no filtro somosAdmin: tentar alterar grupo em que você não é admin só gera erro.

O espaçamento é o ponto central. Duzentos grupos a 15 segundos cada levam menos de uma hora — e não há motivo para ter pressa numa troca de descrição. O que chama atenção é uma instância alterando dezenas de grupos por minuto.

Passo 4: configurações por política

Defina a política por tipo de grupo e aplique pelo inventário:

Tipoannouncementlocked
Avisos (clientes, alunos)simsim
Suporte de um clientenãosim
Comunidade abertanãosim
Time internonãonão
javascript
const POLITICA = {
  avisos: ['announcement', 'locked'],
  suporte: ['not_announcement', 'locked'],
  interno: ['not_announcement', 'unlocked'],
};

async function aplicarPolitica(g) {
  for (const s of POLITICA[g.tipo] ?? []) {
    await fetch(`${BASE}/groups/${g.id}?setting=${s}`, { method: 'PATCH' });
    await esperar(2000);
  }
}

Rodar isso periodicamente também corrige o grupo em que alguém do cliente mudou a configuração sem querer.

Passo 5: atividade e grupos mortos

O webhook de grupos diz quando cada grupo teve movimento. No formato meta, toda mensagem de grupo traz group_id; basta atualizar ultima_atividade:

javascript
app.post('/webhook/grupos', (req, res) => {
  res.sendStatus(200);
  const msg = req.body?.entry?.[0]?.changes?.[0]?.value?.messages?.[0];
  if (msg?.group_id) db.grupos.tocar(msg.group_id, new Date());
});

Com isso, "grupo morto" vira consulta: nenhuma mensagem em 60 dias, nenhum dono no cadastro, poucos membros. Para métricas mais finas — entradas, saídas, membros silenciosos — veja métricas de grupo.

Passo 6: limpeza

Grupo morto custa pouco, mas polui o inventário e as métricas. A limpeza segue um ritual simples:

  1. Marque como arquivar e avise o responsável (se houver).
  2. Depois de um prazo, atualize a descrição avisando que o grupo foi encerrado e deixe em announcement.
  3. Saia com DELETE /{key}/groups/{id} e registre data e motivo.
bash
curl -X DELETE "https://us.api-wa.me/SUA_KEY/groups/[email protected]"

Uma saída por vez, com intervalo. Sair de cinquenta grupos no mesmo minuto é o tipo de rajada que não tem motivo para existir.

A fila que segura tudo

Todas as operações acima passam pelo mesmo princípio: uma fila por instância, uma operação por vez, espaçamento com variação. Se a API responder 429, a fila espera e continua de onde parou. Se o webhook de conexão trouxer o evento de saúde recomendando pausa, a fila para inteira até alguém olhar.

A WAME já cuida da camada de conexão: identidade de dispositivo própria por instância, envios com tempo humano, reconexão espalhada e o alerta de saúde. Com a sua fila respeitando o ritmo, gerir centenas de grupos tem taxa de bloqueio muito baixa. O desenho de fila, retry e backoff está em fila, rate limit e retry.

Um diagnóstico rápido

Se as operações de grupo começarem a falhar em série, antes de investigar código, rode o diagnóstico:

bash
curl "https://us.api-wa.me/SUA_KEY/groups/readiness"

Na instância não oficial, os grupos funcionam pela sessão conectada — então falha em série quase sempre é sessão caída ou número sem admin. Na oficial, o mesmo endpoint lista os bloqueios que impedem o uso de grupos.

Onde cada peça se encaixa

Esta é a camada de operação. Para criar e configurar grupos individualmente, o ponto de partida é automatizar grupos pela API. Se os seus grupos se organizam por tema, uma comunidade do WhatsApp agrupa tudo sob um guarda-chuva. E para moderar em todos os grupos com a mesma regra, veja anti-link e anti-spam.

Conclusão

Gerenciar centenas de grupos pela API não oficial da WAME é, no fundo, gestão de inventário: listar com GET /groups, auditar admins com /members, padronizar nome, descrição, foto e configurações em lote, acompanhar atividade pelo webhook e sair dos grupos mortos com critério. O que faz isso funcionar sem susto é a fila com espaçamento, que trata 429 e o evento de saúde como ordens de pausa. Com essa base, cem grupos dão o mesmo trabalho que dez. Os endpoints completos estão na documentação.

Pronto para automatizar seu WhatsApp?

Crie sua conta gratuita e comece a enviar mensagens pela API em minutos.

Começar grátis

Perguntas frequentes

Como listar todos os grupos de um número pela API?+

Com GET /{key}/groups, que devolve todos os grupos em que a instância é membro, com os metadados de cada um. Para os participantes e seus papéis (admin, superadmin ou membro), use GET /{key}/groups/{id}/members em cada grupo.

Dá para mudar nome, descrição e foto de vários grupos de uma vez?+

Sim, em lote pelo seu código: PUT /{key}/groups/{id} para nome e descrição e PUT /{key}/groups/{id}/picture para a foto, um grupo de cada vez, com alguns segundos entre as chamadas. O número precisa ser admin de cada grupo.

Como descobrir em quais grupos o número não é mais admin?+

Rode uma auditoria: para cada grupo do inventário, busque os membros e verifique o papel do número da instância. Grupos em que ele virou membro comum não aceitam mudanças de configuração, e grupos sem nenhum admin do seu time merecem atenção.

Como sair de grupos que não uso mais?+

Com DELETE /{key}/groups/{id}, que faz a instância sair do grupo. Antes de sair, registre no seu inventário o motivo e a data. Faça a limpeza em lote com espaçamento, nunca dezenas de saídas no mesmo minuto.

Gerenciar muitos grupos aumenta o risco de bloqueio?+

O número de grupos não é o problema; o ritmo é. Operações em rajada — dezenas de alterações por minuto, mesma mensagem em todos os grupos ao mesmo tempo — parecem automação abusiva. Com fila e espaçamento, a gestão em lote tem taxa de bloqueio muito baixa.

Continue lendo