Cenário 3 — dados entrando no X-Adm¶
Status: Aprovado · Responsável: Gustavo Madruga · Atualizado em: 2026-09-25
Aplica-se a: equipe X-Adm (ERP/ZIM) e quem opera a nuvem.
O que é¶
Um sistema de fora (um parceiro, como a PIED) gera dados que precisam entrar no ERP — por exemplo, pedidos pagos que viram pedidos no X-Adm. O caminho:
- um app do parceiro na nuvem (
pied.<cliente>.xadm.biz) recebe do parceiro e traduz para o formato do X-Adm; - ele entrega ao integrador (
int.<cliente>), que grava nas mesmas tabelas-espelho do cenário 1, marcadas como pendentes de importação; - o PowerSync leva os pendentes ao
integrador-client, um programa Java no servidor do cliente; - o
integrador-clientchama a rotinapAbastdo ZIM, que grava no ERP, e devolve o resultado linha a linha à nuvem.
Clientes neste cenário hoje: Maxsul (pedidos da PIED). O mesmo mecanismo faz a baixa de MDF-e com a Sascar (ver §MDF-e).
sequenceDiagram
participant PIED as PIED (parceiro)
participant APP as pied.<cliente>
participant INT as int.<cliente>
participant PS as ps.<cliente>
participant IC as integrador-client (servidor do cliente)
participant ZIM as ERP X-Adm (pAbast)
PIED->>APP: webhook do pedido (e consulta periódica)
APP->>APP: guarda o original, traduz para o formato X-Adm
APP->>INT: PUT /api/v1/xadm (Origem INT-PIED)
INT->>INT: grava no espelho com cod_retorno = 000 (pendente)
INT->>PS: replicação
PS->>IC: linhas pendentes
IC->>ZIM: dXpEnvio + zimrtmu.exe pAbast
ZIM-->>IC: dXpRetorno (código por linha)
IC->>INT: POST /api/v1/powersync (006 gravado ou 1XX erro)
INT->>PS: status atualizado
PS->>APP: (o app consulta o status pelo integrador)
O status de cada linha: cod_retorno¶
Toda linha que vai para o ERP carrega um código de retorno. É o que se olha para saber onde um pedido está.
cod_retorno |
Significa | Próximo passo |
|---|---|---|
000 |
pendente — ainda não foi ao ERP | o integrador-client pega no próximo ciclo |
001 |
em processamento no integrador-client |
aguardar |
006 |
gravado no X-Adm | fim |
1XX |
erro de dado, definitivo (ex.: 120-Cliente CPF … não cadastrado) |
corrigir a causa e re-armar (ver §Verificação); não volta sozinho |
9XX |
erro temporário | o integrador-client tenta de novo sozinho |
O texto do erro vem em msg_retorno, como o ZIM escreveu.
Linhas que dependem umas das outras (cliente → pedido → itens → fórmula do kit) são agrupadas numa
remessa: o integrador-client só envia ao ERP a remessa completa, para o ERP nunca receber um
item sem o pedido. A remessa fica ABERTA (a caminho), ENTREGUE (tudo 006), TRAVADA (alguma
linha 1XX) ou RESOLVIDA_MANUAL (o operador lançou à mão no X-Adm e fechou).
Pré-requisitos¶
- Base do cliente na nuvem: banco, integrador e PowerSync (Cliente novo, passos 1 a 6 — inclusive o cadastro na Central).
- No integrador do cliente,
CLIENTE_IDeCENTRAL_API_TOKENpreenchidos (sinal de vida dointegrador-client). - No servidor do cliente: Windows 64 bits, Java 8 ou mais novo de 64 bits, saída HTTPS para
ps.<cliente>.xadm.bizeint.<cliente>.xadm.biz. - A rotina
pAbastinstalada no ZIM do cliente (equipe X-Adm), na versão que conhece o fluxo.
Passos¶
1. Definir o que entra e em quais tabelas¶
A equipe X-Adm e a nuvem combinam, por fluxo:
- quais tabelas do X-Adm recebem o dado (na PIED:
propriedades,fones,estoque,contratos,itensped,formulas) e quais campos de cada uma; - a chave de cada registro — sempre a do X-Adm; o código do parceiro entra só como campo de rastreio, nunca como chave;
- o layout de cada tabela no arquivo
dXpEnvioe os códigos de retorno dopAbast— é o contrato pAbast, que a equipe X-Adm valida.
Tabela ou coluna nova segue o mesmo caminho do cenário 1 (§Definir o banco-espelho).
2. O app do parceiro — pied.<cliente>.xadm.biz¶
Cada parceiro tem o seu app, dono das próprias tabelas (pied_*). O da PIED:
- Recebe o webhook da PIED em
POST https://pied.<cliente>.xadm.biz/webhook/piede, de tempos em tempos, consulta a API da PIED para não perder nada. Guarda o original antes de processar. - Só envia pedido pago. O pedido vai para o X-Adm quando o pagamento vira
received. - Traduz para o formato do X-Adm (natureza de operação por UF, kit × produto simples, telefone) e
envia ao integrador com
Origem: "INT-PIED", na ordem cliente → contato → produto → pedido → itens → fórmulas. - Não reenvia o que não mudou (compara o conteúdo) e, se o integrador estiver fora, guarda numa fila e tenta de novo.
- Mostra cada pedido, o seu status e o retorno do ERP no painel
https://pied.<cliente>.xadm.biz/.
Na Maxsul o fluxo está em produção: o pedido pago segue sozinho, sem liberação manual
(PIED_INTEGRACAO_MODO=PRODUCAO). Pendente: as telas do app ainda não pedem login — o gate de
login Google (@xadm.com.br) está planejado. Até lá, o endereço do painel não deve circular fora da
equipe.
Implantação do app — recurso no Coolify, variáveis e a ordem segura de ligar (primeiro só capturar,
depois homologação, depois produção):
Implantação do maxsul-pied ·
Configuração.
A PIED desliga o webhook sozinha
Se uma entrega falhar (app fora do ar, erro), a PIED desativa o webhook e não religa. O app tem um vigia que avisa; o recadastro é manual no painel da PIED: Recadastrar o webhook.
3. O integrador¶
Nada específico a configurar além do Cliente novo — integrador:
o integrador recebe o PUT do app do parceiro exatamente como recebe o do X-Adm, grava as linhas com
cod_retorno = 000 e monta as remessas. Duas regras:
- o
INTEGRADOR_API_TOKENdo app do parceiro é o mesmo do integrador; - a origem nova do parceiro precisa estar na lista de origens conhecidas do integrador, senão os erros
dela não geram alerta (
INT-PIEDjá está).
4. Sincronização: o que o integrador-client enxerga¶
No powersync.yaml do cliente entram as tabelas do fluxo e as remessas vivas. Na Maxsul:
streams:
global:
auto_subscribe: true
queries:
- SELECT * FROM contratos WHERE deleted = false
- SELECT * FROM propriedades WHERE deleted = false
- SELECT * FROM fones WHERE deleted = false
- SELECT * FROM itensped WHERE deleted = false
- SELECT * FROM estoque WHERE deleted = false
- SELECT * FROM formulas WHERE deleted = false
- SELECT * FROM integracao_remessa WHERE (status = 'ABERTA' OR status = 'TRAVADA')
- SELECT * FROM integracao_remessa_item WHERE remessa_id IN (SELECT id FROM integracao_remessa WHERE (status = 'ABERTA' OR status = 'TRAVADA'))
E a chave pública do integrador-client do cliente entra em client_auth (passo 6). Toda mudança
exige publicar o repo do PowerSync.
5. Importação no ERP: integrador-client e pAbast¶
A cada ciclo (na hora em que chega dado novo, e de 5 em 5 minutos como segurança), o
integrador-client:
- junta as linhas com
cod_retorno000ou9XX— só remessas completas, até 999 linhas por lote — e marca como001; - escreve o arquivo
dXpEnviona pasta do X-Adm (largura fixa,windows-1252, uma linha por registro); - executa
zimrtmu.exe pAbastnessa pasta; - espera o ZIM escrever
Iniciou ZimnodXpRetornoe responde com o literal do fluxo (IMPORTA_PIEDna PIED) — a partir daqui o ERP está gravando; - lê o
dXpRetorno: um código e uma mensagem por linha enviada, na mesma ordem; - grava o código de cada linha e devolve à nuvem (
POST https://int.<cliente>.xadm.biz/api/v1/powersync). Sem internet nessa hora, o resultado fica numa fila local e sobe quando a rede voltar.
O lado da equipe X-Adm é a rotina pAbast: ler o dXpEnvio, gravar, e escrever o retorno de
cada linha com o código certo — 006 para gravado, 1XX para erro de dado (com a mensagem), 9XX
para erro que vale tentar de novo. O layout de cada tabela, os literais e os casos de erro estão no
contrato pAbast.
O pAbast precisa aceitar a mesma linha duas vezes
Se o integrador-client cair depois de o ERP começar a gravar e antes de receber o retorno, ele
reenvia a linha no próximo ciclo. Reenviar um pedido já gravado não pode gerar um pedido novo.
6. Instalar o integrador-client¶
Na nuvem, antes de ir ao cliente:
-
Gerar o par de chaves da instalação — a chave privada é a credencial do cliente:
openssl genpkey -algorithm RSA -pkeyopt rsa_keygen_bits:2048 -out <cliente>-private.pem openssl rsa -in <cliente>-private.pem -pubout -out <cliente>-public.pem -
Colocar a pública no
powersync.yamldo cliente (client_auth,kid<cliente>-ps-v1,audience<cliente>) e publicar o repo do PowerSync. - Montar o pacote: o
.jar, ointegrador-client.propertiespreenchido e o<cliente>-private.pem.
No servidor do cliente, numa pasta só (ex.: C:\integrador-client\):
| Arquivo | O que é |
|---|---|
integrador-client.jar |
o programa |
integrador-client.properties |
a configuração (abaixo) |
<cliente>-private.pem |
a credencial — nunca copie, mande por e-mail ou suba em repositório |
rodar.bat |
inicia o programa; cadastrado no Agendador de Tarefas para subir com o Windows |
Configuração mínima:
cliente=<cliente>
powersync.url=https://ps.<cliente>.xadm.biz
jwt.chavePrivada=<cliente>-private.pem
jwt.kid=<cliente>-ps-v1
jwt.issuer=<cliente>-ps
jwt.audience=<cliente>
jwt.subject=<cliente>-ps-java
powersync.upload.url=https://int.<cliente>.xadm.biz/api/v1/powersync
powersync.upload.token=<INTEGRADOR_API_TOKEN do cliente>
zim.executavel=C:/Zim/zimrtmu.exe
zim.diretorio=C:/X-Adm
zim.fluxos=pied
zim.fluxos é obrigatório; valores válidos: pied, abastecimento, encerra-mdfe (vários, separados
por vírgula). Valor inválido faz o programa sair na largada.
Homologar com a equipe X-Adm antes de ligar: rodar java -jar integrador-client.jar --debug,
listar os pendentes e processar um lote acompanhado — processar grava no ERP e devolve o status à
nuvem. Runbook completo, com códigos de saída e problemas comuns:
Instalação do integrador-client.
MDF-e com a Sascar¶
Mesmo mecanismo, outro gatilho. O X-Adm envia o MDF-e aberto ao integrador (cenário 1, origem
PMDFE). O integrador pede ao app compartilhado sascar.xadm.biz que vigie o caminhão; quando a
Sascar indica que ele chegou, o app avisa o integrador, que marca o MDF-e para baixa com
cod_retorno = 000. O integrador-client (fluxo encerra-mdfe) chama o pAbast, que encerra o
MDF-e no ERP. Clientes: Vantroba e Pontual.
Contrato de encerramento de MDF-e.
Verificação¶
| Conferir | Como | Esperado |
|---|---|---|
| Pedido chegou do parceiro | painel https://pied.<cliente>.xadm.biz/ |
pedido listado, status ENVIADO ou CONFIRMADO |
| Pedido no espelho | SELECT pied_x_ped, cod_retorno, msg_retorno FROM contratos WHERE pied_x_ped = '<pedido>'; |
a linha, 000 antes do ERP e 006 depois |
| Remessas travadas | GET https://int.<cliente>.xadm.biz/api/v1/integracao/remessas?status=TRAVADA (Bearer) |
vazio; senão, cada item em 1XX com a mensagem do ERP |
integrador-client vivo |
aba Deploy da Central (central.xadm.biz) |
instalação do cliente com sinal de vida recente (alerta após 6 horas úteis sem sinal) |
Log do integrador-client |
logs\integrador-client.log na pasta do programa |
ciclos sem erro |
Destravar uma remessa (1XX): corrigir a causa (por exemplo, o cadastro que faltava no X-Adm) e
re-armar: POST https://int.<cliente>.xadm.biz/api/v1/xadm/retorno/pedido/reenfileirar?chave=<pedido>
(Bearer) — as linhas voltam a 000. Se o pedido foi lançado à mão no X-Adm, fechar pelo botão
Importado manualmente no painel do app do parceiro.
Problemas comuns¶
| Sintoma | Causa provável | O que fazer |
|---|---|---|
integrador-client com 401 PSYNC_S2101 |
chave privada não corresponde à pública do powersync.yaml (ou kid/audience diferentes) |
conferir o par; republicar o PowerSync |
| Status não sobe para a nuvem | powersync.upload.token diferente do INTEGRADOR_API_TOKEN |
conferir o token |
Todo lote fica em 001 e volta |
ZIM não respondeu Iniciou Zim em 3 s — normalmente licença ZIM ou pAbast ausente |
conferir o ZIM com a equipe X-Adm |
Linha 120-… não cadastrado |
o ERP recebeu um filho sem o pai (cliente, produto, pedido) | cadastrar/corrigir e re-armar |
| Pedidos novos pararam de chegar da PIED | webhook desativado pela PIED | recadastrar o webhook |
App do parceiro recebe 401 do integrador |
INTEGRADOR_API_TOKEN ausente ou diferente no app |
conferir a variável no Coolify; reenviar a fila pelo painel |