Last update:2024-09-03 17:00:38
This example demonstrates how to build a small static website using Edge KV and Edge Cloud Apps Function. The function retrieves files from Edge KV based on the URL path, determines the appropriate content type, and sends the content back to the client. This approach is ideal for quickly deploying a lightweight static website with high performance, high availability, and low latency.
Advantages of Edge Static Websites
In this example, Edge KV is responsible for storing the website’s static resources, such as HTML files, images, and videos. The Edge Cloud Apps Function handles user requests, retrieving the corresponding resources from Edge KV based on the requested URL and returning them to the user.
/*
* Data storage format in Edge KV:
* | KEY | VALUE |
* | -------------- | ------------ |
* | /index.html | Corresponding file data |
* | /img/about.jpg | Corresponding file data |
* Assuming the requested URL is: http://www.test.com/catalog-z/index.html
* We take the filename at the end, /index.html, as the key to retrieve the file data.
*/
async function handleRequest(request) {
// Get the requested filename from the URL
let { pathname } = new URL(request.url.toLowerCase());
if (pathname.endsWith('/')) {
pathname = pathname.substring(0, pathname.length - 1);
}
pathname = pathname.substring("/catalog-z".length); // Remove the path prefix
if (pathname === '') {
pathname = '/index.html'; // Default to index.html
}
// Retrieve the file content from Edge KV using the filename as the key.
// Note that the namespace is "catalog_z2", which was used when uploading the files.
const kv = new EdgeKV({namespace: "catalog_z2"});
const content = await kv.get(pathname, {type: "stream"});
// Return a 404 error if the file is not found
if (content === null) {
return new Response("Page not found", {status: 404});
}
// Generate the response to the client
const contentType = contentTypeOfFile(pathname); // Determine Content-Type based on the filename
const headers = { 'Content-Type': contentType, 'Cache-Control': 'max-age=180' }; // Set cache control
console.log(`Requested filename: ${pathname}, type: ${contentType}`);
return new Response(content, {headers: headers});
}
// Determine the Content-Type based on the file extension
function contentTypeOfFile(fileName) {
const ext = fileName.split('.').pop();
switch (ext) {
case 'html': return 'text/html';
case 'css': return 'text/css';
case 'js': return 'application/javascript';
case 'jpg': return 'image/jpeg';
case 'png': return 'image/png';
case 'mp4': return 'video/mp4';
case 'eot': return 'application/vnd.ms-fontobject';
case 'svg':
case 'svgz': return 'image/svg+xml';
case 'woff': return 'font/woff';
case 'woff2': return 'font/woff2';
default: return 'application/octet-stream';
}
}
addEventListener("fetch", event => {
return event.respondWith(handleRequest(event.request));
});