#82207·gutenberg

Navigation with a top-level Page List produces invalid ul > ul markup

Author: Jiwoon-KimCreated Aug 29, 2026Updated Sep 18, 2026
Labels[Type] Bug[Status] In Progress[Block] Navigation[Block] Page List

Description

When a top-level core/page-list is placed between navigation items, the Navigation block can render a <ul> directly inside its navigation container <ul>:

xml
<ul class="wp-block-navigation__container">
  <li class="wp-block-navigation-item">Home</li>
  <ul class="wp-block-page-list">
    <li class="wp-block-pages-list__item wp-block-navigation-item">Blog</li>
  </ul>
  <li class="wp-block-navigation-item">Last</li>
</ul>

That violates the HTML content model for ul: its children may be li or script-supporting elements, not another ul. It can also result in inconsistent list semantics for assistive technologies.

The issue occurs because WP_Navigation_Block_Renderer::get_inner_blocks_html() treats an inner block as a list item when its rendered markup contains any LI tag. A top-level Page List therefore opens the Navigation container list, but Page List still emits its own outer ul.

The Page List renderer already knows when it is a Navigation child (showSubmenuIcon is present in its block context). It only suppresses its outer list when core/isInsideSubmenu is true.

Related discussion: #81282.

Step-by-step reproduction instructions

  1. Create a Navigation block with no menu reference, or edit a navigation menu.
  2. Add a Navigation Link.
  3. Add a Page List as a top-level Navigation child.
  4. Add another Navigation Link after it.
  5. Render the page and inspect the Navigation markup.

For example:

xml
<!-- wp:navigation {"layout":{"type":"flex","justifyContent":"space-between"}} -->
<!-- wp:navigation-link {"label":"Home","url":"/","kind":"custom"} /-->
<!-- wp:page-list /-->
<!-- wp:navigation-link {"label":"Last","url":"/last","kind":"custom"} /-->
<!-- /wp:navigation -->

Actual result

core/page-list emits an outer ul even though it is a direct Navigation child. The Navigation renderer then places that ul inside .wp-block-navigation__container, alongside the surrounding li items.

This also makes the Page List a separate flex child, so justify-content: space-between, wrapping, and item spacing do not treat its generated page items as peers of adjacent Navigation links.

Expected result

Every top-level navigation destination should participate in the same list and layout contract. A Page List should expand into peer li elements at its insertion point; a nested page list belongs inside the li for its parent page:

xml
<ul class="wp-block-navigation__container">
  <li class="wp-block-navigation-item">Home</li>
  <li class="wp-block-pages-list__item wp-block-navigation-item">
    About
    <ul>
      <li class="wp-block-pages-list__item wp-block-navigation-item">Team</li>
    </ul>
  </li>
  <li class="wp-block-navigation-item">Last</li>
</ul>

In particular, the navigation container should not contain a direct child ul produced by a top-level Page List.

Possible minimal fix

One candidate is to keep the existing meaning of $is_nested intact and only change Page List's wrapper decision:

php
$wrapper_markup = ( $is_nested || $is_navigation_child )
    ? '%2$s'
    : '<ul %1$s>%2$s</ul>';

This would let a top-level Page List in Navigation emit its generated li items into the Navigation container, as it already does for a Page List inside a submenu.

There is a compatibility consideration: omitting Page List's wrapper also omits the wp-block-page-list wrapper class. An alternative is to address this in the Navigation renderer by defining an explicit item/fragment contract for children. Either approach should preserve standalone Page List rendering and submenu overlay-color behavior.

Environment info

WordPress 7.1

Confirmed local reproduction

This was also reproduced on a running local WordPress 7.1 environment at http://localhost:8884/, not only by reading source. Its published wp_navigation menu contains a top-level Page List, and the rendered home page contains:

xml
<ul class="wp-block-navigation__container ...">
  <ul class="wp-block-page-list">
    <li class="wp-block-pages-list__item wp-block-navigation-item">...</li>
  </ul>
</ul>

The local environment renders this shape in two Navigation instances on the same page.

References