Skip to content

feat(pages): show and edit grid pages of an application - #3215

Open
rubenvdlinde wants to merge 3 commits into
feat/noid/grid-widget-editorfrom
feat/noid/grid-pages-ui
Open

rubenvdlinde wants to merge 3 commits into
feat/noid/grid-widget-editorfrom
feat/noid/grid-pages-ui

Conversation

@rubenvdlinde

@rubenvdlinde rubenvdlinde commented Nov 3, 2026 •

Copy link
Copy Markdown

Part of #3099, on top of #3214 (widget dialog). An application gets a page bar under its description, and the people who manage it can add grid pages and arrange widgets on them. The start page still lists its tables and views as before; #3216 shows it as a grid page too.

Size: 1453 lines: 1094 code and 359 tests.

What changes

  • The page bar shows the start page first, then the grid pages in the order they were added, each with its icon. It follows the WAI-ARIA tabs pattern: a tablist with one tab stop, the arrow keys, Home and End move between tabs, Enter or Space opens one, and each tab has aria-selected and aria-controls pointing at the page panel, which is labelled by its tab. In a right-to-left language the arrow keys follow the reading direction.
  • Adding a page asks for a title, an icon from the named icon set, a technical name and a description. The technical name is optional; the form checks it like the server (lower case letters, digits and underscores, starting with a letter) and refuses the page_<number> form the server keeps for itself. Without one the page gets page_<id>.
  • A grid page shows its widgets for everyone who can open the application. People who manage it get Edit page, Edit page details and Delete page.
  • Edit mode works on a copy: add a widget, configure or remove one, drag and resize, or move and resize from the widget's menu with the keyboard. Save sends all widgets at once through PATCH /api/2/contexts/{contextId}/pages/{pageId}, Cancel drops every change, and leaving the page or closing the tab with unsaved changes asks first.
  • Deleting a page asks for confirmation; its tables and views stay in the application.
  • Routes: /application/{contextId}/page/{pageId} opens a grid page.
  • Who sees edit controls: the owner of the application, the same rule the existing Edit application dialog uses. The server checks manage access on every page endpoint itself (feat(api): pages and widgets on api/2 #3133); a sharee who calls them gets a 403.

Where else applications show up

Applications and their pages have no public share page, and the Smart Picker and reference widgets only cover tables and views, so there's nothing to wire up there.

How it was tested

On Nextcloud 34 with PostgreSQL:

  • Playwright context-grid-pages.spec.ts: adding a page with a title, icon, technical name and description, adding a header and a table widget and finding them after a reload, Cancel drops changes, a sharee sees the page read-only and gets a 403 on PATCH, a table removed from the application leaves its widget asking for a new one, and moving and resizing a widget from its menu
  • Cypress component tests ContextPageBar.cy.js (order, one tab stop, arrow keys, Home and End, add only for managers) and ContextPageForm.cy.js (technical name checks, keeping an automatic name)
  • npm run lint, npm run stylelint and npm run build
  • no PHP changes

🖼️ Screenshots

Desktop (1400 px) Phone (420 px)
A grid page
Editing the page
Adding a page

🏁 Checklist

  • ⛑️ Tests (unit and/or integration) are included or not needed
  • 🔙 Backport requests are created or not needed: /backport to stableX.X
  • 📅 Milestone is set
  • 🌸 PR title is meaningful (if it should be in the changelog: is it meaningful to users?)

🤖 AI (if applicable)

  • The content of this PR was partly or fully generated using AI

An application gets a page bar under its description, built as a tab
list: one tab stop, the arrow keys, Home and End move between pages.
Its owner can add grid pages with a title, a named icon, a technical
name and a description, and arrange their widgets in an edit mode that
saves the whole grid through the api/2 page endpoints. Widgets can be
moved and resized from their menu with the keyboard, and unsaved
changes are confirmed before leaving the page.

Assisted-by: ClaudeCode:claude-opus-5-5
Signed-off-by: Ruben van der Linde <ruben@conduction.nl>
…up the texts

The page tabs look like the tabs of NcAppSidebar: an icon above the title, the
selected tab tinted and underlined. The start page of an application is called Home
until it gets a title, like the home of a conversation in Talk. Saving a page uses the
checkmark, and the page actions sit on the right also when the page shows no heading.
The descriptions of the application and of a page line up with the page tabs and the
texts in the widgets.

Assisted-by: ClaudeCode:claude-opus-5-5
Signed-off-by: Ruben van der Linde <ruben@conduction.nl>
@rubenvdlinde
rubenvdlinde force-pushed the feat/noid/grid-pages-ui branch from d05e9b5 to 844d24f Compare November 5, 2026 11:59
The start page still lists its tables here, so they keep their own heading. Only a table
in a widget of a grid page shows its title in the widget.

Assisted-by: ClaudeCode:claude-opus-5-5
Signed-off-by: Ruben van der Linde <ruben@conduction.nl>
@rubenvdlinde

Copy link
Copy Markdown
Author

Following @jancborchardt's feedback on #3099: the page tabs look like the NcAppSidebar tabs, the start page is called Home, saving uses the checkmark, "Edit page" sits on the right on every page, and the descriptions line up with the page tabs and the widget texts.

Desktop (1400 px) Phone (420 px)
Home
A page
Editing the page

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant