4) Sincronização offline

Esta rota envia ao ERP os registros criados offline no aplicativo e recebe atualizações do produtor, vínculo atual com o franqueado e controle de versão do aplicativo.

Auth: X-APP-KEY + X-DEVICE-TOKEN Offline-first Retirada de produto Aplicação com trilha GPS Obrigatório: app_version

Objetivo deste fluxo

A sincronização offline do G10 Bio Produtor também poderá receber os dados das entregas pendentes destinadas ao produtor, incluindo os QR Codes individuais necessários para a conferência opcional dos produtos. Os dados recebidos devem ser armazenados no SQLite para permitir a operação offline.

A rota também sincroniza sessões de aplicação, pontos GPS coletados a cada 3 segundos, dados atualizados do produtor, vínculo com o franqueado e versão do aplicativo.

Atualização — 01/09/2026

Sincronização das entregas pendentes do produtor

A resposta da sincronização deverá passar a disponibilizar também as entregas pendentes destinadas ao produtor autenticado.

Cada entrega pendente deverá conter o QR Code único da entrega e o manifesto físico dos produtos vinculados àquela entrega.

Esses dados serão utilizados quando o produtor optar pela conferência individual dos produtos antes de confirmar o recebimento.

Estrutura esperada na resposta

"entregas_pendentes": {
  "snapshot_completo": true,
  "entregas": [
    {
      "id_entrega": 123,
      "codigo_entrega": "ENT-ABC123",
      "competencia": "2026-09",
      "status": "AGUARDANDO_CONFIRMACAO",
      "itens": [
        {
          "id_remessa_item": 501,
          "codigo_qr": "G10BIO:ITEM:AAA",
          "produto": "G10 VITALIS",
          "volume_embalagem": 20
        },
        {
          "id_remessa_item": 502,
          "codigo_qr": "G10BIO:ITEM:BBB",
          "produto": "G10 VITALIS",
          "volume_embalagem": 4
        }
      ]
    }
  ]
}

Tratamento no aplicativo

  • Salvar no SQLite as entregas pendentes retornadas pelo ERP.
  • Salvar também os QR Codes individuais pertencentes a cada entrega.
  • O manifesto deve ficar disponível offline depois de uma sincronização bem-sucedida.
  • O aplicativo somente poderá utilizar na conferência os QR Codes pertencentes às entregas do próprio produtor autenticado.
  • Uma nova sincronização deve atualizar o snapshot local das entregas pendentes.
  • Entregas que deixarem de ser retornadas pelo ERP como pendentes devem ser removidas ou marcadas como encerradas no cache local.

Uso do manifesto

O manifesto não altera o fluxo normal da sincronização. Ele apenas permite que o produtor tenha duas formas de confirmar o recebimento:

1. QR Code único da entrega
   → confirmação rápida

2. QR Codes individuais das embalagens
   → conferência detalhada
   → comparação com o manifesto salvo no SQLite

A conferência individual deve funcionar mesmo sem internet, desde que o manifesto da entrega tenha sido sincronizado anteriormente.

Como funciona no aplicativo

  1. Toda ação é salva primeiro no SQLite.
  2. Cada evento recebe um client_event_id único.
  3. Havendo internet, o app tenta enviar imediatamente.
  4. Sem internet ou em caso de falha, o evento permanece na fila local.
  5. Quando o app voltar a ficar online, chama f=sincronizacao_offline.
  6. O ERP confirma os eventos processados.
  7. O app remove da fila somente os eventos confirmados.
  8. O app atualiza localmente os dados do produtor e o vínculo ativo.

Endpoint

POST https://agroecologia.grupoekos.com.br/router/action.php

Headers obrigatórios

X-APP-KEY: <APP_KEY_FIXA_DO_APP_PRODUTOR>
X-DEVICE-TOKEN: <DEVICE_TOKEN_DO_APARELHO>

Body

action=apiG10bio_produtor
f=sincronizacao_offline
app_version=1.0.0
last_sync_at=YYYY-MM-DD HH:MM:SS
eventos_retirada=<JSON>
sessoes_aplicacao=<JSON>
pontos_aplicacao=<JSON>
Campo Obrigatório Descrição
app_version Sim Versão instalada no aparelho.
last_sync_at Não Data e hora da última sincronização concluída.
eventos_retirada Não Lista JSON com eventos pendentes de retirada de produto.
sessoes_aplicacao Não Lista JSON com sessões de aplicação iniciadas ou finalizadas.
pontos_aplicacao Não Lista JSON com pontos GPS coletados durante a aplicação.

Evento: retirada de produto

[
  {
    "client_event_id": "550e8400-e29b-41d4-a716-446655440000",
    "qrcode_embalagem": "G10BIO_PRODUTO_ABC123",
    "data": "2026-07-23",
    "hora": "08:30:00",
    "latitude": -21.864500,
    "longitude": -47.499700,
    "device_name": "Celular do produtor"
  }
]

O id_franqueado não deve ser confiado somente ao valor enviado pelo app. A API deve identificar o franqueado pelo vínculo ativo do produtor associado ao X-DEVICE-TOKEN.

