-
-
Notifications
You must be signed in to change notification settings - Fork 1.4k
fix: nonce #5522
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
fix: nonce #5522
Changes from all commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -7,7 +7,7 @@ import type { RouterManagedTag } from '@tanstack/router-core' | |
|
|
||
| export const useTags = () => { | ||
| const router = useRouter() | ||
|
|
||
| const nonce = router.options.ssr?.nonce | ||
| const routeMeta = useRouterState({ | ||
| select: (state) => { | ||
| return state.matches.map((match) => match.meta!).filter(Boolean) | ||
|
|
@@ -46,6 +46,7 @@ export const useTags = () => { | |
| tag: 'meta', | ||
| attrs: { | ||
| ...m, | ||
| nonce, | ||
| }, | ||
| }) | ||
| } | ||
|
|
@@ -56,6 +57,15 @@ export const useTags = () => { | |
| resultMeta.push(title) | ||
| } | ||
|
|
||
| if (router.options.ssr?.nonce) { | ||
| resultMeta.push({ | ||
| tag: 'meta', | ||
| attrs: { | ||
| property: 'csp-nonce', | ||
| content: router.options.ssr.nonce, | ||
| }, | ||
| }) | ||
| } | ||
| resultMeta.reverse() | ||
|
|
||
| return resultMeta | ||
|
|
@@ -71,6 +81,7 @@ export const useTags = () => { | |
| tag: 'link', | ||
| attrs: { | ||
| ...link, | ||
| nonce, | ||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Nonce applied to constructed links, but missing on preload and asset links. While constructed links receive the nonce attribute (line 84), both:
do not receive the nonce. This inconsistency may cause CSP violations if those links contain resources that require nonce validation. Apply this diff to add nonce to preload links: router.ssr?.manifest?.routes[route.id]?.preloads
?.filter(Boolean)
.forEach((preload) => {
preloadMeta.push({
tag: 'link',
attrs: {
rel: 'modulepreload',
href: preload,
+ nonce,
},
})
}),And this diff to add nonce to manifest assets: .map(
(asset) =>
({
tag: 'link',
- attrs: asset.attrs,
+ attrs: {
+ ...asset.attrs,
+ nonce,
+ },
}) satisfies RouterManagedTag,
) |
||
| }, | ||
| })) satisfies Array<RouterManagedTag> | ||
|
|
||
|
|
@@ -87,7 +98,7 @@ export const useTags = () => { | |
| (asset) => | ||
| ({ | ||
| tag: 'link', | ||
| attrs: asset.attrs, | ||
| attrs: { ...asset.attrs, nonce }, | ||
| }) satisfies RouterManagedTag, | ||
| ) | ||
|
|
||
|
|
@@ -110,6 +121,7 @@ export const useTags = () => { | |
| attrs: { | ||
| rel: 'modulepreload', | ||
| href: preload, | ||
| nonce, | ||
| }, | ||
| }) | ||
| }), | ||
|
|
@@ -130,6 +142,7 @@ export const useTags = () => { | |
| tag: 'style', | ||
| attrs: { | ||
| ...style, | ||
| nonce, | ||
| }, | ||
| children, | ||
| })), | ||
|
|
@@ -146,6 +159,7 @@ export const useTags = () => { | |
| tag: 'script', | ||
| attrs: { | ||
| ...script, | ||
| nonce, | ||
| }, | ||
| children, | ||
| })), | ||
|
|
@@ -172,6 +186,7 @@ export const useTags = () => { | |
| */ | ||
| export function HeadContent() { | ||
| const tags = useTags() | ||
|
|
||
| return ( | ||
| <MetaProvider> | ||
| {tags().map((tag) => ( | ||
|
|
||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -5,7 +5,7 @@ import type { RouterManagedTag } from '@tanstack/router-core' | |
|
|
||
| export const Scripts = () => { | ||
| const router = useRouter() | ||
|
|
||
| const nonce = router.options.ssr?.nonce | ||
| const assetScripts = useRouterState({ | ||
| select: (state) => { | ||
| const assetScripts: Array<RouterManagedTag> = [] | ||
|
|
@@ -23,7 +23,7 @@ export const Scripts = () => { | |
| .forEach((asset) => { | ||
| assetScripts.push({ | ||
| tag: 'script', | ||
| attrs: asset.attrs, | ||
| attrs: { ...asset.attrs, nonce }, | ||
| children: asset.children, | ||
| } as any) | ||
| }), | ||
|
Comment on lines
23
to
29
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 🛠️ Refactor suggestion | 🟠 Major 🧩 Analysis chainVerify the type assertion and ensure type safety. The Please verify:
Run the following script to check the 🏁 Script executed: #!/bin/bash
# Description: Find the RouterManagedTag type definition to verify if nonce is properly typed
# Search for RouterManagedTag type definition
ast-grep --pattern 'type RouterManagedTag = $$$'
# Also search for interface definition
ast-grep --pattern 'interface RouterManagedTag {
$$$
}'
# Search for nonce in type definitions
rg -n --type=ts 'RouterManagedTag' -A 10 -B 2Length of output: 30501 Replace The } satisfies RouterManagedTag)Alternatively, remove the assertion entirely, since other scripts in react-router follow this approach without needing individual assertions. 🤖 Prompt for AI Agents |
||
|
|
@@ -44,6 +44,7 @@ export const Scripts = () => { | |
| tag: 'script', | ||
| attrs: { | ||
| ...script, | ||
| nonce, | ||
| }, | ||
| children, | ||
| })), | ||
|
|
||
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Potential data loss: entire
router.options.ssrobject is overwritten.Assigning
router.options.ssr = { nonce }discards any pre-existing properties onrouter.options.ssr. If other parts of the hydration flow or user configuration set additional properties on this object, they will be lost.Apply this diff to preserve existing properties:
const meta = document.querySelector('meta[property="csp-nonce"]') as | HTMLMetaElement | undefined const nonce = meta?.content - router.options.ssr = { - nonce, - } + router.options.ssr = { + ...router.options.ssr, + nonce, + }📝 Committable suggestion
🤖 Prompt for AI Agents