ryanahamilton opened a new pull request, #71554:
URL: https://github.com/apache/airflow/pull/71554
Consolidates the shared `DataTable` chrome into a single header row above
the table, and fixes the defects that surfaced along the way.
## Why
The column visibility menu was rendered inside the last `<th>`, so its
position shifted with column order and it disappeared entirely whenever a table
had no rows. Because hidden columns persist in `localStorage`, a user who
filtered down to an empty result was left with no control that could bring them
back.
Every list page also hand-rolled its own row of controls, which left the
display toggle in a different row from the heading it belongs beside, and
several pages duplicated the row count heading `DataTable` already renders.
## What changed
**Layout.** `DataTable` owns one header row: `[heading + headingExtra] …
[actions][columns menu][display toggle]`. New `actions` and `headingExtra`
slots let pages contribute their own controls (`ExpandCollapseButtons`, sort
selects) rather than building a parallel row. The columns menu moved out of
`TableList`, so it stays reachable on an empty table.
**Empty state** moved down into `TableList`/`CardList`. In table display the
column headers stay visible and the message renders in a cell spanning every
column.
**Props.** `allowFiltering` → `showColumnsMenu` (no call site passed it, and
the menu toggles column *visibility*, not filtering). `showRowCountHeading` →
`hideRowCountHeading`, since an optional boolean defaulting to `true` reads
badly at call sites. `total` is now optional: a table whose endpoint reports no
count names its model instead of claiming zero rows.
**i18n.** Six tables named their model with a page-*title* key, so counts
read "1 Jobs" or "950 XCom" regardless of the count. Added proper
`_one`/`_other` keys and repointed them. The count-free plural label now reads
the `_other` key directly, because Russian CLDR never selects `_other` for an
integer count — the form translators supplied was unreachable.
**Bug fixes.** Removed the unreachable row-expansion machinery
(`getRowCanExpand`/`renderSubComponent`: `TableState` has no `expanded` field,
so `getIsExpanded()` was always false and no call site passed either prop).
Offset pagination no longer renders with `count={0}` on tables that report no
total. `Tasks` shows table skeletons instead of 10 empty rows while loading.
## Tests
117 files / 916 unit tests pass on this branch. Every new test was
mutation-verified: each fix was reverted in turn to confirm the intended test
failed and nothing else did.
`modelName.test.ts` is worth a look — it scans the source for
`modelName="…"` literals and resolves each through a real i18next instance,
asserting singular and plural both resolve and differ. Nothing previously
validated code-side translation keys (the i18n lint rules only compare locale
files against each other), which is how the six mis-keyed tables went
unnoticed. It found two more on its first run.
Also fixed 11 test files whose `react-i18next` mock omitted `i18n` (latent
crashes for any future test rendering a real `DataTable`), and excluded the new
empty-state row from 19 e2e row locators behind a shared `DATA_ROWS` selector —
otherwise several "at least one row exists" assertions would pass against an
empty table.
## Reviewer notes
- **No screenshots yet.** The template asks for before/after on user-facing
UI changes and I have not captured them; worth holding review on.
- **e2e suite not run.** The `DATA_ROWS` locator change is validated by
`tsc`/`eslint` only.
- Rebased on top of #71252 (restored counts for Dag Run and Task Instance
lists). Where that change and this one disagreed I took its semantics —
cursor-paginated tables *do* show a count — and dropped the test I had
asserting the opposite.
- Newsfragment to follow now that a PR number exists.
---
##### Was generative AI tooling used to co-author this PR?
- [X] Yes — Claude Code (Opus 5)
--
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.
To unsubscribe, e-mail: [email protected]
For queries about this service, please contact Infrastructure at:
[email protected]