Summary
When the Header Footer Grid Builder contains the Footer Menu in both desktop and mobile footer layouts, both rendered menu lists receive id="footer-menu". Each list is expected to have a unique DOM ID, but the responsive variants coexist in the document with the same ID. This produces invalid HTML, is reported by accessibility validators, and can make ID-based menu identification ambiguous for assistive technology and frontend selectors.
Customer context
- Product / area: Neve, Header Footer Grid Builder, Footer Menu
- Version: Neve 4.2.10
- Environment: WordPress 7.0.2
- Integration / third party: No dependency identified; Neve Pro is active, but the affected runtime template belongs to the Neve theme
- Reported error / symptom: Two responsive Footer Menu lists render with
id="footer-menu"; WAVE and axe-based tools report the duplicate ID
- Impact: Accessibility and HTML validation failure on the reported configuration
Reproduction notes
- In Neve 4.2.10, configure the Header Footer Grid Builder so the Footer Menu is present in both desktop and mobile footer layouts.
- Publish or preview a frontend page.
- Inspect the complete DOM rather than only the visible breakpoint variant.
- Observe two Footer Menu lists matching
ul#footer-menu.
The customer reports this result with WAVE and axe-based validation. Runtime reproduction was not performed locally; the rendered path was confirmed from the source and the v4.2.10 tag.
Diagnosis
Conclusion
The defect is confirmed by source inspection and is present in tag v4.2.10. Neve renders every populated responsive footer layout, and each Footer Menu render invokes the same template with the literal menu_id value footer-menu. When the component is present in both device layouts, both list elements therefore receive the same ID. The Pro add-on has no runtime override for this template, so the issue routes to Codeinwp/neve.
Where this likely occurs
header-footer-grid/templates/components/component-nav-footer.php — template scope around lines 34–44, wp_nav_menu() arguments: assigns the literal menu_id value footer-menu on each render. Git blame traces this assignment to commit 04d5d8690; tag v4.2.10 contains the same value.
header-footer-grid/Core/Components/NavFooter.php — NavFooter::render_component() lines 218–226: loads the shared Footer Menu template for each component render. NavFooter::add_settings() lines 104–133 also contains a CSS selector tied to #footer-menu.
header-footer-grid/Core/Builder/Abstract_Builder.php — Abstract_Builder::render() lines 826–843 and Abstract_Builder::new_render_components() lines 1269–1459: iterates populated device layouts and renders the same registered component instance for each responsive occurrence.
header-footer-grid/templates/footer-row-wrapper.php — template scope lines 24–36 and 54–64: keeps desktop and mobile rows in the document and controls visibility through responsive classes before rendering their components.
- Responsive footer support entered in commit
f6ed0b8ff and is present from v3.8.0 onward. Commit e59ee0eca later qualified footer row IDs by device but did not alter the nested Footer Menu ID.
Engineering notes
The confirmed scope is the Neve theme's Footer Menu component when both responsive footer variants are rendered. The desktop and mobile rows coexist in the DOM while CSS controls visibility. The affected ID also appears in a generated hover selector, so ID-dependent styling is part of this path. A prior closed report, GitHub issue #4256, covered duplicate IDs in responsive header navigation such as the secondary menu; its associated commits addressed those component paths, while the inspected Footer Menu template retains its fixed ID. No runtime Footer Menu template override was found in neve-pro-addon.
Test coverage status
e2e-tests/specs/customizer/hfg/hfg-footer-mobile.spec.ts lines 48–58 has an ID uniqueness test, but it checks only device-qualified footer row IDs. Its fixture, e2e-tests/fixtures/customizer/hfg/footer-mobile-setup.json lines 1–3, places the Footer Menu only in the mobile layout. e2e-tests/specs/customizer/hfg/hfg-footer-menu-component.spec.ts lines 5–36 exercises desktop Footer Menu styling, and e2e-tests/fixtures/customizer/hfg/footer-menu-setup.json lines 1–6 configures only a desktop Footer Menu. These suites do not cover the reported dual-layout path.
What to verify or explore next
- Reproduce with
footer-menu configured in both desktop and mobile footer rows and count ul#footer-menu in the complete DOM.
- Run
npx playwright test e2e-tests/specs/customizer/hfg/hfg-footer-mobile.spec.ts against a fixture containing the Footer Menu in both layouts.
- Verify ID-based Footer Menu styling and hover behavior at desktop and mobile viewports.
- Check the inherited-mobile-layout path introduced by commit
9e251bbe4 separately from an explicitly configured mobile layout.
Unknowns / follow-up
A local WordPress runtime reproduction was not executed. The ticket reports explicit dual markup and validator findings, while the source and release tag establish the duplicate assignment deterministically for the described layout.
Confidence
Confidence: 98/100
Repository inspection confirms that Neve 4.2.10 renders each populated responsive footer layout through one Footer Menu template whose wp_nav_menu() arguments contain the literal menu_id value footer-menu. Existing end-to-end coverage verifies row IDs but does not exercise the Footer Menu in both layouts or assert its ID uniqueness.
Source: HelpScout #3405021142
Generated by bug-report-triage (ID: bug-report-triage_6a6dd1ca6e8ff9.59186925)
Summary
When the Header Footer Grid Builder contains the Footer Menu in both desktop and mobile footer layouts, both rendered menu lists receive
id="footer-menu". Each list is expected to have a unique DOM ID, but the responsive variants coexist in the document with the same ID. This produces invalid HTML, is reported by accessibility validators, and can make ID-based menu identification ambiguous for assistive technology and frontend selectors.Customer context
id="footer-menu"; WAVE and axe-based tools report the duplicate IDReproduction notes
ul#footer-menu.The customer reports this result with WAVE and axe-based validation. Runtime reproduction was not performed locally; the rendered path was confirmed from the source and the
v4.2.10tag.Diagnosis
Conclusion
The defect is confirmed by source inspection and is present in tag
v4.2.10. Neve renders every populated responsive footer layout, and each Footer Menu render invokes the same template with the literalmenu_idvaluefooter-menu. When the component is present in both device layouts, both list elements therefore receive the same ID. The Pro add-on has no runtime override for this template, so the issue routes toCodeinwp/neve.Where this likely occurs
header-footer-grid/templates/components/component-nav-footer.php— template scope around lines 34–44,wp_nav_menu()arguments: assigns the literalmenu_idvaluefooter-menuon each render. Git blame traces this assignment to commit04d5d8690; tagv4.2.10contains the same value.header-footer-grid/Core/Components/NavFooter.php—NavFooter::render_component()lines 218–226: loads the shared Footer Menu template for each component render.NavFooter::add_settings()lines 104–133 also contains a CSS selector tied to#footer-menu.header-footer-grid/Core/Builder/Abstract_Builder.php—Abstract_Builder::render()lines 826–843 andAbstract_Builder::new_render_components()lines 1269–1459: iterates populated device layouts and renders the same registered component instance for each responsive occurrence.header-footer-grid/templates/footer-row-wrapper.php— template scope lines 24–36 and 54–64: keeps desktop and mobile rows in the document and controls visibility through responsive classes before rendering their components.f6ed0b8ffand is present fromv3.8.0onward. Commite59ee0ecalater qualified footer row IDs by device but did not alter the nested Footer Menu ID.Engineering notes
The confirmed scope is the Neve theme's Footer Menu component when both responsive footer variants are rendered. The desktop and mobile rows coexist in the DOM while CSS controls visibility. The affected ID also appears in a generated hover selector, so ID-dependent styling is part of this path. A prior closed report, GitHub issue
#4256, covered duplicate IDs in responsive header navigation such as the secondary menu; its associated commits addressed those component paths, while the inspected Footer Menu template retains its fixed ID. No runtime Footer Menu template override was found inneve-pro-addon.Test coverage status
e2e-tests/specs/customizer/hfg/hfg-footer-mobile.spec.tslines 48–58 has an ID uniqueness test, but it checks only device-qualified footer row IDs. Its fixture,e2e-tests/fixtures/customizer/hfg/footer-mobile-setup.jsonlines 1–3, places the Footer Menu only in the mobile layout.e2e-tests/specs/customizer/hfg/hfg-footer-menu-component.spec.tslines 5–36 exercises desktop Footer Menu styling, ande2e-tests/fixtures/customizer/hfg/footer-menu-setup.jsonlines 1–6 configures only a desktop Footer Menu. These suites do not cover the reported dual-layout path.What to verify or explore next
footer-menuconfigured in both desktop and mobile footer rows and countul#footer-menuin the complete DOM.npx playwright test e2e-tests/specs/customizer/hfg/hfg-footer-mobile.spec.tsagainst a fixture containing the Footer Menu in both layouts.9e251bbe4separately from an explicitly configured mobile layout.Unknowns / follow-up
A local WordPress runtime reproduction was not executed. The ticket reports explicit dual markup and validator findings, while the source and release tag establish the duplicate assignment deterministically for the described layout.
Confidence
Confidence: 98/100
Repository inspection confirms that Neve 4.2.10 renders each populated responsive footer layout through one Footer Menu template whose
wp_nav_menu()arguments contain the literalmenu_idvaluefooter-menu. Existing end-to-end coverage verifies row IDs but does not exercise the Footer Menu in both layouts or assert its ID uniqueness.Source: HelpScout #3405021142
Generated by bug-report-triage (ID: bug-report-triage_6a6dd1ca6e8ff9.59186925)