Feat/bounded entity linkage (STIT-573) - #200
Conversation
CD summary
|
| service | url | fqdn |
|---|---|---|
| api | open | pr-200-api.purplegrass-c07d0a94.westus2.azurecontainerapps.io |
| entity-linkage | open | pr-200-entity-linkage.purplegrass-c07d0a94.westus2.azurecontainerapps.io |
| frontend | https://witty-mushroom-017a3dc1e-200.westus2.1.azurestaticapps.net | |
| stitch-llm | open | pr-200-stitch-llm.purplegrass-c07d0a94.westus2.azurecontainerapps.io |
Database (1)
| db_name | postgres_host | postgres_port | postgres_db |
|---|---|---|---|
| pr_200 | stitch-dev.postgres.database.azure.com |
5432 |
pr_200 |
Jobs (2)
| job | image | postgres_db | api_url | auth_mode |
|---|---|---|---|---|
| db-migrations | ghcr.io/rmi/stitch-api:pr-200@sha256:eb15abcfa986e436d06ada2d2502d8f59db5d03eaa6b4ea55bdb9620b2ff53ca |
pr_200 |
||
| seed | ghcr.io/rmi/stitch-seed:pr-200@sha256:917973f214efd3cb6a3ac71773ffbb7084b1febc841b54d454fbdc1a2f4d91ed |
https://pr-200-api.purplegrass-c07d0a94.westus2.azurecontainerapps.io/api/v1 |
stitch-client-bearer-token |
Images (4)
| build_time | commit_time | git_sha | image | image_digest |
|---|---|---|---|---|
| 2026-07-29T13:15:44Z | 2026-07-29T13:15:18Z | f137747 | ghcr.io/rmi/stitch-api:pr-200 |
ghcr.io/rmi/stitch-api:pr-200@sha256:eb15abcfa986e436d06ada2d2502d8f59db5d03eaa6b4ea55bdb9620b2ff53ca |
| 2026-07-29T13:15:42Z | 2026-07-29T13:15:18Z | f137747 | ghcr.io/rmi/stitch-entity-linkage:pr-200 |
ghcr.io/rmi/stitch-entity-linkage:pr-200@sha256:576a4b5d07abd76d7cbcd476d912da5cff47eb969bc12bc42b71a021936569ba |
| 2026-07-29T13:15:40Z | 2026-07-29T13:15:18Z | f137747 | ghcr.io/rmi/stitch-seed:pr-200 |
ghcr.io/rmi/stitch-seed:pr-200@sha256:917973f214efd3cb6a3ac71773ffbb7084b1febc841b54d454fbdc1a2f4d91ed |
| 2026-07-29T13:15:43Z | 2026-07-29T13:15:18Z | f137747 | ghcr.io/rmi/stitch-stitch-llm:pr-200 |
ghcr.io/rmi/stitch-stitch-llm:pr-200@sha256:444c958a2ec542d10a9f33fed95edef47102482bbf86bf043cd48469e9a5fd31 |
There was a problem hiding this comment.
Pull request overview
This PR introduces a bounded-memory entity-linkage flow by adding per-resource and bulk “link” endpoints to the entity-linkage service, and extending the Stitch client to support server-side filtering + streaming iteration so production-scale runs don’t require materializing the full dataset in memory.
Changes:
- Extend
AsyncStitchClient(and the entity-linkageStitchApiClientwrapper) to supportq/name/countryfilters, streaming iteration (iter_oil_gas_fields), and listing merge candidates. - Add bounded per-resource and bulk linkage endpoints (
/oil-gas-fields/{id}/linkand/oil-gas-fields/link) plus a newmatchingmodule to drive the linkage pass. - Refactor shared normalization/user-label helpers into
entities.pyand add unit/integration tests for the new behavior.
Reviewed changes
Copilot reviewed 19 out of 19 changed files in this pull request and generated 5 comments.
Show a summary per file
| File | Description |
|---|---|
| PLAN.md | Design/approach document for bounded-memory linkage and success criteria. |
| packages/stitch-client/src/stitch/client/async_client.py | Adds filter params, streaming iterator, and list_merge_candidates(); adds _expect_list(). |
| packages/stitch-client/tests/test_async_client.py | Adds tests for filter param forwarding, streaming iteration, and list_merge_candidates(). |
| deployments/entity-linkage/src/stitch/entity_linkage/entities.py | Adds normalize_name, normalize_country, user_label, and new response models for link endpoints. |
| deployments/entity-linkage/src/stitch/entity_linkage/client.py | Mirrors client filters/streaming + merge-candidate listing in the entity-linkage wrapper. |
| deployments/entity-linkage/src/stitch/entity_linkage/matching.py | New bounded-matcher implementation and bulk driver. |
| deployments/entity-linkage/src/stitch/entity_linkage/routers/link.py | New API endpoints for per-resource and bulk linking with permission enforcement. |
| deployments/entity-linkage/src/stitch/entity_linkage/routers/start.py | Refactors to use shared helpers (normalize_country, user_label). |
| deployments/entity-linkage/src/stitch/entity_linkage/main.py | Mounts the new link router under /api/v1. |
| deployments/entity-linkage/tests/test_matching.py | Unit tests for matching/linking logic (fingerprints, dedupe, skip behavior). |
| deployments/entity-linkage/tests/test_link_api.py | API-level tests for new endpoints + auth/502 translation. |
| deployments/entity-linkage/tests/test_start.py | Updates tests to use refactored helper functions. |
| deployments/entity-linkage/README.md | Updates service docs to describe new endpoints and bounded-memory behavior. |
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
CD summary
|
| service | url | fqdn |
|---|---|---|
| api | open | pr-200-api.purplegrass-c07d0a94.westus2.azurecontainerapps.io |
| entity-linkage | open | pr-200-entity-linkage.purplegrass-c07d0a94.westus2.azurecontainerapps.io |
| frontend | https://witty-mushroom-017a3dc1e-200.westus2.1.azurestaticapps.net | |
| stitch-llm | open | pr-200-stitch-llm.purplegrass-c07d0a94.westus2.azurecontainerapps.io |
Database (1)
| db_name | postgres_host | postgres_port | postgres_db |
|---|---|---|---|
| pr_200 | stitch-dev.postgres.database.azure.com |
5432 |
pr_200 |
Jobs (1)
| job | image | postgres_db |
|---|---|---|
| db-migrations | ghcr.io/rmi/stitch-api:pr-200@sha256:4e3695660daa558199d0f86a93d1f3e9b8f3d1cb262ca357f09093cc7c6a030c |
pr_200 |
Images (4)
| build_time | commit_time | git_sha | image | image_digest |
|---|---|---|---|---|
| 2026-07-29T14:31:18Z | 2026-07-29T14:30:53Z | d838187 | ghcr.io/rmi/stitch-api:pr-200 |
ghcr.io/rmi/stitch-api:pr-200@sha256:4e3695660daa558199d0f86a93d1f3e9b8f3d1cb262ca357f09093cc7c6a030c |
| 2026-07-29T14:31:12Z | 2026-07-29T14:30:53Z | d838187 | ghcr.io/rmi/stitch-entity-linkage:pr-200 |
ghcr.io/rmi/stitch-entity-linkage:pr-200@sha256:578df8d3feaa18afc3a35fa80cd3b485f15e3369885f3319cbb692234103c794 |
| 2026-07-29T14:31:18Z | 2026-07-29T14:30:53Z | d838187 | ghcr.io/rmi/stitch-seed:pr-200 |
ghcr.io/rmi/stitch-seed:pr-200@sha256:76dcdf929ecee92fd69afdaf708142ff9c03f3701a9c49d9d6d102c9d2c94d29 |
| 2026-07-29T14:31:14Z | 2026-07-29T14:30:53Z | d838187 | ghcr.io/rmi/stitch-stitch-llm:pr-200 |
ghcr.io/rmi/stitch-stitch-llm:pr-200@sha256:7b2b0078e63b79be6442835abb77aa44aeaeaae0a6febae5eb0e620beb62bc92 |
CD summary
|
| service | url | fqdn |
|---|---|---|
| api | open | pr-0200-api.purplegrass-c07d0a94.westus2.azurecontainerapps.io |
| stitch-llm | open | pr-0200-llm.purplegrass-c07d0a94.westus2.azurecontainerapps.io |
Database (1)
| db_name | postgres_host | postgres_port | postgres_db |
|---|---|---|---|
| pr_0200 | stitch-dev.postgres.database.azure.com |
5432 |
pr_0200 |
Jobs (2)
| job | image | postgres_db | api_url | auth_mode |
|---|---|---|---|---|
| db-migrations | ghcr.io/rmi/stitch-api:pr-0200@sha256:7247908ba0af4a9bfe7d19e1e342d8ab98fc18e31fc9ecee2ae029a3ab9b25d1 |
pr_0200 |
||
| seed | ghcr.io/rmi/stitch-seed:pr-0200@sha256:da9ade27a9f520e18a3ba2695b36e537563aac4e05360b91b5c525acfedfd53c |
https://pr-0200-api.purplegrass-c07d0a94.westus2.azurecontainerapps.io/api/v1 |
stitch-client-bearer-token |
Images (3)
| build_time | commit_time | git_sha | image | image_digest |
|---|---|---|---|---|
| 2026-08-04T16:27:38Z | 2026-08-04T16:27:23Z | dc5b326 | ghcr.io/rmi/stitch-api:pr-0200 |
ghcr.io/rmi/stitch-api:pr-0200@sha256:7247908ba0af4a9bfe7d19e1e342d8ab98fc18e31fc9ecee2ae029a3ab9b25d1 |
| 2026-08-04T16:27:44Z | 2026-08-04T16:27:23Z | dc5b326 | ghcr.io/rmi/stitch-seed:pr-0200 |
ghcr.io/rmi/stitch-seed:pr-0200@sha256:da9ade27a9f520e18a3ba2695b36e537563aac4e05360b91b5c525acfedfd53c |
| 2026-08-04T16:27:39Z | 2026-08-04T16:27:23Z | dc5b326 | ghcr.io/rmi/stitch-stitch-llm:pr-0200 |
ghcr.io/rmi/stitch-stitch-llm:pr-0200@sha256:629339227f0bde27de0d600d005934e92f8c9c99a5d14a69992d20f2910a76f5 |
CD summary
|
| db_name | postgres_host | postgres_port | postgres_db |
|---|---|---|---|
| pr_0200 | stitch-dev.postgres.database.azure.com |
5432 |
pr_0200 |
Images (4)
| build_time | commit_time | git_sha | image | image_digest |
|---|---|---|---|---|
| 2026-08-05T10:52:40Z | 2026-08-05T10:52:10Z | 57f08b0 | ghcr.io/rmi/stitch-api:pr-0200 |
ghcr.io/rmi/stitch-api:pr-0200@sha256:a956f11a9ec966a1ba81acbd76fbaade48cff995dc24bbd5fd0624a4a2ee5700 |
| 2026-08-05T10:52:38Z | 2026-08-05T10:52:10Z | 57f08b0 | ghcr.io/rmi/stitch-entity-linkage:pr-0200 |
ghcr.io/rmi/stitch-entity-linkage:pr-0200@sha256:b62d7647912f98cfe16f9d28d8d0977999284cd6e42064693e9a758673ee931f |
| 2026-08-05T10:52:33Z | 2026-08-05T10:52:10Z | 57f08b0 | ghcr.io/rmi/stitch-seed:pr-0200 |
ghcr.io/rmi/stitch-seed:pr-0200@sha256:72c19c7a9c46c8b0ba569b33b25c89d0a849eb3130b658246be60d1f905d4421 |
| 2026-08-05T10:52:35Z | 2026-08-05T10:52:10Z | 57f08b0 | ghcr.io/rmi/stitch-stitch-llm:pr-0200 |
ghcr.io/rmi/stitch-stitch-llm:pr-0200@sha256:ff88e12e47c429daac6751af1553a2a181b53a04a590c6ccd61834086f9caced |
CD summary
|
| service | url | fqdn |
|---|---|---|
| api | open | pr-0200-api.purplegrass-c07d0a94.westus2.azurecontainerapps.io |
| entity-linkage | open | pr-0200-el.purplegrass-c07d0a94.westus2.azurecontainerapps.io |
| frontend | https://witty-mushroom-017a3dc1e-200.westus2.1.azurestaticapps.net | |
| stitch-llm | open | pr-0200-llm.purplegrass-c07d0a94.westus2.azurecontainerapps.io |
Database (1)
| db_name | postgres_host | postgres_port | postgres_db |
|---|---|---|---|
| pr_0200 | stitch-dev.postgres.database.azure.com |
5432 |
pr_0200 |
Jobs (1)
| job | image | postgres_db |
|---|---|---|
| db-migrations | ghcr.io/rmi/stitch-api:pr-0200@sha256:d0aea2f6e217b2028b7809101895c6ee0656bf0502f9a10021afbcd42eeb50aa |
pr_0200 |
Images (4)
| build_time | commit_time | git_sha | image | image_digest |
|---|---|---|---|---|
| 2026-08-05T12:15:14Z | 2026-08-05T12:14:42Z | 10f81dd | ghcr.io/rmi/stitch-api:pr-0200 |
ghcr.io/rmi/stitch-api:pr-0200@sha256:d0aea2f6e217b2028b7809101895c6ee0656bf0502f9a10021afbcd42eeb50aa |
| 2026-08-05T12:15:12Z | 2026-08-05T12:14:42Z | 10f81dd | ghcr.io/rmi/stitch-entity-linkage:pr-0200 |
ghcr.io/rmi/stitch-entity-linkage:pr-0200@sha256:9c3a2f46d20709c90c523f47c2e29cc9a217caa2e332a4e1a937523ea2bc43c1 |
| 2026-08-05T12:15:03Z | 2026-08-05T12:14:42Z | 10f81dd | ghcr.io/rmi/stitch-seed:pr-0200 |
ghcr.io/rmi/stitch-seed:pr-0200@sha256:78c2c5de39e2f106339c3de575edf0eaae4eeca00a3be8095b7b4ac95dca95e3 |
| 2026-08-05T12:15:02Z | 2026-08-05T12:14:42Z | 10f81dd | ghcr.io/rmi/stitch-stitch-llm:pr-0200 |
ghcr.io/rmi/stitch-stitch-llm:pr-0200@sha256:8900ed73370f6bb748dbac5c31089f0d3c38f6c57102521fbf1dc0205e86a0a5 |
CD summary
|
| service | url | fqdn |
|---|---|---|
| api | open | pr-0200-api.purplegrass-c07d0a94.westus2.azurecontainerapps.io |
| entity-linkage | open | pr-0200-el.purplegrass-c07d0a94.westus2.azurecontainerapps.io |
| frontend | https://witty-mushroom-017a3dc1e-200.westus2.1.azurestaticapps.net | |
| stitch-llm | open | pr-0200-llm.purplegrass-c07d0a94.westus2.azurecontainerapps.io |
Database (1)
| db_name | postgres_host | postgres_port | postgres_db |
|---|---|---|---|
| pr_0200 | stitch-dev.postgres.database.azure.com |
5432 |
pr_0200 |
Jobs (1)
| job | image | postgres_db |
|---|---|---|
| db-migrations | ghcr.io/rmi/stitch-api:pr-0200@sha256:6df47010856a025471c77fb7b49de8d53073cebcadfa8e07f44a6f70a513c4bd |
pr_0200 |
Images (4)
| build_time | commit_time | git_sha | image | image_digest |
|---|---|---|---|---|
| 2026-08-05T12:55:01Z | 2026-08-05T12:54:37Z | 1d7e0ed | ghcr.io/rmi/stitch-api:pr-0200 |
ghcr.io/rmi/stitch-api:pr-0200@sha256:6df47010856a025471c77fb7b49de8d53073cebcadfa8e07f44a6f70a513c4bd |
| 2026-08-05T12:54:59Z | 2026-08-05T12:54:37Z | 1d7e0ed | ghcr.io/rmi/stitch-entity-linkage:pr-0200 |
ghcr.io/rmi/stitch-entity-linkage:pr-0200@sha256:0d28ce629ba73e079afec86be1bbfc98b86bc039f44ff98fb35baadfb2f8c5fa |
| 2026-08-05T12:55:06Z | 2026-08-05T12:54:37Z | 1d7e0ed | ghcr.io/rmi/stitch-seed:pr-0200 |
ghcr.io/rmi/stitch-seed:pr-0200@sha256:747098a3e55a773025710592c4da8be1e9fe39445ee6faabc5866e1374050277 |
| 2026-08-05T12:54:56Z | 2026-08-05T12:54:37Z | 1d7e0ed | ghcr.io/rmi/stitch-stitch-llm:pr-0200 |
ghcr.io/rmi/stitch-stitch-llm:pr-0200@sha256:f71e209bf2e6291f28fb7393eaec2515b281e10299c3fab69fcfd3c9139131f5 |
There was a problem hiding this comment.
Pull request overview
Copilot reviewed 20 out of 20 changed files in this pull request and generated no new comments.
Suppressed comments (1)
deployments/entity-linkage/src/stitch/entity_linkage/matching.py:69
find_match_group_for_resourcepasses the rawseed.nameinto the APIqfilter. If the stored name has leading/trailing whitespace (e.g. " Ghawar "),qwill include those spaces and the substring search can miss true same-name candidates that differ only by surrounding whitespace, undermining the intended normalize/strip blocking. Strip the seed name before using it asq.
async for candidate in client.iter_oil_gas_fields(q=seed.name):
CD summary
|
| service | url | fqdn |
|---|---|---|
| api | open | pr-0200-api.purplegrass-c07d0a94.westus2.azurecontainerapps.io |
| entity-linkage | open | pr-0200-el.purplegrass-c07d0a94.westus2.azurecontainerapps.io |
| frontend | https://witty-mushroom-017a3dc1e-200.westus2.1.azurestaticapps.net | |
| stitch-llm | open | pr-0200-llm.purplegrass-c07d0a94.westus2.azurecontainerapps.io |
Database (1)
| db_name | postgres_host | postgres_port | postgres_db |
|---|---|---|---|
| pr_0200 | stitch-dev.postgres.database.azure.com |
5432 |
pr_0200 |
Jobs (1)
| job | image | postgres_db |
|---|---|---|
| db-migrations | ghcr.io/rmi/stitch-api:pr-0200@sha256:1ef06c4428ea0c393eec0a4f6754113cd588c36725a101f608456ef33ae149c9 |
pr_0200 |
Images (4)
| build_time | commit_time | git_sha | image | image_digest |
|---|---|---|---|---|
| 2026-08-05T13:37:09Z | 2026-08-05T13:36:43Z | 2254534 | ghcr.io/rmi/stitch-api:pr-0200 |
ghcr.io/rmi/stitch-api:pr-0200@sha256:1ef06c4428ea0c393eec0a4f6754113cd588c36725a101f608456ef33ae149c9 |
| 2026-08-05T13:37:07Z | 2026-08-05T13:36:43Z | 2254534 | ghcr.io/rmi/stitch-entity-linkage:pr-0200 |
ghcr.io/rmi/stitch-entity-linkage:pr-0200@sha256:386d6055efac1fc8b84c8a9c438594d122d4992ec5bec278ddb6afe20e5bb794 |
| 2026-08-05T13:37:08Z | 2026-08-05T13:36:43Z | 2254534 | ghcr.io/rmi/stitch-seed:pr-0200 |
ghcr.io/rmi/stitch-seed:pr-0200@sha256:9ff1828ed259f05fa7ad35a0715aba08dff414d89b9f5deb2bb89853c8e63551 |
| 2026-08-05T13:37:08Z | 2026-08-05T13:36:43Z | 2254534 | ghcr.io/rmi/stitch-stitch-llm:pr-0200 |
ghcr.io/rmi/stitch-stitch-llm:pr-0200@sha256:ae35e85f0e56fb0161f7988d507ca28fdd94d66d9f27601b0e490f675dc9b73c |
Reuse the jobs infrastructure from the ETL repo.
CD summary
|
| service | url | fqdn |
|---|---|---|
| api | open | pr-0200-api.purplegrass-c07d0a94.westus2.azurecontainerapps.io |
| entity-linkage | open | pr-0200-el.purplegrass-c07d0a94.westus2.azurecontainerapps.io |
| frontend | https://witty-mushroom-017a3dc1e-200.westus2.1.azurestaticapps.net | |
| stitch-llm | open | pr-0200-llm.purplegrass-c07d0a94.westus2.azurecontainerapps.io |
Database (1)
| db_name | postgres_host | postgres_port | postgres_db |
|---|---|---|---|
| pr_0200 | stitch-dev.postgres.database.azure.com |
5432 |
pr_0200 |
Jobs (1)
| job | image | postgres_db |
|---|---|---|
| db-migrations | ghcr.io/rmi/stitch-api:pr-0200@sha256:7ce7fdd133fe9915b0af67e44a98303d4c9773d2c42c4573980c9d4264c045a9 |
pr_0200 |
Images (4)
| build_time | commit_time | git_sha | image | image_digest |
|---|---|---|---|---|
| 2026-08-05T14:16:41Z | 2026-08-05T14:16:13Z | 6b90ec5 | ghcr.io/rmi/stitch-api:pr-0200 |
ghcr.io/rmi/stitch-api:pr-0200@sha256:7ce7fdd133fe9915b0af67e44a98303d4c9773d2c42c4573980c9d4264c045a9 |
| 2026-08-05T14:16:36Z | 2026-08-05T14:16:13Z | 6b90ec5 | ghcr.io/rmi/stitch-entity-linkage:pr-0200 |
ghcr.io/rmi/stitch-entity-linkage:pr-0200@sha256:3400e01252a0a12a8e6098dad71b0955f166def916f74aacc696e65e1359db5f |
| 2026-08-05T14:16:45Z | 2026-08-05T14:16:13Z | 6b90ec5 | ghcr.io/rmi/stitch-seed:pr-0200 |
ghcr.io/rmi/stitch-seed:pr-0200@sha256:4701f5787fff83603ae6642d33f53a9a39d89818a5e7b6de17527cd93688904d |
| 2026-08-05T14:16:44Z | 2026-08-05T14:16:13Z | 6b90ec5 | ghcr.io/rmi/stitch-stitch-llm:pr-0200 |
ghcr.io/rmi/stitch-stitch-llm:pr-0200@sha256:24ed173e8e395d76520e6d783907374ae13ecd1e9e487bca3e20b1b1ce6097f8 |
There was a problem hiding this comment.
Pull request overview
Copilot reviewed 20 out of 20 changed files in this pull request and generated no new comments.
Suppressed comments (2)
deployments/stitch-frontend/src/pages/EntityLinkagePage.jsx:214
- The auto-poll uses
setIntervalto call an asyncfetchStatus()without awaiting it, so slow network/token fetches can cause overlapping in-flight polls (and unnecessary load). AsetTimeoutloop that schedules the next poll only after the previous one completes avoids request pile-ups.
// Auto-poll while a run is active; stop once it reaches a terminal state.
useEffect(() => {
if (record?.state !== "running") return undefined;
const id = setInterval(() => {
fetchStatus();
}, POLL_INTERVAL_MS);
return () => clearInterval(id);
}, [record?.state, fetchStatus]);
packages/stitch-client/tests/test_async_client.py:322
- This test asserts an exact query-string (including parameter order). That’s brittle because URL param ordering can change even when the request is correct; comparing parsed params avoids false negatives.
def handler(request: httpx.Request) -> httpx.Response:
captured["query"] = request.url.query.decode("utf-8")
return httpx.Response(200, json={"items": [], "total_pages": 1})
client, raw_client = make_client(handler)
await client.list_oil_gas_fields_page(q="Ghawar")
assert captured["query"] == "page=1&page_size=50&q=Ghawar"
|
@mbarlow12 , @jdhoffa Note to look at PR 220 as the test environment here. Noting that this is very slow in its current form, but the turtle is working |
Summary
Fixes STIT-573 — entity linkage failed at production data scale. The old pass (
POST /api/v1/start) pulled the entire resource table into memory and ran the whole reconciliation synchronously in one request, so it blew up on the full GEM + WoodMac + regulator (ccr) dataset while working fine at dev/staging volumes (long time on OOM).This reworks it into a bounded, per-resource match plus a background bulk job:
job_id, polled for status), so it's non-blocking and pollable at scale instead of holding a request open.What changed
stitch-clientlist_oil_gas_fields_pageaccepts server-side filters (q/name/country).iter_oil_gas_fieldsstreaming iterator (bounded memory) andlist_merge_candidates.entity-linkage service
matching.py): per-resource blocking on normalized name + country, producing merge candidates. Name matching widens with the API's case-insensitiveq(ILIKE) and re-narrows client-side to preserve the exact casefold/strip blocking (a DB-side normalized-name match is a tracked follow-up).POST /api/v1/oil-gas-fields/{id}/link(synchronous single-resource link);POST /api/v1/oil-gas-fields/link(launches a background linkage run —202, returnsjob_id;409if one is already running);GET /api/v1/oil-gas-fields/link/status(polls run state + result summary).jobs.py), borrowed from the stitch-etl-poc start/status pattern.POST /api/v1/startpass.frontend
EntityLinkagePagereworked to the async job flow (start → auto-poll status), reusing the ETL page's design via a sharedStateBadgecomponent.Breaking change
POST /api/v1/startis removed — callers now get a404. It was an internal pre-scale endpoint and the frontend has been migrated to the new endpoints; no external consumers are expected.Testing
make checkand CI green (lint, format, pytest, frontend unit tests, docker builds, lockfile, migration drift).min_lengthguard, dedup/skip), job manager (success/failure/concurrent-start), client (filters, streaming, list), async start/status/409/404, and the reworked frontend page./startgrouping on the seed data.SEED_FAKER_POST_COUNTladder indeployments/PERFORMANCE.md) — confirm the run completes with bounded memory at a volume where the old path failed.AI assistance
Claude Code was used to explore the codebase, design the approach, implement the change, and write the tests.
Follow-ups (separate tickets)
🤖 Generated with Claude Code