Playing with routing
What is this?
Here we are in part seven of my learning experience. The aim is to learn node in order to make an opensource web app that can be used by sysadmins for daily tasks.
If you're interested in reading earlier posts here's the index page.
So you mean express
?
No, I know express.js
is a thing and I know people like it but I thought, to start with at least, I'd try my hand at making a custom router. I don't intend to make it do anything fancy just a simple thing to help me understand the greater concept.
Starting point
To start with I made an incredibly simple proof on concept.
const http = require('http');
function router(url) {
let address = url.split('/')[1] || "index";
return address;
}
http.createServer((req, res) => {
res.writeHead(200, { 'Content-Type': 'text/plain' });
res.end(router(req.url));
}).listen(80);
It looks at the URL path and prints the first part to the screen, if there's nothing there it prints index. Super simple but proofs we can use a function to work out what need to be printed.
Loading files
The next step was having it load files rather than just pushing text.
const http = require('http');
const fs = require("fs");
const pages = "pages";
function router(url) {
let address = url.split('/')[1] || "index";
let content;
try {
content = fs.readFileSync(`.\\${pages}\\${address}.html`, 'utf8');
} catch (err) {
content = fs.readFileSync(`.\\${pages}\\404.html`, 'utf8');
}
return content;
}
http.createServer((req, res) => {
res.writeHead(200, { 'Content-Type': 'text/html' });
res.end(router(req.url));
}).listen(80);
I just used readFileSync
from fs
, it checks if the file exists, if it does it will serve the file if not it will serve the 404 page.
There are a couple of problems with this approach. If I try and browser to http://localhost/home?beta=true
I'll get a 404 as .\pages\home?beta=true.html
can't be opened, anchors do work, however. Also, there is no support for deeper links like http://localhost/api/userlist
.
Limitations
I've already mentioned there are solutions for this out there already so I'm not going to try and overcome these limitations. Though if you want to tell me some ways you'd have solved them I'd love to hear them.
What's next
Next week I'm going to look at express.js
and try my hand at making a quick project, I was thinking perhaps a MySQL client to read and maybe write, data. Though, if you have a suggestion for something else I should do I'll happily concider that.
Sorry for the short post, hopefully, I'll be back to the longer ones soon, unless you prefer the short ones of course.
Thanks for reading! 🦄🦄🦄
Top comments (2)
Great progress, I enjoy reading these posts!
Glad you asked!
Since you're not using the query string at all, the easiest is to simply ignore it. You can use node's url module to parse the url and get the path and query string separately.
Incidentally, this would also address the other limitation you mention. Using
url.parse(...).pathname
will get you the full path without the host or the query string, so you can use that to read the correct file.path.join(pages, ...address.split('/'))
will basically return the right file path in any OS, it will append thepages
folder to the file's folder (__dirname
is the folder where your source file is located) and then replace all slashes in the url path with the OS character to separate folders.Lookin' good so far! I can't wait to see where it goes from here 😊