Settlement and Split
Ahora que Mercatto sabe que los audífonos llegaron, abre la caja. Ishtaran toma su propio pequeño Platform Fee del total, y luego divide lo que queda exactamente como especificó el pedido en Creating an order: 90% para Bob, 10% para Mercatto.
Código
const executed = await mercatto.settlements.executeSettlement(transactionId);
const settlement = await completeSelfCustodySettlement(mercatto, environmentId, executed.settlementId, executionSigner);
const summary = await mercatto.settlements.getSummary(transactionId);
Resultado
{
"status": "COMPLETED",
"signingRequestId": "…sr…",
"grossAmount": "200.000000000000000000",
"platformFeeAmount": "1.800000000000000000",
"distributableAmount": "198.200000000000000000",
"feePercentageApplied": "0.900000000000000000",
"splitAllocations": [
{ "accountId": "…bob…", "amount": "178.380000000000000000", "status": "EXECUTED" },
{ "accountId": "…mercatto…", "amount": "19.820000000000000000", "status": "EXECUTED" }
]
}
Qué pasó por debajo
executeSettlement por sí solo no mueve dinero y no registra Ledger Entries — bajo
SelfCustody (DEC-037, el único modelo de custodia real hoy), construye un SigningRequest
real: una execution leg por cada beneficiario (Bob, la comisión propia de Mercatto) más una leg
para el propio Platform Fee, cada una dirigida usando el ExecutionDestination registrado en
Seller onboarding — con origen en la dirección que realmente retiene el
depósito confirmado de Alice. executeSettlement retorna de inmediato con el Settlement en
Executing y signingRequestId poblado; todavía no hay nada final.
completeSelfCustodySettlement (examples/marketplace-mercatto/self-custody-settlement.ts) es lo
que realmente termina el trabajo: obtiene el SigningRequest, firma cada leg localmente con la
execution wallet propia de Mercatto (registrada en Seller onboarding; la
private key nunca sale de este proceso), envía cada firma, y — una vez que la compuerta de
todas-las-firmas de la plataforma transmite cada leg — espera a que cada una confirme (Sandbox:
simulado, sandbox.simulateBroadcastConfirmation; una red real en Production). Solo cuando cada
leg confirma es que Ishtaran registra las Ledger Entries y mueve el Settlement a Completed.
"Settled" nunca significa "Ledger actualizado" bajo SelfCustody — significa que la transferencia
real fue confirmada. Un Settlement sin nada que ejecutar on-chain (todos los beneficiarios
retenidos, Fee en cero) se salta la firma por completo: signingRequestId simplemente es null,
y completeSelfCustodySettlement resuelve de inmediato.
El porcentaje del Fee no está hardcodeado en ningún lugar de este ejemplo: no existe una ruta pública para leer la Pricing Policy por adelantado (Known Limitations §F.3), así que Mercatto lo lee de vuelta desde el propio resultado del Settlement, de la misma forma en que cualquier integrador tiene que hacerlo hoy.
Transmitir esas legs cuesta recursos de red reales (Energy/Bandwidth de TRON) — alguien tiene que
pagar por eso, por separado del Platform Fee. Justo después de dar de alta a Bob y Alice
(examples/marketplace-mercatto/register-network-cost-payer-account.ts), Mercatto registra su
propia Account de ingresos como el NetworkCostPayerAccount para este AssetNetwork — una decisión
de negocio real (el costo de red sale de la propia comisión de Mercatto), no un detalle técnico.
Sin esto, esta misma llamada fallaría con 422 antes incluso de construir un SigningRequest: bajo
SelfCustody, executeSettlement resuelve un NetworkCostPayerAccount y reserva el costo de red
real, cotizado (usando el mismo Network Execution Engine que usa Withdrawals — ver
Withdrawal) antes de mover el dinero de cualquier beneficiario. Ese costo reservado
nunca aparece en grossAmount/platformFeeAmount/splitAllocations arriba — es una reserva de
Ledger separada contra la propia Account de comisión de Mercatto, liquidada en cuanto cada leg
confirma.
La Account de un beneficiario no siempre está lista para recibir. Si la Account de Bob
estuviera congelada justo en este momento, su asignación sería RETAINED en vez de EXECUTED —
no se construye ninguna execution leg para una asignación retenida, y el resto del Settlement
igual se completa normalmente. Ver Failure scenarios para ese caso exacto,
trabajado con números reales.
El Settlement no tiene que ocurrir todo de una vez — ver Partial Settlement.