<%= icone :telefone, espaco: false %> WhatsApp — conexão

Pareia o número da empresa com este servidor lendo um QR code, como no WhatsApp Web.

<%= render 'shared/flash' %> <%# O aviso fica na TELA, não só no código: quem parear precisa saber o que está aceitando. %>

<%= icone :alerta, cor: nil, tamanho: 'w-5 h-5', espaco: false %> Este canal não é oficial.

A conexão por QR usa a porta do WhatsApp Web por engenharia reversa. É gratuita e ilimitada, mas está fora dos Termos do WhatsApp — a Meta pode banir o número sem aviso. Use um chip dedicado, nunca o número principal da operação.

Disparo em rajada é o que mais causa banimento. O intervalo entre mensagens fica em <%= link_to 'Configurações → Notificações', admin_configuracao_notificacao_path, data: { turbo: false }, class: 'underline hover:text-white transition-colors' %> (hoje: <%= @config.intervalo_envio %>s).

<% if @estado['conectado'] %>
<%# Ponto pulsante: à distância, é o que diz "está no ar" sem ler o texto. %>

Conectado

Número <%= @estado['numero'] %> <% if @config.whatsapp_conectado_em %> · desde <%= l @config.whatsapp_conectado_em, format: :short rescue @config.whatsapp_conectado_em %> <% end %>

<%= form_with url: testar_admin_whatsapp_sessao_path, method: :post, data: { turbo: false }, class: 'flex flex-wrap items-end gap-3' do |f| %>
<%= f.label :numero, 'Enviar teste para', class: 'block text-sm font-medium text-gray-300 mb-1.5' %> <%= f.text_field :numero, placeholder: '(11) 92005-1157', class: 'w-full px-4 py-3 bg-[#0a0a0a] border border-white/10 rounded-xl text-white placeholder-gray-600 focus:outline-none focus:border-[#f97316] focus:ring-1 focus:ring-[#f97316] transition-colors' %>
<%= f.submit 'Enviar teste', class: 'px-6 py-3 bg-[#f97316] hover:bg-orange-500 text-white font-semibold rounded-xl transition-colors cursor-pointer min-h-[48px]' %> <% end %>
<%= button_to desconectar_admin_whatsapp_sessao_path, method: :delete, form: { data: { turbo_confirm: 'Isso encerra a sessão e para TODOS os envios de WhatsApp até você ler o QR de novo. Confirmar?' } }, class: 'inline-flex items-center gap-2 px-5 py-2.5 rounded-xl text-sm border border-red-500/30 text-red-400 hover:bg-red-900/20 hover:border-red-500/50 transition-colors cursor-pointer' do %> <%= icone :sair, cor: nil, tamanho: 'w-4 h-4', espaco: false %> Desconectar <% end %>
<% elsif @estado['qr'].present? %>
Aguardando leitura

Leia o QR code

No celular do chip dedicado: WhatsApp → Aparelhos conectadosConectar um aparelho → aponte para o código abaixo.

<%# O QR expira em ~20s e a ponte gera outro — o polling abaixo troca a imagem sozinho, senão o operador ficaria lendo um código morto. %> QR code do WhatsApp

O código se renova sozinho a cada poucos segundos.

<% else %>

Desconectado

<%= @estado['erro'].presence || @estado['ultimo_erro'].presence || 'A ponte ainda não gerou um QR code. Aguarde alguns segundos e recarregue.' %>

<% unless @cliente.configurado? %>

Falta configurar a ponte: defina WHATSAPP_TOKEN no .env (o mesmo valor do container whatsapp) e suba os containers.

<% end %>
<% end %>