SlideShare ist ein Scribd-Unternehmen logo
1 von 54
Downloaden Sie, um offline zu lesen
BRINGING CHAOS TO ORDER
IN YOUR NODE.JS APP
DAN JENKINS
NIMBLE APE
https://nimblea.pe
WHO AM I?
WHO AM I?
DAN JENKINS
NODE.JS DEVELOPER / ARCHITECT
GOOGLE DEVELOPER EXPERT IN WEBRTC
LOVE LEGO & TECHNIC
GENERAL GEEK
FOUNDER OF NIMBLE APE LTD
❤ OPEN SOURCE
3
4
/danjenkins
5
@dan_jenkins
6
nimblea.pe | @nimbleapeltd
NODE.JS & I
STARTED WITH NODE.JS WHEN IT WAS A BABY - 0.4
BUILT MANY, MANY MICROSERVICES AND REST APIS WITH NODE
SPENTTHE PASTYEAR WORKING ON A PLATFORM CALLED RESPOKE - WEBRTC
8
FUNNY STORY…
9
H E L L O
my name is
Dan
G O O G L E I / O
WARNING…
SOME BAD PRACTICES ARE USED IN SOME OF THE EXAMPLES.
I KNOW YOU SHOULDN’T DO THESE THINGS.
BUT, ITS THE EASIEST WAYTO SHOW THE POINT IN THE SMALL CONFINES OF A
SLIDE DECK.
I PROMISE I KNOW WHAT I’M DOING…
10
NODE.JS APPS CAN GET
IN A REAL MESS…
WHO’S WRITTEN CODE LIKE THIS ?
12
createAdministrator: function (req, res) {
Administrators.create({some: data}, function cb(error, admin) {
if (error) {
console.error('Error creating Admin');
res.send(500)
return;
}
res.admin = admin;
doAnotherCall(res, function cb2(err2){
res.send(200, res.admin);
});
});
}
OR LIKE THIS
13
var http = require('http');
var uuid = require('uuid');
function respond(res) {
console.log('Got request with ID', res.id);
res.end('Response');
}
var server = http.createServer(function handleRequest(req, res){
res.id = uuid();
respond(res)
});
server.listen(8080, function(){
console.log("Server listening on: http://localhost:8080");
});
OR LIKE THIS
14
var http = require('http');
var uuid = require('uuid');
function doSomething(res, id) {
console.log('Do something with request with ID', id);
respond(res, id);
}
function respond(res, id) {
console.log('Responding to request with ID', id);
res.end('Response');
}
var server = http.createServer(function handleRequest(req, res){
var id = uuid();
doSomething(res, id);
});
server.listen(8080, function(){
console.log("Server listening on: http://localhost:8080");
});
EVERYONE HAS AT SOME POINT…
DON’T TRY AND DENY IT…
WHAT PROBLEM ARE WE
TRYING TO SOLVE?
PASSING DATA AROUND TO OTHER
FUNCTIONS FOR USE LATER
19
req.id = ‘foo’;
console.log(req.id);
FOR EXAMPLE, SERVICE
BASED LOGGING
21
ASSIGN A REQUEST ID HERE
AND HAVE IT SENT ON TO ALL
OTHER SERVICES
WHICH MEANS ALLYOUR LOGS FROM ALLYOUR SERVICES ALLTIE TOGETHER
WHAT’S THE ANSWER?
23
OBVIOUSLY…
CLS
NODE-CONTINUATION-LOCAL-STORAGE
USERLAND MODULE
UTILISES ASYNC-LISTENER
24
/othiym23/node-continuation-local-storage
/ continuation-local-storage
/package/async-listener
IT HAS NOTHING TO DO WITH
LOCAL-STORAGE IN THE BROWSER
“Continuation-local storage
works like thread-local storage in
threaded programming, but is
based on chains of Node-style
callbacks instead of threads.”
26
IT MEANS YOU CAN STOP DOING THIS…
27
var http = require('http');
var uuid = require('uuid');
function respond(res) {
console.log('Got request with ID', res.id);
res.end('Response');
}
var server = http.createServer(function handleRequest(req, res){
res.id = uuid();
respond(res);
});
server.listen(8080, function(){
console.log("Server listening on: http://localhost:8080");
});
AND START DOING THIS…
28
var http = require('http');
var uuid = require('uuid');
var createNamespace = require('continuation-local-storage').createNamespace;
var namespace = createNamespace('request-life');
function respond(res) {
console.log('Got request with ID', namespace.get('requestId'));
res.end('Response');
}
var server = http.createServer(function handleRequest(req, res){
namespace.set('requestId', uuid());
respond(res);
});
server.listen(8080, function(){
console.log('Server listening on: http://localhost:8080');
});
IT’S MORE IMPRESSIVE THAN IT
LOOKS IN THIS SIMPLE EXAMPLE
I PROMISE
THAT’S AWESOME!
WHAT DO I NEED TO DO?
1
31
var createNamespace = require('continuation-local-storage').createNamespace;
var session = createNamespace('my session');
var db = require('./lib/db.js');
function start(options, next) {
db.fetchUserById(options.id, function (error, user) {
if (error) return next(error);
session.set('user', user);
next();
});
}
2
32
var getNamespace = require('continuation-local-storage').getNamespace;
var session = getNamespace('my session');
var render = require('./lib/render.js')
function finish(response) {
var user = session.get('user');
render({user: user}).pipe(response);
}
SO IT JUST WORKS?
I DON’T HAVE TO DO ANYTHING FUNKY?
KINDA…
BEWARE NATIVE INTERACTIONS
ANYTHING THAT TOUCHES NATIVE
CODE; YOU’LL NEED TO SHIM
SHIM ALL THE THINGS
/package/shimmer
/othiym23/shimmer
39
var http = require('http');
var shimmer = require('shimmer');
shimmer.wrap(http, 'request', function (original) {
return function () {
console.log("Starting request!");
var returned = original.apply(this, arguments)
console.log("Done setting up request -- OH YEAH!");
return returned;
};
});
OR USE AN EXISTING ONE
41
require('cls-mysql')(ns);
require('cls-redis')(ns);
require('cls-q')(ns);
require('cls-bluebird')(ns);
require('cls-es6-promise')(ns);
require('cls-bcrypt')(ns);
42
YOU NEED TO BE WARY!
44
// Copyright (c) 2015. David M. Lee, II
'use strict';
var shimmer = require('shimmer');
// require mysql first; otherwise you can get some bizarre
// "object is not a function" errors if cls-mysql is loaded first.
require('mysql');
var Protocol = require('mysql/lib/protocol/Protocol');
var Pool = require('mysql/lib/Pool');
module.exports = function(ns) {
shimmer.wrap(Protocol.prototype, '_enqueue', function(enqueue) {
return function(sequence) {
sequence._callback = ns.bind(sequence._callback);
return enqueue.call(this, sequence);
};
});
shimmer.wrap(Pool.prototype, 'getConnection', function(getConnection) {
return function(cb) {
return getConnection.call(this, ns.bind(cb));
};
});
};
YOU HAVE TO KNOW WHAT
TO SHIM!
AND BEWARE THE INTERNALS
OF THE MODULE CHANGING
AN INTERNAL
MODULE CHANGE !== A PUBLIC API
CHANGE
WHICH MEANS YOU COULD BE
HIT BY A MINOR VERSION BUMP
WHICH COULD RESULT IN A
FAILING APPLICATION
IT ALSO HAS A PERFORMANCE COST
THE MORE YOU HAVE,THE MORE YOU’LL IMPACTYOUR PERFORMANCE
COST IS AGAINST A NAMESPACE, NOT DATA IN THE NAMESPACE
KEEP THINGS TO A MINIMUM
50
SO WHY USE IT?
IF YOU’RE DOING IT RIGHT…
YOU SHOULD BE USING SHRINKWRAP ANYWAY
(OR ANOTHER TECHNIQUE TO LOCK DEPENDENCIES)
SO BREAKAGES SHOULD BE LIMITED TO YOUR DEVELOPMENT ENVIRONMENT
WHICH MEANS MOAR BONUS FOR LITTLE TO NO RISK
VERY LOW PERFORMANCE COST
52
THANKS!
DAN JENKINS
@dan_jenkins
MOST EXAMPLES WERE TAKEN FROM
https://github.com/othiym23/node-continuation-local-storage
https://github.com/othiym23/shimmer
https://github.com/building5/cls-mysql
54

