Pular para o conteúdo principal
A reconciliação no mundo real frequentemente envolve transações que não correspondem 1:1. Um único pagamento pode cobrir múltiplas faturas, ou vários depósitos podem se consolidar em uma única entrada bancária. O Matcher lida com esses cenários complexos através de correspondência dividida e agregada.

Visão geral


O Matcher permite quatro padrões de correspondência:
PadrãoDescriçãoExemplo
1:1Uma origem para um destinoPagamento de fatura única
1:NUma origem para vários destinosPagamento em lote cobrindo faturas
N:1Várias origens para um destinoDepósitos consolidados no banco
N:MVárias origens para vários destinosCompensação complexa

Habilitando correspondência complexa


Configuração de contexto

Habilite a correspondência dividida e agregada no nível do contexto:
cURL
curl -X PATCH "https://api.matcher.example.com/v1/config/contexts/{contextId}" \
 -H "Authorization: Bearer $TOKEN" \
 -H "Content-Type: application/json" \
 -d '{
   "settings": {
     "matching": {
       "allow_split": true,
       "allow_aggregate": true,
       "allow_many_to_many": false,
       "max_transactions_per_group": 20,
       "require_full_allocation": true
     }
   }
 }'

Resposta

{
  "id": "{contextId}",
  "name": "Payment Reconciliation",
  "settings": {
    "matching": {
      "allow_split": true,
      "allow_aggregate": true,
      "allow_many_to_many": false,
      "max_transactions_per_group": 20,
      "require_full_allocation": true
    }
  }
}

Configurações de correspondência

ConfiguraçãoTipoPadrãoDescrição
allow_splitBooleanfalseHabilita correspondência 1:N
allow_aggregateBooleanfalseHabilita correspondência N:1
allow_many_to_manyBooleanfalseHabilita correspondência N:M
max_transactions_per_groupInteger10Máximo de transações em um grupo
require_full_allocationBooleantrueRequer alocação de 100%
partial_match_thresholdDecimal0.95Alocação mínima para parcial (95%)

Correspondência dividida 1:N


Uma transação de origem corresponde a múltiplas transações de destino.

Casos de uso comuns

  • Pagamento em lote: Uma única transferência cobrindo múltiplas faturas
  • Folha de pagamento: Um débito bancário para múltiplos pagamentos de salário
  • Liquidação: Um pagamento de gateway para múltiplos pedidos

Exemplo: pagamento de faturas em lote

Origem (Extrato Bancário):
IDValorReferência
bank_001$15.000,00BULK-PAY-2024-001
Destinos (Lançamentos Contábeis):
IDValorFatura
inv_001$5.000,00INV-2024-001
inv_002$7.500,00INV-2024-002
inv_003$2.500,00INV-2024-003
Resultado: Correspondência 1:3 com alocação total

API: criar correspondência dividida

cURL
curl -X POST "https://api.matcher.example.com/v1/matching/manual" \
 -H "Authorization: Bearer $TOKEN" \
 -H "Content-Type: application/json" \
 -d '{
   "contextId": "{contextId}",
   "type": "SPLIT",
   "source_transactions": [
     {
       "transaction_id": "bank_001",
       "amount": 15000.0
     }
   ],
   "target_transactions": [
     {
       "transaction_id": "inv_001",
       "allocated_amount": 5000.0
     },
     {
       "transaction_id": "inv_002",
       "allocated_amount": 7500.0
     },
     {
       "transaction_id": "inv_003",
       "allocated_amount": 2500.0
     }
   ]
 }'

Resposta

{
  "match_id": "match_split_001",
  "type": "SPLIT",
  "status": "PROPOSED",
  "confidence": 95,
  "source": {
    "transaction_count": 1,
    "total_amount": 15000.0,
    "allocated_amount": 15000.0,
    "allocation_percent": 100.0
  },
  "targets": {
    "transaction_count": 3,
    "total_amount": 15000.0,
    "allocated_amount": 15000.0,
    "allocation_percent": 100.0
  },
  "residual": 0.0,
  "transactions": [
    {
      "id": "bank_001",
      "role": "SOURCE",
      "amount": 15000.0,
      "allocated": 15000.0
    },
    {
      "id": "inv_001",
      "role": "TARGET",
      "amount": 5000.0,
      "allocated": 5000.0
    },
    {
      "id": "inv_002",
      "role": "TARGET",
      "amount": 7500.0,
      "allocated": 7500.0
    },
    {
      "id": "inv_003",
      "role": "TARGET",
      "amount": 2500.0,
      "allocated": 2500.0
    }
  ],
  "created_at": "2024-01-20T10:00:00Z"
}

