Skip to content

Commit

Permalink
feat: allow hrefResolver to return UrlObject instead of string
Browse files Browse the repository at this point in the history
Allows easier usage of eg. localized slugs in next-intl, which requires an UrlObject.
  • Loading branch information
marcusforsberg committed Jun 4, 2024
1 parent 7b6cca6 commit cdc90d9
Showing 1 changed file with 33 additions and 9 deletions.
42 changes: 33 additions & 9 deletions src/helpers/generateHref.ts
Original file line number Diff line number Diff line change
@@ -1,19 +1,43 @@
import {type UrlObject} from 'url'

import {InternalLink, LinkValue} from '../types'
import {isCustomLink, isEmailLink, isExternalLink, isPhoneLink} from './typeGuards'

export const generateHref = {
internal: (link: LinkValue, hrefResolver?: (link: InternalLink) => string) => {
internal: (link: LinkValue, hrefResolver?: (link: InternalLink) => string | UrlObject) => {
const internalLink = link as InternalLink
const resolvedHref =
internalLink.internalLink && hrefResolver ? hrefResolver(internalLink) : undefined

// Support UrlObjects, e.g. from Next.js
if (typeof resolvedHref === 'object' && 'pathname' in resolvedHref) {
resolvedHref.hash = internalLink.anchor?.replace(/^#/, '')

if (internalLink.parameters) {
const params = new URLSearchParams(internalLink.parameters)
const resolvedParams = new URLSearchParams(resolvedHref.query?.toString())

for (const [key, value] of params.entries()) {
resolvedParams.set(key, value)
}

resolvedHref.query = resolvedParams.toString()
}

return resolvedHref
}

let href =
resolvedHref ||
(internalLink.internalLink?.slug?.current
? `/${internalLink.internalLink.slug.current.replace(/^\//, '')}`
: undefined)

const href = internalLink.internalLink
? hrefResolver
? hrefResolver(internalLink)
: `/${internalLink.internalLink.slug?.current?.replace(/^\//, '')}`
: undefined
if (href && typeof href === 'string') {
href += (internalLink.parameters?.trim() || '') + (internalLink.anchor?.trim() || '')
}

return href
? href + (internalLink.parameters?.trim() || '') + (internalLink.anchor?.trim() || '')
: '#'
return href || '#'
},
external: (link: LinkValue) =>
isExternalLink(link) && link.url
Expand Down

0 comments on commit cdc90d9

Please sign in to comment.