From 554675f45fdcc63204e1af36c6732b2fcb50f82b Mon Sep 17 00:00:00 2001 From: David Humphrey Date: Thu, 4 Apr 2019 14:12:37 -0400 Subject: [PATCH] Use encodeURI() for pathname urls --- dist/nohost-sw.js | 4 ++-- example/index.js | 2 +- src/html-formatter.js | 7 +++++-- src/nohost-sw.js | 4 +++- 4 files changed, 11 insertions(+), 6 deletions(-) diff --git a/dist/nohost-sw.js b/dist/nohost-sw.js index bf6ca01..06cdae5 100644 --- a/dist/nohost-sw.js +++ b/dist/nohost-sw.js @@ -11,12 +11,12 @@ var t;parcelRequire=function(e,n,r,i){var o="function"==typeof parcelRequire&&pa },{}],"xVBo":[function(require,module,exports) { module.exports.back="data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABQAAAAWBAMAAAAyb6E1AAAAElBMVEX////M//+ZmZlmZmYzMzMAAACei5rnAAAAAnRSTlP/AOW3MEoAAAABYktHRACIBR1IAAAAYElEQVQIW0XP0QnAMAhFUVew4ACFLpARUl4XKHH/VdqXRPUjHC5+GNEc4dOQvICelY4KVEWviqo2qVz1Re3HQxq33UnXP02a7xENDcn4Sshb1lv37jh5pC3Me70+ZMWYD08uJsBsi+cYAAAAVnRFWHRjb21tZW50AFRoaXMgYXJ0IGlzIGluIHRoZSBwdWJsaWMgZG9tYWluLiBLZXZpbiBIdWdoZXMsIGtldmluaEBlaXQuY29tLCBTZXB0ZW1iZXIgMTk5NXb275wAAAAASUVORK5CYII=",module.exports.blank="data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABQAAAAWAQMAAAD6jy5FAAAABlBMVEX////M//9zUa6lAAAAAnRSTlP/AOW3MEoAAAABYktHRACIBR1IAAAAD0lEQVQIHWP8z/CRkQYYAFlpKreJcPlsAAAAVnRFWHRjb21tZW50AFRoaXMgYXJ0IGlzIGluIHRoZSBwdWJsaWMgZG9tYWluLiBLZXZpbiBIdWdoZXMsIGtldmluaEBlaXQuY29tLCBTZXB0ZW1iZXIgMTk5NXb275wAAAAASUVORK5CYII=",module.exports.folder="data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABQAAAAWBAMAAAAyb6E1AAAAElBMVEX/////zJnM//+ZZjMzMzMAAADCEvqoAAAAA3RSTlP//wDXyg1BAAAAAWJLR0QAiAUdSAAAAFJJREFUCFtjUIIDBsLMUCCAMFUFgSAIzAwEMUVDQ4OUGIJBTEMgDyhqDARAnnAQRAEQGLvCmcKuVBYVhgJXBlVjCDBxZVAKcYGAEAYl1VAIcAIAfgAgxXnPTZkAAABWdEVYdGNvbW1lbnQAVGhpcyBhcnQgaXMgaW4gdGhlIHB1YmxpYyBkb21haW4uIEtldmluIEh1Z2hlcywga2V2aW5oQGVpdC5jb20sIFNlcHRlbWJlciAxOTk1dvbvnAAAAABJRU5ErkJggg==",module.exports.image2="data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABQAAAAWBAMAAAAyb6E1AAAAJFBMVEX/////MzPM///MzMyZmZlmZmZmAAAzMzMAmcwAmTMAM2YAAADMt1kEAAAAA3RSTlP//wDXyg1BAAAAAWJLR0QAiAUdSAAAAIxJREFUCFtFzjsKwkAUheEDVxjEaggIae8KtPFVp3MBrsEuxGIis4FgFRCLu4VsYTbnnUeSv/o41YFLdcyMFpoxK9GtNJHW2spA58T9zns/M4RQiE1zT6zli8KR5IDIY00iLUWenlflLRJbEXl9Eo3Ir8+ktzyGTJxdPxM0LLwspEkra0zpmpye5FDiP+BZOkuqcu7kAAAAVnRFWHRjb21tZW50AFRoaXMgYXJ0IGlzIGluIHRoZSBwdWJsaWMgZG9tYWluLiBLZXZpbiBIdWdoZXMsIGtldmluaEBlaXQuY29tLCBTZXB0ZW1iZXIgMTk5NXb275wAAAAASUVORK5CYII=",module.exports.movie="data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABQAAAAWBAMAAAAyb6E1AAAAFVBMVEX////M///MzMyZmZlmZmYzMzMAAAC3QbbwAAAAAnRSTlP/AOW3MEoAAAABYktHRACIBR1IAAAAOUlEQVQIW2NIg4JEQYYkNTBLKRXEdAECNhAzLc3Z2NiYLQ0sCmYqoTKJUMAABFAF9LUCzhQNhQJBAGWZNOmfH9xVAAAAVnRFWHRjb21tZW50AFRoaXMgYXJ0IGlzIGluIHRoZSBwdWJsaWMgZG9tYWluLiBLZXZpbiBIdWdoZXMsIGtldmluaEBlaXQuY29tLCBTZXB0ZW1iZXIgMTk5NXb275wAAAAASUVORK5CYII=",module.exports.text="data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABQAAAAWBAMAAAAyb6E1AAAAD1BMVEX////M//+ZmZkzMzMAAABVsTOVAAAAAnRSTlP/AOW3MEoAAAABYktHRACIBR1IAAAAT0lEQVQIW5XIsQ3AIAwF0VNgAa+AGABkD0Dx958pRRy55qrTw93dfZsZC6C1WnZtq2Ubq0unR0Rql5TKM2YqjPmpdCjlVuFG//XxFYYpsxfEkhYAImC9XwAAAFZ0RVh0Y29tbWVudABUaGlzIGFydCBpcyBpbiB0aGUgcHVibGljIGRvbWFpbi4gS2V2aW4gSHVnaGVzLCBrZXZpbmhAZWl0LmNvbSwgU2VwdGVtYmVyIDE5OTV29u+cAAAAAElFTkSuQmCC",module.exports.unknown="data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABQAAAAWBAMAAAAyb6E1AAAAD1BMVEX////M//+ZmZkzMzMAAABVsTOVAAAAAnRSTlP/AOW3MEoAAAABYktHRACIBR1IAAAAYklEQVQIW23O0Q2AIBAD0AZcgA0IYQAJDGCw+8/k3SFoov16FEKKaikhBOyQeP8QxZjIE17pqJR6kK014cZuJ+MBMuXxg1vUewxmst+UMi5GLGLS8mn/+Xo7WdOIjAw60EZeVZkZLhf9K5EAAABWdEVYdGNvbW1lbnQAVGhpcyBhcnQgaXMgaW4gdGhlIHB1YmxpYyBkb21haW4uIEtldmluIEh1Z2hlcywga2V2aW5oQGVpdC5jb20sIFNlcHRlbWJlciAxOTk1dvbvnAAAAABJRU5ErkJggg=="; },{}],"0nsJ":[function(require,module,exports) { -"use strict";var t=require("./content-type"),n=t.isMedia,e=t.isImage,r=t.getMimeType,o=require("filer"),a=o.path,c=require("../icons/icons"),h=c.back,i=c.blank,d=c.folder,s=c.image2,l=c.movie,u=c.text,m=c.unknown,g=function(t){var n=t.getDate(),e=t.toLocaleString("en-us",{month:"short"}),r=t.getFullYear(),o=t.getHours(),a=t.getMinutes();return"".concat(n,"-").concat(e,"-").concat(r," ").concat(o,":").concat(a)},f=function(t){if(!t)return"-";var n=0|Math.floor(Math.log(t)/Math.log(1024));return Math.round(t/Math.pow(1024,n),2)+["","K","M"][n]},p=function(t){var n=arguments.length>1&&void 0!==arguments[1]?arguments[1]:"[ ]",e=arguments.length>2?arguments[2]:void 0,r=arguments.length>3?arguments[3]:void 0,o=arguments.length>4?arguments[4]:void 0,a=arguments.length>5?arguments[5]:void 0;return"").concat(n,"\n ").concat(r,"\n ").concat(g(new Date(o)),"\n ").concat(f(a)," ")},b="
nohost (Web Browser Server)
";function v(t){return{body:"\n \n \n 404 Not Found\n \n

Not Found

\n

The requested URL ".concat(t," was not found on this server.

\n
").concat(b),config:{status:404,statusText:"Not Found",headers:{"Content-Type":"text/html"}}}}function T(t,n){return{body:"\n \n \n 500 Internal Server Error\n \n

Internal Server Error

\n

The server encountered an internal error while attempting to access ".concat(t,".

\n

The error was: ").concat(n.message,".

\n
").concat(b),config:{status:500,statusText:"Internal Error",headers:{"Content-Type":"text/html"}}}}function y(t,r,o){var c=a.dirname(r)||"/",m="\n \n Index of ".concat(r," \n

Index of ").concat(r,"

\n \n \n \n \n \n \n "),g="
[ICO]NameLast modifiedSizeDescription

[DIR]Parent Directory  -  

".concat(b);return{body:m+o.map(function(o){var c,h,i=a.extname(o.name),m="".concat(t).concat(a.join(r,o.name));return"DIRECTORY"===o.type?(c=d,h="[DIR]"):e(i)?(c=s,h="[IMG]"):n(i)?(c=l,h="[MOV]"):(c=u,h="[TXT]"),p(c,h,m,o.name,o.mtime,o.size)}).join("\n")+g,config:{status:200,statusText:"OK",headers:{"Content-Type":"text/html"}}}}function x(t,n){return{body:n,config:{status:200,statusText:"OK",headers:{"Content-Type":r(t)}}}}module.exports={format404:v,format500:T,formatDir:y,formatFile:x}; +"use strict";var t=require("./content-type"),n=t.isMedia,e=t.isImage,r=t.getMimeType,o=require("filer"),a=o.path,c=require("../icons/icons"),h=c.back,i=c.blank,d=c.folder,s=c.image2,l=c.movie,u=c.text,m=c.unknown,g=function(t){var n=t.getDate(),e=t.toLocaleString("en-us",{month:"short"}),r=t.getFullYear(),o=t.getHours(),a=t.getMinutes();return"".concat(n,"-").concat(e,"-").concat(r," ").concat(o,":").concat(a)},f=function(t){if(!t)return"-";var n=0|Math.floor(Math.log(t)/Math.log(1024));return Math.round(t/Math.pow(1024,n),2)+["","K","M"][n]},p=function(t){var n=arguments.length>1&&void 0!==arguments[1]?arguments[1]:"[ ]",e=arguments.length>2?arguments[2]:void 0,r=arguments.length>3?arguments[3]:void 0,o=arguments.length>4?arguments[4]:void 0,a=arguments.length>5?arguments[5]:void 0;return"").concat(n,"\n ").concat(r,"\n ").concat(g(new Date(o)),"\n ").concat(f(a)," ")},b="
nohost (Web Browser Server)
";function v(t){return{body:"\n \n \n 404 Not Found\n \n

Not Found

\n

The requested URL ".concat(t," was not found on this server.

\n
").concat(b),config:{status:404,statusText:"Not Found",headers:{"Content-Type":"text/html"}}}}function T(t,n){return{body:"\n \n \n 500 Internal Server Error\n \n

Internal Server Error

\n

The server encountered an internal error while attempting to access ".concat(t,".

\n

The error was: ").concat(n.message,".

\n
").concat(b),config:{status:500,statusText:"Internal Error",headers:{"Content-Type":"text/html"}}}}function y(t,r,o){var c=a.dirname(r)||"/",m=encodeURI(t+c),g="\n \n Index of ".concat(r," \n

Index of ").concat(r,"

\n \n \n \n \n \n \n "),f="
[ICO]NameLast modifiedSizeDescription

[DIR]Parent Directory  -  

".concat(b);return{body:g+o.map(function(o){var c,h,i=a.extname(o.name),m=encodeURI("".concat(t).concat(a.join(r,o.name)));return"DIRECTORY"===o.type?(c=d,h="[DIR]"):e(i)?(c=s,h="[IMG]"):n(i)?(c=l,h="[MOV]"):(c=u,h="[TXT]"),p(c,h,m,o.name,o.mtime,o.size)}).join("\n")+f,config:{status:200,statusText:"OK",headers:{"Content-Type":"text/html"}}}}function I(t,n){return{body:n,config:{status:200,statusText:"OK",headers:{"Content-Type":r(t)}}}}module.exports={format404:v,format500:T,formatDir:y,formatFile:I}; },{"./content-type":"KEOA","filer":"KyOv","../icons/icons":"xVBo"}],"4itQ":[function(require,module,exports) { "use strict";var e=new URL(location);function r(){var r=e.searchParams.get("route")||"fs";return r=(r=r.replace(/^\/*/,"/")).replace(/\/*$/,"")}module.exports={route:r(),disableIndexes:null!==e.searchParams.get("disableIndexes"),directoryIndex:e.searchParams.get("route")||"index.html",debug:null!==e.searchParams.get("debug")}; },{}],"/tkn":[function(require,module,exports) { "use strict";var n=require("filer"),e=n.fs,t=n.Path,i=require("./config"),o=i.route,r=i.disableIndexes,c=i.directoryIndex,f=new e.Shell;function a(n,e){var i=t.basename(n),o=e.mtime.toUTCString();return'attachment; filename="'.concat(i,'"; modification-date="').concat(o,'"; size=').concat(e.size,";")}var s=function(n,i,s){return new Promise(function(u){function d(n){return new Response(n.body,n.config)}function m(n,e){if("ENOENT"===e.code)return u(d(i.format404(n)));u(d(i.format500(n,e)))}function l(n,t){e.readFile(n,function(e,o){if(e)return m(n,e);var r=i.formatFile(n,o,t);200===r.config.status&&s&&(r.config.headers["Content-Disposition"]=a(n,t)),u(new Response(r.body,r.config))})}function g(n){var a;a=t.join(n,c),e.stat(a,function(e,t){e?"ENOENT"!==e.code||r?m(n,e):f.ls(n,function(e,t){if(e)return m(n,e);var r=i.formatDir(o,n,t);u(new Response(r.body,r.config))}):l(a,t)})}e.stat(n,function(e,t){if(e)return m(n,e);t.isDirectory()?g(n):l(n,t)})})};module.exports.serve=s; },{"filer":"KyOv","./config":"4itQ"}],"JQ+3":[function(require,module,exports) { -var r=require("./json-formatter"),e=require("./html-formatter"),o=require("./webserver"),t=o.serve,a=require("./config"),n=a.debug,s=a.route;importScripts("https://storage.googleapis.com/workbox-cdn/releases/4.1.1/workbox-sw.js"),workbox.setConfig({debug:n});var i=new RegExp("".concat(s,"(/.*)")),c=new RegExp("".concat(s,"$"));workbox.routing.registerRoute(i,function(o){var a=o.url,n=a.pathname.match(i)[1],s=null!==a.searchParams.get("json")?r:e,c=null!==a.searchParams.get("download")||null!==a.searchParams.get("dl");return t(n,s,c)},"GET"),workbox.routing.registerRoute(c,function(r){var e=r.url;return e.pathname="".concat(s,"/"),Promise.resolve(Response.redirect(e,302))},"GET"),workbox.core.skipWaiting(),workbox.core.clientsClaim(); +var e=require("./json-formatter"),r=require("./html-formatter"),o=require("./webserver"),t=o.serve,a=require("./config"),n=a.debug,s=a.route;importScripts("https://storage.googleapis.com/workbox-cdn/releases/4.1.1/workbox-sw.js"),workbox.setConfig({debug:n});var i=new RegExp("".concat(s,"(/.*)")),c=new RegExp("".concat(s,"$"));workbox.routing.registerRoute(i,function(o){var a=o.url,n=a.pathname.match(i)[1];n=decodeURIComponent(n);var s=null!==a.searchParams.get("json")?e:r,c=null!==a.searchParams.get("download")||null!==a.searchParams.get("dl");return t(n,s,c)},"GET"),workbox.routing.registerRoute(c,function(e){var r=e.url;return r.pathname="".concat(s,"/"),Promise.resolve(Response.redirect(r,302))},"GET"),workbox.core.skipWaiting(),workbox.core.clientsClaim(); },{"./json-formatter":"55+A","./html-formatter":"0nsJ","./webserver":"/tkn","./config":"4itQ"}]},{},["JQ+3"], null) //# sourceMappingURL=/nohost-sw.js.map \ No newline at end of file diff --git a/example/index.js b/example/index.js index b428364..37098a9 100644 --- a/example/index.js +++ b/example/index.js @@ -10,7 +10,7 @@ function serverInstall() { console.log('Server installed for first time'); const fs = window.Filer.fs; - fs.writeFile('/readme.txt', 'hello world!', function(err) { + fs.writeFile('/hello world.txt', 'hello world!', function(err) { if(err) console.error(err); }); } diff --git a/src/html-formatter.js b/src/html-formatter.js index b87558d..969197d 100644 --- a/src/html-formatter.js +++ b/src/html-formatter.js @@ -89,6 +89,8 @@ function format500(path, err) { */ function formatDir(route, dirPath, entries) { const parent = path.dirname(dirPath) || '/'; + // Maintain path sep, but deal with things like spaces in filenames + const url = encodeURI(route + parent); const header = ` Index of ${dirPath} @@ -98,13 +100,14 @@ function formatDir(route, dirPath, entries) { SizeDescription
[DIR] - Parent Directory  + Parent Directory  -  `; const footer = `
${footerClose}`; const rows = entries.map(entry => { const ext = path.extname(entry.name); - const href = `${route}${path.join(dirPath, entry.name)}`; + // Maintain path sep, but deal with things like spaces in filenames + const href = encodeURI(`${route}${path.join(dirPath, entry.name)}`); let icon; let alt; diff --git a/src/nohost-sw.js b/src/nohost-sw.js index 9a76efb..f7f226c 100644 --- a/src/nohost-sw.js +++ b/src/nohost-sw.js @@ -18,7 +18,9 @@ workbox.routing.registerRoute( wwwRegex, ({ url }) => { // Pull the filesystem path off the url - const path = url.pathname.match(wwwRegex)[1]; + let path = url.pathname.match(wwwRegex)[1]; + // Deal with encoding in the filename (e.g., spaces as %20) + path = decodeURIComponent(path); // Allow passing `?json` on URL to get back JSON vs. raw response const formatter =