🧩 Dynamics4Omni
ERP connector platform · proof of concept

One reusable integration for hundreds of independent Dynamics 365 environments.

A connector platform where a customer's credentials, environment URL, field names and custom columns are data on a connection — not code branches. The Dataverse Web API behind one interface, over Entra ID client-credentials auth, with bidirectional sync that is resumable, idempotent, conflict-aware and observable.

▶ Open the docs page 🖥️ The running app — dashboard & API

Opens the live Omni app, signed in to the demo account, on the documentation page.

Nothing signs in until you click — the demo account is shared, so this page never logs you in on its own.

Live platform · API docs (OpenAPI) · Prometheus metrics · Grafana dashboard · Repository

What the demo shows you

A landing pane and a documentation panel, each a note — one tab per document, so you can edit the docs and see the tab follow. The platform itself runs on the same box: the dashboard can start the scenario, inject faults and configure field mappings.

🔌 The Dataverse Web API, one interface

  • OData v4 record calls at /api/data/v9.2
  • Entra ID client-credentials tokens, cached and refreshed
  • @odata.bind writes, _x_value reads
  • A modifiedon gt … delta window

🛡️ Reliability is the product

  • Idempotent writes — a lost response cannot duplicate an invoice
  • Jittered retries that honour Retry-After
  • A per-connection circuit breaker
  • Conflict detection that refuses to guess

🧪 Evidence, not claims

  • 18 tests against a fake Dataverse that speaks the real wire protocol
  • Six environments built to be hostile: legacy customisations, a missing column, a required custom column, a least-privilege role and a 2,000-row history
  • Fault injection: 429s, 5xx, a lost write, schema drift
  • Every step prints its own numbers

📈 Observable, and instrumented for real

Run it yourself

The deployed instance is the same code, one bash deploy/install-vps.sh away. No Dynamics 365 tenant or Azure subscription required — the bundled simulator speaks the real wire protocol.

git clone <this repo> && cd erp-connector-poc
make install        # python 3.11+ venv + deps
make sim-dynamics   # the fake Dataverse environment on :8012
make api            # the platform API on :8000
make test           # the suite, including tests/test_dynamics365.py

# or as services on a box (this is what erppoc.stage.lohan.me runs):
bash deploy/install-vps.sh --dry-run

Inside the demo account

The notes are real Omni notes: searchable, editable, and the page follows them.

Two connectors, one platform

Dynamics 365 is the platform's second real connector — after NetSuite. Adding it was one connector class and one register() call: nothing under hub/ or api/ changed. That is the claim this demo is here to evidence.

The NetSuite build of this same demo lives at netsuite4omni.stage.lohan.me.