Query HubSpot and Stripe together with your AI agent

Connect CRM and billing context through Combined. Use a customer mapping, a copyable agent prompt and runnable SQL to compare open pipeline with paid invoices without duplicate totals.

Use Combined to give your AI agent SQL access to synced HubSpot and Stripe records. Map CRM companies to billing customers, aggregate each side separately, then join by company and currency. This gives you one useful view of open opportunities and paid invoices without multiplying totals when a customer has several deals.

Connect the data your question needs

Ask a concrete question: “Which companies have open opportunities, and what do their paid invoices total over the last 90 days?” HubSpot supplies the pipeline context; Stripe supplies the invoice context. Combined handles ingestion, storage and read-only agent access in one managed workflow.

In Connected Apps, add HubSpot and Stripe as separate sources and complete their authorization forms. Choose the datasets needed for the question and run the first sync. Follow the HubSpot connection guide for the CRM side; use the current Stripe connector fields for the billing side. Connector credentials belong in those authorization forms, while the agent gets its own Combined access.

Include company and deal identifiers, company associations, stage, amount and currency from the CRM. For invoices, retain customer ID, status, amount paid, currency and payment timestamp. Keep the fields used by your customer mapping. Use Set up or Access to connect the agent and grant only the relevant sources. The MCP tools let it discover datasets, inspect fields and query them.

For a one-off lookup or a billing operation, the applications' own MCP servers may be enough. This tutorial is for repeatable analysis across the two datasets. The MCP selection guide compares those choices.

Make the customer match explicit

A HubSpot company ID and a Stripe customer ID identify records in different systems. Use a maintained mapping between them: for example, a company identifier stored in customer metadata, a CRM custom property, or a mapping dataset you already maintain. Confirm that the mapping fields are available in the selected connector output before querying.

Each Stripe customer should resolve to one CRM company for this calculation. A company may have several billing customers; aggregate those together after mapping. Resolve missing or ambiguous matches before interpreting a total. Company names and shared email domains alone are weak join keys.

Customer mapping in the downloadable sample
CompanyCRM company IDStripe customer ID
Atlas101cus_atlas
Birch102cus_birch
Cedar103cus_cedar

Download the complete runnable SQL example. It includes synthetic companies, deals, invoices and the mapping above. Run it in DuckDB to inspect the arithmetic without connecting any account. The example uses normalized teaching fields; your agent should discover the actual logical relations and fields in your Combined workspace.

Aggregate each side before joining

Atlas has two open deals worth $12,000 and $8,000, plus two paid invoices worth $3,000 and $2,000. Joining every deal to every invoice produces four rows. Summing that raw join would report $40,000 of pipeline and $10,000 of paid invoices: both twice the intended amounts. Aggregate deals and invoices separately first.

WITH open_pipeline AS (
  SELECT company_id, currency, COUNT(*) AS open_deals,
         SUM(amount) AS open_pipeline_amount
  FROM deals
  WHERE is_closed = false
  GROUP BY company_id, currency
),
paid_invoices AS (
  SELECT m.company_id, i.currency,
         SUM(i.amount_paid_minor) / 100.0 AS paid_invoice_amount
  FROM invoices i
  JOIN customer_map m USING (stripe_customer_id)
  WHERE i.status = 'paid'
    AND i.paid_at >= TIMESTAMP '2026-06-12 00:00:00'
    AND i.paid_at < TIMESTAMP '2026-09-10 00:00:00'
  GROUP BY m.company_id, i.currency
)
SELECT p.company_id, p.currency, p.open_deals,
       p.open_pipeline_amount, b.paid_invoice_amount
FROM open_pipeline p
LEFT JOIN paid_invoices b
  ON p.company_id = b.company_id AND p.currency = b.currency
ORDER BY p.company_id, p.currency
LIMIT 20;

This sample measures paid invoices with a payment timestamp from June 12 through September 9, 2026 in UTC, using an exclusive September 10 boundary. It uses USD and EUR, so dividing minor units by 100 is appropriate here. Other currencies can use different units. The amount paid on paid invoices is not MRR, ARR, or revenue net of refunds; define those as separate metrics if you need them.

Expected output from the complete sample
CompanyCurrencyOpen dealsOpen pipelinePaid invoices
AtlasUSD2$20,000$5,000
BirchUSD1$6,000No match
CedarEUR1€4,000€1,500

Birch stays in the result even though its sample has no paid invoice in the selected window. Its open invoice and older paid invoice do not qualify. Keep “no matching record” visible; in a real workspace, incomplete syncs or missing customer mappings can also explain a missing match.

Give your agent the question and calculation rules

Use my granted HubSpot and Stripe sources in Combined.
Discover the logical datasets and describe the required fields first.
Check freshness for both sources and confirm the customer-ID mapping.

Which companies have open deals, and how much is paid on their paid
invoices in the last 90 complete UTC days?

Map closed stages explicitly. Aggregate deals and invoices separately
by company and currency, then join the aggregates. Use invoice payment
timestamps for the window. Keep companies with no matching invoice.
Flag unknown mappings, duplicate mapping keys, missing amounts and
incomplete coverage. Do not turn missing records into a proven zero.
Handle currency units correctly and keep currencies separate.

Return at most 20 companies, with the complete-dataset aggregates,
exact time bounds, both source timestamps and the query receipt.
Do not modify CRM or billing records.

Review the first result with the same filters in your source reports. Then ask a useful follow-up, such as which paying customers have the largest open expansion opportunities. Specify the deal type and confirm that its field is available before classifying an opportunity as an expansion.

Stop preparing a new export for every CRM-and-billing question. Give your agent Combined's managed business-data layer, connect the relevant sources and keep asking. You can begin with an initial 5 million MAR without a card.

Sources and further reading

Explore the documentation behind this guide. Product details checked on September 10, 2026.