Evento: sessão de aplicação

[
  {
    "client_event_id": "650e8400-e29b-41d4-a716-446655440001",
    "qrcode_embalagem": "G10BIO_PRODUTO_ABC123",
    "data_inicio": "2026-07-23",
    "hora_inicio": "09:00:00",
    "data_fim": "2026-07-23",
    "hora_fim": "10:20:00",
    "latitude_inicio": -21.864500,
    "longitude_inicio": -47.499700,
    "latitude_fim": -21.865100,
    "longitude_fim": -47.500200,
    "status": "FINALIZADA",
    "device_name": "Celular do produtor"
  }
]

Pontos GPS da aplicação

Durante a aplicação, o app deve registrar localmente um ponto a cada 3 segundos. Os pontos devem ser enviados em lotes para evitar timeout.

[
  {
    "client_event_id": "750e8400-e29b-41d4-a716-446655440010",
    "aplicacao_client_event_id": "650e8400-e29b-41d4-a716-446655440001",
    "ordem": 1,
    "data": "2026-07-23",
    "hora": "09:00:03",
    "latitude": -21.864510,
    "longitude": -47.499710,
    "accuracy": 8.5,
    "speed": 2.1,
    "heading": 180
  }
]
  • Cada ponto deve possuir seu próprio client_event_id.
  • aplicacao_client_event_id vincula o ponto à sessão principal.
  • O app deve manter a ordem dos pontos.
  • Em caso de falha, reenviar com os mesmos identificadores.

Resposta esperada — HTTP 200

{
  "success": true,
  "msg": "Sincronização realizada com sucesso.",
  "data": {
    "server_time": "2026-07-23 10:30:00",
    "device_id": 123,
    "cliente_id": 550,
    "account_type": "produtor",
    "id_franquia": 1,
    "id_franqueado": 10,
    "id_vinculo_produtor": 85,
    "vinculo_atual": {
      "situacao": "ATIVO",
      "data_inicio": "2026-07-01",
      "data_fim": null
    },
    "dados_produtor": {
      "nome": "José da Silva",
      "telefone": "(18) 99999-9999",
      "cidade": "Presidente Prudente",
      "uf": "SP"
    },
    "versao_app": {
      "versao_instalada": "1.0.0",
      "versao_atual": "1.0.1",
      "atualizado": 0,
      "atualizacao_obrigatoria": 0,
      "bloqueado_por_versao": 0,
      "observacao": "Nova versão disponível."
    },
        "eventos_confirmados": {
      "retiradas": [
        "550e8400-e29b-41d4-a716-446655440000"
      ],
      "sessoes_aplicacao": [
        "650e8400-e29b-41d4-a716-446655440001"
      ],
      "pontos_aplicacao": [
        "750e8400-e29b-41d4-a716-446655440010"
      ]
    },

    "entregas_pendentes": {
      "snapshot_completo": true,
      "entregas": []
    }
  }
}

Como tratar a resposta

Controle de vínculo com o franqueado

A sincronização deve sempre retornar o vínculo ativo identificado pelo ERP.

Caso a franqueadora aprove uma transferência, o app receberá o novo id_franqueado na próxima sincronização e deverá atualizar o contexto local.

SE id_franqueado retornado for diferente do salvo localmente
→ atualizar id_franqueado
→ atualizar id_franquia
→ atualizar id_vinculo_produtor
→ manter o mesmo device_token
→ continuar usando o app normalmente

Controle de versão do aplicativo

  • O app deve enviar app_version
  • Se atualizacao_obrigatoria=0, apenas exibir aviso.
  • Se atualizacao_obrigatoria=1 e atualizado=0, bloquear novas operações.
  • Eventos já salvos no SQLite não devem ser apagados.

Erros comuns

Em qualquer falha, manter os eventos no SQLite e tentar novamente depois.

NÃO IMPLEMENTAR nesta sincronização

  • Download indiscriminado de QR Codes. É permitido sincronizar somente os QR Codes vinculados às entregas pendentes do próprio produtor para fins de conferência.
  • Cache de QR Codes com TTL.
  • Blocos de fazendas ou geocercas do Regenera G10.
  • Perfis colaborador ou produtor_funcionario.
  • Preparação Eko´s Bio.
  • Coleta de análise.
  • Página pública.
  • Chamadas ao controlador apiG10bio_franqueado.

Exemplo de chamada cURL

curl -X POST "https://agroecologia.grupoekos.com.br/router/action.php" \
  -H "Content-Type: application/x-www-form-urlencoded; charset=UTF-8" \
  -H "X-APP-KEY: SUA_APP_KEY" \
  -H "X-DEVICE-TOKEN: SEU_DEVICE_TOKEN" \
  --data-urlencode "action=apiG10bio_produtor" \
  --data-urlencode "f=sincronizacao_offline" \
  --data-urlencode "app_version=1.0.0" \
  --data-urlencode "last_sync_at=2026-07-23 08:00:00" \
  --data-urlencode "eventos_retirada=[]" \
  --data-urlencode "sessoes_aplicacao=[]" \
  --data-urlencode "pontos_aplicacao=[]"