Correspondência agregada N:1


Múltiplas transações de origem correspondem a uma transação de destino.

Casos de uso comuns

  • Depósitos bancários: Múltiplos cheques depositados como um único crédito
  • Liquidações de cartão: Lote diário de transações como um único depósito
  • Consolidação de caixa: Múltiplos recebimentos de caixa registradora para um depósito

Exemplo: depósito consolidado

Origens (Ponto de Venda):
IDValorCaixa
pos_001$1.250,00REG-01
pos_002$980,00REG-02
pos_003$1.770,00REG-03
Destino (Extrato Bancário):
IDValorReferência
bank_002$4.000,00DEPOSIT-20240120
Resultado: Correspondência 3:1 com alocação total

API: criar correspondência agregada

cURL
curl -X POST "https://api.matcher.example.com/v1/matching/manual" \
 -H "Authorization: Bearer $TOKEN" \
 -H "Content-Type: application/json" \
 -d '{
   "contextId": "{contextId}",
   "type": "AGGREGATE",
   "source_transactions": [
     {
       "transaction_id": "pos_001",
       "allocated_amount": 1250.0
     },
     {
       "transaction_id": "pos_002",
       "allocated_amount": 980.0
     },
     {
       "transaction_id": "pos_003",
       "allocated_amount": 1770.0
     }
   ],
   "target_transactions": [
     {
       "transaction_id": "bank_002",
       "amount": 4000.0
     }
   ]
 }'

Resposta

{
  "match_id": "match_agg_001",
  "type": "AGGREGATE",
  "status": "PROPOSED",
  "confidence": 92,
  "source": {
    "transaction_count": 3,
    "total_amount": 4000.0,
    "allocated_amount": 4000.0,
    "allocation_percent": 100.0
  },
  "targets": {
    "transaction_count": 1,
    "total_amount": 4000.0,
    "allocated_amount": 4000.0,
    "allocation_percent": 100.0
  },
  "residual": 0.0
}

Correspondência N:M muitos-para-muitos


Múltiplas transações de origem correspondem a múltiplas transações de destino. Este é o padrão mais complexo e requer o solucionador de grafo.

Casos de uso comuns

  • Compensação intercompany: Múltiplas faturas compensadas contra múltiplos pagamentos
  • Liquidações de negociação: Compensação complexa com preenchimentos parciais
  • Reconhecimento de receita: Múltiplas entregas contra múltiplos adiantamentos

Exemplo: compensação intercompany

Origens (Contas a Pagar da Empresa A):
IDValorReferência
pay_001$10.000,00IC-PAY-001
pay_002$8.000,00IC-PAY-002
Destinos (Contas a Receber da Empresa A):
IDValorReferência
rec_001$12.000,00IC-REC-001
rec_002$6.000,00IC-REC-002
Resultado: Correspondência 2:2, $18.000 total correspondido

API: criar correspondência N:M

cURL
curl -X POST "https://api.matcher.example.com/v1/matching/manual" \
 -H "Authorization: Bearer $TOKEN" \
 -H "Content-Type: application/json" \
 -d '{
   "contextId": "{contextId}",
   "type": "MANY_TO_MANY",
   "source_transactions": [
     {
       "transaction_id": "pay_001",
       "allocated_amount": 10000.0
     },
     {
       "transaction_id": "pay_002",
       "allocated_amount": 8000.0
     }
   ],
   "target_transactions": [
     {
       "transaction_id": "rec_001",
       "allocated_amount": 12000.0
     },
     {
       "transaction_id": "rec_002",
       "allocated_amount": 6000.0
     }
   ]
 }'

Rastreamento de alocação


O Matcher rastreia quanto de cada transação foi alocado para correspondências.

Status de alocação de transação

StatusDescrição
UNALLOCATEDSem alocação (0%)
PARTIALLY_ALLOCATEDAlocação parcial (1-99%)
FULLY_ALLOCATEDAlocação completa (100%)

Visualizar alocação de transação

