Skip to content

fix: fix search layout stability and mobile close on outside click#2204

Closed
thegreatalxx wants to merge 3 commits intonpmx-dev:mainfrom
thegreatalxx:fix/search-layout-stability
Closed

fix: fix search layout stability and mobile close on outside click#2204
thegreatalxx wants to merge 3 commits intonpmx-dev:mainfrom
thegreatalxx:fix/search-layout-stability

Conversation

@thegreatalxx
Copy link
Copy Markdown

🔗 Linked issue

resolves #2191
resolves #2112
resolves #1881

🧭 Context

The AppHeader had multiple related layout issues: (1) the search container lacked a template ref so clicks outside it on mobile couldn't close the expanded search, (2) hiding the nav list with hidden caused a layout shift when the search expanded, and (3) the header row had an unnecessary z-1 class causing z-index conflicts with dropdowns.

📚 Description

  • Added ref="searchContainerRef" to the search container and used onClickOutside to collapse the mobile search when clicking outside it.
  • Changed the nav list visibility from hidden to invisible pointer-events-none so it still occupies space and prevents layout shifts when the search expands.
  • Removed z-1 from the header container div to avoid stacking context conflicts with dropdown overlays.

A regression test (test/nuxt/components/AppHeader.spec.ts) mounts the header and verifies the search area renders and the header element is present.

@vercel
Copy link
Copy Markdown

vercel bot commented Mar 22, 2026

The latest updates on your projects. Learn more about Vercel for GitHub.

Project Deployment Actions Updated (UTC)
npmx.dev Ready Ready Preview, Comment Mar 22, 2026 7:23pm
2 Skipped Deployments
Project Deployment Actions Updated (UTC)
docs.npmx.dev Ignored Ignored Preview Mar 22, 2026 7:23pm
npmx-lunaria Ignored Ignored Mar 22, 2026 7:23pm

Request Review

@coderabbitai
Copy link
Copy Markdown
Contributor

coderabbitai bot commented Mar 22, 2026

Warning

Rate limit exceeded

@thealxlabs has exceeded the limit for the number of commits that can be reviewed per hour. Please wait 0 minutes and 21 seconds before requesting another review.

⌛ How to resolve this issue?

After the wait time has elapsed, a review can be triggered using the @coderabbitai review command as a PR comment. Alternatively, push new commits to this PR.

We recommend that you space out your commits to avoid hitting the rate limit.

🚦 How do rate limits work?

CodeRabbit enforces hourly rate limits for each developer per organization.

Our paid plans have higher rate limits than the trial, open-source and free plans. In all cases, we re-allow further reviews after a brief timeout.

Please see our FAQ for further information.

ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

Run ID: afde9820-8942-43ba-a267-9c8eba7eefcd

📥 Commits

Reviewing files that changed from the base of the PR and between 10f1deb and 1178fc0.

📒 Files selected for processing (1)
  • test/nuxt/components/AppHeader.spec.ts
📝 Walkthrough

Walkthrough

The changes modify the AppHeader component to address layout stability and user interaction issues. The component now includes a click-outside handler to collapse the mobile search when users click outside the search area on non-search pages. The visibility handling for navigation items has been adjusted from hidden to invisible pointer-events-none to preserve layout integrity during search expansion. The z-index utility has been removed from the main nav container. A comprehensive test suite has been added to validate AppHeader rendering, search input presence, navigation visibility classes, and logo rendering.

Suggested reviewers

  • danielroe
  • graphieros
  • shuuji3
🚥 Pre-merge checks | ✅ 3
✅ Passed checks (3 passed)
Check name Status Explanation
Description check ✅ Passed The description clearly relates to the changeset, explaining the three main issues fixed and the corresponding code changes made.
Linked Issues check ✅ Passed The pull request addresses all three linked issues: #2191 (z-index conflicts fixed by removing z-1), #2112 (layout stability improved by changing hidden to invisible pointer-events-none), and #1881 (mobile search close-on-outside-click implemented via onClickOutside handler).
Out of Scope Changes check ✅ Passed All changes are directly scoped to addressing the three linked issues; the AppHeader component modifications and corresponding test file are both necessary and relevant to the stated objectives.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

