How to-node-core

60
How To Node Core NodeConf 2013

description

 

Transcript of How to-node-core

Page 1: How to-node-core

How To Node CoreNodeConf 2013

Page 2: How to-node-core

Pre-test: Raise your hand if…

•You do not have Node checked out on your computer

•You do not have Node built

•Node isn't working on your computer right now

•If so, `make -j4` now.

Page 3: How to-node-core

Who should contribute?

•Super star C++ haxx0rz?

•Low-level OS people?

•Close to metal?

•JavaScript ninja rockstar gurus?

Page 4: How to-node-core

NO!* You!

•You will hit bugs.

•You are a Node programmer.

•You can fix those bugs.

•You can achieve immortality in code.

*well, yes, those people. but ALSO you.

Page 5: How to-node-core

OSS

•Open Source Software

•Ownership of Software Stack

•If you use it, know it.

•If it's busted, fix it.

•Be involved.

Page 6: How to-node-core

TODO

•Writing good tests

•Structure (brief 50¢ tour)

•Let's Feature!

•Homework

Page 7: How to-node-core

tests

Page 8: How to-node-core

tests

•Node's tests are simple JavaScript programs that either throw, or don't.

•Not throwing = test pass

•Tests (mostly) go intests/simple/test-*.js

•No test = Rejected pull req

Page 9: How to-node-core

Running tests•`make test` or `vcbuild test`Runs simple tests, and jslint

•`make test-all``vcbuild test-all`Runs ALL the tests,even slow pummel tests

•./node test/simple/test-x.jsTo run a single test

Page 10: How to-node-core

Bad Test Names

•test-GH4313.js

•test-rfc3523.js

•test-breaks-on-linux.js

•test-thisisnotveryreadable.js

Page 11: How to-node-core

Good Test Names

•test-https-keepalive.js

•test-url-double-encode.js

•test-tls-large-request.js

•test-http-simple.js

•test-fs-writefile.js

Page 12: How to-node-core

Good Test Output

•Should be almost nothing.

•I personally like doing `console.log('ok')` at the very end, just so I know it ran fully.

•More than that is too much!

Page 13: How to-node-core

Good Test Speed

•Each test should take less than 100ms to run in the normal case.

•Rule of thumb:If you can read the name while `make test` runs, it's taking too long.

Page 14: How to-node-core

Good Test Code

•Short and simple

•Entirely self-contained

•Do not use tests/fixtures/ unless ABSOLUTELY necessary

•assert something in process.on('exit')

Page 15: How to-node-core

Always include the test header

//

// copyright mumbo jumbo

//

var common = require('../common');

var assert = require('assert');

Page 16: How to-node-core

Be parallel-friendly

•Servers listen on common.PORT

•Hard-coded ports don't play nicely with CI servers!

Page 17: How to-node-core

Exit Gracefully

•Close servers, unref timers

•Don't process.exit() explicitly.

•Exiting early can hide serious problems!

Page 18: How to-node-core

Be Relevant!

•Tests FAIL without your patch

•Tests PASS with your patch

•otherwise… what's the point?

Page 19: How to-node-core

Be Relevant!

•Test the failure cases as well as success cases.

•If something SHOULD fail, make sure it DOES fail.

Page 20: How to-node-core

questions?

Page 21: How to-node-core

Exercise

•Write test-net-hello-world.js

•Assert that require('net').hello() returns the string 'world'

•Verify that test fails

Page 22: How to-node-core

structure

Page 23: How to-node-core

