Looks like this topic quieted.  I am attempting to summarize the points made 
into the wiki so it is easier to digest.  If my summary is off, or people have 
more points to make please email on this thread.

A few thoughts:

1.       I found a pretty detailed paper on configuring Nginx as an API gateway 
for microservices but its beyond my technical scope to say if it is relevant.  
To EF’s point, something like this may be easier than reinventing the wheel. 
https://www.nginx.com/blog/building-microservices-using-an-api-gateway/

2.       I like the idea of a two-tiered system with mandated auth at the 
gateway and optional additional auth at the services.  I also like the idea 
that some services or endpoints like data reads for portal charts could be done 
with less auth overhead than say modifying or building services which should be 
tightly controlled.

3.       I think an attack scenario planning should be built in to the system 
design at least for likely scenarios.  The planning around “fail open” vs. 
“fail closed” seems pertinent as well as ideas for how we maintain control and 
the ability to fix affected services in these types of scenarios.

Ryan Durfey    M | 303-524-5099
CDN Support (24x7): 866-405-2993 or 
[email protected]<mailto:[email protected]>


From: "Eric Friedrich (efriedri)" <[email protected]>
Reply-To: "[email protected]" 
<[email protected]>
Date: Sunday, May 7, 2017 at 9:21 PM
To: "[email protected]" 
<[email protected]>
Subject: Re: API GW route configuration

From a higher level- what is purpose of the API Gateway?  It seems like there 
may have been some previous discussions about API Gateway. Are there any notes 
or description that I can catch up on?

How will it be deployed? (Is it a standalone service or something that runs 
inside the experimental Traffic Ops)?

Is this new component required or optional?

—Eric