Weitere ähnliche Inhalte

Was ist angesagt?

Was ist angesagt? (20)

Open Canary - novahackers
Open Canary - novahackersOpen Canary - novahackers
Open Canary - novahackers
 
HTTP/3 is next generation HTTP
HTTP/3 is next generation HTTPHTTP/3 is next generation HTTP
HTTP/3 is next generation HTTP
 
Landing code in curl
Landing code in curlLanding code in curl
Landing code in curl
 
Getting started with libcurl
Getting started with libcurlGetting started with libcurl
Getting started with libcurl
 
Presentation at ClueCon 2019 - Chicago, IL, USA 🇺🇸
Presentation at ClueCon 2019 - Chicago, IL, USA 🇺🇸Presentation at ClueCon 2019 - Chicago, IL, USA 🇺🇸
Presentation at ClueCon 2019 - Chicago, IL, USA 🇺🇸
 
HTTP/3 an early overview
HTTP/3 an early overviewHTTP/3 an early overview
HTTP/3 an early overview
 
HTTP/2 and SAP Fiori
HTTP/2 and SAP FioriHTTP/2 and SAP Fiori
HTTP/2 and SAP Fiori
 
Why async matters
Why async mattersWhy async matters
Why async matters
 
Presentation at JSConf.be 2019 - Alessandro Polidori
Presentation at JSConf.be 2019 - Alessandro PolidoriPresentation at JSConf.be 2019 - Alessandro Polidori
Presentation at JSConf.be 2019 - Alessandro Polidori
 
