Search code examples
htmlnode.jslocalhostrelative-pathfile-location

How do I serve static files through Node.js locally?


I have the following file locations :

file:///Users/MyName/Developer/sitename/scripts (contains all .js files..)
file:///Users/MyName/Developer/sitename/css (contains all .css files..)
file:///Users/MyName/Developer/sitename/images (contains all .jpg/png/etc. files..)
file:///Users/MyName/Developer/sitename/sitename.html
file:///Users/MyName/Developer/sitename/server.js

Inside sitename.html I load all necessary files as follows for example :

<html>
  <head>
    <script src="scripts/somefile.js"></script>
  </head>
  ...
</html>

So whenever I open up file:///Users/MyName/Developer/sitename/sitename.html everything works fine.

However, whenever I try to load file:///Users/MyName/Developer/sitename/sitename.html via a local Node.js server that I've setup (server file location : file:///Users/MyName/Developer/sitename/server.js) as follows :

var http = require("http"); 
var fs = require("fs");

fs.readFile('./sitename.html', function (err, html) 
{
    if (err) throw err; 

    http.createServer(function (request,response)
    {  
        // serve site
        if (request.url === "/")
        {
            response.writeHeader(200, {"Content-Type": "text/html"});  
            response.write(html);  
        }
        response.end(); 
    }).listen(8080); 
});

sitename.html is found and loaded but all the other files that are supposed to load through it fail to load because they're all given the prefix http://localhost:8080/ (http://localhost:8080/scripts/somefile.jsis not a valid file path for example).

It looks like as soon as the server is created (inside http.createServer(.....);) the context changes and the parent directory now becomes http://localhost:8080/ instead of file:///Users/MyName/Developer/sitename/ which makes sense I guess but is not very helpful when using files that are still stored locally.

How do I work around that? Is the fact that I'm storing server.js (just for the time being) in the same directory making things even more confusing?

Thanks!


Solution

  • You're able to load the files using the file:// URL because it's a feature of your web browser.

    When loading the address http://localhost:8080 you're no longer leveraging the browser's ability to serve the files (you're accessing the Node.js server). The HTML page being served contains relative paths which work in conjunction with the current hostname to load the assets.

    There is a multitude of options for serving the assets.

    You could serve the files with Node.js:

    Alternatively you could use a web server to serve the files for you. This is likely to be the most performant option. Here is an example of serving static content with nginx.