Skip to content

Commit 23d04fc

Browse files
sapphi-redCopilot
andauthored
fix: respond with correct headers and status code for HEAD requests (#20421)
Co-authored-by: copilot-swe-agent[bot] <198982749+Copilot@users.noreply.github.com>
1 parent ead2dec commit 23d04fc

File tree

4 files changed

+39
-4
lines changed

4 files changed

+39
-4
lines changed

packages/vite/src/node/server/middlewares/transform.ts

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -120,7 +120,10 @@ export function transformMiddleware(
120120
return async function viteTransformMiddleware(req, res, next) {
121121
const environment = server.environments.client
122122

123-
if (req.method !== 'GET' || knownIgnoreList.has(req.url!)) {
123+
if (
124+
(req.method !== 'GET' && req.method !== 'HEAD') ||
125+
knownIgnoreList.has(req.url!)
126+
) {
124127
return next()
125128
}
126129

packages/vite/src/node/server/send.ts

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -92,6 +92,10 @@ export function send(
9292
}
9393

9494
res.statusCode = 200
95-
res.end(content)
95+
if (req.method === 'HEAD') {
96+
res.end()
97+
} else {
98+
res.end(content)
99+
}
96100
return
97101
}

playground/resolve/__tests__/resolve.spec.ts

Lines changed: 25 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,8 @@
11
import fs from 'node:fs'
22
import path from 'node:path'
33
import { fileURLToPath } from 'node:url'
4-
import { expect, test } from 'vitest'
5-
import { isBuild, isWindows, page, testDir, viteTestUrl } from '~utils'
4+
import { describe, expect, test } from 'vitest'
5+
import { isBuild, isServe, isWindows, page, testDir, viteTestUrl } from '~utils'
66

77
test('bom import', async () => {
88
expect(await page.textContent('.utf8-bom')).toMatch('[success]')
@@ -263,3 +263,26 @@ test.runIf(isBuild)('sideEffects field glob pattern is respected', async () => {
263263
)
264264
expect(sideEffectValues).toStrictEqual(['success'])
265265
})
266+
267+
describe.runIf(isServe)('HEAD request handling', () => {
268+
test('HEAD request to JS file returns correct Content-Type', async () => {
269+
const response = await fetch(new URL('/absolute.js', viteTestUrl), {
270+
method: 'HEAD',
271+
})
272+
expect(response.headers.get('content-type')).toBe('text/javascript')
273+
expect(response.status).toBe(200)
274+
const text = await response.text()
275+
expect(text).toBe('')
276+
})
277+
278+
test('HEAD request to CSS file returns correct Content-Type', async () => {
279+
const response = await fetch(new URL('/style.css', viteTestUrl), {
280+
method: 'HEAD',
281+
headers: {
282+
Accept: 'text/css',
283+
},
284+
})
285+
expect(response.headers.get('content-type')).toBe('text/css')
286+
expect(response.status).toBe(200)
287+
})
288+
})

playground/resolve/style.css

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
/* Simple CSS for HEAD request testing */
2+
body {
3+
margin: 0;
4+
padding: 0;
5+
}

0 commit comments

Comments
 (0)
pFad - Phonifier reborn

Pfad - The Proxy pFad of © 2024 Garber Painting. All rights reserved.

Note: This service is not intended for secure transactions such as banking, social media, email, or purchasing. Use at your own risk. We assume no liability whatsoever for broken pages.


Alternative Proxies:

Alternative Proxy

pFad Proxy

pFad v3 Proxy

pFad v4 Proxy