Skip to content

Commit e1f44e9

Browse files
authoredJan 7, 2025··
fix(core)!: drop vmid, hid, children body keys (#447)
* fix!: drop `vmid`, `hid`, `children` `body` keys * fix: handle `body` and `children` * fix: dupe
1 parent a6c5bf1 commit e1f44e9

19 files changed

+49
-61
lines changed
 

‎docs/content/1.usage/2.guides/2.positions.md

-1
Original file line numberDiff line numberDiff line change
@@ -17,7 +17,6 @@ Possible values:
1717
- `bodyClose` - Render at the end of the `<body>`
1818

1919
Note:
20-
- Providing `body: true` is the same as `tagPosition: 'bodyClose'`.
2120
- Sorting may not be stricly honoured when moving outside the head
2221

2322
## Examples

‎docs/content/1.usage/2.guides/6.handling-duplicates.md

+1-3
Original file line numberDiff line numberDiff line change
@@ -18,7 +18,7 @@ There is different logic used to determine what tags are duplicates:
1818
- Any of the following tags: `base`, `title`, `titleTemplate`, `bodyAttrs`, `htmlAttrs`.
1919
- `<link rel="canonical">`
2020
- `<meta charset="">`
21-
- Custom provided `key` attribute (`hid` and `vmid` is also supported)
21+
- Custom provided `key` attribute
2222
- Meta `content`, `property` and `http-equiv` attributes
2323

2424
Example of a dedupe using the meta `content`.
@@ -114,8 +114,6 @@ useHead({
114114
})
115115
```
116116

117-
Note: this shares the same behaviour with `hid` and `vmid` from vue-meta.
118-
119117
## `tagDuplicateStrategy`
120118

121119
The default behaviour when a duplicate is found, is to `replace` it.

‎packages/schema/src/tags.ts

-14
Original file line numberDiff line numberDiff line change
@@ -17,14 +17,6 @@ export interface ResolvesDuplicates {
1717
* @default 'replace' (some tags will default to 'merge', such as htmlAttr)
1818
*/
1919
tagDuplicateStrategy?: 'replace' | 'merge'
20-
/**
21-
* @deprecated Use `key` instead
22-
*/
23-
hid?: string
24-
/**
25-
* @deprecated Use `key` instead
26-
*/
27-
vmid?: string
2820
}
2921

3022
export type ValidTagPositions = 'head' | 'bodyClose' | 'bodyOpen'
@@ -51,12 +43,6 @@ export interface InnerContent {
5143
* Sets the textContent of an element. Safer for XSS.
5244
*/
5345
textContent?: InnerContentVal
54-
/**
55-
* Sets the textContent of an element.
56-
*
57-
* @deprecated Use `textContent` or `innerHTML`.
58-
*/
59-
children?: InnerContentVal
6046
}
6147

6248
export interface TagPriority {

‎packages/shared/src/constants.ts

+1-1
Original file line numberDiff line numberDiff line change
@@ -24,7 +24,7 @@ export const ValidHeadTags = new Set([
2424

2525
export const UniqueTags = new Set(['base', 'title', 'titleTemplate', 'bodyAttrs', 'htmlAttrs', 'templateParams'])
2626

27-
export const TagConfigKeys = new Set(['tagPosition', 'tagPriority', 'tagDuplicateStrategy', 'children', 'innerHTML', 'textContent', 'processTemplateParams'])
27+
export const TagConfigKeys = new Set(['tagPosition', 'tagPriority', 'tagDuplicateStrategy', 'innerHTML', 'textContent', 'processTemplateParams'])
2828

2929
export const IsBrowser = typeof window !== 'undefined'
3030

‎packages/shared/src/normalise.ts

+3-10
Original file line numberDiff line numberDiff line change
@@ -19,21 +19,14 @@ export function normaliseTag<T extends HeadTag>(tagName: T['tag'], input: HeadTa
1919
// @ts-expect-error untyped
2020
const val = tag.props[k] !== undefined ? tag.props[k] : e[k]
2121
if (val !== undefined) {
22-
// strip innerHTML and textContent for tags which don't support it=
23-
if (!(k === 'innerHTML' || k === 'textContent' || k === 'children') || TagsWithInnerContent.has(tag.tag)) {
22+
// strip innerHTML and textContent for tags which don't support it
23+
if (!(k === 'innerHTML' || k === 'textContent') || TagsWithInnerContent.has(tag.tag)) {
2424
// @ts-expect-error untyped
25-
tag[k === 'children' ? 'innerHTML' : k] = val
25+
tag[k] = val
2626
}
2727
delete tag.props[k]
2828
}
2929
}
30-
// TODO remove v2
31-
if (tag.props.body) {
32-
// inserting dangerous javascript potentially
33-
tag.tagPosition = 'bodyClose'
34-
// clean up
35-
delete tag.props.body
36-
}
3730
// shorthand for objects
3831
if (tag.tag === 'script') {
3932
if (typeof tag.innerHTML === 'object') {
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,24 @@
1+
import { defineHeadPlugin } from '@unhead/shared'
2+
3+
export const DeprecationsPlugin = defineHeadPlugin({
4+
hooks: {
5+
'tag:normalise': ({ tag }) => {
6+
if (tag.props.children) {
7+
tag.innerHTML = tag.props.children
8+
delete tag.props.children
9+
}
10+
if (tag.props.hid) {
11+
tag.key = tag.props.hid
12+
delete tag.props.hid
13+
}
14+
if (tag.props.vmid) {
15+
tag.key = tag.props.vmid
16+
delete tag.props.vmid
17+
}
18+
if (tag.props.body) {
19+
tag.tagPosition = 'bodyClose'
20+
delete tag.props.body
21+
}
22+
},
23+
},
24+
})
Original file line numberDiff line numberDiff line change
@@ -1 +1,2 @@
1+
export * from './deprecations'
12
export * from './promises'

‎packages/unhead/src/plugins/dedupe.ts

-9
Original file line numberDiff line numberDiff line change
@@ -6,15 +6,6 @@ const UsesMergeStrategy = new Set(['templateParams', 'htmlAttrs', 'bodyAttrs'])
66
export default defineHeadPlugin(head => ({
77
hooks: {
88
'tag:normalise': ({ tag }) => {
9-
// support for third-party dedupe keys
10-
if (tag.props.hid) {
11-
tag.key = tag.props.hid
12-
delete tag.props.hid
13-
}
14-
if (tag.props.vmid) {
15-
tag.key = tag.props.vmid
16-
delete tag.props.vmid
17-
}
189
if (tag.props.key) {
1910
tag.key = tag.props.key
2011
delete tag.props.key

‎packages/unhead/src/plugins/templateParams.ts

-1
Original file line numberDiff line numberDiff line change
@@ -62,7 +62,6 @@ export default defineHeadPlugin(head => ({
6262
},
6363
'tags:afterResolve': ({ tags }) => {
6464
// we need to re-process in case then user had a function as the titleTemplate
65-
// TODO drop support for function in v2
6665
let title: HeadTag | undefined
6766
for (let i = 0; i < tags.length; i += 1) {
6867
const tag = tags[i]

‎packages/vue/test/dom/innerContent.test.ts

+2-2
Original file line numberDiff line numberDiff line change
@@ -12,7 +12,7 @@ describe('vue dom innerContent', () => {
1212
const entry = head.push({
1313
script: [
1414
{
15-
children: 'console.log(\'hello\')',
15+
innerHTML: 'console.log(\'hello\')',
1616
},
1717
],
1818
})
@@ -38,7 +38,7 @@ describe('vue dom innerContent', () => {
3838
entry.patch({
3939
script: [
4040
{
41-
children: 'console.log(\'hello world\')',
41+
innerHTML: 'console.log(\'hello world\')',
4242
},
4343
],
4444
})

‎packages/vue/test/dom/lifecycle.test.ts

+1-1
Original file line numberDiff line numberDiff line change
@@ -139,7 +139,7 @@ describe('vue dom', () => {
139139
},
140140
script: [
141141
{
142-
children: 'console.log(\'hello\')',
142+
innerHTML: 'console.log(\'hello\')',
143143
tagPosition: 'bodyClose',
144144
},
145145
],

‎packages/vue/test/promises.test.ts

+1-1
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,7 @@ describe('vue promises', () => {
1111
script: [
1212
{ src: new Promise(resolve => resolve('https://example.com/script.js')) },
1313
{
14-
children: new Promise<string>(resolve => setTimeout(() => resolve('test'), 250)),
14+
innerHTML: new Promise<string>(resolve => setTimeout(() => resolve('test'), 250)),
1515
},
1616
],
1717
})

‎packages/vue/test/ssr/innerContent.test.ts

+2-2
Original file line numberDiff line numberDiff line change
@@ -2,8 +2,8 @@ import { useHead } from '@unhead/vue'
22
import { describe } from 'vitest'
33
import { ssrRenderHeadToString } from '../util'
44

5-
describe('vue ssr innerContent', () => {
6-
it('children', async () => {
5+
describe('vue ssr innerHTML', () => {
6+
it('innerHTML', async () => {
77
const headResult = await ssrRenderHeadToString(() => {
88
useHead({
99
script: [

‎test/unhead/dom/innerHTML.test.ts

+1-1
Original file line numberDiff line numberDiff line change
@@ -53,7 +53,7 @@ describe('dom innerHTML', () => {
5353
useHead({
5454
noscript: [
5555
{
56-
children: `<iframe src="https://www.googletagmanager.com/ns.html?id=GTM-XXXXXX"
56+
innerHTML: `<iframe src="https://www.googletagmanager.com/ns.html?id=GTM-XXXXXX"
5757
height="0" width="0" style="display:none;visibility:hidden"></iframe>`,
5858
},
5959
],

