CSE 190m Extra Sessions

Section #9 - node.js

By Shiny Yang and Mason Remy

Node.js

  1. Big Picture
  2. Basics
  3. Networking
  4. img push
  5. Multiplayer game
  6. Security

Big Picture

node.js lets you:

node javascript object flow

Basics - node.js console

On a server with node.js installed, you can simply run node to interact with node.js in a console window

Since node.js just reads regular javascript that we know and love, we can already dive in

[remyw@webster node] 0 $ node
> console.log("cool!");
cool!
undefined
> function plans(name) {
... if (name == "Marty") {
..... return "Party";
..... }
... return "Study for 190m final >=(";
..... }
undefined
> plans("Marty");
'Party'

				

Basics - Setting Up Your Server

Need the "socket.io" package downloaded

Setting up a listener:

Call the require() function with a directory path to the socket.io file, and then call listen() on the returned object with the port you want to listen on

This returns you an object which we'll use later

require(path-to-socket-file).listen(port)

var io = require("socket.io").listen(1500);
				

Basics - Accepting a connection

Now that we're listening on a port, we have to do something when a user tries to "connect"

We'll set how a user "connects" later

With the io object we got earlier, listen for a connection with the call

io.sockets.on(event, function-to-call);

io.sockets.on("connection", myAwesomeFunction);
function myAwesomeFunction() { ... }
				

Here, the function to call is just like the onSuccess function that when we do Ajax requests (everyone's favorite)

Basics - Accepting a connection

Now that we know someone has connected, let's do something about it

When our function gets called, we get a socket object which is like a direct communication line to the person who connected

telephone
io.sockets.on("connection", function(socket) {
	...
});
				

Basics - Writing to a connection

Let's tell them that they're connected

To say something to the client (the other end of the socket), use the emit function: io.sockets.emit(event, json);

io.sockets.on("connection", function(socket) {
	io.sockets.emit("connect", {message: "you're all connected yo"});
});
				

Basics - Client side connecting

We know how to listen for and accept connections, how do we make a connection in the first place?

On the client side (i.e. your desktop at home), the code is similar

The tricky part is getting an io object like we had before

In the html of our page we'll need to include the socket.io javascript running on the server

...
<head>
    <title>My Page Title</title>
        <script src="http://webster.cs.washington.edu:1500/socket.io/socket.io.js"></script>
        <script type="text/javascript" src="http://ajax.googleapis.com/ajax/libs/prototype/1.6.1.0/prototype.js"></script> 
        ...
				

This will now get us an io object we can do things with (it's a global variable)

Basics - Client side connecting

Now to finally connect to a server, we call the connect function on our io object:

var socket = io.connect(server);

var socket;

document.observe("dom:loaded", function() {
	socket = io.connect("http://webster.cs.washington.edu:1500");
	...
});
				

Basics - Client side listening for responses

Now that we can connect to our server, we want to be able to do things when it sends us messages

We add listeners (similar to dom element listeners), to our socket object with the on function

socket.on(event, function);

When the function gets called, we also get a data object as a parameter, holding whatever the server sent us

var socket;

document.observe("dom:loaded", function() {
	socket = io.connect("http://webster.cs.washington.edu:1500");
	socket.on("connect", function(data) {
		if (data) {
			console.log(data);
		}
	});
	...
};
				

Basics - Client side listening for responses

Suppose we know the server is sending us something with a key of "message", how do we access it?

(It's just regular JSON!)

var socket;

document.observe("dom:loaded", function() {
	socket = io.connect("http://webster.cs.washington.edu:1500");
	socket.on("connect", function(data) {
		if (data) {
			console.log(data.message);
		}
	});
};
				
> you're all connected yo
				

Basics - Using the console on the server side

What if I wanted to send information from the server to all my clients whenever I feel like it?

Use the console to interact with your server code (call functions, write strings, etc.)

In the server code, use the process object (think of it like the window or document object that we're used to in javascript)

Call the openStdin function to allow the server user to type in the console

var stdin = process.openStdin();
				

Basics - Using the console on the server side

Now that we have the stdin object, we need to add a listener to it (notice the pattern?)

stdin.on(event, function);

stdin.on('data', function(chunk) {
	console.log("you typed in: " + chunk.toString());
	...
});
				

To make it more powerful, we can use the eval function to run whatever is typed in as javascript

stdin.on('data', function(chunk) {
	eval(chunk.toString());
});
				

Basics - Running the whole thing

We run our server code with the node command, giving it a javascript file as an argument

[root@webster node] 0 # node server.js 
   info  - socket.io started
				

Where server.js holds our server code:

var stdin = process.openStdin();
var io = require("socket.io").listen(1500);
io.set("log level", 1);

io.sockets.on("connection", function(socket) {
		io.sockets.emit("connect", {message:"bitchin'"});
});

stdin.on('data', function(chunk) {
	eval(chunk.toString());
});
				

Networking interlude - RPC

What's really going on?

What we're doing is really a bunch of RPC (remote procedure call)

The idea behind RPC is

  1. I do something on my computer
  2. A function on your server gets called
  3. You send me the results
(this is what's going on with php web services, everyone's enjoying hw9 right?)

This goes both ways too! Your server can call functions in my code since we have a persistent connection

Networking interlude - IP Problem

Why can I do this on webster but not on my computer at home?

NAT (Network Address Translation)

LAN diagram

Networking interlude - IP Problem

NAT (Network Address Translation)

Why do we do NAT'ing?

  • Save $$$
  • IPs (IPv4) are only 32-bits long - why is this a problem?

Networking interlude - IP Problem

How do I solve this problem?

  1. You don't

Kind of...

  1. Port forwarding (punch a hole in the router)
  2. Actually buy a unique ip

Security

What we've written is about as secure as a shoebox

The average person who doesn't care can't easily mess it up, but the first person to give it a small try will break it down

What are some vulnerabilities we have?

How could we do it better?