Three systems, three numbers: write a metric contract before you put an AI agent on your CRM and ERP

2026-11-12来源 dev.to AIEnglish

A sales manager asks for one number. The CRM says 100 sold. The ERP says 80 invoiced. Somebody's spreadsheet says 120. None of them has to be wrong: each system records a different moment of the same sale, entered by different people at different times.

This is the normal state of many mid-sized companies that run Salesforce next to a separate ERP and glue them together with spreadsheets. It is also exactly the setup where teams now want to add an AI agent that "answers questions about the business". If you do that without fixing the definitions first, the agent inherits the same argument and picks one of the three numbers for you.

This post shows a small, practical artifact that helps before any agent work: a metric contract.

Why the numbers disagree

Take "sales this month". In a Salesforce org alone there are already two valid answers:

-- Won opportunities closed this month SELECT SUM(Amount) FROM Opportunity WHERE IsWon = true AND CloseDate = THIS_MONTH -- Activated orders effective this month SELECT SUM(TotalAmount) FROM Order WHERE Status = 'Activated' AND EffectiveDate = THIS_MONTH 

Both queries are correct SOQL and they can return different totals on the same day. "Invoiced" lives in the ERP and has its own date logic. The spreadsheet usually mixes all of them plus manual corrections. Three sources, three numbers, one meeting to decide which one wins.

The metric contract

A metric contract is a short, versioned file that says, for each number leadership asks about, exactly where it comes from and who owns it. YAML is enough:

metric: sales_this_month question: "How much did we sell this month?" definition: "Sum of activated orders by effective date" source_of_truth: salesforce object: Order filter: "Status = 'Activated' AND EffectiveDate = THIS_MONTH" amount_field: TotalAmount owner: sales_operations not_this: ["won opportunities", "invoices issued"] reconciles_with: - metric: invoiced_this_month expected_gap: "orders activated but not yet invoiced" --- metric: invoiced_this_month question: "How much did we invoice this month?" definition: "Sum of posted invoices by invoice date" source_of_truth: erp owner: finance 

The values above are an example of the format, not a real company's setup. What matters is that every metric has exactly one source of truth, one owner, and an explicit list of what it is not.

What changes for the agent

With a contract in place, an agent that answers "how much did we sell?" has a single query to run and a documented gap to explain when the invoiced number is lower. Without it, the agent has three sources that disagree and no rule for choosing.

A few practical rules that follow:

  • Give the agent the contract as context, not just database access.
  • If a metric needs a spreadsheet to compute, the contract should say so. That row is a candidate for removal, not for automation.
  • Review the contract when a process changes, the same way you review code.

When a single data source removes the problem

The contract reduces arguments, but it does not remove the reconciliation work when sales, invoicing and inventory live in separate databases. That is why we build EGA Futura ERP natively on Salesforce: sales, invoicing, inventory, purchasing, treasury and accounting share the same database as the CRM, so the "sold" and "invoiced" metrics in the contract point to the same place. If you are earlier in the journey, the contract is still the cheapest first step.

I wrote the business side of this, in Spanish, as the typical day of a manager reconciling Salesforce, the ERP and Excel.

Juan Manuel Garrido, founder of EGA Futura and co-founder of Vantegrate.

原文:https://www.a8q9.cn/en/article/three-systems-three-numbers-write-a-metric-contract-before-you-put-an-ai-agent-o-2ee11d.html

相关文章