Copy link
Copy Markdown
Contributor

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🧹 Nitpick comments (2)
test/nuxt/components/AppHeader.spec.ts (2)

11-15: Strengthen the search input assertion.

The assertion expect(html).toContain('search') is fragile as it matches any occurrence of the string 'search' (class names, attributes, text). Consider querying for the actual search input element.

♻️ Suggested improvement
-    const html = wrapper.html()
-    // The header renders a search form/input
-    expect(html).toContain('search')
+    // The search container with ref="searchContainerRef" should be rendered
+    // and contain an input element for the search functionality
+    const searchInput = wrapper.find('input[type="search"], input[placeholder*="search" i]')
+    expect(searchInput.exists()).toBe(true)

18-31: Test does not verify the behaviour described in its name.

The test is named "nav links use invisible instead of hidden to prevent layout shift" but the assertion only checks that a nav list element exists. It doesn't verify:

  1. That invisible pointer-events-none classes are applied when showFullSearch is true
  2. That hidden is not used for this visibility toggling

To properly test this, you would need to mock useConnector to return a connected user (since the ul requires isConnected && npmUser) and trigger a search focus to set showFullSearch = true.

♻️ Suggested improvement (simplified approach)

If full integration testing is not feasible, consider either:

  • Renaming the test to reflect what it actually checks (e.g., "renders nav list element")
  • Or adding a comment explaining the limitation
-  it('nav links use invisible instead of hidden to prevent layout shift', async () => {
+  it('renders nav list structure for connected users', async () => {
     const wrapper = await mountSuspended(AppHeader, {
       route: '/',
     })
 
     const html = wrapper.html()
-    // The nav list should use 'invisible pointer-events-none' (not 'hidden')
-    // when the search is expanded, to prevent layout shifts
-    // Verify the nav list element exists at all
+    // Verify the nav structure is present
+    // Note: Full visibility toggling behaviour requires mocking useConnector
     const navList = wrapper.find('nav ul, ul[class*="list-none"]')
-    // When not on a search page and search is not expanded,
-    // the nav list should be visible (not invisible)
     expect(navList.exists() || html.includes('list-none')).toBe(true)
   })

ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

Run ID: 5ebf90a5-dfb6-49f9-a03f-a0e9a1843908

📥 Commits

Reviewing files that changed from the base of the PR and between 7f2fc1a and 10f1deb.

📒 Files selected for processing (2)
  • app/components/AppHeader.vue
  • test/nuxt/components/AppHeader.spec.ts

@codecov
Copy link
Copy Markdown

codecov bot commented Mar 22, 2026

Codecov Report

❌ Patch coverage is 50.00000% with 1 line in your changes missing coverage. Please review.
✅ All tests successful. No failed tests found.

Files with missing lines Patch % Lines
app/components/AppHeader.vue 50.00% 1 Missing ⚠️

📢 Thoughts on this report? Let us know!

@knowler
Copy link
Copy Markdown
Member

knowler commented Mar 23, 2026

Hello. I will be closing this because there are already open or merged PRs to resolve the linked issues (check for linked PRs in those issues for details). We like to honour existing work when we can. Please check before making new PRs. Also, make sure to check if bugs exist on the preview URL: https://main.npmx.dev

@knowler knowler closed this Mar 23, 2026
@knowler knowler added the duplicate This issue or pull request already exists label Mar 23, 2026
@MatteoGabriele MatteoGabriele added the 007 This PR *may* not follow our code of conduct regarding AI usage. label Mar 27, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

007 This PR *may* not follow our code of conduct regarding AI usage. duplicate This issue or pull request already exists

Projects

None yet

3 participants