Microsoft Dynamics 365 F&O and Procore integration
Procore runs construction project management, including commitments, subcontractor invoices, and direct costs. Microsoft Dynamics 365 F&O runs the company's finance and procurement back office. Connecting the two moves project costs that originate in the field into the ERP without re-keying. Purchase order contracts, subcontractor requisitions, and direct costs captured in Procore post into Microsoft Dynamics 365 F&O as purchase orders and vendor invoices coded to the right GL accounts and financial dimensions, and vendor records stay aligned on both sides. ml-connector handles the very different APIs and moves the data as Procore activity is approved.
What moves between them
The main flow runs from Procore into Microsoft Dynamics 365 F&O. As commitments are executed, ml-connector reads Procore purchase order contracts and writes them into D365 F&O as purchase orders, then reads approved subcontractor requisitions and direct costs and posts them as vendor invoices coded to the matching GL accounts and financial dimensions. Procore vendors are reconciled against D365 vendors so every cost references a vendor that exists in the ERP. Cost codes and cost types from Procore are mapped to D365 financial dimensions in a setup step that both directions depend on. D365 posted journal entries are read-only over OData, so ml-connector never writes financial entries back into Procore.
How ml-connector handles it
ml-connector stores both credential sets encrypted, mints a Procore DMSA token and refreshes it before the 5400-second expiry, and obtains a D365 OAuth2 bearer token from Microsoft Entra ID scoped to the customer's environment host, which is held as a credential field since each tenant has its own URL. Procore webhooks on Commitments, Requisitions, DirectCosts, and Vendors trigger work as activity is approved, and because Procore signs nothing, the connector verifies the shared secret header set at registration; a nightly reconciliation poll backfills anything a webhook missed, since Procore documents no delivery retry. Procore payloads carry only a resource id, so the full record is fetched over the Procore REST API before mapping. Cost codes are mapped to D365 financial dimensions first, and dimensions are written as the formatted display string D365 requires, so a wrong format is caught early. D365 OData writes use natural keys such as InvoiceNumber plus VendorAccount and have no idempotency header, so each job is deduplicated on its own key, and 429 responses on either side are retried with backoff against the Retry-After hint. Every record carries a full audit trail and can be replayed if a downstream call fails.
A real-world example
A mid-sized general contractor running fifteen active jobs uses Procore as the system of record for commitments, subcontractor billings, and direct costs in the field, and Microsoft Dynamics 365 F&O for corporate AP, procurement, and the general ledger. Before the integration, project accountants exported committed cost and subcontractor invoice data from each Procore project every week and re-entered it into D365 by hand, which delayed AP and left job cost in the ledger trailing what the field already knew. With Microsoft Dynamics 365 F&O and Procore connected, executed purchase order contracts and approved requisitions flow into the ERP as purchase orders and vendor invoices coded to the right job dimensions, vendors stay aligned, and AP works from current numbers instead of stale spreadsheets.
What you can do
- Post executed Procore purchase order contracts into Microsoft Dynamics 365 F&O as purchase orders coded to the right financial dimensions.
- Write approved Procore requisitions and direct costs into D365 F&O as vendor invoices against the matching GL accounts.
- Keep Procore vendors and D365 vendors aligned so every project cost references a vendor that exists in the ERP.
- Map Procore cost codes and cost types to D365 financial dimensions so job costs land on valid accounts.
- Trigger on Procore webhooks, verify the shared secret header, and backfill with a reconciliation poll since Procore documents no delivery retry.
Questions
- Which direction does data move between Microsoft Dynamics 365 F&O and Procore?
- The main flow is Procore into Microsoft Dynamics 365 F&O. Purchase order contracts, subcontractor requisitions, and direct costs move from Procore into the ERP as purchase orders and vendor invoices, while vendors and cost code mappings are aligned across both sides. D365 posted journal entries are read-only over OData, so ml-connector does not write financial entries back into Procore.
- How does the integration handle authentication across the two systems?
- Procore uses OAuth2 client credentials through a Developer Managed Service Account, and the token expires after 5400 seconds, so ml-connector refreshes it proactively. Microsoft Dynamics 365 F&O uses OAuth2 client credentials through Microsoft Entra ID, scoped to the tenant-specific environment host that is held as a credential field. ml-connector stores both credential sets encrypted and presents the correct token to each system on every call.
- What happens with Procore webhooks given there is no signature?
- Procore pushes create, update, and delete events but provides no HMAC signature, so a shared secret header is set when the webhook is registered and verified on every inbound payload. Because the payload carries only a resource id, ml-connector fetches the full record over the Procore REST API before mapping it. Since Procore documents no retry schedule for failed deliveries, a scheduled reconciliation poll catches any events that were missed.
Related integrations
More Microsoft Dynamics 365 F&O integrations
Other systems that connect to Procore
Connect Microsoft Dynamics 365 F&O and Procore
Free to use. Add your credentials, ping your real systems, and see if we fit.
Get started