SlideShare uma empresa Scribd logo
1 de 104
Real World Lessons on the Pain Points of
Node.js Applications
@Ben_Hall
Ben@BenHall.me.uk
OcelotUproar.com / Katacoda.com
@Ben_Hall / Blog.BenHall.me.uk
Tech Support > Tester > Developer >
Founder
Software Development Studio
WHOAMI?
Agenda
• Creating strong foundation
– Node v5, NPM, Security
• Error Handling
• Async/Promises
• Deploying / Scaling
• Performance
• Debugging
Provide overview of the main
point points we’ve
experienced and how we
resolved them
Strong Foundations
Upgrading from Node v0.10.38
to v5.3.0
https://github.com/nodejs/node/wiki/
API-changes-between-v0.10-and-v4
• The domain module has been scheduled for
deprecation, awaiting an alternative for those
who absolutely need domains.
• fs.exists() is now deprecated. It is suggested to
use either fs.access() or fs.stat(). Please read the
documentation carefully.
• Updated setImmediate() to process the full queue
each turn of the event loop, instead of one per
queue.
https://nodejs.org/en/blog/release/v5
.0.0/
• Breaking changes.
• When parsing HTTP, don't add duplicates of the
following headers
• HTTP methods and header names must now conform
to the RFC 2616 "token" rule
• zlib: Decompression now throws on truncated input
• buffer: Removed both 'raw' and 'raws' encoding types
from Buffer, these have been deprecated for a long
time.
Docker to test deployment
• Didn’t need to install anything on host
> docker run -it -v $(pwd):/src -p 3000 node:5
root@container:> npm install
root@container:> npm start
Default to Underscore.js ?
Fixing NPM
Lock down NPM dependencies
because no-one respects SemVer
AngularJs 1.2 => 1.3
"dependencies": {
"angular": "^1.2.16”
}
Angular 1.2 => 1.3
> angular.element(document)
[#document]
> angular.element(document)
TypeError: undefined is not a function
Lock Down Dependencies
Randomly breaking builds and
deployments will occur otherwise
$ npm shrinkwrap
Lock down dependencies to what’s
running locally
Hard code versions in
package.json
"dependencies": {
"angular": “1.2.23”
}
$ npm outdated
.npmrc
• https://docs.npmjs.com/misc/config
> cat .npmrc
save=true
save-exact=true
npm install -g
Replaced Glup, Grunt with Make
• Bugs, Bugs everywhere!
templates:
handlebars views/templates/*.hbs -f public/js/templates.js
> make templates
Security
Cover Your Bases
• Barry Dorrans, Troy Hunt, Niall Merrigan
• Troy Hunt and Barry Dorrans sessions
• A security testers toolkit - Niall Merrigan
• https://vimeo.com/131641274
• Going beyond OWASP - Barry Dorrans
• https://vimeo.com/131642364
Child Process Exec
child_process.exec(req.query.url, function (err, data) {
console.log(data);
});
https://localhost:49155/api/openUrlInDefaultBrowser?url=c:/windows/sy
stem32/calc.exe
Thanks TrendMicro Antivirus on Windows!
https://code.google.com/p/google-security-research/issues/detail?id=693
Cross-Site Request Forgery
var csrf = require('csurf');
var csrfProtection = csrf({ cookie: true });
var parseForm = bodyParser.urlencoded({ extended: false });
app.get('/form', csrfProtection, function(req, res) {
res.render('send', { csrfToken: req.csrfToken() });
});
app.post('/process', parseForm, csrfProtection, function(req, res) {
res.send('data is being processed');
});
https://blog.risingstack.com/node-js-security-checklist/
Rate Limiting
var ratelimit = require('koa-ratelimit');
var ipBasedRatelimit = ratelimit({
db: redis.createClient(),
duration: 60000,
max: 10,
id: function (context) {
return context.ip;
}
});
app.post('/login', ipBasedRatelimit, handleLogin);
https://blog.risingstack.com/node-js-security-checklist/
Security Audit NPM Packages
> npm install nsp
> nsp check
(+) 18 vulnerabilities found
https://nodesecurity.io/
• Root Path Disclosure (2x)
• Regular Expression Denial of Service (10x)
• Incorrect Handling of Non-Boolean Comparisons
During Minification
• Denial-of-Service Extended Event Loop Blocking
• Denial-of-Service Memory Exhaustion
• Symlink Arbitrary File Overwrite
• Remote Memory Disclosure (2x)
NPM Credentials Leaks
• https://github.com/ChALkeR/notes/blob/mast
er/Do-not-underestimate-credentials-
leaks.md
Create Strong Foundations
Error Handling
Wasn’t great from the start
Try {} Catch {}
Try {} Catch {}
Domains haven’t really worked
https://raw.githubusercontent.com/strongloop/zone/master/showcase/curl/curl-zone.js
Zones? No. Not really
Returning String as Error
Strongly typed errors
Generators + Error Handling
Async Flow Control
Promises
Promises… Promises… Never break
your promises.
Personally, I never make promises.
http://domenic.me/2012/10/14/youre-missing-the-point-of-promises/
Not part of the Node
Makes integration more difficult.
Makes swapping code in / out more
painful.
Callbacks
So good it’s got it’s own website
callbackhell.com
“The goal isn’t about removing
levels of indentation but rather
writing modular code that is easy to
reason about”
Strongloop Blog
http://strongloop.com/strongblog/node-js-callback-hell-promises-generators/
Loops + Async Callbacks
Loops + Async Callbacks
“You can't get into callback hell if
you don't go there.”
Isaac Schlueter
Generators are coming!
See Node >=0.11.2
http://blog.alexmaccaw.com/how-yield-will-transform-node
http://blog.alexmaccaw.com/how-yield-will-transform-node
DEPLOY!
Single Threaded
CPU Intensive?
Array Filtering / Sorting / Processing
Have more threads
Solved Problem?
var cluster = require('cluster');
var http = require('http');
var numCPUs = require('os').cpus().length;
if (cluster.isMaster) {
// Fork workers.
for (var i = 0; i < numCPUs; i++) {
cluster.fork();
}
cluster.on('exit', function(worker, code, signal) {
console.log('worker ' + worker.process.pid + ' died');
});
} else {
// Workers can share any TCP connection
// In this case it is an HTTP server
http.createServer(function(req, res) {
res.writeHead(200);
res.end("hello worldn");
}).listen(8000);
}
> NODE_DEBUG=cluster node server.js
23521,Master Worker 23524 online
23521,Master Worker 23526 online
23521,Master Worker 23523 online
23521,Master Worker 23528 online
Deploying with Docker
Container
https://www.docker.com/whatisdocker/
Container
Deploying Node App via Docker
> cat Dockerfile
FROM node:5-onbuild
EXPOSE 3000
> docker build –t my-node-app .
> docker run –p 3000:3000 my-node-app
59,040
environments/day/server
112,320
environments/day/server
> docker run -d 
-p 80:80 
-v /var/run/docker.sock:/tmp/docker.sock:ro 
jwilder/nginx-proxy
> docker run --name web 
-e VIRTUAL_HOST=www.katacoda.com
my-node-app
Load Balancer
Nginx Proxy
Node Node
Node Node
Node Node
Nginx Proxy
Node Node
Node Node
Node Node
Nginx Proxy
Node Node
Node Node
Node Node
Health Endpoints
router.get('/_specialfunctions/_check', function(req, res) {
async.parallel([
check_docker,
check_starter,
check_redis,
check_pg
], function(err, results) {
if(err) {
console.log("Health check failed", err);
res.status(500);
return res.json({healthy: false, details: err});
}
res.json({healthy: true});
})
});
var check_docker = function(cb) {
docker.ping(function(err) { handle_error('docker', err, cb);});
};
var check_redis = function(cb) {
redis.status(function(err, connected) {
if(err === null && connected === "ready") {
cb();
} else {
handle_error('redis', {msg: 'Not Connected', err: err}, cb);
}
})
};
var check_pg = function(cb) {
pg.status(function(err) { handle_error('postgres', err, cb);});
};
Careful!
socket.io and global state
Sticky Sessions
Compiled Nginx + OSS Modules
Global State as a Service
Microservices FTW!!
Code Performance Still Matters
Performance
var Ocelite = require('ocelite');
var db = new Ocelite();
db.init('data.db', ['user'], function() {
db.save('user', {name: 'Barbara Fusinska', twitter: 'basiafusinska'}, ['twitter'],
function() {
db.get('user', 'twitter', 'basiafusinska', function(err, obj) {
console.log(obj);
});
});
});
> npm install v8-profiler
const profiler = require('v8-profiler')
const fs = require('fs')
var profilerRunning = false
function toggleProfiling () {
if (profilerRunning) {
const profile = profiler.stopProfiling()
console.log('stopped profiling')
profile.export()
.pipe(fs.createWriteStream('./myapp-'+Date.now()+'.cpuprofile'))
.once('error', profiler.deleteAllProfiles)
.once('finish', profiler.deleteAllProfiles)
profilerRunning = false
return
}
profiler.startProfiling()
profilerRunning = true
console.log('started profiling')
}
process.on('SIGUSR2', toggleProfiling)
> kill -SIGUSR2 <pid>
JetBrains WebStorm
Debugging
require(‘debug’);
Webstorm
VS Code
Summary
• Update to Node.js v5
• Start using ES6
• Security
• Manage your errors
• Forgot making promises
• Scale using Docker
Thank you!
@Ben_Hall
Ben@BenHall.me.uk
Blog.BenHall.me.uk
www.Katacoda.com
www.OcelotUproar.com

Mais conteúdo relacionado

Mais procurados

Mais procurados (20)

Real World Lessons on the Pain Points of Node.JS Application
Real World Lessons on the Pain Points of Node.JS ApplicationReal World Lessons on the Pain Points of Node.JS Application
Real World Lessons on the Pain Points of Node.JS Application
 
Deploying applications to Windows Server 2016 and Windows Containers
Deploying applications to Windows Server 2016 and Windows ContainersDeploying applications to Windows Server 2016 and Windows Containers
Deploying applications to Windows Server 2016 and Windows Containers
 
파이썬 개발환경 구성하기의 끝판왕 - Docker Compose
파이썬 개발환경 구성하기의 끝판왕 - Docker Compose파이썬 개발환경 구성하기의 끝판왕 - Docker Compose
파이썬 개발환경 구성하기의 끝판왕 - Docker Compose
 
Running High Performance and Fault Tolerant Elasticsearch Clusters on Docker
Running High Performance and Fault Tolerant Elasticsearch Clusters on DockerRunning High Performance and Fault Tolerant Elasticsearch Clusters on Docker
Running High Performance and Fault Tolerant Elasticsearch Clusters on Docker
 
Docker Runtime Security
Docker Runtime SecurityDocker Runtime Security
Docker Runtime Security
 
2017-03-11 02 Денис Нелюбин. Docker & Ansible - лучшие друзья DevOps
2017-03-11 02 Денис Нелюбин. Docker & Ansible - лучшие друзья DevOps2017-03-11 02 Денис Нелюбин. Docker & Ansible - лучшие друзья DevOps
2017-03-11 02 Денис Нелюбин. Docker & Ansible - лучшие друзья DevOps
 
Docker remote-api
Docker remote-apiDocker remote-api
Docker remote-api
 
Scaling Next-Generation Internet TV on AWS With Docker, Packer, and Chef
Scaling Next-Generation Internet TV on AWS With Docker, Packer, and ChefScaling Next-Generation Internet TV on AWS With Docker, Packer, and Chef
Scaling Next-Generation Internet TV on AWS With Docker, Packer, and Chef
 
kubernetes practice
kubernetes practicekubernetes practice
kubernetes practice
 
Docker orchestration v4
Docker orchestration v4Docker orchestration v4
Docker orchestration v4
 
Docker Security in Production Overview
Docker Security in Production OverviewDocker Security in Production Overview
Docker Security in Production Overview
 
Vagrant for real (codemotion rome 2016)
Vagrant for real (codemotion rome 2016)Vagrant for real (codemotion rome 2016)
Vagrant for real (codemotion rome 2016)
 
Docker, c'est bonheur !
Docker, c'est bonheur !Docker, c'est bonheur !
Docker, c'est bonheur !
 
Wordpress y Docker, de desarrollo a produccion
Wordpress y Docker, de desarrollo a produccionWordpress y Docker, de desarrollo a produccion
Wordpress y Docker, de desarrollo a produccion
 
Docker command
Docker commandDocker command
Docker command
 
手把手帶你學Docker 03042017
手把手帶你學Docker 03042017手把手帶你學Docker 03042017
手把手帶你學Docker 03042017
 
Amazon EC2 Container Service in Action
Amazon EC2 Container Service in ActionAmazon EC2 Container Service in Action
Amazon EC2 Container Service in Action
 
Docker security
Docker securityDocker security
Docker security
 
Continuous Security
Continuous SecurityContinuous Security
Continuous Security
 
Docker practice
Docker practiceDocker practice
Docker practice
 

Semelhante a Real World Lessons on the Pain Points of Node.js Applications

Writing robust Node.js applications
Writing robust Node.js applicationsWriting robust Node.js applications
Writing robust Node.js applications
Tom Croucher
 
Automating Software Development Life Cycle - A DevOps Approach
Automating Software Development Life Cycle - A DevOps ApproachAutomating Software Development Life Cycle - A DevOps Approach
Automating Software Development Life Cycle - A DevOps Approach
Akshaya Mahapatra
 
Creating Scalable JVM/Java Apps on Heroku
Creating Scalable JVM/Java Apps on HerokuCreating Scalable JVM/Java Apps on Heroku
Creating Scalable JVM/Java Apps on Heroku
Joe Kutner
 
Kraken
KrakenKraken
Kraken
PayPal
 

Semelhante a Real World Lessons on the Pain Points of Node.js Applications (20)

Writing robust Node.js applications
Writing robust Node.js applicationsWriting robust Node.js applications
Writing robust Node.js applications
 
introduction to node.js
introduction to node.jsintroduction to node.js
introduction to node.js
 
Kraken Front-Trends
Kraken Front-TrendsKraken Front-Trends
Kraken Front-Trends
 
OWASP ZAP Workshop for QA Testers
OWASP ZAP Workshop for QA TestersOWASP ZAP Workshop for QA Testers
OWASP ZAP Workshop for QA Testers
 
Scaling Docker Containers using Kubernetes and Azure Container Service
Scaling Docker Containers using Kubernetes and Azure Container ServiceScaling Docker Containers using Kubernetes and Azure Container Service
Scaling Docker Containers using Kubernetes and Azure Container Service
 
Building and Scaling Node.js Applications
Building and Scaling Node.js ApplicationsBuilding and Scaling Node.js Applications
Building and Scaling Node.js Applications
 
Node azure
Node azureNode azure
Node azure
 
Solving anything in VCL
Solving anything in VCLSolving anything in VCL
Solving anything in VCL
 
Next Generation DevOps in Drupal: DrupalCamp London 2014
Next Generation DevOps in Drupal: DrupalCamp London 2014Next Generation DevOps in Drupal: DrupalCamp London 2014
Next Generation DevOps in Drupal: DrupalCamp London 2014
 
soft-shake.ch - Hands on Node.js
soft-shake.ch - Hands on Node.jssoft-shake.ch - Hands on Node.js
soft-shake.ch - Hands on Node.js
 
How to create your own hack environment
How to create your own hack environmentHow to create your own hack environment
How to create your own hack environment
 
Automating Software Development Life Cycle - A DevOps Approach
Automating Software Development Life Cycle - A DevOps ApproachAutomating Software Development Life Cycle - A DevOps Approach
Automating Software Development Life Cycle - A DevOps Approach
 
Creating Scalable JVM/Java Apps on Heroku
Creating Scalable JVM/Java Apps on HerokuCreating Scalable JVM/Java Apps on Heroku
Creating Scalable JVM/Java Apps on Heroku
 
Kubernetes Navigation Stories – DevOpsStage 2019, Kyiv
Kubernetes Navigation Stories – DevOpsStage 2019, KyivKubernetes Navigation Stories – DevOpsStage 2019, Kyiv
Kubernetes Navigation Stories – DevOpsStage 2019, Kyiv
 
Altitude San Francisco 2018: Testing with Fastly Workshop
Altitude San Francisco 2018: Testing with Fastly WorkshopAltitude San Francisco 2018: Testing with Fastly Workshop
Altitude San Francisco 2018: Testing with Fastly Workshop
 
J1 2015 "Debugging Java Apps in Containers: No Heavy Welding Gear Required"
J1 2015 "Debugging Java Apps in Containers: No Heavy Welding Gear Required"J1 2015 "Debugging Java Apps in Containers: No Heavy Welding Gear Required"
J1 2015 "Debugging Java Apps in Containers: No Heavy Welding Gear Required"
 
Kraken
KrakenKraken
Kraken
 
NodeJS for Beginner
NodeJS for BeginnerNodeJS for Beginner
NodeJS for Beginner
 
Docker & ECS: Secure Nearline Execution
Docker & ECS: Secure Nearline ExecutionDocker & ECS: Secure Nearline Execution
Docker & ECS: Secure Nearline Execution
 
Andrey Adamovich and Luciano Fiandesio - Groovy dev ops in the cloud
Andrey Adamovich and Luciano Fiandesio - Groovy dev ops in the cloudAndrey Adamovich and Luciano Fiandesio - Groovy dev ops in the cloud
Andrey Adamovich and Luciano Fiandesio - Groovy dev ops in the cloud
 

Mais de Ben Hall

Mais de Ben Hall (19)

The Art Of Documentation - NDC Porto 2022
The Art Of Documentation - NDC Porto 2022The Art Of Documentation - NDC Porto 2022
The Art Of Documentation - NDC Porto 2022
 
The Art Of Documentation for Open Source Projects
The Art Of Documentation for Open Source ProjectsThe Art Of Documentation for Open Source Projects
The Art Of Documentation for Open Source Projects
 
Three Years of Lessons Running Potentially Malicious Code Inside Containers
Three Years of Lessons Running Potentially Malicious Code Inside ContainersThree Years of Lessons Running Potentially Malicious Code Inside Containers
Three Years of Lessons Running Potentially Malicious Code Inside Containers
 
Containers without docker
Containers without dockerContainers without docker
Containers without docker
 
Deploying windows containers with kubernetes
Deploying windows containers with kubernetesDeploying windows containers with kubernetes
Deploying windows containers with kubernetes
 
The Art of Documentation and Readme.md for Open Source Projects
The Art of Documentation and Readme.md for Open Source ProjectsThe Art of Documentation and Readme.md for Open Source Projects
The Art of Documentation and Readme.md for Open Source Projects
 
How Secure Are Docker Containers?
How Secure Are Docker Containers?How Secure Are Docker Containers?
How Secure Are Docker Containers?
 
The Challenges of Becoming Cloud Native
The Challenges of Becoming Cloud NativeThe Challenges of Becoming Cloud Native
The Challenges of Becoming Cloud Native
 
The art of documentation and readme.md
The art of documentation and readme.mdThe art of documentation and readme.md
The art of documentation and readme.md
 
Experimenting and Learning Kubernetes and Tensorflow
Experimenting and Learning Kubernetes and TensorflowExperimenting and Learning Kubernetes and Tensorflow
Experimenting and Learning Kubernetes and Tensorflow
 
Tips on solving E_TOO_MANY_THINGS_TO_LEARN with Kubernetes
Tips on solving E_TOO_MANY_THINGS_TO_LEARN with KubernetesTips on solving E_TOO_MANY_THINGS_TO_LEARN with Kubernetes
Tips on solving E_TOO_MANY_THINGS_TO_LEARN with Kubernetes
 
Learning Patterns for the Overworked Developer
Learning Patterns for the Overworked DeveloperLearning Patterns for the Overworked Developer
Learning Patterns for the Overworked Developer
 
Implementing Google's Material Design Guidelines
Implementing Google's Material Design GuidelinesImplementing Google's Material Design Guidelines
Implementing Google's Material Design Guidelines
 
Architecting .NET Applications for Docker and Container Based Deployments
Architecting .NET Applications for Docker and Container Based DeploymentsArchitecting .NET Applications for Docker and Container Based Deployments
Architecting .NET Applications for Docker and Container Based Deployments
 
The Art Of Building Prototypes and MVPs
The Art Of Building Prototypes and MVPsThe Art Of Building Prototypes and MVPs
The Art Of Building Prototypes and MVPs
 
Node.js Anti Patterns
Node.js Anti PatternsNode.js Anti Patterns
Node.js Anti Patterns
 
What Designs Need To Know About Visual Design
What Designs Need To Know About Visual DesignWhat Designs Need To Know About Visual Design
What Designs Need To Know About Visual Design
 
Real World Lessons On The Anti-Patterns of Node.JS
Real World Lessons On The Anti-Patterns of Node.JSReal World Lessons On The Anti-Patterns of Node.JS
Real World Lessons On The Anti-Patterns of Node.JS
 
Learning to think "The Designer Way"
Learning to think "The Designer Way"Learning to think "The Designer Way"
Learning to think "The Designer Way"
 

Último

+971581248768>> SAFE AND ORIGINAL ABORTION PILLS FOR SALE IN DUBAI AND ABUDHA...
+971581248768>> SAFE AND ORIGINAL ABORTION PILLS FOR SALE IN DUBAI AND ABUDHA...+971581248768>> SAFE AND ORIGINAL ABORTION PILLS FOR SALE IN DUBAI AND ABUDHA...
+971581248768>> SAFE AND ORIGINAL ABORTION PILLS FOR SALE IN DUBAI AND ABUDHA...
?#DUbAI#??##{{(☎️+971_581248768%)**%*]'#abortion pills for sale in dubai@
 
Artificial Intelligence: Facts and Myths
Artificial Intelligence: Facts and MythsArtificial Intelligence: Facts and Myths
Artificial Intelligence: Facts and Myths
Joaquim Jorge
 
Why Teams call analytics are critical to your entire business
Why Teams call analytics are critical to your entire businessWhy Teams call analytics are critical to your entire business
Why Teams call analytics are critical to your entire business
panagenda
 
Cloud Frontiers: A Deep Dive into Serverless Spatial Data and FME
Cloud Frontiers:  A Deep Dive into Serverless Spatial Data and FMECloud Frontiers:  A Deep Dive into Serverless Spatial Data and FME
Cloud Frontiers: A Deep Dive into Serverless Spatial Data and FME
Safe Software
 

Último (20)

Axa Assurance Maroc - Insurer Innovation Award 2024
Axa Assurance Maroc - Insurer Innovation Award 2024Axa Assurance Maroc - Insurer Innovation Award 2024
Axa Assurance Maroc - Insurer Innovation Award 2024
 
AWS Community Day CPH - Three problems of Terraform
AWS Community Day CPH - Three problems of TerraformAWS Community Day CPH - Three problems of Terraform
AWS Community Day CPH - Three problems of Terraform
 
+971581248768>> SAFE AND ORIGINAL ABORTION PILLS FOR SALE IN DUBAI AND ABUDHA...
+971581248768>> SAFE AND ORIGINAL ABORTION PILLS FOR SALE IN DUBAI AND ABUDHA...+971581248768>> SAFE AND ORIGINAL ABORTION PILLS FOR SALE IN DUBAI AND ABUDHA...
+971581248768>> SAFE AND ORIGINAL ABORTION PILLS FOR SALE IN DUBAI AND ABUDHA...
 
Real Time Object Detection Using Open CV
Real Time Object Detection Using Open CVReal Time Object Detection Using Open CV
Real Time Object Detection Using Open CV
 
How to Troubleshoot Apps for the Modern Connected Worker
How to Troubleshoot Apps for the Modern Connected WorkerHow to Troubleshoot Apps for the Modern Connected Worker
How to Troubleshoot Apps for the Modern Connected Worker
 
Artificial Intelligence: Facts and Myths
Artificial Intelligence: Facts and MythsArtificial Intelligence: Facts and Myths
Artificial Intelligence: Facts and Myths
 
Apidays Singapore 2024 - Building Digital Trust in a Digital Economy by Veron...
Apidays Singapore 2024 - Building Digital Trust in a Digital Economy by Veron...Apidays Singapore 2024 - Building Digital Trust in a Digital Economy by Veron...
Apidays Singapore 2024 - Building Digital Trust in a Digital Economy by Veron...
 
A Year of the Servo Reboot: Where Are We Now?
A Year of the Servo Reboot: Where Are We Now?A Year of the Servo Reboot: Where Are We Now?
A Year of the Servo Reboot: Where Are We Now?
 
Workshop - Best of Both Worlds_ Combine KG and Vector search for enhanced R...
Workshop - Best of Both Worlds_ Combine  KG and Vector search for  enhanced R...Workshop - Best of Both Worlds_ Combine  KG and Vector search for  enhanced R...
Workshop - Best of Both Worlds_ Combine KG and Vector search for enhanced R...
 
Why Teams call analytics are critical to your entire business
Why Teams call analytics are critical to your entire businessWhy Teams call analytics are critical to your entire business
Why Teams call analytics are critical to your entire business
 
Cloud Frontiers: A Deep Dive into Serverless Spatial Data and FME
Cloud Frontiers:  A Deep Dive into Serverless Spatial Data and FMECloud Frontiers:  A Deep Dive into Serverless Spatial Data and FME
Cloud Frontiers: A Deep Dive into Serverless Spatial Data and FME
 
Bajaj Allianz Life Insurance Company - Insurer Innovation Award 2024
Bajaj Allianz Life Insurance Company - Insurer Innovation Award 2024Bajaj Allianz Life Insurance Company - Insurer Innovation Award 2024
Bajaj Allianz Life Insurance Company - Insurer Innovation Award 2024
 
A Domino Admins Adventures (Engage 2024)
A Domino Admins Adventures (Engage 2024)A Domino Admins Adventures (Engage 2024)
A Domino Admins Adventures (Engage 2024)
 
Deploy with confidence: VMware Cloud Foundation 5.1 on next gen Dell PowerEdg...
Deploy with confidence: VMware Cloud Foundation 5.1 on next gen Dell PowerEdg...Deploy with confidence: VMware Cloud Foundation 5.1 on next gen Dell PowerEdg...
Deploy with confidence: VMware Cloud Foundation 5.1 on next gen Dell PowerEdg...
 
Boost Fertility New Invention Ups Success Rates.pdf
Boost Fertility New Invention Ups Success Rates.pdfBoost Fertility New Invention Ups Success Rates.pdf
Boost Fertility New Invention Ups Success Rates.pdf
 
Bajaj Allianz Life Insurance Company - Insurer Innovation Award 2024
Bajaj Allianz Life Insurance Company - Insurer Innovation Award 2024Bajaj Allianz Life Insurance Company - Insurer Innovation Award 2024
Bajaj Allianz Life Insurance Company - Insurer Innovation Award 2024
 
Top 5 Benefits OF Using Muvi Live Paywall For Live Streams
Top 5 Benefits OF Using Muvi Live Paywall For Live StreamsTop 5 Benefits OF Using Muvi Live Paywall For Live Streams
Top 5 Benefits OF Using Muvi Live Paywall For Live Streams
 
Connector Corner: Accelerate revenue generation using UiPath API-centric busi...
Connector Corner: Accelerate revenue generation using UiPath API-centric busi...Connector Corner: Accelerate revenue generation using UiPath API-centric busi...
Connector Corner: Accelerate revenue generation using UiPath API-centric busi...
 
Repurposing LNG terminals for Hydrogen Ammonia: Feasibility and Cost Saving
Repurposing LNG terminals for Hydrogen Ammonia: Feasibility and Cost SavingRepurposing LNG terminals for Hydrogen Ammonia: Feasibility and Cost Saving
Repurposing LNG terminals for Hydrogen Ammonia: Feasibility and Cost Saving
 
Data Cloud, More than a CDP by Matt Robison
Data Cloud, More than a CDP by Matt RobisonData Cloud, More than a CDP by Matt Robison
Data Cloud, More than a CDP by Matt Robison
 

Real World Lessons on the Pain Points of Node.js Applications

Notas do Editor

  1. var d = require('domain').create(); d.on('error', function(err){ // handle the error safely console.log(err); }); // catch the uncaught errors in this // asynchronous or synchronous code block d.run(function(){ // the asynchronous or synchronous code // that we want to catch thrown errors on var err = new Error('example'); throw err; });
  2. var util = require('util'); function UserNameAlreadyExistsError(err) { Error.call(this); this.name = 'UserNameAlreadyExistsError'; if(typeof err === 'string') { this.message = err; } else { this.message = err.message; } this.detail = err.details; } util.inherits(UserNameAlreadyExistsError, Error); module.exports = UserNameAlreadyExistsError;
  3. try { var files = yield readdir(dir) } catch (er) { console.error('something happened whilst reading the directory') }
  4. getTweetsFor("domenic") // promise-returning function .then(function (tweets) { var shortUrls = parseTweetsForUrls(tweets); var mostRecentShortUrl = shortUrls[0]; return expandUrlUsingTwitterApi(mostRecentShortUrl); // promise-returning function }) .then(httpGet) // promise-returning function .then( function (responseBody) { console.log("Most recent link text:", responseBody); }, function (error) { console.error("Error with the twitterverse:", error); } );
  5. var repo_url = $(site).find('li[data-tab="repo"]').find('a').attr('href'); var activity_url = $(site).find('li[data-tab="activity"]').find('a').attr('href'); request.get("http://github.com" + repo_url, function(rr, repo_html) { var $_repo = cheerio.load(repo_html); var repo_list = $_repo('.repolist li'); var results = []; repo_list.each(function(ix, p) { var source = true; if($(p).hasClass('fork')) source = false; var repo = { link: "http://github.com" + $(p).find('.repolist-name a').attr('href'), title: $(p).find('.repolist-name').text().clean(), stars: parseInt($(p).find('.stargazers a').text().clean(), 10), is_source: source, language: $(p).find('.language').text()}; if(repo_list.length === (ix + 1)) { request.get("https://github.com" + activity_url, function(err, activity_html) { var $_activity = cheerio.load(activity_html); var repo_list = $_activity('.alert'); var results = []; repo_list.each(function(ix, p) { var repo = {title: $(p).find('.title').text().clean(), actioned_at: $(p).find('.js-relative-date').attr('datetime')}; results.push(repo); if(repo_list.length === (ix + 1)) { data.repositories = results.repo; data.public_activity = results.activity; callback({parser: 'github', id: data.username, profile: data}); } }); }); } }); });
  6. var repo_url = $(site).find('li[data-tab="repo"]').find('a').attr('href'); var activity_url = $(site).find('li[data-tab="activity"]').find('a').attr('href'); request.get("http://github.com" + repo_url, function(rr, repo_html) { var $_repo = cheerio.load(repo_html); var repo_list = $_repo('.repolist li'); var results = []; repo_list.each(function(ix, p) { var source = true; if($(p).hasClass('fork')) source = false; var repo = { link: "http://github.com" + $(p).find('.repolist-name a').attr('href'), title: $(p).find('.repolist-name').text().clean(), stars: parseInt($(p).find('.stargazers a').text().clean(), 10), is_source: source, language: $(p).find('.language').text()}; if(repo_list.length === (ix + 1)) { request.get("https://github.com" + activity_url, function(err, activity_html) { var $_activity = cheerio.load(activity_html); var repo_list = $_activity('.alert'); var results = []; repo_list.each(function(ix, p) { var repo = {title: $(p).find('.title').text().clean(), actioned_at: $(p).find('.js-relative-date').attr('datetime')}; results.push(repo); if(repo_list.length === (ix + 1)) { data.repositories = results.repo; data.public_activity = results.activity; callback({parser: 'github', id: data.username, profile: data}); } }); }); } }); });
  7. var repo_url = $(site).find('li[data-tab="repo"]').find('a').attr('href'); var activity_url = $(site).find('li[data-tab="activity"]').find('a').attr('href'); request.get("http://github.com" + repo_url, function(rr, repo_html) { var $_repo = cheerio.load(repo_html); var repo_list = $_repo('.repolist li'); var results = []; repo_list.each(function(ix, p) { var source = true; if($(p).hasClass('fork')) source = false; var repo = { link: "http://github.com" + $(p).find('.repolist-name a').attr('href'), title: $(p).find('.repolist-name').text().clean(), stars: parseInt($(p).find('.stargazers a').text().clean(), 10), is_source: source, language: $(p).find('.language').text()}; if(repo_list.length === (ix + 1)) { request.get("https://github.com" + activity_url, function(err, activity_html) { var $_activity = cheerio.load(activity_html); var repo_list = $_activity('.alert'); var results = []; repo_list.each(function(ix, p) { var repo = {title: $(p).find('.title').text().clean(), actioned_at: $(p).find('.js-relative-date').attr('datetime')}; results.push(repo); if(repo_list.length === (ix + 1)) { data.repositories = results.repo; data.public_activity = results.activity; callback({parser: 'github', id: data.username, profile: data}); } }); }); } }); });
  8. var repo_url = $(site).find('li[data-tab="repo"]').find('a').attr('href'); var activity_url = $(site).find('li[data-tab="activity"]').find('a').attr('href'); request.get("http://github.com" + repo_url, function(rr, repo_html) { var $_repo = cheerio.load(repo_html); var repo_list = $_repo('.repolist li'); var results = []; repo_list.each(function(ix, p) { var source = true; if($(p).hasClass('fork')) source = false; var repo = { link: "http://github.com" + $(p).find('.repolist-name a').attr('href'), title: $(p).find('.repolist-name').text().clean(), stars: parseInt($(p).find('.stargazers a').text().clean(), 10), is_source: source, language: $(p).find('.language').text()}; if(repo_list.length === (ix + 1)) { request.get("https://github.com" + activity_url, function(err, activity_html) { var $_activity = cheerio.load(activity_html); var repo_list = $_activity('.alert'); var results = []; repo_list.each(function(ix, p) { var repo = {title: $(p).find('.title').text().clean(), actioned_at: $(p).find('.js-relative-date').attr('datetime')}; results.push(repo); if(repo_list.length === (ix + 1)) { data.repositories = results.repo; data.public_activity = results.activity; callback({parser: 'github', id: data.username, profile: data}); } }); }); } }); });
  9. var repo_url = $(site).find('li[data-tab="repo"]').find('a').attr('href'); var activity_url = $(site).find('li[data-tab="activity"]').find('a').attr('href'); request.get("http://github.com" + repo_url, function(rr, repo_html) { var $_repo = cheerio.load(repo_html); var repo_list = $_repo('.repolist li'); var results = []; repo_list.each(function(ix, p) { var source = true; if($(p).hasClass('fork')) source = false; var repo = { link: "http://github.com" + $(p).find('.repolist-name a').attr('href'), title: $(p).find('.repolist-name').text().clean(), stars: parseInt($(p).find('.stargazers a').text().clean(), 10), is_source: source, language: $(p).find('.language').text()}; if(repo_list.length === (ix + 1)) { request.get("https://github.com" + activity_url, function(err, activity_html) { var $_activity = cheerio.load(activity_html); var repo_list = $_activity('.alert'); var results = []; repo_list.each(function(ix, p) { var repo = {title: $(p).find('.title').text().clean(), actioned_at: $(p).find('.js-relative-date').attr('datetime')}; results.push(repo); if(repo_list.length === (ix + 1)) { data.repositories = results.repo; data.public_activity = results.activity; callback({parser: 'github', id: data.username, profile: data}); } }); }); } }); });
  10. var parse_repositories = function(repo_url, callback) { request.get("http://github.com" + repo_url, function(rr, repo_html) { var $_repo = cheerio.load(repo_html); var repo_list = $_repo('.repolist li'); var results = []; repo_list.each(function(ix, p) { var source = true; if($_repo(p).hasClass('fork')) source = false; var repo = { link: "http://github.com" + $_repo(p).find('.repolist-name a').attr('href'), title: $_repo(p).find('.repolist-name').text().clean(), stars: parseInt($_repo(p).find('.stargazers a').text().clean(), 10), is_source: source, language: $_repo(p).find('.language').text()}; if(repo.title !== '') { results.push(repo); } if(repo_list.length === (ix + 1)) { callback(null, results); } }); if(repo_list.length === 0) { callback(null, []); } }); };
  11. run(function* () { console.log("Starting") var file = yield readFile("./async.js”) console.log(file.toString()) })
  12. app.post('/users', function *(request) { var user = new User(request.params); if (yield user.save()) { return JSON.stringify(user); } else { return 422; } });
  13. Story
  14. Story