‎test/unhead/e2e/json.test.ts

+2-2
Original file line numberDiff line numberDiff line change
@@ -15,7 +15,7 @@ describe('unhead e2e json', () => {
1515
script: [
1616
{
1717
type: 'application/json',
18-
children: {
18+
innerHTML: {
1919
foo: 'bar',
2020
},
2121
},
@@ -41,7 +41,7 @@ describe('unhead e2e json', () => {
4141
script: [
4242
{
4343
type: 'application/json',
44-
children: {
44+
innerHTML: {
4545
foo: 'bar',
4646
},
4747
},

‎test/unhead/promises.test.ts

+1-1
Original file line numberDiff line numberDiff line change
@@ -12,7 +12,7 @@ describe('promises', () => {
1212
script: [
1313
{ src: new Promise(resolve => resolve('https://example.com/script.js')) },
1414
{
15-
children: new Promise<string>(resolve => setTimeout(() => resolve('test'), 250)),
15+
innerHTML: new Promise<string>(resolve => setTimeout(() => resolve('test'), 250)),
1616
},
1717
],
1818
})

‎test/unhead/ssr/deduping.test.ts

+4-1
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
import { renderSSRHead } from '@unhead/ssr'
22
import { useHead } from 'unhead'
3+
import { DeprecationsPlugin } from 'unhead/optionalPlugins'
34
import { describe, it } from 'vitest'
45
import { createHeadWithContext } from '../../util'
56

@@ -215,7 +216,9 @@ describe('dedupe', () => {
215216
})
216217

217218
it('dedupes legacy', async () => {
218-
const head = createHeadWithContext()
219+
const head = createHeadWithContext({
220+
plugins: [DeprecationsPlugin],
221+
})
219222
head.push({
220223
meta: [
221224
{

‎test/unhead/ssr/innerHTML.test.ts

+1-10
Original file line numberDiff line numberDiff line change
@@ -58,7 +58,7 @@ describe('ssr innerHTML', () => {
5858
head.push({
5959
noscript: [
6060
{
61-
children: `<iframe src="https://www.googletagmanager.com/ns.html?id=GTM-XXXXXX"
61+
innerHTML: `<iframe src="https://www.googletagmanager.com/ns.html?id=GTM-XXXXXX"
6262
height="0" width="0" style="display:none;visibility:hidden"></iframe>`,
6363
},
6464
],
@@ -126,14 +126,5 @@ describe('ssr innerHTML', () => {
126126
],
127127
})
128128
expect(await head.resolveTags()).toMatchInlineSnapshot('[]')
129-
130-
head.push({
131-
script: [
132-
{
133-
children: '',
134-
},
135-
],
136-
})
137-
expect(await head.resolveTags()).toMatchInlineSnapshot('[]')
138129
})
139130
})

‎test/unhead/ssr/tagPosition.test.ts

+4-1
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,5 @@
11
import { renderSSRHead } from '@unhead/ssr'
2+
import { DeprecationsPlugin } from 'unhead/optionalPlugins'
23
import { createHeadWithContext } from '../../util'
34

45
describe('tagPosition', () => {
@@ -24,7 +25,9 @@ describe('tagPosition', () => {
2425
`)
2526
})
2627
it('body: true', async () => {
27-
const head = createHeadWithContext()
28+
const head = createHeadWithContext({
29+
plugins: [DeprecationsPlugin],
30+
})
2831
head.push({
2932
script: [
3033
{

0 commit comments

Comments
 (0)
Please sign in to comment.