Building and deploying cloud native APIs is a complex operation, and can require a multitude of components. In this workshop we focus on the fundamentals of deploying the runtime API code and publishing the API through an API gateway. To achieve this we use NGINX Unit as a polyglot application server and NGINX web server as an API gateway. With this combination we deliver a solution lightweight enough for dev and strong enough for production.
You will learn how to use NGINX Unit to run one or more apps and APIs in a variety of languages, including seamlessly deploying new versions. You will then see the best practices for how to configure NGINX to perform the common API gateway functions of request routing, rate limiting, and authentication for multiple APIs. We will also touch on advanced use cases such as HTTP method enforcement, and JSON validation.
No previous experience of NGINX or NGINX Unit is required, but a basic knowledge of HTTP and JSON/REST APIs is valuable.
3. What we’re going to build
API Client Internet / WAN API Gateway Backend APIs
4. Agenda
1. Introducing NGINX
2. Running APIs with NGINX
Unit
3. Q&A
4. Break (15 mins)
5. Deploying NGINX web
server as an API gateway
6. Q&A
5. 5
“... when I started NGINX,
I focused on a very specific
problem – how to handle more
customers per a single server.”
- Igor Sysoev, NGINX creator and founder
6. Introducing NGINX
6
2004
• NGINX
0.1
2007
• “Viable”
2011
• NGINX, Inc.
• NGINX 1.0
2013
• NGINX Plus R1
2018
• NGINX Unit 1.0
• Controller 1.0
2019
• Controller 2.0
(API mgmt.)
• NGINX Plus
R19
• Acquired by
F5 Networks
7.
8. Agenda
1. Introducing NGINX
2. Running APIs with
NGINX Unit
3. Break / Q&A
4. Deploying NGINX web
server as an API
gateway
5. Q&A
9. What we’re going to build
API Client Internet / WAN API Gateway Backend APIs
10. What is NGINX Unit
10
“NGINX Unit is a polyglot app
server, a reverse proxy, and a static
file server, available for Unix-like
systems”
24. Unit in docker
24
• Use the nginx/unit base images
• Make use of the /docker-entrypoint-d features
◦ Apply initial configurtion
◦ Apply initial uploding of certificates for TLS encryption
◦ Run Shell-scripts
25. What we have now
Developers
Machine
Backend APIs
AWS EC2
AWS
Container
Registry
push pull
API Gateway
26. Agenda
1. Introducing NGINX
2. Running APIs with
NGINX Unit
3. Break / Q&A
4. Deploying NGINX web
server as an API
gateway
5. Q&A
27. Agenda
1. Introducing NGINX
2. Running APIs with
NGINX Unit
3. Break / Q&A
4. Deploying NGINX web
server as an API
gateway
5. Q&A
28. What we’re going to build
API Client Internet / WAN API Gateway Backend APIs
29. #1 40%“Most websites use NGINX” of NGINX deployments
are as an API gateway
Source: NGINX User survey 2017, 2018, 2019Source: Netcraft April 2019 Web Server Survey
32. NGINX Open Source Cycle
Stable retired
Mainline forked
Mainline “bump”
New stable
Critical bugfix
Stable
1.even.0
Mainline
1.odd.0
April
• Mainline
• New features
• 8-12 releases per year
• Stable
• Critical bug fixes only
• 1-2 releases per year
NGINX 1.0 and Unit 1.0 released 12th Apr (International Day of Human Space Flight – Yuri Gagarin)
2020 – let’s pretend it didn’t happen!
*** ADD RELOAD COMMANDS ***
Other error formats are available
Let’s now take a look at the architecture for NGINX Unit
This is how we built Unit for performance, security and consistency
We’ll start at the top of this diagram
And drill-in on the various processes
*click*
When Unit starts up we get
the “main” process
the “controller” process
and the “router” process
The controller process exposes an HTTP interface for API configuration
By default it is a Unix socket but can also listen as a TCP port on the network
API calls are handled by the controller process
Configuration is analyzed by the controller and passed to the main process
And then into the router process
*click*
The router is interesting
There are several threads: a main thread and a number of workers
Whereas configuration requests are handled by the controller process
Client requests for applications are handled by the router process
The router accepts client HTTP connections but only when you ask Unit to bind an application to a specific port do you enable that application
Such changes do not reload the workers, but simply modify their configuration
The router process transfers requests to the application processes
We don’t include PHP, Python or Go with Unit
That is, we don’t compile them in
We use system-level interpreters – which means we can have several of them, all co-existing on the same instance.
In this example we have PHP5 and PHP7 running different applications
GO, however, is a different animal ;)
Unlike PHP and Python, GO applications listen on HTTP ports directly
GO provides a network-level web server as a builtin facility
Therefore in order for a GO application to run within Unit we replace the ‘http’ listener with a ‘unit’ listener
So without Unit it will listen directly
With Unit it will not listen on a port, but communicate with the Unit router using shared memory
But why would you run a GO application with Unit?
This brings us back to the benefits of a consistent application stack.
You have the same control and configuration for GO as you do for PHP and Python
And so it will work the same way as the rest of your distributed application
Greatly simplifying the deployment and DevOps workload
if you use nodejs "http", then you need to proxy http over a socket connection, that has additional overhead
Unit adds dynamic control to your "http" in nodejs with routing and etc... all the features that we to add in the future, also it should be more scalable... lots of things in nodejs http are written in javascript, while Unit is in C
the idea is that people will no more need in additional proxy layer in front of their nodejs apps
*** ADD RELOAD COMMANDS ***
Other error formats are available
How to apply new Unit configuration
We’re going to use port 8080 for all of the APIs – if that’s a conflict for you then choose another and map 8080 to it
Single server{} benefits TLS footprint and use of keepalives
This is the first config reload – make sure it’s working
Nested locations not useful yet – we use them for policies
Exact (=), regex (~) and prefix () matching
Might also use an external auth server with proxy_pass to perform OAuth 2.0 token introspection (see blog)