fix(superset): API datamodel fields + SQL lineage, cache datasource/database fetches - #30353
Conversation
…atabase fetches - api_source: populate datamodel sql/description/sourceUrl and real column names - api_source/mixin: SQL (virtual dataset) lineage for API mode via _get_input_tables -> _parse_lineage_from_dataset_sql -> _get_source_table_fqn, plus a shared _resolve_lineage_database_name helper - client: bound LRUCache on fetch_datasource/fetch_database (cachedmethod) to drop the redundant per-chart/per-prefix/per-source-table REST calls made during datamodel + lineage resolution - tests: cache dedup, dataset-SQL parsing, source-table fqn
✅ PR checks passedThe linked issue has a description and all required Shipping project fields set. Thanks! |
|
Hi there 👋 Thanks for your contribution! The OpenMetadata team will review the PR shortly! Once it has been labeled as Let us know if you need any help! |
…resolution - client: cache datasource/database responses on success only (manual LRUCache writes) instead of @cachedmethod, so a transient REST failure stays retryable rather than poisoning the id with an empty result for the rest of the run - api_source: guard _resolve_lineage_database_name against an unregistered db service (get_by_name -> None), and wrap _get_source_table_fqn in try/except so one unresolvable source table no longer aborts the whole dashboard's lineage - tests: transient-failure retry + missing-db-service no-crash
Type-only: widen the _get_input_tables override param, narrow Optional model accesses (result/database), guard None args to get_by_name/build_es. No runtime behavior change; base mixin untouched.
Avoid a wasted GET /database/None call in _resolve_lineage_database_name when the datasource carries no database id; resolve the default database name only when an id is present. Behavior-identical (name was None either way).
✅ Playwright Results — workflow succeededValidated commit ✅ 107 passed · ❌ 0 failed · 🟡 0 flaky · ⏭️ 0 skipped · 🧰 0 lifecycle flaky PerformanceBlocking targets: ✅ met · Optimization targets: 🟡 in progress Shard-job maxima below are not the full workflow wall time; the linked run includes build, fixture, planning, and reporting. 🕒 Full workflow signal wall (to summary) 46m 48s ⏱️ Max setup 3m 7s · max shard execution 11m 25s · max shard-job elapsed before upload 17m 44s · reporting 3s 🌐 211.04 requests/attempt · 1.76 app boots/UI scenario · 0.00% common-shard skew Optimization targets still in progress:
How to debug locally# Download playwright-test-results-<shard> artifact and unzip
npx playwright show-trace path/to/trace.zip # view trace |
🚦 Removed from the merge queue —
|
|
🚦 Removed from the merge queue —
|
|
Changes have been cherry-picked to the 2.0 branch. |
…atabase fetches (#30353) * fix(superset): API datamodel fields + SQL lineage, cache datasource/database fetches - api_source: populate datamodel sql/description/sourceUrl and real column names - api_source/mixin: SQL (virtual dataset) lineage for API mode via _get_input_tables -> _parse_lineage_from_dataset_sql -> _get_source_table_fqn, plus a shared _resolve_lineage_database_name helper - client: bound LRUCache on fetch_datasource/fetch_database (cachedmethod) to drop the redundant per-chart/per-prefix/per-source-table REST calls made during datamodel + lineage resolution - tests: cache dedup, dataset-SQL parsing, source-table fqn * fix(superset): cache successful fetches only + guard lineage db-name resolution - client: cache datasource/database responses on success only (manual LRUCache writes) instead of @cachedmethod, so a transient REST failure stays retryable rather than poisoning the id with an empty result for the rest of the run - api_source: guard _resolve_lineage_database_name against an unregistered db service (get_by_name -> None), and wrap _get_source_table_fqn in try/except so one unresolvable source table no longer aborts the whole dashboard's lineage - tests: transient-failure retry + missing-db-service no-crash * fix(superset): satisfy basedpyright on api_source lineage type hints Type-only: widen the _get_input_tables override param, narrow Optional model accesses (result/database), guard None args to get_by_name/build_es. No runtime behavior change; base mixin untouched. * fix(superset): skip fetch_database when datasource has no database id Avoid a wasted GET /database/None call in _resolve_lineage_database_name when the datasource carries no database id; resolve the default database name only when an id is present. Behavior-identical (name was None either way). (cherry picked from commit c052e5c)
|
Failed to cherry-pick changes to the 1.13 branch. |
Code Review ✅ Approved 2 resolved / 2 findingsAdds SQL virtual dataset lineage, enriched datamodel metadata, and success-only caching for Superset API fetches to significantly reduce REST overhead. No issues found. ✅ 2 resolved✅ Edge Case: Cached datasource/database error fallbacks poison cache for the run
✅ Edge Case: Missing database triggers spurious /database/None REST call
OptionsDisplay: compact → Showing less information. Comment with these commands to change the behavior for this request:
Was this helpful? React with 👍 / 👎 | Powered by Gitar — free for open source |



Fixes #30407
What
Two related improvements to the Superset API source (plus a perf fix uncovered while doing them):
sql,descriptionandsourceUrlfrom the dataset payload, and columns use the realcolumn_nameinstead of the numeric dataset-column id._parse_lineage_from_dataset_sql, and each source table's FQN is resolved (_get_input_tables→_get_source_table_fqn), with a shared_resolve_lineage_database_namehelper to avoid duplication.fetch_datasource/fetch_database— a boundedLRUCache(viacachetools.cachedmethod) on the Superset client. The same dataset/database was being re-fetched over REST many times per run — once per chart, again per lineage pass /dbServicePrefix, and again per SQL-parsed source table. These responses are immutable within a run.Why
API-mode datamodels were missing
sql/description/sourceUrland displayed numeric column ids; virtual (SQL) datasets produced no source-table lineage. Resolving datamodels and lineage also amplified redundant/dataset/{id}and/database/{id}REST calls, which the cache removes.Performance — same ingestion, byte-identical output
Local benchmark ingesting the same dashboards/datasets with
dbServicePrefixes: [retail_mysql, analytics_pg]:GET /dataset/{id}callsGET /database/{id}callsIngested output verified identical before/after — datamodels, columns, SQL, dashboards, charts and lineage edges all diff-clean, 0 errors. The cache changes how many times Superset is called, not what is ingested.
Tests
Added to
test_superset.py: cache dedup (same id → 1 network call, distinct ids → N), dataset-SQL parsing to source tables, and source-table FQN resolution. Existing tests already cover the datamodel fields and real column names.Greptile Summary
This PR improves Superset API metadata ingestion and lineage. The main changes are:
Confidence Score: 5/5
This looks safe to merge.
Important Files Changed
Reviews (10): Last reviewed commit: "Merge branch 'main' into fix/superset-da..." | Re-trigger Greptile
Context used (3)