Modern Perl for the Unfrozen Paleolithic Perl Programmer
Modern Perl for the Unfrozen Paleolithic Perl ProgrammerModern Perl for the Unfrozen Paleolithic Perl Programmer
Modern Perl for the Unfrozen Paleolithic Perl Programmer
 
PyParis 2017 / Writing a C Python extension in 2017, Jean-Baptiste Aviat
PyParis 2017 / Writing a C Python extension in 2017, Jean-Baptiste Aviat PyParis 2017 / Writing a C Python extension in 2017, Jean-Baptiste Aviat
PyParis 2017 / Writing a C Python extension in 2017, Jean-Baptiste Aviat
 
Package manages and Puppet - PuppetConf 2015
Package manages and Puppet - PuppetConf 2015Package manages and Puppet - PuppetConf 2015
Package manages and Puppet - PuppetConf 2015
 
Puppet Camp LA 2/19/2015
Puppet Camp LA 2/19/2015Puppet Camp LA 2/19/2015
Puppet Camp LA 2/19/2015
 
SWIFT: Tango's Infrastructure For Real-Time Video Call Service
SWIFT: Tango's Infrastructure For Real-Time Video Call ServiceSWIFT: Tango's Infrastructure For Real-Time Video Call Service
SWIFT: Tango's Infrastructure For Real-Time Video Call Service
 
Puppet Camp Atlanta 2014: DEV Toolsets for Ops (Beginner) -
Puppet Camp Atlanta 2014: DEV Toolsets for Ops (Beginner) - Puppet Camp Atlanta 2014: DEV Toolsets for Ops (Beginner) -
Puppet Camp Atlanta 2014: DEV Toolsets for Ops (Beginner) -
 
Automate Yo' Self
Automate Yo' SelfAutomate Yo' Self
Automate Yo' Self
 
Debugging PHP with xDebug inside of Eclipse PDT 2.1
Debugging PHP with xDebug inside of Eclipse PDT 2.1Debugging PHP with xDebug inside of Eclipse PDT 2.1
Debugging PHP with xDebug inside of Eclipse PDT 2.1
 
DevOOPS: Attacks and Defenses for DevOps Toolchains
DevOOPS: Attacks and Defenses for DevOps ToolchainsDevOOPS: Attacks and Defenses for DevOps Toolchains
DevOOPS: Attacks and Defenses for DevOps Toolchains
 
HTTP/2 in Examples
HTTP/2 in ExamplesHTTP/2 in Examples
HTTP/2 in Examples
 
Chef Conf 2015: Package Management & Chef
Chef Conf 2015: Package Management & ChefChef Conf 2015: Package Management & Chef
Chef Conf 2015: Package Management & Chef
 

Ähnlich wie Bringing choas to order in your node.js app

Writing robust Node.js applications
Writing robust Node.js applicationsWriting robust Node.js applications
Writing robust Node.js applications
Tom Croucher
 
