Title Page Copyright and Credits Node.js Complete Reference Guide About Packt Why subscribe? Packt.com Contributors About the authors Packt is searching for authors like you Preface Who this book is for What this book covers To get the most out of this book Download the example code files Conventions used Get in touch Reviews About Node.js The capabilities of Node.js Server-side JavaScript Why should you use Node.js? Popularity JavaScript at all levels of the stack Leveraging Google's investment in V8 Leaner, asynchronous, event-driven model Microservice architecture Node.js is stronger for having survived a major schism and hostile fork Threaded versus event-driven architecture Performance and utilization Is Node.js a cancerous scalability disaster? Server utilization, the business bottom line, and green web hosting Embracing advances in the JavaScript language Deploying ES2015/2016/2017/2018 JavaScript code Node.js, the microservice architecture, and easily testable systems Node.js and the Twelve-Factor app model Summary Setting up Node.js System requirements Installing Node.js using package managers Installing on macOS with MacPorts Installing on macOS with Homebrew Installing on Linux, *BSD, or Windows from package management systems Installing Node.js in the Windows Subsystem for Linux (WSL) Opening an administrator-privileged PowerShell on Windows Installing the Node.js distribution from nodejs.org Installing from source on POSIX-like systems Installing prerequisites Installing developer tools on macOS Installing from source for all POSIX-like systems Installing from source on Windows Installing multiple Node.js instances with nvm Installing nvm on Windows Native code modules and node-gyp Node.js versions policy and what to use Editors and debuggers Running and testing commands Node.js's command-line tools Running a simple script with Node.js Conversion to async functions and the Promise paradigm Launching a server with Node.js NPM – the Node.js package manager Node.js, ECMAScript 2015/2016/2017, and beyond  Using Babel to use experimental JavaScript features Summary Node.js Modules Defining a module CommonJS and ES2015 module formats CommonJS/Node.js module format ES6 module format JSON modules Supporting ES6 modules on older Node.js versions Demonstrating module-level encapsulation Finding and loading CommonJS and JSON modules using require File modules Modules baked into Node.js binary Directories as modules Module identifiers and pathnames An example of application directory structure Finding and loading ES6 modules using import Hybrid CommonJS/Node.js/ES6 module scenarios Dynamic imports with import() The import.meta feature npm - the Node.js package management system The npm package format Finding npm packages Other npm commands Installing an npm package Installing a package by version number Global package installs Avoiding global module installation Maintaining package dependencies with npm Automatically updating package.json dependencies Fixing bugs by updating package dependencies Packages that install commands Configuring the PATH variable to handle commands installed by modules Configuring the PATH variable on Windows Avoiding modifications to the PATH variable Updating outdated packages you've installed Installing packages from outside the npm repository Initializing a new npm package Declaring Node.js version compatibility Publishing an npm package Explicitly specifying package dependency version numbers The Yarn package management system Summary HTTP Servers and Clients Sending and receiving events with EventEmitters JavaScript classes and class inheritance The EventEmitter Class The EventEmitter theory HTTP server applications ES2015 multiline and template strings HTTP Sniffer – listening to the HTTP conversation Web application frameworks Getting started with Express Setting environment variables in Windows cmd.exe command line Walking through the default Express application The Express middleware Middleware and request paths Error handling Calculating the Fibonacci sequence with an Express application Computationally intensive code and the Node.js event loop Algorithmic refactoring Making HTTP Client requests Calling a REST backend service from an Express application Implementing a simple REST server with Express Refactoring the Fibonacci application for REST Some RESTful modules and frameworks Summary Your First Express Application Promises, async functions, and Express router functions Promises and error handling Flattening our asynchronous code Promises and generators birthed async functions Express and the MVC paradigm Creating the Notes application Your first Notes model Understanding ES-2015 class definitions Filling out the in-memory Notes model The Notes home page Adding a new note – create Viewing notes – read Editing an existing note – update Deleting notes – destroy Theming your Express application Scaling up – running multiple Notes instances Summary Implementing the Mobile-First Paradigm Problem – the Notes app isn't mobile friendly Mobile-first paradigm Using Twitter Bootstrap on the Notes application Setting it up Adding Bootstrap to application templates Alternative layout frameworks Flexbox and CSS Grids Mobile-first design for the Notes application Laying the Bootstrap grid foundation Responsive page structure for the Notes application Using icon libraries and improving visual appeal Responsive page header navigation bar Improving the Notes list on the front page Cleaning up the Note viewing experience Cleaning up the add/edit note form Cleaning up the delete-note window Building a customized Bootstrap Pre-built custom Bootstrap themes Summary Data Storage and Retrieval Data storage and asynchronous code Logging Request logging with Morgan Debugging messages Capturing stdout and stderr Uncaught exceptions Unhandled Promise rejections Using the ES6 module format Rewriting app.js as an ES6 module Rewriting bin/www as an ES6 module Rewriting models code as ES6 modules Rewriting router modules as ES6 modules Storing notes in the filesystem Dynamic import of ES6 modules Running the Notes application with filesystem storage Storing notes with the LevelUP data store Storing notes in SQL with SQLite3 SQLite3 database schema SQLite3 model code Running Notes with SQLite3 Storing notes the ORM way with Sequelize Sequelize model for the Notes application Configuring a Sequelize database connection Running the Notes application with Sequelize Storing notes in MongoDB MongoDB model for the Notes application Running the Notes application with MongoDB Summary Multiuser Authentication the Microservice Way Creating a user information microservice User information model A REST server for user information Scripts to test and administer the user authentication server Login support for the Notes application Accessing the user authentication REST API Login and logout routing functions Login/logout changes to app.js Login/logout changes in routes/index.mjs Login/logout changes required in routes/notes.mjs View template changes supporting login/logout Running the Notes application with user authentication Twitter login support for the Notes application Registering an application with Twitter Implementing TwitterStrategy Securely keeping secrets and passwords The Notes application stack Summary Dynamic Client/Server Interaction with Socket.IO Introducing Socket.IO Initializing Socket.IO with Express Real-time updates on the Notes homepage The Notes model as an EventEmitter class Real-time changes in the Notes home page Changing the homepage and layout templates Running Notes with real-time homepage updates Real-time action while viewing notes Changing the note view template for real-time action Running Notes with real-time updates while viewing a note Inter-user chat and commenting for Notes Data model for storing messages Adding messages to the Notes router Changing the note view template for messages Using a Modal window to compose messages Sending, displaying, and deleting messages Running Notes and passing messages Other applications of Modal windows Summary Deploying Node.js Applications Notes application architecture and deployment considerations Traditional Linux Node.js service deployment Prerequisite – provisioning the databases Installing Node.js on Ubuntu Setting up Notes and user authentication on the server Adjusting Twitter authentication to work on the server Setting up PM2 to manage Node.js processes Node.js microservice deployment with Docker Installing Docker on your laptop Starting Docker with Docker for Windows/macOS Kicking the tires of Docker Creating the AuthNet for the user authentication service MySQL container for Docker Initializing AuthNet Script execution on Windows Linking Docker containers The db-userauth container Dockerfile for the authentication service Configuring the authentication service for Docker Building and running the authentication service Docker container Exploring Authnet Creating FrontNet for the Notes application MySQL container for the Notes application Dockerizing the Notes application Controlling the location of MySQL data volumes Docker deployment of background services Deploying to the cloud with Docker compose Docker compose files Running the Notes application with Docker compose Deploying to cloud hosting with Docker compose Summary Unit Testing and Functional Testing Assert – the basis of testing methodologies Testing a Notes model Mocha and Chai­ – the chosen test tools Notes model test suite Configuring and running tests More tests for the Notes model Testing database models Using Docker to manage test infrastructure Docker Compose to orchestrate test infrastructure Executing tests under Docker Compose MongoDB setup under Docker and testing Notes against MongoDB Testing REST backend services Automating test results reporting Frontend headless browser testing with Puppeteer Setting up Puppeteer Improving testability in the Notes UI Puppeteer test script for Notes Running the login scenario The Add Note scenario Mitigating/preventing spurious test errors in Puppeteer scripts Configuring timeouts Tracing events on the Page and the Puppeteer instance Inserting pauses Avoiding WebSockets conflicts Taking screenshots Summary REST – What You Did Not Know REST fundamentals Principle 1 – Everything is a resource Principle 2 – Each resource is identifiable by a unique identifier Principle 3 – Manipulate resources via standard HTTP methods Principle 4 – Resources can have multiple representations Principle 5 – Communicate with resources in a stateless manner The REST goals Separation of the representation and the resource Visibility Reliability Scalability and performance Working with WADL Documenting RESTful APIs with Swagger Taking advantage of the existing infrastructure Summary Building a Typical Web API Specifying the API Implementing routes Querying the API using test data Content negotiation API versioning Self-test questions Summary Using NoSQL Databases MongoDB – a document store database Database modeling with Mongoose Testing a Mongoose model with Mocha Creating a user-defined model around a Mongoose model Wiring up a NoSQL database module to Express Self-test questions Summary Restful API Design Guidelines Endpoint URLs and HTTP status codes best practices Extensibility and versioning Linked data Summary Implementing a Full Fledged RESTful Service Working with arbitrary data Linking Implementing paging and filtering Caching Supplying the Cache-Control header in Express applications Discovering and exploring RESTful services Summary Consuming a RESTful API Consuming RESTful services with jQuery Troubleshooting and identifying problems on the wire Cross Origin Resource Sharing Content Delivery Networks Handling HTTP status codes on the client side Summary Securing the Application Authentication Basic authentication Passport Passport's basic authentication strategy Passport's OAuth Strategy Passport's third-party authentication strategies Authorization Transport layer security Self-test questions Summary The Age of Microservices From monolith to microservices Patterns of microservices Decomposable Autonomous Scalable Communicable Summary Modules and Toolkits Seneca Hydra Summary Building a Microservice Using Hydra Using Seneca Plugins Summary State State Storing state MySQL RethinkDB Redis Conclusion Security Summary Testing Integrating tests Using chai Adding code coverage Covering all code Mocking our services Summary Design Patterns Choosing patterns Architectural patterns Front Controller Layered Service Locator Observer Publish-Subscribe Using patterns Planning your microservice Obstacles when developing Summary Other Books You May Enjoy Leave a review - let other readers know what you think