From e927ff915b40f2a774621cbc8b801de0c478f72d Mon Sep 17 00:00:00 2001 From: Cory McWilliams Date: Sat, 15 Jan 2022 19:05:59 +0000 Subject: [PATCH] Do some HTTP caching, because we have all of the information to make it easy. git-svn-id: https://www.unprompted.com/svn/projects/tildefriends/trunk@3764 ed5197a5-7fde-0310-b194-c3ffbd925b24 --- core/core.js | 52 +++++++++++++++++++++++++++++++++++----------------- 1 file changed, 35 insertions(+), 17 deletions(-) diff --git a/core/core.js b/core/core.js index 3dde2085..00facd83 100644 --- a/core/core.js +++ b/core/core.js @@ -374,27 +374,27 @@ async function wellKnownHandler(request, response, path) { } } -function sendData(response, data, type) { +function sendData(response, data, type, headers) { if (data) { if (startsWithBytes(data, [0xff, 0xd8, 0xff, 0xdb]) || startsWithBytes(data, [0xff, 0xd8, 0xff, 0xe0, 0x00, 0x10, 0x4a, 0x46, 0x49, 0x46, 0x00, 0x01]) || startsWithBytes(data, [0xff, 0xd8, 0xff, 0xee]) || startsWithBytes(data, [0xff, 0xd8, 0xff, 0xe1, null, null, 0x45, 0x78, 0x69, 0x66, 0x00, 0x00])) { - response.writeHead(200, {"Content-Type": "image/jpeg", "Content-Length": data.byteLength}); + response.writeHead(200, Object.assign({"Content-Type": "image/jpeg", "Content-Length": data.byteLength}, headers || {})); response.end(data); } else if (startsWithBytes(data, [0x89, 0x50, 0x4e, 0x47, 0x0d, 0x0a, 0x1a, 0x0a])) { - response.writeHead(200, {"Content-Type": "image/png", "Content-Length": data.byteLength}); + response.writeHead(200, Object.assign({"Content-Type": "image/png", "Content-Length": data.byteLength}, headers || {})); response.end(data); } else if (startsWithBytes(data, [0x47, 0x49, 0x46, 0x38, 0x37, 0x61]) || startsWithBytes(data, [0x47, 0x49, 0x46, 0x38, 0x39, 0x61])) { - response.writeHead(200, {"Content-Type": "image/gif", "Content-Length": data.byteLength}); + response.writeHead(200, Object.assign({"Content-Type": "image/gif", "Content-Length": data.byteLength}, headers || {})); response.end(data); } else { - response.writeHead(200, {"Content-Type": type || "text/javascript; charset=utf-8", "Content-Length": data.byteLength}); + response.writeHead(200, Object.assign({"Content-Type": type || "text/javascript; charset=utf-8", "Content-Length": data.byteLength}, headers || {})); response.end(data); } } else { - response.writeHead(404, {"Content-Type": "text/plain; charset=utf-8", "Content-Length": "File not found".length}); + response.writeHead(404, Object.assign({"Content-Type": "text/plain; charset=utf-8", "Content-Length": "File not found".length}, headers || {})); response.end("File not found"); } } @@ -446,16 +446,24 @@ async function blobHandler(request, response, blobId, uri) { if (match = /^\/\~(\w+)\/(\w+)$/.exec(blobId)) { var id = await new Database(match[1]).get('path:' + match[2]); if (id) { - data = await getBlobOrContent(id); - if (match[3]) { - var app = JSON.parse(data); - data = app.files[match[3]]; + if (request.headers['if-none-match'] && request.headers['if-none-match'] == '"' + id + '"') { + response.writeHead(304, {}); + response.end(); + } else { + data = await getBlobOrContent(id); + if (match[3]) { + var app = JSON.parse(data); + data = app.files[match[3]]; + } + sendData(response, data, undefined, {etag: '"' + id + '"'}); } + } else { + sendData(response, data); } } else { data = await getBlobOrContent(blobId); + sendData(response, data); } - sendData(response, data); } else if (uri == "/save") { let newBlobId = await ssb.blobStore(request.body); @@ -478,23 +486,33 @@ async function blobHandler(request, response, blobId, uri) { } else { var data; var type; + var headers; if (match = /^\/\~(\w+)\/(\w+)$/.exec(blobId)) { var db = new Database(match[1]); var id = await db.get('path:' + match[2]); if (id) { - data = utf8Decode(await getBlobOrContent(id)); - var app = JSON.parse(data); - data = app.files[uri.substring(1)]; - data = await getBlobOrContent(data); - type = guessType(uri); + if (request.headers['if-none-match'] && request.headers['if-none-match'] == '"' + id + '"') { + response.writeHead(304, {}); + response.end(); + } else { + data = utf8Decode(await getBlobOrContent(id)); + var app = JSON.parse(data); + data = app.files[uri.substring(1)]; + data = await getBlobOrContent(data); + type = guessType(uri); + headers = {'ETag': '"' + id + '"'}; + sendData(response, data, type, headers); + } + } else { + sendData(response, data, type, headers); } } else { data = utf8Decode(await getBlobOrContent(blobId)); var app = JSON.parse(data); data = app.files[uri.substring(1)]; data = await getBlobOrContent(data); + sendData(response, data, type, headers); } - sendData(response, data, type); } } }