Consulte grupos de correspondência para visualizar detalhes de alocação para transações dentro de uma execução de correspondência.
cURL
curl -X GET "https://api.matcher.example.com/v1/matching/runs/{runId}/groups" \
 -H "Authorization: Bearer $TOKEN"

Resposta (exemplo de alocação)

{
  "transaction_id": "bank_001",
  "total_amount": 15000.0,
  "currency": "USD",
  "allocation_status": "FULLY_ALLOCATED",
  "allocations": [
    {
      "match_id": "match_split_001",
      "allocated_amount": 15000.0,
      "allocation_percent": 100.0,
      "status": "CONFIRMED"
    }
  ],
  "available_amount": 0.0,
  "available_percent": 0.0
}

Exemplo de alocação parcial

Transação com valor não alocado restante:
{
  "transaction_id": "bank_003",
  "total_amount": 10000.0,
  "allocation_status": "PARTIALLY_ALLOCATED",
  "allocations": [
    {
      "match_id": "match_002",
      "allocated_amount": 7500.0,
      "allocation_percent": 75.0,
      "status": "CONFIRMED"
    }
  ],
  "available_amount": 2500.0,
  "available_percent": 25.0
}

Correspondências parciais


Por padrão, o Matcher requer alocação total. Habilite correspondência parcial para cenários onde a correspondência completa não é possível.

Habilitar correspondência parcial

{
  "settings": {
    "matching": {
      "require_full_allocation": false,
      "partial_match_threshold": 0.9,
      "partial_match_behavior": "propose_with_residual"
    }
  }
}

Comportamentos de correspondência parcial

ComportamentoDescrição
propose_with_residualCriar correspondência, rastrear residual
create_exceptionCriar exceção para porção não correspondida
hold_for_reviewReter até chegarem transações adicionais

Resposta de correspondência parcial

{
  "match_id": "match_partial_001",
  "type": "SPLIT",
  "status": "PROPOSED",
  "confidence": 78,
  "source": {
    "total_amount": 10000.0,
    "allocated_amount": 9500.0,
    "allocation_percent": 95.0
  },
  "targets": {
    "total_amount": 9500.0,
    "allocated_amount": 9500.0,
    "allocation_percent": 100.0
  },
  "residual": {
    "amount": 500.0,
    "percent": 5.0,
    "status": "UNALLOCATED",
    "exception_id": "exc_residual_001"
  }
}

Solucionador de grafo


Para cenários N:M complexos, o Matcher usa um solucionador de grafo bipartido para encontrar correspondências ótimas.

Como funciona

  1. Construir Grafo: Criar grafo bipartido com origens e destinos como nós
  2. Pesos das Arestas: Calcular confiança de correspondência como pesos das arestas
  3. Resolver: Encontrar correspondência de peso máximo
  4. Alocar: Distribuir valores entre pares correspondidos

Configuração do solucionador de grafo

{
  "settings": {
    "graph_solver": {
      "enabled": true,
      "algorithm": "hungarian",
      "max_nodes": 100,
      "min_edge_confidence": 50,
      "optimization_goal": "maximize_allocation"
    }
  }
}

Algoritmos do solucionador

AlgoritmoMelhor ParaComplexidade
hungarianGrafos pequenos (<100 nós)O(n³)
auctionGrafos médios (<1000 nós)O(n² log n)
greedyGrafos grandes (>1000 nós)O(n log n)

Executar solucionador de grafo

O solucionador de grafo é executado automaticamente durante a correspondência quando a correspondência N:M está habilitada. Acione uma execução de correspondência para invocar o solucionador:
cURL
curl -X POST "https://api.matcher.example.com/v1/matching/contexts/{contextId}/run" \
 -H "Authorization: Bearer $TOKEN" \
 -H "Content-Type: application/json" \
 -d '{
   "options": {
     "algorithm": "hungarian",
     "allow_partial": true,
     "min_confidence": 60
   }
 }'

Resposta

{
  "solver_id": "solve_001",
  "status": "COMPLETED",
  "algorithm": "hungarian",
  "execution_time_ms": 45,
  "results": {
    "proposed_matches": [
      {
        "match_id": "match_proposed_001",
        "type": "MANY_TO_MANY",
        "confidence": 88,
        "allocations": [
          {
            "source": "pay_001",
            "target": "rec_001",
            "amount": 10000.0
          },
          {
            "source": "pay_002",
            "target": "rec_001",
            "amount": 2000.0
          },
          {
            "source": "pay_002",
            "target": "rec_002",
            "amount": 6000.0
          }
        ]
      }
    ],
    "unmatched_sources": [],
    "unmatched_targets": [],
    "total_matched": 18000.0,
    "match_rate": 100.0
  }
}

