But what if your services are written in different languages from each other and they need to perform similar authz checks? Sure, each service might need be responsible for its own data fetching, but the actual logic over the data can be written in one common language (Rego) and have one single source of truth.
claytongulick|4 years ago
The approach I've taken is to implement my own application gateway using node-http-proxy.
I use npm workspaces to share common functionality between all the node parts of the application, including the api gateway / reverse proxy.
I configure the other services to trust a HTTP header that's injected in the api gateway (and explicitly deleted from incoming requests) that includes details about the user. For example, Apache Superset (and several other services) support the REMOTE_USER header.
Honestly, doing this in a high-level language like NodeJS with node-http-proxy is even simpler to do and easier to read / audit than what I've seen in Rego, plus I get to use all the common utilities for dynamic service access, database access, etc...
This borders on a "NIH" thing, but I think if you saw the actual implementation, it's even less complex than what I'm seeing from these examples. It took me a couple hours to throw together, it's easy to extend, and supports a multitude of authentication scenarios, including shared-session (which would be tough with Rego).
ogazitt|4 years ago
Also, once you start incorporating resource-specific information in your authorization decisions, this approach starts to break down. The gateway could be made to understand resource-specific information, but then you're essentially moving the problem from the application to the gateway. And typically you want your API gateway to make forward/block decisions quickly.
Happy to chat about your use case! You can find me at @omrig / omri at aserto dot com.
ogazitt|4 years ago
And Rego syntax is much easier to grok than other "-as-code" approaches (read: wall-of-yaml)