1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
|
# Authorization via OIDC and OAuth 2.0
[OAuth 2.0][3] is a framework for Authz and can be extended [OpenID Connect][4]
for Authn.
```plaintext
OAuth 2.0 Protocol Flow
+--------+ +---------------+
| |--(A)- Authorization Request ->| Resource |
| | | Owner |
| |<-(B)-- Authorization Grant ---| |
| | +---------------+
| |
| | +---------------+
| |--(C)-- Authorization Grant -->| Authorization |
| Client | | Server |
| |<-(D)----- Access Token -------| |
| | +---------------+
| |
| | +---------------+
| |--(E)----- Access Token ------>| Resource |
| | | Server |
| |<-(F)--- Protected Resource ---| |
+--------+ +---------------+
```
```plaintext
OIDC Protocol Flow
+--------+ +--------+
| | | |
| |---------(1) AuthN Request-------->| |
| | | |
| | +--------+ | |
| | | | | |
| | | End- |<--(2) AuthN & AuthZ-->| |
| | | User | | |
| RP | | | | OP |
| | +--------+ | |
| | | |
| |<--------(3) AuthN Response--------| |
| | | |
| |---------(4) UserInfo Request----->| |
| | | |
| |<--------(5) UserInfo Response-----| |
| | | |
+--------+ +--------+
```
The IDToken is a [JWT][5] with the standard claims.
The `scope` claim includes a space delimited list of
permissions that the current subject is entitled to.
For example:
```json
{
"sub": "<uuid-of-principal>",
"aud": "https://api.cmdzero.io",
"iss": "https://auth0.com",
"exp": "unix-timestamp-expires-at",
"iat": "unix-timestamp-issued-at"
"scope": "write:groups read:incident",
}
```
If an `IDToken` is provided as part of an OpenID Connect transaction then this
token can be used to fetch any profile information update from the OpenID user
profile endpoint to stay in sync with any profile changes that occur.
All Authz permissions (claims) for a given Principal (Resource Owner) can be
included in a stateless Access Token that can be used to access a REST
API (Resource Server). The API can check the validity of a token and its
permissions by checking the disposition of the provided token against the
[token introspection endpoint][1] and/or it can verify the signature of the
token if the Access Token is a [JWT][5]
Request:
```plaintext
POST /introspect HTTP/1.1
Host: auth0.com
Accept: application/json
Content-Type: application/json
{
"token": "mF_9.B5f-4.1JqM",
"token_type_hint": "access_token"
}
```
Response:
```
HTTP/1.1 200 OK
Content-Type: application/json
{
"active": true,
"sub": "<uuid-of-principal>",
"aud": "https://api.cmdzero.io",
"iss": "https://auth0.com",
"exp": "unix-timestamp-expires-at",
"iat": "unix-timestamp-issued-at"
"scope": "write:groups",
}
```
## API Gateway Example Flow
```plaintext
||======================================================||
|| ||
|| VPC ||
|| ||
--------------- || --------------------- ------- --------- --------- || ------
| Client (RP) | || | API Gateway (PEP) | | PDP | | API A | | API B | || | OP |
--------------- || --------------------- ------- --------- --------- || ------
| || | | | | || |
| GET /login | | | | || |
|----------------------------------------------------------------||-->|
| || | | | | || |
| ... || |
| ... || |
|<---------------------------------------------------------------||---|
| || return access_token: "x.y.z" | | || |
| || | | | | || |
| GET /my/organizations | | | | || |
| Authorization: "x.y.z"| | | | || |
|---------------------->| | | | || |
| || | | | | || |
| || |------------>| | | || |
| || | | | | || |
| || |<------------| | | || |
| || | Allow | | | || |
| || | | | | || |
| || |---------------------->| | || |
| || | | | | || |
| || |<----------------------| | || |
| || | | | | || |
|<----------------------| | | | || |
| || | | | | || |
| || | | | | || |
| GET /my/notifications | | | | || |
| Authorization: "x.y.z"| | | | || |
|---------------------->| | | | || |
| || | | | | || |
| || |------------>| | | || |
| || | | | | || |
| || |<------------| | | || |
| || | Allow | | | || |
| || | | | | || |
| || |--------------------------------->| || |
| || | | | | || |
| || |<---------------------------------| || |
| || | | | | || |
|<----------------------| | | | || |
| || | | | | || |
| DELETE /admin/users | | | | || |
| Authorization: "x.y.z"| | | | || |
|---------------------->| | | | || |
| || | | | | || |
| || |------------>| | | || |
| || | | | | || |
| || |<------------| | | || |
| || | Deny | | | || |
|<----------------------| | | | || |
| || | | | | || |
| || || |
| ||======================================================|| |
```
[Auth0][2] can be used as the OP in the diagram above.
## Microservices Security in Action
* https://learning.oreilly.com/library/view/microservices-security-in/9781617295959/
* TLS Bridging: proxy server terminates TLS for incoming connection and creates
a new TLS connection to the destination of the message.
* TLS Tunneling creates a tunnel between the client and the microservices.
The API gateway terminates all client connections at the edge. It dispatches
requests to the upstream service if all looks good. The initial client/user
context needs to be passed through as well.
Service to Server authn
1. Trust the network
1. Mutual TLS
1. JSON Web Tokens
Service-level authz
1. centalized PDP
1. embedded PDP
Propagating User Context
1. Send user context as an HTTP Header
1. Use a self signed JWT
1. Use a JWT issued by a trusted external STS
```plaintext
----------
| Client |
----------
|
||=====================|========================||
|| V ||
|| |--------------| ||
|| | API Gateway | ||
|| |--------------| ||
|| | ||
|| ----<----| ||
|| | ||
|| *******V********* ******************* ||
|| * | |----->---------------- * ||
|| * | | * * | * ||
|| * V | * * V * ||
|| * ========= * * --------- * ||
|| * | |<----<-----| * | | * ||
|| * | API A | * | * | API B | * ||
|| * | |----->--| | * | | * ||
|| * ========= * | | * --------- * ||
|| * | A * | | * * ||
|| * V | * V |-<-----<-----| * ||
|| * | ------- * | * ------- * ||
|| * |->| STS | * |---->------->| STS | * ||
|| * ------- * * ------- * ||
|| ***************** ******************* ||
|| ||
||=====================|========================||
```
* The API Gateway pattern is used to expose microservices to client applications
as APIs.
* The API gateway helps to expose microservices of different flavors by using a
consistent and easy-to-understand interface to the consumers of these
services.
* Protocols such as basic authn and mTLS are not sufficient to secure API's.
* An access token can be a reference token or a self-contained token (JWT). If
it is a reference token, the gateway has to talk to the issuer to validate it.
* Self contained tokens need short TTL's mitigate token revocation.
### Same Origin Policy
Cross origin resource sharing (CORS) is the exception to the same-origin policy.
It allows an app running on `localhost:4200` to access resources on
`localhost:8080`. Web browsers use the `OPTIONS` HTTP method along with special
HTTP headers to determine whether to allow or deny a cross-origin request.
Before sending a request to a different origin the browser will send an HTTP
`OPTIONS` request to the resource on the particular origin. This is known as a
_preflight request_. The request includes the following HTTP headers:
* `Access-Control-Request-Headers`: indicates the HTTP headers that the request
is about to send to the server.
* `Access-Control-Request-Method`: indicates the HTTP method about to be
executed by the request (e.g. `GET`).
* `Origin`: indicates the origin of the web application. (e.g. `http://localhost:4200`)
The server responds to the preflight request with the following headers:
* `Access-Control-Allow-Credentials`: indicates whether the server allows the
request originator to send credentials in the form of authorization headers,
cookies, or TLS client certificates. (e.g. `true` or `false`)
* `Access-Control-Allow-Headers`: indicates the list of headers allowed by the
particular resource on the server.
* `Access-Control-Allow-Methods`: indicates the list of HTTP methods allowed by
the particular resource on the server.
* `Access-Control-Allow-Origin`: indicates the cross-origin allowed by the
server.
* `Access-Control-Max-Age`: indicates for how long to cache the preflight request.
## Glossary
* PAP: Policy Administration Point.
* PEP: Policy Enforcement Point is a gateway that protects all requests routed
to this point to make a decision. It takes the incoming HTTP request and
creates an authz specific request. Usually this is the API Gateway.
* PDP: Policy Decision Point consumes an authz request send from the PEP to make
a decision on whether to allow or deny the request.
* RP: Relying Party is the OAuth 2.0 Client application.
* OP: OpenID Provider is the OAuth 2.0 Authorization Server that is capable of
Authn and providing claims to a RP about the authn event and User.
* STS: Security Token Service
* `X-Forwarded-For` HTTP header field is a common method for identifying the
originating IP address of a client connecting to a web server through an HTTP
proxy or load balancer.
[1]: https://datatracker.ietf.org/doc/html/rfc7662#section-2
[2]: https://auth0.com/docs/authenticate/login/oidc-conformant-authentication/oidc-adoption-access-tokens
[3]: https://datatracker.ietf.org/doc/html/rfc6749
[4]: https://openid.net/specs/openid-connect-core-1_0.html#Overview
[5]: https://datatracker.ietf.org/doc/html/rfc7519
|