Node.js — Non Blocking Evented ServerSide Javascript

Posted by feydr | Posted in Uncategorized | Posted on 27-07-2010

View Comments


“Because nothing blocks, less-than-expert programmers are able to develop fast systems.”
http://nodejs.org

Birds Eye View of Node.js

I’m sure you’ve all seen/heard stuff about using real-time websockets — this guy used node.js but a lot of ppl don’t know that there is so much more to this framework than meets the eye.

First off, it has no locks, is non-blocking in as many places as possible and uses very little memory. Oh yeh, pretty much everything has a callback, following an evented model. Some POSIX operations return a ‘promise’ which signal a ‘success’ or ‘error’. Node is ridiculously powerful as you can see by reading over the api. There is so much here to do and really allows you to do some ‘system-level’ style of programming with a whole slew of POSIX style (compliant?) system calls

Concurrency without Multi-Threading?
Most of the built in hard-core concurrency comes from the evented nature of the framework. Being able to immediately respond to incoming requests while something is off reading from a database provides much needed clock cycles. Right now it appears there is no straight-forward way of utilizing multiple cores other than putting a load balancer of sorts in front and sending over unix sockets or something but there are plans to including forking in the future so that different processes may emerge taking advantage of the cores and utilize message passing to talk to each other. You can of course fork new processes using the system calls available.

Apparently the developers of node are looking towards using web workers available in HTML5 which will also alleviate some concurrency issues.

So who uses it? Is it production quality yet? Well, you can always ask the good folks over at Plurk.com (twitter for japan) who run it w/over 100k concurrent users — apparently this runs on one box with 8 proccesses…. uhhhh…


wtf

…. that’s what I was thinking tha fuck!?

… maybe I should go spend some time in japan … I keep finding all sorts of shit I like from there

Hello World in Node.js

var sys = require('sys');
sys.puts('hello!');

so first off we include the sys lib then we do our puts statement .. pretty simple
let’s take a look at a

Simple Node.js HTTP Server

var http = require('http');
http.createServer(function (req, res) {
  res.writeHead(200, {'Content-Type': 'text/plain'});
  res.end('Hello World\n');
}).listen(8124, "127.0.0.1");
console.log('Server running at http://127.0.0.1:8124/');

yeh… it doesn’t really get too hard but this shows the evented nature of node — shit is retardo fast


wiley coyote rockets

Speed Demon Benches

ab -c 100 -n 1000 http://127.0.0.1:8124/
Requests per second:    6792.23 [#/sec] (mean)

… but it’s not just for HTTP

if you have any need for networking this is a badass framework to be using. It uses a microkernel design by including modules that you need rather than a bunch of shit you *might* use — big win in my favor..even down to sys/http modules.

you can find a list of supporting modules here

Binary Data

I’m including this section here because when I was looking for information on sending bytes here and there I found lots of articles on the internet saying this was not easily done with node.js — this IS EASILY DONE now. You CAN make a buffer with binary data now and NOT have to specify ‘utf8′, ‘ascii’, ‘base64′, etc…the ‘net2 branch’ that you might see referenced to on the net is already merged in and the api docs are current though can be rather confusing after reading older documentation found around…so ignore that old shit — so, just to clarify, if you are sending binary data through some random socket you can do that now.

Want to see an example of this mysterious byte buffer?

  Buffer = require('buffer').Buffer;
  buf = new Buffer(8);
  for(i =0; i < 8; i+=1) { buf[i] = 0; }

be careful as your buffer will be initialized with random data so I’d advise clearing it first

very interesting that you can do this now since javascript doesn’t like binary data that well

buffer.copy does a memcpy() …. begging to get owned by some hackers — remember to sanitize your data

Downloading/Installing

before doing anything else go ahead and grab the latest (as of this writing):

wget http://nodejs.org/dist/node-v0.1.102.tar.gz
./configure && make && sudo make install

woohoo! simple build process ftw

want to use express? it’s pretty cool, like sinatra and it’ll allow you to get to know the most tubular npm tool.

let’s check our version because all of this code is bleeding edge stuff

feydr@mhu:~$ node -v
v0.1.102

also, let’s grab npm first:

git clone http://github.com/isaacs/npm
cd npm; sudo make install

now we can install express and it’s supporting modules that we want:

sudo npm install jade
sudo npm install less
sudo npm install connect
sudo npm install express

playing with it:

mkdir test/; cd test;
express # generates a new app
node app.js # to start the server
# switch to a diff. window
curl 127.0.0.1:3000

speed?
much slower than native node.js but hey, it takes a lot of pain away
it’s still slightly retarded fast compared to say rails and django

ab -c 100 -n 1000 http://127.0.0.1:3000/
Requests per second:    1200.16 [#/sec] (mean)

Support && References
shit tons of ppl on the #node.js irc channel

Need something to show the boss — some slides

My mind is literally wheeling with the crazy shit that this framework allows you to do… particularly remotely…

Last thing before you leave, watch this.

  • Jimbastard
    benchmarking with apache ab is a joke. you'll hit the upper limits of apache ab before you hit the limits of node.
  • Steve Jobs
    Or set your -n of benchmarks to say, 100,000 and see what happens.
  • feydr
    ROFLcopter! wtf do you bench with? just trying to compare apples to apples here ... I'd use ab or httperf to look at requests/second on php/ruby or this ... but I do hear your point
blog comments powered by Disqus