Socket applications
Socket applicationsSocket applications
Socket applications
João Moura
 

Ähnlich wie Bringing choas to order in your node.js app (20)

DevOps in PHP environment
DevOps in PHP environment DevOps in PHP environment
DevOps in PHP environment
 
Node.js: CAMTA Presentation
Node.js: CAMTA PresentationNode.js: CAMTA Presentation
Node.js: CAMTA Presentation
 
Fun with Ruby and Cocoa
Fun with Ruby and CocoaFun with Ruby and Cocoa
Fun with Ruby and Cocoa
 
HTML5 for the Silverlight Guy
HTML5 for the Silverlight GuyHTML5 for the Silverlight Guy
HTML5 for the Silverlight Guy
 
Original slides from Ryan Dahl's NodeJs intro talk
Original slides from Ryan Dahl's NodeJs intro talkOriginal slides from Ryan Dahl's NodeJs intro talk
Original slides from Ryan Dahl's NodeJs intro talk
 
Playing With Fire - An Introduction to Node.js
Playing With Fire - An Introduction to Node.jsPlaying With Fire - An Introduction to Node.js
Playing With Fire - An Introduction to Node.js
 
Intro To Node.js
Intro To Node.jsIntro To Node.js
Intro To Node.js
 
PSGI and Plack from first principles
PSGI and Plack from first principlesPSGI and Plack from first principles
PSGI and Plack from first principles
 
Who pulls the strings?
Who pulls the strings?Who pulls the strings?
Who pulls the strings?
 
Writing robust Node.js applications
Writing robust Node.js applicationsWriting robust Node.js applications
Writing robust Node.js applications
 
php[world] 2016 - You Don’t Need Node.js - Async Programming in PHP
php[world] 2016 - You Don’t Need Node.js - Async Programming in PHPphp[world] 2016 - You Don’t Need Node.js - Async Programming in PHP
php[world] 2016 - You Don’t Need Node.js - Async Programming in PHP
 
Questioning the status quo
Questioning the status quoQuestioning the status quo
Questioning the status quo
 
Zend con 2016 - Asynchronous Prorgamming in PHP
Zend con 2016 - Asynchronous Prorgamming in PHPZend con 2016 - Asynchronous Prorgamming in PHP
Zend con 2016 - Asynchronous Prorgamming in PHP
 
Getting Started with iBeacons (Designers of Things 2014)
Getting Started with iBeacons (Designers of Things 2014)Getting Started with iBeacons (Designers of Things 2014)
Getting Started with iBeacons (Designers of Things 2014)
 
Pentesting an unfriendly environment: bypassing (un)common defences and mate ...
Pentesting an unfriendly environment: bypassing (un)common defences and mate ...Pentesting an unfriendly environment: bypassing (un)common defences and mate ...
Pentesting an unfriendly environment: bypassing (un)common defences and mate ...
 
RubyEnRails2007 - Dr Nic Williams - Keynote
RubyEnRails2007 - Dr Nic Williams - KeynoteRubyEnRails2007 - Dr Nic Williams - Keynote
RubyEnRails2007 - Dr Nic Williams - Keynote
 
Introduction to NodeJS with LOLCats
Introduction to NodeJS with LOLCatsIntroduction to NodeJS with LOLCats
Introduction to NodeJS with LOLCats
 
Socket applications
Socket applicationsSocket applications
Socket applications
 
Fatc
FatcFatc
Fatc
 
Node Boot Camp
Node Boot CampNode Boot Camp
Node Boot Camp
 

Mehr von Dan Jenkins

Mehr von Dan Jenkins (20)

Yup... WebRTC Still Sucks
Yup... WebRTC Still SucksYup... WebRTC Still Sucks
Yup... WebRTC Still Sucks
 
Professional AV with WebRTC
Professional AV with WebRTCProfessional AV with WebRTC
Professional AV with WebRTC
 
SIMCON 3
SIMCON 3SIMCON 3
SIMCON 3
 
Getting started with WebRTC
Getting started with WebRTCGetting started with WebRTC
Getting started with WebRTC
 
JanusCon - Building Native Mobile Apps with WebRTC
JanusCon - Building Native Mobile Apps with WebRTCJanusCon - Building Native Mobile Apps with WebRTC
JanusCon - Building Native Mobile Apps with WebRTC
 
