diff --git a/docs/LiveDirectory.md b/docs/LiveDirectory.md index 4101da5..7c353f0 100644 --- a/docs/LiveDirectory.md +++ b/docs/LiveDirectory.md @@ -3,7 +3,7 @@ Below is a simple guide on implementing static serving functionality to HyperExp #### Why LiveDirectory? LiveDirectory loads files from the specified path into memory and watches them for updates allowing for instantaneous changes. This is desirable for both development and production environments as we do not have to wait on any I/O operation when serving assets. Each request will serve the most updated file content from memory allowing for high performance and throughput without any bottlenecks. -- See [`> [LiveDirectory]`](./docs/LiveDirectory.md) for all available properties, methods and documentation on this package. +- See [`> [LiveDirectory]`]([./docs/LiveDirectory.md](https://github.com/kartikk221/live-directory)) for all available properties, methods and documentation on this package. #### Getting Started Please install the [`live-directory`](https://github.com/kartikk221/live-directory) using the `npm` package manager. @@ -18,14 +18,29 @@ const LiveDirectory = require('live-directory'); const Server = new HyperExpress.Server(); // Create a LiveDirectory instance to virtualize directory with our assets -const LiveAssets = new LiveDirectory({ - path: '/var/www/website/files', // We want to provide the system path to the folder. Avoid using relative paths. - keep: { - extensions: ['.css', '.js', '.json', '.png', '.jpg', '.jpeg'] // We only want to serve files with these extensions - }, - ignore: (path) => { - return path.startsWith('.'); // We want to ignore dotfiles for safety +// Specify the "path" of the directory we want to consume using this instance as the first argument +const LiveAssets = new LiveDirectory('/var/www/website/files', { + // Optional: Configure filters to ignore or include certain files, names, extensions etc etc. + filter: { + keep: { + // Something like below can be used to only serve images, css, js, json files aka. most common web assets ONLY + extensions: ['.css', '.js', '.json', '.png', '.jpg', '.jpeg'] + }, + ignore: (path) => { + // You can define a function to perform any kind of matching on the path of each file being considered by LiveDirectory + // For example, the below is a simple dot-file ignore match which will prevent any files starting with a dot from being loaded into live-directory + return path.startsWith('.'); + }, } + + // Optional: You can customize how LiveDirectory caches content under the hood + cache: { + // The parameters below can be tuned to control the total size of the cache and the type of files which will be cached based on file size + // For example, the below configuration (default) should cache most <1 MB assets but will not cache any larger assets that may use a lot of memory + // In the scenario that LiveDirectory encounters an uncached file, It will s + max_file_count: 250, // Files will only be cached up to 250 MB of memory usage + max_file_size: 1024 * 1024, // All files under 1 MB will be cached + }, }); // Create static serve route to serve frontend assets @@ -37,9 +52,16 @@ Server.get('/assets/*', (request, response) => { // Return a 404 if no asset/file exists on the derived path if (file === undefined) return response.status(404).send(); - - // Set appropriate mime-type and serve file buffer as response body - return response.type(file.extension).send(file.buffer); + + // Retrieve the file content and serve it depending on the type of content available for this file + const content = file.content; + if (content instanceof Buffer) { + // Set appropriate mime-type and serve file content Buffer as response body (This means that the file content was cached in memory) + return response.type(file.extension).send(content); + } else { + // Set the type and stream the content as the response body (This means that the file content was NOT cached in memory) + return response.type(file.extension).stream(content); + } }); // Some examples of how the above route will map & serve requests: @@ -48,7 +70,4 @@ Server.get('/assets/*', (request, response) => { ``` #### Is This Secure? -LiveDirectory will traverse through all sub-directories and files from your specified path and load its files into memory. Due to this, we do not perform any file system operations for lookups of files. This eliminates any path manipulation vulnerability that may allow a bad actor to access sensitive files on your hardware as only files that loaded into memory are served. To view which files have been loaded into memory by LiveDirectory simply view the `LiveDirectory.files` object. - -#### What Are The Downsides? -Since LiveDirectory loads all files from your specified path into memory, this method of static serving is not suitable for serving large files automatically. It is strongly recommended to use read streams combined with the `Response.write` method to write large files in chunks to prevent exhaustion of your system's memory. \ No newline at end of file +LiveDirectory will traverse through all sub-directories and files from your specified path ahead of time and load its files into memory during startup. Due to this, we do not perform any file system operations for any `get()` calls making things performant. This eliminates any path manipulation vulnerability that may allow a bad actor to access sensitive files on your hardware as only files that loaded into memory are served. You can inspect the `LiveDirectory.files` property at any time to confirm which file paths are being loaded by `LiveDirectory` to detect any unintended files.