Intro to
Node.js
Chris Cowan
Twitter: @uhduh
Github: ccowan
The GOAL of NODE.JS IS TO provide an easy way to build scaleable network programs
NODE.JS IS NOT ANOTHER WEB FRAMEWORK
NODE.JS IS:
A Web Server
TCP Server
Awesome Robot Server
Drone Controller
Command Line Application
Proxy Server
Steaming Server
VoiceMail Server
Music Machine
(any thing that has to deal with I/0)
NODE.JS IS
NODE.JS is
FUN!
WHY NODE.JS?
Non-Blocking I/O
Based On Chrome's V8 Engine
20,000+ Modules
Very Active Community
Supported on Mac, Linux, and Windows
One Language to Rule them All
JavaScript is the Language of the Web
Mostly True Facts
About Node.jS
9 out of 10 Web Developers prefer to use Node.js
It increases employee satisfaction by 99.99999%
Every 2 minutes a developer decides to rewrite their PHP site with Node.js
94.7% of Hackathons are won using
Node.js and Socket.io.
Basic Example
Create helloworld.js with:
console.log('Hello World');
On the command line run
node helloworld.js
You should see
Hello World
Basic HTTP SERVER
var http = require('http');
var server = http.createServer(function (req, res) {
res.writeHead(200);
res.end('Hello World');
});
server.listen(4000);
* Running this script on my development box I can achieve 10,000+ requests per second with 100 concurrent connections without breaking a sweat.
What is
Non-Blocking IO?
AND WHY SHOULD I CARE?
BLOCKING I/0
// Get Users - 20ms
$query = 'SELECT * FROM users WHERE id = ?';
$users = query($query, array($_GET['id']));
print_r($users);
// Get Activities - 130ms
$query = 'SELECT * FROM activities WHERE user_id = ? ORDER BY TIMESTAMP LIMIT 50';
$activities = query($query, array($_GET['id']));
print_r($activities);
// Get Leader Board - 120ms
$query = 'SELECT count(points),user_id FROM activities GROUP BY user_id LIMIT 50';
$leader_board = query($query);
print_r($leader_board);
270ms = SUM($user, $activities, $leader_board)
NON-BLOCKING I/0
// Get Users - 20ms
var query = 'SELECT * FROM users WHERE id = ?';
db.query(query, [req.query.id], function (err, users) {
console.log(users);
});
// Get Activities - 130ms
query = 'SELECT * FROM activities WHERE user_id = ? ORDER BY TIMESTAMP LIMIT 50';
db.query(query, [req.query.id], function (err, activities) {
console.log(activities);
});
// Get Leader Board - 120ms
query = 'SELECT count(points),user_id FROM activities GROUP BY user_id LIMIT 50';
db.query(query, function (err, leader_board) {
console.log(leader_board);
});
130ms = SUM(user, activities, leader_board)
ReAL WORLD EXAMPLE
of Why Non-Blocking I/O Matters
10 Separate Data Calls!
THE MOST JARRING THING ABOUT SERVER SIDE JAVASCRIPT IS THINKING IN CALLBACKS
The NODE.JS CALLBACK PATTERN
awesomeFunction(args, function (err, data) {
if (err) {
// Handle Error
}
// Do something awesome with the data
});
- Error First then success... ALWAYS!
- Because this is the defacto standard, 99.99999% of the time you will be able to guess how a Node.js module works
Some people will say
Callbacks are the devil'S WORK
db.query(userQuery, [id], function (err, userResults) {
db.query(activityQuery, [id], function (err, activityResults) {
db.query(leaderBoardQuery, function (err, leaderBoardResults) {
// I HATE MY LIFE!
});
});
});
One of the biggest mistakes is to get yourself in to CALLBACK HELL by nesting callbacks inside of callbacks inside of callbacks inside of callbacks inside of callbacks... aaahhhrrigh!
AVOIDING CALLBACK HELL
Keep your code shallow
Break up your code into small chunks
Use a sequential library like async
Visit http://callbackhell.com
Async Module Example
var async = require('async');
var db = require(’db');
function getUser (callback) {
var query = 'SELECT * FROM users WHERE id = ?';
db.query(query, [userId], callback);
}
function getActivities (callback) {
var query = 'SELECT * FROM activities ORDER BY timestamp LIMIT 50';
db.query(query, callback);
}
function getLeaderBoard (callback) {
var query = 'SELECT count(points) as total, user_id FROM activities LIMIT 50';
db.query(query, callback);
}
var tasks = [getUser, getActivities, getLeaderBoard];
async.parallel(tasks, function (err, results) {
var user = results[0][0];
var activities = results[1];
var leaderBoard = results[2];
});
The Node PAckage manager
otherwise known as NPM!
NPM is how you harness the awesomeness of the Node.js community
USING NPM
It's standard practice to install modules locally for your current project. Modules are installed in
./node-modules
in the current directory
To install a new module:
npm install <module>
To find a module in the repo:
npm find <module>
To list the modules (and depedancies) for the curent project:
npm list
Basic Module Example
var currentCount = 0;
module.exports.incr = function () {
return ++currentCount;
};
Once you've created a module in counter.js you use it like this...
var counter = require('./counter');
counter.incr();
var count = counter.inrc();
Keep this in mind... modules are loaded once and cached. So when you load the module a second time in your app, require just returns the cached module object. This lets you do interesting things...
CREATING YOU OWN MODULES
require('./example') will load either example.js or example/index.js or the entry point defined in package.json
Run npm init to bootstrap your new module, this will create the package.json
Try to stick to creating "Pure JavaScript" module if possible. It will give you less headaches down the road
INSTALLING YOUR MODULES
Run npm link in the module directory. Then run
npm link module in the project directory.
Add the module's Gitub URL to your package.json dependancies and run npm install.
"dependencies": {
"my-module": "https://github.com/my-name/my-module/tarball/master"
}
Link the module by hand to your projects node_modules directory
OPRAH's Favorite Modules
request async node-dev hogan.js connect underscore restify moment schemajs grunt coffee-script mysql mocha redis lessQuestions?
Twitter: @uhduh
introtonodejs
By ccowan
introtonodejs
- 4,082