Getting physical with web bluetooth in the browser hackference
Getting physical with web bluetooth in the browser hackferenceGetting physical with web bluetooth in the browser hackference
Getting physical with web bluetooth in the browser hackference
 
Getting Physical with Web Bluetooth in the Browser Full Stack Toronto
Getting Physical with Web Bluetooth in the Browser Full Stack TorontoGetting Physical with Web Bluetooth in the Browser Full Stack Toronto
Getting Physical with Web Bluetooth in the Browser Full Stack Toronto
 
Getting physical with web bluetooth in the browser
Getting physical with web bluetooth in the browserGetting physical with web bluetooth in the browser
Getting physical with web bluetooth in the browser
 
Getting physical with web bluetooth in the browser
Getting physical with web bluetooth in the browserGetting physical with web bluetooth in the browser
Getting physical with web bluetooth in the browser
 
WebRTC Reborn SignalConf 2016
WebRTC Reborn SignalConf 2016WebRTC Reborn SignalConf 2016
WebRTC Reborn SignalConf 2016
 
Web technology is getting physical, join the journey
Web technology is getting physical, join the journeyWeb technology is getting physical, join the journey
Web technology is getting physical, join the journey
 
Building the Best Experience for Your Customers and Your Business
Building the Best Experience for Your Customers and Your BusinessBuilding the Best Experience for Your Customers and Your Business
Building the Best Experience for Your Customers and Your Business
 
WebRTC Reborn - Full Stack Toronto
WebRTC Reborn -  Full Stack TorontoWebRTC Reborn -  Full Stack Toronto
WebRTC Reborn - Full Stack Toronto
 
WebRTC Reborn - Cloud Expo / WebRTC Summit
WebRTC Reborn - Cloud Expo / WebRTC SummitWebRTC Reborn - Cloud Expo / WebRTC Summit
WebRTC Reborn - Cloud Expo / WebRTC Summit
 
WebRTC Reborn - Full Stack
WebRTC Reborn  - Full StackWebRTC Reborn  - Full Stack
WebRTC Reborn - Full Stack
 
Developing Yourself for Industry - University of Kent EDA MTD DA
Developing Yourself for Industry - University of Kent EDA MTD DADeveloping Yourself for Industry - University of Kent EDA MTD DA
Developing Yourself for Industry - University of Kent EDA MTD DA
 
Building 21st Century Contact Centre Applications
Building 21st Century Contact Centre ApplicationsBuilding 21st Century Contact Centre Applications
Building 21st Century Contact Centre Applications
 
WebRTC Reborn Hackference
WebRTC Reborn HackferenceWebRTC Reborn Hackference
WebRTC Reborn Hackference
 
WebRTC Reborn Over The Air
WebRTC Reborn Over The AirWebRTC Reborn Over The Air
WebRTC Reborn Over The Air
 
WebRTC Reborn London Node User Group
WebRTC Reborn London Node User GroupWebRTC Reborn London Node User Group
WebRTC Reborn London Node User Group
 

Kürzlich hochgeladen

CHEAP Call Girls in Pushp Vihar (-DELHI )🔝 9953056974🔝(=)/CALL GIRLS SERVICE
CHEAP Call Girls in Pushp Vihar (-DELHI )🔝 9953056974🔝(=)/CALL GIRLS SERVICECHEAP Call Girls in Pushp Vihar (-DELHI )🔝 9953056974🔝(=)/CALL GIRLS SERVICE
CHEAP Call Girls in Pushp Vihar (-DELHI )🔝 9953056974🔝(=)/CALL GIRLS SERVICE
9953056974 Low Rate Call Girls In Saket, Delhi NCR
 

Kürzlich hochgeladen (20)

%in tembisa+277-882-255-28 abortion pills for sale in tembisa
%in tembisa+277-882-255-28 abortion pills for sale in tembisa%in tembisa+277-882-255-28 abortion pills for sale in tembisa
%in tembisa+277-882-255-28 abortion pills for sale in tembisa
 
Pharm-D Biostatistics and Research methodology
Pharm-D Biostatistics and Research methodologyPharm-D Biostatistics and Research methodology
Pharm-D Biostatistics and Research methodology
 
AI & Machine Learning Presentation Template
AI & Machine Learning Presentation TemplateAI & Machine Learning Presentation Template
AI & Machine Learning Presentation Template
 