src/*.{cc,h}

•The C++ code, a lot like .node addons.

•This code is unforgiving. assert(0) on any weird stuff!

Page 24: How to-node-core

process.binding

•Private API function for loading binding layer

•NODE_MODULE(node_foo, fn)results in:process.binding('foo')

Page 25: How to-node-core

lib/*.js

•JavaScript Node modules that are bundled with the node binary.

•"Native modules"

•Public API

•Just like normal Node modules

Page 26: How to-node-core

lib/*.js

•Wrap process.binding() APIs in a friendly JavaScript coating

•Validate input

•Throw on bad args, emit('error') or cb(er) for run-time failures

Page 27: How to-node-core

src/node.js

•Boot-straps the module system

•Figures out what main module to load

•Sets up process object

Page 28: How to-node-core

questions?

Page 29: How to-node-core

tcp

Page 30: How to-node-core

tcp

•src/tcp_wrap.cc:process.binding('tcp_wrap')

•lib/net.js: require('net')

•Today, that's as deep as we'll go.

•(We'll cover pipes and ttys in the level 2 class.)

Page 31: How to-node-core

net.Socket

•JavaScript abstraction of a TCP connection

•Duplex stream, with methods to do TCP type stuff

•Defined in lib/net.js

Page 32: How to-node-core

net.Server

•TCP server abstraction

•connection cb => gets a connected net.Socket object

•call listen(cb) to bind to a port/IP or fs socket path

•listen cb => actually listening (async)

Page 33: How to-node-core

net.connect()

•TCP client abstraction

•Returns a net.Socket object

•Not yet connected, but in the process of connecting

Page 34: How to-node-core

Exercise

•Add a "hello" method to process.binding('tcp_wrap')

•Export this method from require('net')

•Verify test passingtest-net-hello-world

Page 35: How to-node-core

questions?

Page 36: How to-node-core

http

Page 37: How to-node-core

How HTTP Works

•TCP server waits for connections

•TCP client connects, writes HTTP formatted request

•Server replies with HTTP formatted response

Page 38: How to-node-core

http_parser

•process.binding('http_parser')

•C utility for parsing HTTP

•interprets a stream of bytes as HTTP data, headers, chunked encoding, etc.

Page 39: How to-node-core

http.Server

•Inherits from net.Server

•'request' event gets request/response objects

•Pipes incoming Sockets through http_parser

•wraps up response headers/body/trailers for transport

Page 40: How to-node-core

http.request

•HTTP client abstraction

•Returns a request object, emits 'response' with a response

Page 41: How to-node-core

HTTP Client

•Request = ClientRequest

•Response = IncomingMessage

Page 42: How to-node-core

HTTP Server

•Request = IncomingMessage

•Response = ServerResponse

Page 43: How to-node-core

IncomingMessage

•Incoming messages are messages that the OTHER party is sending to YOU.(They're COMING IN.)

•Server Request object

•Client Response object

Page 44: How to-node-core

Outgoing Message

•Outgoing messages are messages that the YOU are sending to the OTHER party.(They're GOING OUT.)

•ServerResponse

•ClientRequest

Page 45: How to-node-core

questions?

Page 46: How to-node-core

let's feature!

Page 47: How to-node-core

Protips:

•Say hi to your neighbors.

•This is your team.

•Write the test first(or don’t, it’s not like this will land in core anyway ;)

Page 48: How to-node-core

.json(obj)

•Client:request.json({some:'obj'})

•Server:response.json({some:'obj'})

Page 49: How to-node-core

.json(obj)

•JSON.stringify the object

•Set headers:content-type:application/jsoncontent-length:<number>

•Call this.end()

•emit('error') if can't be JSON encoded

Page 50: How to-node-core

Extra Credit

•Take optional arguments for JSON.stringify pretty-printing

•.json(obj, [indent])

Page 51: How to-node-core

pop quiz

Page 52: How to-node-core

What prototype?

A) IncomingMessage

B) OutgoingMessage

C) ServerResponse

D) ClientRequest

E) None of the above

Page 53: How to-node-core

What prototype?

A) IncomingMessage

B) OutgoingMessage

C) ServerResponse

D) ClientRequest

E) None of the above

Page 54: How to-node-core

ok for realsdo it now

•We'll give you about 15 minutes to add this function

•Raise your hand if you get stuck.

•Protip: lib/_http_outgoing.js

Page 55: How to-node-core

.json(obj)• JSON.stringify the object

• Set headers:content-type:application/jsoncontent-length:<number>

• Call this.end()

• emit('error') if can't be JSON encoded

• Add optional arguments for JSON.stringify pretty-printing

• .json(obj, [indent])

Page 56: How to-node-core

homework

Page 57: How to-node-core

Homework Assignment #1

•Required reading: CONTRIBUTING.md

•Sign the CLAhttp://nodejs.org/cla.html

•Write good commit messages

•Be friendly on GitHub

Page 58: How to-node-core

Of course…

•It's silly to add a response.json() method to node-core

•This is an example only, it clearly belongs in userland

•"Real" bug fixes are usually much trickier

Page 59: How to-node-core

Homework Assignment #2

•Go tohttps://github.com/joyent/node/issues

•Find a bug

•Write a test to confirm it

•Send a patch to fix it

Page 60: How to-node-core

Homework Assignment #3

•Write this as a userland module, with a package.json

•(optional)