Skip to content

Commit

Permalink
fix(Link): Do not ignore onMouseEnter prop with absolute href (#32012)
Browse files Browse the repository at this point in the history
Fixes #22733

Regardless of whether it's recommended that Link be used with external href values or not, they can be used and `onMouseEnter` being swallowed with an external href value is unexpected behavior.

## Bug

- [x] Related issues linked using `fixes #number`
- [ ] Integration tests added
- [ ] Errors have helpful link attached, see `contributing.md`

## Documentation / Examples

- [x] Make sure the linting passes by running `yarn lint`
  • Loading branch information
ericmatthys authored Dec 1, 2021
1 parent 332cd06 commit f225179
Show file tree
Hide file tree
Showing 3 changed files with 31 additions and 2 deletions.
5 changes: 3 additions & 2 deletions packages/next/client/link.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -291,11 +291,12 @@ function Link(props: React.PropsWithChildren<LinkProps>) {
}

childProps.onMouseEnter = (e: React.MouseEvent) => {
if (!isLocalURL(href)) return
if (child.props && typeof child.props.onMouseEnter === 'function') {
child.props.onMouseEnter(e)
}
prefetch(router, href, as, { priority: true })
if (isLocalURL(href)) {
prefetch(router, href, as, { priority: true })
}
}

// If child is an <a> tag and doesn't have a href attribute, or if the 'passHref' property is
Expand Down
13 changes: 13 additions & 0 deletions test/integration/client-navigation/pages/absolute-url.js
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,8 @@ export async function getServerSideProps({ query: { port } }) {

export default function Page({ port }) {
const router = useRouter()
const [hover, setHover] = React.useState(false)

return (
<>
<Link href="https://vercel.com/">
Expand Down Expand Up @@ -61,6 +63,17 @@ export default function Page({ port }) {
<Link href="mailto:[email protected]">
<a id="mailto-link">mailto:[email protected]</a>
</Link>
<br />
<Link href="https://vercel.com/">
<a
id="absolute-link-mouse-events"
data-hover={hover}
onMouseEnter={() => setHover(true)}
onMouseLeave={() => setHover(false)}
>
https://vercel.com/
</a>
</Link>
</>
)
}
15 changes: 15 additions & 0 deletions test/integration/client-navigation/test/index.test.js
Original file line number Diff line number Diff line change
Expand Up @@ -118,6 +118,21 @@ describe('Client Navigation', () => {
)
})

it('should call mouse handlers with an absolute url', async () => {
const browser = await webdriver(
context.appPort,
`/absolute-url?port=${context.appPort}`
)

await browser.elementByCss('#absolute-link-mouse-events').moveTo()

expect(
await browser
.waitForElementByCss('#absolute-link-mouse-events')
.getAttribute('data-hover')
).toBe('true')
})

it('should navigate an absolute local url', async () => {
const browser = await webdriver(
context.appPort,
Expand Down

0 comments on commit f225179

Please sign in to comment.