Learn the Fundamentals of XCUITest Framework_ A Beginner's Guide.pdf
Learn the Fundamentals of XCUITest Framework_ A Beginner's Guide.pdfLearn the Fundamentals of XCUITest Framework_ A Beginner's Guide.pdf
Learn the Fundamentals of XCUITest Framework_ A Beginner's Guide.pdf
 
The Top App Development Trends Shaping the Industry in 2024-25 .pdf
The Top App Development Trends Shaping the Industry in 2024-25 .pdfThe Top App Development Trends Shaping the Industry in 2024-25 .pdf
The Top App Development Trends Shaping the Industry in 2024-25 .pdf
 
Shapes for Sharing between Graph Data Spaces - and Epistemic Querying of RDF-...
Shapes for Sharing between Graph Data Spaces - and Epistemic Querying of RDF-...Shapes for Sharing between Graph Data Spaces - and Epistemic Querying of RDF-...
Shapes for Sharing between Graph Data Spaces - and Epistemic Querying of RDF-...
 
Optimizing AI for immediate response in Smart CCTV
Optimizing AI for immediate response in Smart CCTVOptimizing AI for immediate response in Smart CCTV
Optimizing AI for immediate response in Smart CCTV
 
Direct Style Effect Systems - The Print[A] Example - A Comprehension Aid
Direct Style Effect Systems -The Print[A] Example- A Comprehension AidDirect Style Effect Systems -The Print[A] Example- A Comprehension Aid
Direct Style Effect Systems - The Print[A] Example - A Comprehension Aid
 
%in Midrand+277-882-255-28 abortion pills for sale in midrand
%in Midrand+277-882-255-28 abortion pills for sale in midrand%in Midrand+277-882-255-28 abortion pills for sale in midrand
%in Midrand+277-882-255-28 abortion pills for sale in midrand
 
Unlocking the Future of AI Agents with Large Language Models
Unlocking the Future of AI Agents with Large Language ModelsUnlocking the Future of AI Agents with Large Language Models
Unlocking the Future of AI Agents with Large Language Models
 
Introducing Microsoft’s new Enterprise Work Management (EWM) Solution
Introducing Microsoft’s new Enterprise Work Management (EWM) SolutionIntroducing Microsoft’s new Enterprise Work Management (EWM) Solution
Introducing Microsoft’s new Enterprise Work Management (EWM) Solution
 
Software Quality Assurance Interview Questions
Software Quality Assurance Interview QuestionsSoftware Quality Assurance Interview Questions
Software Quality Assurance Interview Questions
 
Azure_Native_Qumulo_High_Performance_Compute_Benchmarks.pdf
Azure_Native_Qumulo_High_Performance_Compute_Benchmarks.pdfAzure_Native_Qumulo_High_Performance_Compute_Benchmarks.pdf
Azure_Native_Qumulo_High_Performance_Compute_Benchmarks.pdf
 
ManageIQ - Sprint 236 Review - Slide Deck
ManageIQ - Sprint 236 Review - Slide DeckManageIQ - Sprint 236 Review - Slide Deck
ManageIQ - Sprint 236 Review - Slide Deck
 
BUS PASS MANGEMENT SYSTEM USING PHP.pptx
BUS PASS MANGEMENT SYSTEM USING PHP.pptxBUS PASS MANGEMENT SYSTEM USING PHP.pptx
BUS PASS MANGEMENT SYSTEM USING PHP.pptx
 
%in Stilfontein+277-882-255-28 abortion pills for sale in Stilfontein
%in Stilfontein+277-882-255-28 abortion pills for sale in Stilfontein%in Stilfontein+277-882-255-28 abortion pills for sale in Stilfontein
%in Stilfontein+277-882-255-28 abortion pills for sale in Stilfontein
 
%in kaalfontein+277-882-255-28 abortion pills for sale in kaalfontein
%in kaalfontein+277-882-255-28 abortion pills for sale in kaalfontein%in kaalfontein+277-882-255-28 abortion pills for sale in kaalfontein
%in kaalfontein+277-882-255-28 abortion pills for sale in kaalfontein
 
The Real-World Challenges of Medical Device Cybersecurity- Mitigating Vulnera...
The Real-World Challenges of Medical Device Cybersecurity- Mitigating Vulnera...The Real-World Challenges of Medical Device Cybersecurity- Mitigating Vulnera...
The Real-World Challenges of Medical Device Cybersecurity- Mitigating Vulnera...
 