On May 7, 2017, at 8:28 PM, Jan van Doorn 
<[email protected]<mailto:[email protected]>> wrote:
I looked into this a year or so ago, and I couldn't make nginx or http do
what we need.
We can still have the services check the auth as well after the proxy auth,
and make things better than today, where we have the same problem that if
the TO mojo app is compromised, everything is compromised.
If we always route to TO, we don't untangle the mess of being dependent on
the monolithic TO for everything. Many services today, and more in the
future really just need a check to see if the user is authorized, and
nothing more.
On Sun, May 7, 2017 at 11:55 AM Robert Butts 
<[email protected]<mailto:[email protected]>>
wrote:
What are the advantages of these config files, over an existing reverse
proxy, like Nginx or httpd? It's just as much work as configuring and
deploying an existing product, but more code we have to write and maintain.
I'm having trouble seeing the advantage.
-1 on auth rules as a part of the proxy. Making a proxy care about auth
violates the Single Responsibility Principle, and further, is a security
risk. It creates unnecessary attack surface. If your proxy app or server is
compromised, the entire framework is now compromised. An attacker could
simply rewrite the proxy config to make all routes no-auth.
The simple alternative is for the proxy to always route to TO, and TO
checks the token against the auth service (which may also be proxied), and
redirects unauthorized requests to a login endpoint (which may also be
proxied).
The TO service (and any other service that requires auth) MUST hit the
database (or the auth service, which itself hits the database) to verify
valid tokens' users still have the permissions they did when the token was
created. Otherwise, it's impossible to revoke tokens, e.g. if an employee
quits, or an attacker gains a token, or a user changes their password.
On Sun, May 7, 2017 at 4:35 AM, Amir Yeshurun 
<[email protected]<mailto:[email protected]>> wrote:
Seems that attachments are stripped on this list. Examples pasted below
*rules.json*
[
    { "host": "localhost", "path": "/login",               "forward":
"localhost:9004", "scheme": "https", "auth": false },
    { "host": "localhost", "path": "/api/1.2/innovation/", "forward":
"localhost:8004", "scheme": "http",  "auth": true, "routes-file":
"innovation.json" },
    { "host": "localhost", "path": "/api/1.2/",            "forward":
"localhost:3000", "scheme": "http",  "auth": true, "routes-file":
"traffic-ops-routes.json" },
    { "host": "localhost", "path": "/internal/api/1.2/",   "forward":
"localhost:3000", "scheme": "http",  "auth": true, "routes-file":
"internal-routes.json" }
]
*traffic-ops-routes.json (partial)*
.
.
.
    { "match": "/cdns/health",                        "auth": { "GET":
["cdn-health-read"] }},
    { "match": "/cdns/capacity",                      "auth": { "GET":
["cdn-health-read"] }},
    { "match": "/cdns/usage/overview",                "auth": { "GET":
["cdn-stats-read"] }},
    { "match": "/cdns/name/dnsseckeys/generate",      "auth": { "GET":
["cdn-security-keys-read"] }},
    { "match": "/cdns/name/[^\/]+/?",                 "auth": { "GET":
["cdn-read"] }},
    { "match": "/cdns/name/[^\/]+/sslkeys",           "auth": { "GET":
["cdn-security-keys-read"] }},
    { "match": "/cdns/name/[^\/]+/dnsseckeys",        "auth": { "GET":
["cdn-security-keys-read"] }},
    { "match": "/cdns/name/[^\/]+/dnsseckeys/delete", "auth": { "GET":
["cdn-security-keys-write"] }},
    { "match": "/cdns/[^\/]+/queue_update",           "auth": { "POST":
["queue-updates-write"] }},
    { "match": "/cdns/[^\/]+/snapshot",               "auth": { "PUT":
["cdn-config-snapshot-write"] }},
    { "match": "/cdns/[^\/]+/health",                 "auth": { "GET":
["cdn-health-read"] }},
    { "match": "/cdns/[^\/]+/?",                      "auth": { "GET":
["cdn-read"], "PUT":  ["cdn-write"], "PATCH": ["cdn-write"], "DELETE":
["cdn-write"] }},
    { "match": "/cdns",                               "auth": { "GET":
["cdn-read"], "POST": ["cdn-write"] }},
.
.
.
On Sun, May 7, 2017 at 12:39 PM Amir Yeshurun 
<[email protected]<mailto:[email protected]>> wrote:
Attached please find examples for forwarding rules file (rules.json)
and
the authorization rules file (traffic-ops-routes.json)
On Sun, May 7, 2017 at 10:39 AM Amir Yeshurun 
<[email protected]<mailto:[email protected]>> wrote:
Hi all,
I am about to submit a PR with a first operational version of the API
GW,
to the "experimental" code base.
The API GW forwarding logic is as follow:
   1. Find host to forward the request: Prefix match on the request
path
   against a list of forwarding rules. The matched forwarding rule
defines the
   target's host, and the target's *authorization rules*.
   2. Authorization: Regex match on the request path against a list of
*authorization
   rules*. The matched rule defines the required capabilities to
perform
   the HTTP method on the route. These capabilities are compared
against the
   user's capabilities in the user's JWT
At this moment, the 2 sets of rules are hard-coded in json files. The
files are provided with the API GW distribution and contain
definitions
for
TC 2.0 API routes. I have tested parts of the API, however, there
might
be
mistakes in some of the routes. Please be warned.
Considering manageability and high availability, I am aware that using
local files for storing the set of authorization rules is inferior to
centralized configuration.
We are considering different approaches for centralized configuration,
having the following points in mind
   - Microservice world: API GW will front multiple services, not only
   Mojo. It can also front other TC components like Traffic Stats and
Traffic
   Monitor. Each service defines its own routes and capabilities. Here
comes
   the question of what is the "source of truth" for the route
definitions.
   - Handling private routes. API GW may front non-TC services.
   - User changes to the AAA scheme. The ability for admin user to
makes
   changes in the required capabilities of a route, maybe even define
new
   capability names, was raised in the past as a use case that should
be
   supported.
   - Easy development and deployment of new services.
   - Using TO DB for expediency.
I would appreciate any feedback and views on your approach to manage
route definitions.
Thanks
/amiry


Reply via email to