diff --git a/@kindspells/astro-shield/package.json b/@kindspells/astro-shield/package.json index 5ea4c4c..2c2075d 100644 --- a/@kindspells/astro-shield/package.json +++ b/@kindspells/astro-shield/package.json @@ -1,6 +1,6 @@ { "name": "@kindspells/astro-shield", - "version": "1.6.0", + "version": "1.6.1", "description": "Astro integration to enhance your website's security with SubResource Integrity hashes, Content-Security-Policy headers, and other techniques.", "private": false, "type": "module", diff --git a/@kindspells/astro-shield/src/tests/vercel.test.mts b/@kindspells/astro-shield/src/tests/vercel.test.mts index bca66eb..1f0e1af 100644 --- a/@kindspells/astro-shield/src/tests/vercel.test.mts +++ b/@kindspells/astro-shield/src/tests/vercel.test.mts @@ -157,31 +157,35 @@ describe('buildVercelConfig', () => { version: 3, routes: [ { - src: '/nothing.html', + src: '^/nothing\\.html$', headers: { 'content-security-policy': "script-src 'none'; style-src 'none'", }, + continue: true, }, { - src: '/onlyscripts.html', + src: '^/onlyscripts\\.html$', headers: { 'content-security-policy': "script-src 'self' 'sha256-071spvYLMvnwaR0H7M2dfK0enB0cGtydTbgJkdoWq7c=' 'sha256-KWrCkmqpW9eWGwZRBZ9KqXsoHtAbAH/zPJvmUhsMKpA='; style-src 'none'", }, + continue: true, }, { - src: '/onlystyles.html', + src: '^/onlystyles\\.html$', headers: { 'content-security-policy': "script-src 'none'; style-src 'self' 'sha256-VC84dQdO3Mo7nZIRaNTJgrqPQ0foHI8gdp/DS+e9/lk=' 'sha256-iwd3GNfA+kImEozakD3ZZQSZ8VVb3MFBOhJH6dEMnDE='", }, + continue: true, }, { - src: '/scriptsandstyles.html', + src: '^/scriptsandstyles\\.html$', headers: { 'content-security-policy': "script-src 'self' 'sha256-071spvYLMvnwaR0H7M2dfK0enB0cGtydTbgJkdoWq7c=' 'sha256-KWrCkmqpW9eWGwZRBZ9KqXsoHtAbAH/zPJvmUhsMKpA='; style-src 'self' 'sha256-VC84dQdO3Mo7nZIRaNTJgrqPQ0foHI8gdp/DS+e9/lk=' 'sha256-iwd3GNfA+kImEozakD3ZZQSZ8VVb3MFBOhJH6dEMnDE='", }, + continue: true, }, ], } satisfies VercelConfig) @@ -225,25 +229,28 @@ describe('buildVercelConfig', () => { version: 3, routes: [ { - src: '/nested/', + src: '^/nested/$', headers: { 'content-security-policy': "script-src 'self' 'sha256-071spvYLMvnwaR0H7M2dfK0enB0cGtydTbgJkdoWq7c=' 'sha256-KWrCkmqpW9eWGwZRBZ9KqXsoHtAbAH/zPJvmUhsMKpA='; style-src 'self' 'sha256-VC84dQdO3Mo7nZIRaNTJgrqPQ0foHI8gdp/DS+e9/lk=' 'sha256-iwd3GNfA+kImEozakD3ZZQSZ8VVb3MFBOhJH6dEMnDE='", }, + continue: true, }, { - src: '/nested/index.html', + src: '^/nested/index\\.html$', headers: { 'content-security-policy': "script-src 'self' 'sha256-071spvYLMvnwaR0H7M2dfK0enB0cGtydTbgJkdoWq7c=' 'sha256-KWrCkmqpW9eWGwZRBZ9KqXsoHtAbAH/zPJvmUhsMKpA='; style-src 'self' 'sha256-VC84dQdO3Mo7nZIRaNTJgrqPQ0foHI8gdp/DS+e9/lk=' 'sha256-iwd3GNfA+kImEozakD3ZZQSZ8VVb3MFBOhJH6dEMnDE='", }, + continue: true, }, { - src: '/notindex.html', + src: '^/notindex\\.html$', headers: { 'content-security-policy': "script-src 'self' 'sha256-071spvYLMvnwaR0H7M2dfK0enB0cGtydTbgJkdoWq7c=' 'sha256-KWrCkmqpW9eWGwZRBZ9KqXsoHtAbAH/zPJvmUhsMKpA='; style-src 'self' 'sha256-VC84dQdO3Mo7nZIRaNTJgrqPQ0foHI8gdp/DS+e9/lk=' 'sha256-iwd3GNfA+kImEozakD3ZZQSZ8VVb3MFBOhJH6dEMnDE='", }, + continue: true, }, ], }) @@ -287,25 +294,28 @@ describe('buildVercelConfig', () => { version: 3, routes: [ { - src: '/nested', + src: '^/nested$', headers: { 'content-security-policy': "script-src 'self' 'sha256-071spvYLMvnwaR0H7M2dfK0enB0cGtydTbgJkdoWq7c=' 'sha256-KWrCkmqpW9eWGwZRBZ9KqXsoHtAbAH/zPJvmUhsMKpA='; style-src 'self' 'sha256-VC84dQdO3Mo7nZIRaNTJgrqPQ0foHI8gdp/DS+e9/lk=' 'sha256-iwd3GNfA+kImEozakD3ZZQSZ8VVb3MFBOhJH6dEMnDE='", }, + continue: true, }, { - src: '/nested/index.html', + src: '^/nested/index\\.html$', headers: { 'content-security-policy': "script-src 'self' 'sha256-071spvYLMvnwaR0H7M2dfK0enB0cGtydTbgJkdoWq7c=' 'sha256-KWrCkmqpW9eWGwZRBZ9KqXsoHtAbAH/zPJvmUhsMKpA='; style-src 'self' 'sha256-VC84dQdO3Mo7nZIRaNTJgrqPQ0foHI8gdp/DS+e9/lk=' 'sha256-iwd3GNfA+kImEozakD3ZZQSZ8VVb3MFBOhJH6dEMnDE='", }, + continue: true, }, { - src: '/notindex.html', + src: '^/notindex\\.html$', headers: { 'content-security-policy': "script-src 'self' 'sha256-071spvYLMvnwaR0H7M2dfK0enB0cGtydTbgJkdoWq7c=' 'sha256-KWrCkmqpW9eWGwZRBZ9KqXsoHtAbAH/zPJvmUhsMKpA='; style-src 'self' 'sha256-VC84dQdO3Mo7nZIRaNTJgrqPQ0foHI8gdp/DS+e9/lk=' 'sha256-iwd3GNfA+kImEozakD3ZZQSZ8VVb3MFBOhJH6dEMnDE='", }, + continue: true, }, ], }) @@ -344,16 +354,16 @@ describe('mergeVercelConfig', () => { version: 3, routes: [ { - src: '/nothing.html', + src: '/onlystyles.html', headers: { - 'content-security-policy': "script-src 'none'; style-src 'none'", + 'content-security-policy': + "script-src 'none'; style-src 'self' 'sha256-VC84dQdO3Mo7nZIRaNTJgrqPQ0foHI8gdp/DS+e9/lk=' 'sha256-iwd3GNfA+kImEozakD3ZZQSZ8VVb3MFBOhJH6dEMnDE='", }, }, { - src: '/onlystyles.html', + src: '/nothing.html', headers: { - 'content-security-policy': - "script-src 'none'; style-src 'self' 'sha256-VC84dQdO3Mo7nZIRaNTJgrqPQ0foHI8gdp/DS+e9/lk=' 'sha256-iwd3GNfA+kImEozakD3ZZQSZ8VVb3MFBOhJH6dEMnDE='", + 'content-security-policy': "script-src 'none'; style-src 'none'", }, }, ], diff --git a/@kindspells/astro-shield/src/vercel.mts b/@kindspells/astro-shield/src/vercel.mts index 58dace7..ec7561a 100644 --- a/@kindspells/astro-shield/src/vercel.mts +++ b/@kindspells/astro-shield/src/vercel.mts @@ -104,7 +104,11 @@ export const buildVercelConfig = ( } if (Object.keys(headers).length > 0) { - routes.push({ src: `/${page}`, headers }) + routes.push({ + src: `^/${page.replaceAll('.', '\\.')}$`, + headers, + continue: true, + }) } } @@ -115,7 +119,7 @@ export const mergeVercelConfig = ( base: VercelConfig, patch: VercelConfig, ): VercelConfig => { - return { ...base, routes: [...(base.routes ?? []), ...(patch.routes ?? [])] } + return { ...base, routes: [...(patch.routes ?? []), ...(base.routes ?? [])] } } export const serializeVercelConfig = (config: VercelConfig): string => {