Define the academic and professional writing..pdf
Define the academic and professional writing..pdfDefine the academic and professional writing..pdf
Define the academic and professional writing..pdf
 
CHEAP Call Girls in Pushp Vihar (-DELHI )🔝 9953056974🔝(=)/CALL GIRLS SERVICE
CHEAP Call Girls in Pushp Vihar (-DELHI )🔝 9953056974🔝(=)/CALL GIRLS SERVICECHEAP Call Girls in Pushp Vihar (-DELHI )🔝 9953056974🔝(=)/CALL GIRLS SERVICE
CHEAP Call Girls in Pushp Vihar (-DELHI )🔝 9953056974🔝(=)/CALL GIRLS SERVICE
 

Bringing choas to order in your node.js app

  • 1. BRINGING CHAOS TO ORDER IN YOUR NODE.JS APP DAN JENKINS NIMBLE APE https://nimblea.pe
  • 3. WHO AM I? DAN JENKINS NODE.JS DEVELOPER / ARCHITECT GOOGLE DEVELOPER EXPERT IN WEBRTC LOVE LEGO & TECHNIC GENERAL GEEK FOUNDER OF NIMBLE APE LTD ❤ OPEN SOURCE 3
  • 7.
  • 8. NODE.JS & I STARTED WITH NODE.JS WHEN IT WAS A BABY - 0.4 BUILT MANY, MANY MICROSERVICES AND REST APIS WITH NODE SPENTTHE PASTYEAR WORKING ON A PLATFORM CALLED RESPOKE - WEBRTC 8
  • 9. FUNNY STORY… 9 H E L L O my name is Dan G O O G L E I / O
  • 10. WARNING… SOME BAD PRACTICES ARE USED IN SOME OF THE EXAMPLES. I KNOW YOU SHOULDN’T DO THESE THINGS. BUT, ITS THE EASIEST WAYTO SHOW THE POINT IN THE SMALL CONFINES OF A SLIDE DECK. I PROMISE I KNOW WHAT I’M DOING… 10
  • 11. NODE.JS APPS CAN GET IN A REAL MESS…
  • 12. WHO’S WRITTEN CODE LIKE THIS ? 12 createAdministrator: function (req, res) { Administrators.create({some: data}, function cb(error, admin) { if (error) { console.error('Error creating Admin'); res.send(500) return; } res.admin = admin; doAnotherCall(res, function cb2(err2){ res.send(200, res.admin); }); }); }
  • 13. OR LIKE THIS 13 var http = require('http'); var uuid = require('uuid'); function respond(res) { console.log('Got request with ID', res.id); res.end('Response'); } var server = http.createServer(function handleRequest(req, res){ res.id = uuid(); respond(res) }); server.listen(8080, function(){ console.log("Server listening on: http://localhost:8080"); });
  • 14. OR LIKE THIS 14 var http = require('http'); var uuid = require('uuid'); function doSomething(res, id) { console.log('Do something with request with ID', id); respond(res, id); } function respond(res, id) { console.log('Responding to request with ID', id); res.end('Response'); } var server = http.createServer(function handleRequest(req, res){ var id = uuid(); doSomething(res, id); }); server.listen(8080, function(){ console.log("Server listening on: http://localhost:8080"); });
  • 15. EVERYONE HAS AT SOME POINT…
  • 16. DON’T TRY AND DENY IT…
  • 17. WHAT PROBLEM ARE WE TRYING TO SOLVE?
  • 18. PASSING DATA AROUND TO OTHER FUNCTIONS FOR USE LATER
  • 21. 21 ASSIGN A REQUEST ID HERE AND HAVE IT SENT ON TO ALL OTHER SERVICES WHICH MEANS ALLYOUR LOGS FROM ALLYOUR SERVICES ALLTIE TOGETHER
  • 25. IT HAS NOTHING TO DO WITH LOCAL-STORAGE IN THE BROWSER
  • 26. “Continuation-local storage works like thread-local storage in threaded programming, but is based on chains of Node-style callbacks instead of threads.” 26
  • 27. IT MEANS YOU CAN STOP DOING THIS… 27 var http = require('http'); var uuid = require('uuid'); function respond(res) { console.log('Got request with ID', res.id); res.end('Response'); } var server = http.createServer(function handleRequest(req, res){ res.id = uuid(); respond(res); }); server.listen(8080, function(){ console.log("Server listening on: http://localhost:8080"); });
  • 28. AND START DOING THIS… 28 var http = require('http'); var uuid = require('uuid'); var createNamespace = require('continuation-local-storage').createNamespace; var namespace = createNamespace('request-life'); function respond(res) { console.log('Got request with ID', namespace.get('requestId')); res.end('Response'); } var server = http.createServer(function handleRequest(req, res){ namespace.set('requestId', uuid()); respond(res); }); server.listen(8080, function(){ console.log('Server listening on: http://localhost:8080'); });
  • 29. IT’S MORE IMPRESSIVE THAN IT LOOKS IN THIS SIMPLE EXAMPLE I PROMISE
  • 30. THAT’S AWESOME! WHAT DO I NEED TO DO?
  • 31. 1 31 var createNamespace = require('continuation-local-storage').createNamespace; var session = createNamespace('my session'); var db = require('./lib/db.js'); function start(options, next) { db.fetchUserById(options.id, function (error, user) { if (error) return next(error); session.set('user', user); next(); }); }
  • 32. 2 32 var getNamespace = require('continuation-local-storage').getNamespace; var session = getNamespace('my session'); var render = require('./lib/render.js') function finish(response) { var user = session.get('user'); render({user: user}).pipe(response); }
  • 33. SO IT JUST WORKS? I DON’T HAVE TO DO ANYTHING FUNKY?
  • 36. ANYTHING THAT TOUCHES NATIVE CODE; YOU’LL NEED TO SHIM
  • 37. SHIM ALL THE THINGS
  • 39. 39 var http = require('http'); var shimmer = require('shimmer'); shimmer.wrap(http, 'request', function (original) { return function () { console.log("Starting request!"); var returned = original.apply(this, arguments) console.log("Done setting up request -- OH YEAH!"); return returned; }; });
  • 40. OR USE AN EXISTING ONE
  • 42. 42
  • 43. YOU NEED TO BE WARY!
  • 44. 44 // Copyright (c) 2015. David M. Lee, II 'use strict'; var shimmer = require('shimmer'); // require mysql first; otherwise you can get some bizarre // "object is not a function" errors if cls-mysql is loaded first. require('mysql'); var Protocol = require('mysql/lib/protocol/Protocol'); var Pool = require('mysql/lib/Pool'); module.exports = function(ns) { shimmer.wrap(Protocol.prototype, '_enqueue', function(enqueue) { return function(sequence) { sequence._callback = ns.bind(sequence._callback); return enqueue.call(this, sequence); }; }); shimmer.wrap(Pool.prototype, 'getConnection', function(getConnection) { return function(cb) { return getConnection.call(this, ns.bind(cb)); }; }); };
  • 45. YOU HAVE TO KNOW WHAT TO SHIM!
  • 46. AND BEWARE THE INTERNALS OF THE MODULE CHANGING
  • 47. AN INTERNAL MODULE CHANGE !== A PUBLIC API CHANGE
  • 48. WHICH MEANS YOU COULD BE HIT BY A MINOR VERSION BUMP
  • 49. WHICH COULD RESULT IN A FAILING APPLICATION
  • 50. IT ALSO HAS A PERFORMANCE COST THE MORE YOU HAVE,THE MORE YOU’LL IMPACTYOUR PERFORMANCE COST IS AGAINST A NAMESPACE, NOT DATA IN THE NAMESPACE KEEP THINGS TO A MINIMUM 50
  • 51. SO WHY USE IT?
  • 52. IF YOU’RE DOING IT RIGHT… YOU SHOULD BE USING SHRINKWRAP ANYWAY (OR ANOTHER TECHNIQUE TO LOCK DEPENDENCIES) SO BREAKAGES SHOULD BE LIMITED TO YOUR DEVELOPMENT ENVIRONMENT WHICH MEANS MOAR BONUS FOR LITTLE TO NO RISK VERY LOW PERFORMANCE COST 52
  • 54. MOST EXAMPLES WERE TAKEN FROM https://github.com/othiym23/node-continuation-local-storage https://github.com/othiym23/shimmer https://github.com/building5/cls-mysql 54