Add the artifact registry repositories table
What does this MR do and why?
The artifact registry repositories list rendered a heading and an empty state. It now renders the organization's repositories.
The table carries six columns: format with its ecosystem logo, name with a visibility affordance, type as a badge, downloads, size, and last updated. Counters reach the browser as strings through the BigInt scalar and default to zero, because a repository nothing has been published to yet carries neither. A repository whose content has never changed reads "Never" rather than leaving the cell blank.
The page derives its remaining states from the query: loading, populated, error, and not found. A failed query renders the service-unavailable alert with the heading intact, while a null connection renders the not-found component alone, so the view never confirms that an organization the viewer cannot see exists. The keyset pager holds its cursor in the route query, so a page survives a reload and can be shared.
An aria-live region announces the rendered result state. It enters the DOM with the page rather than with the first result, because a region that appears at the same moment as its content is not reliably announced. The shell's focus watcher narrows to the route path, so the cursor updates this change introduces no longer steal focus back to the shell and interrupt that announcement.
Visibility renders as private only. ADR-021 descopes both public and internal from the closed beta, because each grants read without a role assignment and so breaks closed-by-default. The read enum still decodes every value the registry can return.
Still client-side
The connection is resolved by the local Apollo resolvers in graphql/mock_resolvers.js; the GraphQL backend for it has not landed yet. The query document keeps its @client directive, so graphql-verify skips it. A later step removes the directive and binds the document to the schema.
References
- Plan:
docs/plans/monolith/2026-07-28-repositories-list.md, Step 4 (Repositories table) - The
Typecolumn and the stacked-layout alignment follow the Google Artifact Registry list table,ee/app/assets/javascripts/packages_and_registries/google_artifact_registry/components/list/table.vue - The visibility affordance follows
app/assets/javascripts/vue_shared/components/visibility_icon_button.vue, which uses a focusable button so the tooltip opens on keyboard focus and not hover alone
Screenshots or screen recordings
| State | Result |
|---|---|
| Loading | Header row with all six columns, aria-busy="true", live region reads "Loading repositories." |
| Empty | "No repositories" / "This organization has no repositories yet." |
| Populated | All six columns across Docker, Maven, npm, and OCI repositories |
| Error | Non-dismissible service-unavailable alert, heading retained, no table |
| Not found | Not-found component alone, no heading |
| Before | After |
|---|---|
![]() |
![]() |
How to set up and validate locally
-
Enable the feature flag for your organization:
Feature.enable(:artifact_registry_ui, Organizations::Organization.first) -
Seed the client-side store so the list renders rows, either by creating a repository through the UI's own create form, or by adding entries to
mockRepositoriesinee/app/assets/javascripts/packages_and_registries/artifact_registry/graphql/mock_resolvers.js. -
Visit
/o/<organization>/-/artifact_registry/acme/repositories. -
Narrow the viewport below
mdto check the stacked layout.
MR acceptance checklist
Evaluate this MR against the MR acceptance checklist. It helps you analyze changes to reduce risks in quality, performance, reliability, security, and maintainability.
Related to #602638 (closed)