Regras de tolerância


Configure como a tolerância se aplica a correspondências divididas e agregadas.

Modos de tolerância

ModoDescriçãoCaso de Uso
residualAplicar ao valor final não correspondidoPadrão, mais comum
per_itemAplicar a cada transaçãoCorrespondência rigorosa
totalAplicar à soma de todas as transaçõesCorrespondência flexível

Configurar modo de tolerância

{
  "settings": {
    "matching": {
      "tolerance_mode": "residual",
      "tolerance_percent": 1.0,
      "tolerance_absolute": 50.0
    }
  }
}

Exemplos de tolerância

Modo Residual (Padrão):
  • Origem: $10.000,00
  • Destinos: $9.980,00 total
  • Residual: $20,00 (0,2%)
  • Tolerância: 1% = $100,00
  • Resultado: Correspondência (residual dentro da tolerância)
Modo Por Item:
  • Origem: $10.000,00
  • Destino 1: $5.010,00 (0,2% de variância)
  • Destino 2: $4.980,00 (0,4% de variância)
  • Cada um dentro da tolerância de 1%
  • Resultado: Correspondência (todos os itens dentro da tolerância)

Descoberta automática


O Matcher pode descobrir automaticamente padrões divididos e agregados.

Habilitar descoberta automática

{
  "settings": {
    "auto_discovery": {
      "enabled": true,
      "max_group_size": 10,
      "time_window_days": 7,
      "min_confidence": 75
    }
  }
}

Heurísticas de descoberta

HeurísticaDescrição
Soma de valoresEncontrar combinações que somam ao destino
Padrões de referênciaCorresponder com base em referências comuns
Agrupamento temporalAgrupar transações por proximidade de data
Agrupamento por contraparteAgrupar pela mesma contraparte

Visualizar grupos descobertos

Grupos descobertos aparecem como correspondências propostas nos resultados da execução de correspondência:
cURL
curl -X GET "https://api.matcher.example.com/v1/matching/runs/{runId}/groups" \
 -H "Authorization: Bearer $TOKEN"

Resposta

{
  "discoveries": [
    {
      "id": "disc_001",
      "type": "AGGREGATE",
      "confidence": 85,
      "heuristic": "amount_summing",
      "source_transactions": [
        "pos_001",
        "pos_002",
        "pos_003"
      ],
      "target_transactions": [
        "bank_002"
      ],
      "source_total": 4000.0,
      "target_total": 4000.0,
      "residual": 0.0
    }
  ]
}

Relatórios


Resumo de correspondência de grupo

cURL
curl -X GET "https://api.matcher.example.com/v1/reports/contexts/{contextId}/dashboard" \
 -H "Authorization: Bearer $TOKEN" \
 -G \
 -d "date_from=2024-01-01" \
 -d "date_to=2024-01-31"
{
  "period": {
    "from": "2024-01-01",
    "to": "2024-01-31"
  },
  "summary": {
    "total_matches": 1250,
    "by_type": {
      "one_to_one": 980,
      "split": 150,
      "aggregate": 100,
      "many_to_many": 20
    },
    "avg_group_size": {
      "split": 3.2,
      "aggregate": 4.5,
      "many_to_many": 6.1
    },
    "partial_matches": 45,
    "total_residual": 12500.0
  }
}

Melhores práticas


A correspondência muitos-para-muitos é complexa. Comece com padrões mais simples e habilite N:M apenas quando necessário.
Grupos grandes são mais difíceis de verificar. Limite o tamanho do grupo com base nos seus requisitos de auditoria.
Habilite a descoberta automática para encontrar padrões, mas exija revisão humana antes de confirmar correspondências complexas.
Acompanhe os valores residuais ao longo do tempo. Residuais crescentes podem indicar problemas sistemáticos de correspondência.
Quando múltiplas estratégias de alocação são possíveis, documente por que alocações específicas foram escolhidas.
Antes de habilitar o solucionador de grafo em produção, teste com dados representativos para verificar os resultados.

Próximos passos