پرش به مطلب اصلی

احراز هویت با HTTP Basic

نمونه‌ای برای محدود کردن دسترسی با استفاده از HTTP Basic.

برای استفاده در محیط پروداکشن احتیاط کنید!

این کد یک نمونه است و برای محیط‌های عملیاتی و پروداکشن مناسب نیست. Basic Authentication مقادیر احراز هویت را بدون رمزنگاری ارسال می‌‌کند و برای امنیت بیش‌تر باید با اتصال HTTPS استفاده شود.

'use strict';

addEventListener("fetch", (event) => {
event.respondWith(handleRequest(event.request));
});

async function handleRequest(request) {
const authHeader = request.headers.get("Authorization");
let response;
if (authHeader != null && authHeader.startsWith("Basic")) {
let encodedCredential = authHeader.substring(6);
if (CREDENTIALS.has(encodedCredential)) {
let newUrl = new URL(request.url);
newUrl.protocol = UPSTREAM_PROTOCOL;
newUrl.host = UPSTREAM_HOST;
let newReq = new Request(newUrl.toString(), request);
newReq.headers.delete("Authorization");
response = await fetch(newReq);
}
else {
response = UNAUTHORIZED_INVALID_CREDENTIALS_RESPONSE;
}
}
else {
response = UNAUTHORIZED_NEEDS_LOGIN_RESPONSE;
}
return response;
}


// Credentials for users
const UserPassList = [{ user: "admin", pass: "adminpass" }];
// Upstream url
const UPSTREAM_URL = "http://localhost:4000";

const UNAUTHORIZED_NEEDS_LOGIN_RESPONSE = new Response(null, {
//TODO: Add realm and/or charset if needed
headers: new Headers({
"WWW-Authenticate": "Basic",
}),
status: 401,
});
const UNAUTHORIZED_INVALID_CREDENTIALS_RESPONSE = new Response(null, {
status: 401,
});
// Key: Base64 encoded username:password
// Value: username
const CREDENTIALS = (() => {
const map = new Map();
for (let i of UserPassList) {
// TODO: this may not properly work with utf8
const encoded = btoa(`${i.user}:${i.pass}`);
map.set(encoded, i.user);
}
return map;
})();
const UPSTREAM_PROTOCOL = new URL(UPSTREAM_URL).protocol;
const UPSTREAM_HOST = new URL(UPSTREAM_URL).host;