vary CORS responses by origin

This commit is contained in:
2026-09-06 18:18:19 +03:00
parent 7a3915a679
commit bdde4534f6
3 changed files with 10 additions and 0 deletions
+6
View File
@@ -2030,3 +2030,9 @@ Doğrulama: 288 test geçti, üretim derlemesi başarılı.
HTTP test sunucusu artık yapılandırılmış iki izinli origin ile başlatılıyor; izinli origin preflight yanıtında geri dönerken tanımsız origin CORS başlığı alamıyor. Böylece allowlist davranışı gerçek süreç üzerinden doğrulanıyor. HTTP test sunucusu artık yapılandırılmış iki izinli origin ile başlatılıyor; izinli origin preflight yanıtında geri dönerken tanımsız origin CORS başlığı alamıyor. Böylece allowlist davranışı gerçek süreç üzerinden doğrulanıyor.
Doğrulama: HTTP testleri 19/19, toplam 288 test geçti; üretim derlemesi başarılı. Doğrulama: HTTP testleri 19/19, toplam 288 test geçti; üretim derlemesi başarılı.
### 2026-09-06 · CORS yanıtlarında önbellek ayrımı
Origin allowlistesi etkin olduğunda API ve preflight yanıtlarına `Vary: Origin` eklendi; farklı origin’lere ait CORS yanıtlarının ara önbellekte birbirine karışması engellendi.
Doğrulama: 288 test geçti, üretim derlemesi başarılı.
+3
View File
@@ -629,6 +629,7 @@ function json(res, code, body) {
'Referrer-Policy': 'no-referrer', 'Referrer-Policy': 'no-referrer',
}; };
const origin = res.__ihaleistCorsOrigin; const origin = res.__ihaleistCorsOrigin;
if (CORS_ORIGINS.length) headers.Vary = 'Origin';
if (origin) headers['Access-Control-Allow-Origin'] = origin; if (origin) headers['Access-Control-Allow-Origin'] = origin;
else if (!CORS_ORIGINS.length) headers['Access-Control-Allow-Origin'] = '*'; else if (!CORS_ORIGINS.length) headers['Access-Control-Allow-Origin'] = '*';
res.writeHead(code, headers); res.writeHead(code, headers);
@@ -740,10 +741,12 @@ const server = http.createServer(async (req, res) => {
res.__ihaleistCorsOrigin = CORS_ORIGINS.length && CORS_ORIGINS.includes(requestOrigin) ? requestOrigin : null; res.__ihaleistCorsOrigin = CORS_ORIGINS.length && CORS_ORIGINS.includes(requestOrigin) ? requestOrigin : null;
if (req.method === 'OPTIONS') { if (req.method === 'OPTIONS') {
const headers = { const headers = {
'Vary': CORS_ORIGINS.length ? 'Origin' : undefined,
'Access-Control-Allow-Methods': 'GET,POST,PUT,PATCH,DELETE,OPTIONS', 'Access-Control-Allow-Methods': 'GET,POST,PUT,PATCH,DELETE,OPTIONS',
'Access-Control-Allow-Headers': 'Authorization,Content-Type', 'Access-Control-Allow-Headers': 'Authorization,Content-Type',
'Access-Control-Max-Age': '600', 'Access-Control-Max-Age': '600',
}; };
if (!headers.Vary) delete headers.Vary;
if (res.__ihaleistCorsOrigin) headers['Access-Control-Allow-Origin'] = res.__ihaleistCorsOrigin; if (res.__ihaleistCorsOrigin) headers['Access-Control-Allow-Origin'] = res.__ihaleistCorsOrigin;
else if (!CORS_ORIGINS.length) headers['Access-Control-Allow-Origin'] = '*'; else if (!CORS_ORIGINS.length) headers['Access-Control-Allow-Origin'] = '*';
res.writeHead(204, headers); res.writeHead(204, headers);
+1
View File
@@ -29,6 +29,7 @@ test('HTTP preparation requires auth, persists draft and rejects stale revisions
const preflight=await fetch(base+'/api/me/plan',{method:'OPTIONS',headers:{Origin:'https://client.example', 'Access-Control-Request-Method':'GET', 'Access-Control-Request-Headers':'authorization,content-type'}}); const preflight=await fetch(base+'/api/me/plan',{method:'OPTIONS',headers:{Origin:'https://client.example', 'Access-Control-Request-Method':'GET', 'Access-Control-Request-Headers':'authorization,content-type'}});
assert.equal(preflight.status,204); assert.equal(preflight.status,204);
assert.equal(preflight.headers.get('access-control-allow-origin'),'https://client.example'); assert.equal(preflight.headers.get('access-control-allow-origin'),'https://client.example');
assert.equal(preflight.headers.get('vary'),'Origin');
assert.equal(preflight.headers.get('access-control-allow-headers'),'Authorization,Content-Type'); assert.equal(preflight.headers.get('access-control-allow-headers'),'Authorization,Content-Type');
const denied=await fetch(base+'/api/me/plan',{method:'OPTIONS',headers:{Origin:'https://untrusted.example','Access-Control-Request-Method':'GET'}}); const denied=await fetch(base+'/api/me/plan',{method:'OPTIONS',headers:{Origin:'https://untrusted.example','Access-Control-Request-Method':'GET'}});
assert.equal(denied.status,204);assert.equal(denied.headers.get('access-control-allow-origin'),null); assert.equal(denied.status,204);assert.equal(denied.headers.get('access-control-allow-origin'),null);