mirror of
https://github.com/terribleplan/next.js.git
synced 2024-01-19 02:48:18 +00:00
Dedupe only items with unique key (#5800)
Fixes #3705 Fixes #4656 - No longer automatically dedupe certain tags. Only the ones we know are *never* going to be duplicate like charSet, title etc. - Fix `key=""` behavior, making sure that if a unique key is provided tags are deduped based on that. For example: ```jsx <meta property='fb:pages' content='one'> <meta property='fb:pages' content='two'> ``` Would currently cause ```jsx <meta property='fb:pages' content='two'> ``` ### After this change: ```jsx <meta property='fb:pages' content='one'> <meta property='fb:pages' content='two'> ``` Then if you use next/head multiple times / want to be able to override: ```jsx <meta property='fb:pages' content='one' key="not-unique-key"> <meta property='fb:pages' content='two' key="not-unique-key"> ``` Would cause: ```jsx <meta property='fb:pages' content='two'> ``` As `key` gets deduped correctly after this PR, similar to how React itself works.
This commit is contained in:
parent
58f5dd297a
commit
9890e06907
|
@ -52,8 +52,7 @@ function onStateChange (head) {
|
|||
}
|
||||
}
|
||||
|
||||
const METATYPES = ['name', 'httpEquiv', 'charSet', 'itemProp', 'property']
|
||||
const ALLOWED_DUPLICATES = ['article:tag', 'og:image', 'og:image:alt', 'og:image:width', 'og:image:height', 'og:image:type', 'og:image:secure_url', 'og:image:url']
|
||||
const METATYPES = ['name', 'httpEquiv', 'charSet', 'itemProp']
|
||||
|
||||
/*
|
||||
returns a function for filtering head child elements
|
||||
|
@ -71,6 +70,7 @@ function unique () {
|
|||
if (h.key && h.key.indexOf('.$') === 0) {
|
||||
if (keys.has(h.key)) return false
|
||||
keys.add(h.key)
|
||||
return true
|
||||
}
|
||||
switch (h.type) {
|
||||
case 'title':
|
||||
|
@ -89,7 +89,7 @@ function unique () {
|
|||
} else {
|
||||
const category = h.props[metatype]
|
||||
const categories = metaCategories[metatype] || new Set()
|
||||
if (categories.has(category) && ALLOWED_DUPLICATES.indexOf(category) === -1) return false
|
||||
if (categories.has(category)) return false
|
||||
categories.add(category)
|
||||
metaCategories[metatype] = categories
|
||||
}
|
||||
|
|
|
@ -13,8 +13,8 @@ export default () => <div>
|
|||
{/* allow duplicates for specific tags */}
|
||||
<meta property='article:tag' content='tag1' key='tag1key' />
|
||||
<meta property='article:tag' content='tag2' key='tag2key' />
|
||||
<meta property='dedupe:tag' content='tag3' key='tag3key' />
|
||||
<meta property='dedupe:tag' content='tag4' key='tag4key' />
|
||||
<meta property='dedupe:tag' content='tag3' key='same-key' />
|
||||
<meta property='dedupe:tag' content='tag4' key='same-key' />
|
||||
<meta property='og:image' content='ogImageTag1' key='ogImageTag1Key' />
|
||||
<meta property='og:image' content='ogImageTag2' key='ogImageTag2Key' />
|
||||
<meta property='og:image:alt' content='ogImageAltTag1' key='ogImageAltTag1Key' />
|
||||
|
@ -30,6 +30,9 @@ export default () => <div>
|
|||
<meta property='og:image:url' content='ogImageUrlTag1' key='ogImageUrlTag1Key' />
|
||||
<meta property='og:image:url' content='ogImageUrlTag2' key='ogImageUrlTag2Key' />
|
||||
|
||||
<meta property='fb:pages' content='fbpages1' />
|
||||
<meta property='fb:pages' content='fbpages2' />
|
||||
|
||||
<React.Fragment>
|
||||
<title>Fragment title</title>
|
||||
<meta content='meta fragment' />
|
||||
|
@ -43,5 +46,5 @@ export default () => <div>
|
|||
<link rel='stylesheet' href='dedupe-style.css' key='my-style' />
|
||||
<link rel='stylesheet' href='dedupe-style.css' key='my-style' />
|
||||
</Head>
|
||||
<h1>I can haz meta tags</h1>
|
||||
<h1>I can have meta tags</h1>
|
||||
</div>
|
||||
|
|
|
@ -33,7 +33,7 @@ export default function ({ app }, suiteName, render, fetch) {
|
|||
const html = await (render('/head'))
|
||||
expect(html.includes('<meta charSet="iso-8859-5" class="next-head"/>')).toBeTruthy()
|
||||
expect(html.includes('<meta content="my meta" class="next-head"/>')).toBeTruthy()
|
||||
expect(html.includes('I can haz meta tags')).toBeTruthy()
|
||||
expect(html.includes('I can have meta tags')).toBeTruthy()
|
||||
})
|
||||
|
||||
test('header helper dedupes tags', async () => {
|
||||
|
@ -65,7 +65,8 @@ export default function ({ app }, suiteName, render, fetch) {
|
|||
expect(html).toContain('<meta property="og:image:secure_url" content="ogImageSecureUrlTag1" class="next-head"/>')
|
||||
expect(html).toContain('<meta property="og:image:secure_url" content="ogImageSecureUrlTag2" class="next-head"/>')
|
||||
expect(html).toContain('<meta property="og:image:url" content="ogImageUrlTag1" class="next-head"/>')
|
||||
expect(html).toContain('<meta property="og:image:url" content="ogImageUrlTag2" class="next-head"/>')
|
||||
expect(html).toContain('<meta property="fb:pages" content="fbpages1" class="next-head"/>')
|
||||
expect(html).toContain('<meta property="fb:pages" content="fbpages2" class="next-head"/>')
|
||||
})
|
||||
|
||||
test('header helper renders Fragment children', async () => {
|
||||
|
|
Loading…
Reference in a new issue