Authentication using external service
Authentication using external service

Introduction
EnRoute Ingress API Gateway provides an extremely flexible mechanism to authenticate incoming requests. An external service can check authentication and authorization for requests entering the cluster. Every request before it reaches the destination service can be authenticated.
We explore Authentication support in EnRoute gateway. Using an example we walk through different aspects of external authentication including per-route disable.
What this article covers
We install EnRoute Gateway, expose a service externally and configure an external authentication service

Install EnRoute with External Authentication support
External authentication support is provided in a separate EnRoute image. It can be installed using the following helm command after adding the helm repo and installing the enroute image with wasm
tag. The image has support for both wasm
and ext_authz
envoy filters
helm repo add saaras https://getenroute.io
helm install enroute-demo saaras/enroute \
--set serviceAccount.create=true \
--create-namespace \
--namespace enroutedemo \
--set images.enrouteService.tag=wasm
Install example workload
kubectl create namespace httpbin
kubectl apply -f https://raw.githubusercontent.com/saarasio/enroute/master/helm-chart/httpbin-bin-service.yaml
Program EnRoute to make the service externally available
helm install httpbin-service-policy saaras/service-policy --set service.name=httpbin --set service.prefix=/post --set service.port=80 --namespace httpbin
Send request to External-IP of LoadBalancer
service to verify it works as expected. The getting started guide has details on setting this up.
curl -X POST -H 'Content-Type: application/json' -d '{}' 212.2.241.255/post
{
"args": {},
"data": "{}",
"files": {},
"form": {},
"headers": {
"Accept": "*/*",
"Content-Length": "2",
"Content-Type": "application/json",
"Host": "212.2.241.255",
"User-Agent": "curl/7.68.0",
"X-Envoy-Expected-Rq-Timeout-Ms": "15000",
"X-Envoy-External-Address": "192.168.1.5"
},
"json": {},
"origin": "152.70.114.65,192.168.1.5",
"url": "http://212.2.241.255/post"
}
Create a External Authentication filter
cat <<EOF | kubectl apply -f -
apiVersion: enroute.saaras.io/v1
kind: HttpFilter
metadata:
name: extauthz-filter
namespace: httpbin
spec:
httpFilterConfig:
config: |
{
"url" : "https://ext-authz-ns.ext-auth:8443",
"auth_service" : "ext-auth",
"auth_service_proto" : "http",
"body_max_bytes" : 4096,
"body_allow_partial" : true,
"status_on_error" : 403,
"failure_mode_allow" : true,
"timeout" : 10,
"path_prefix" : "",
"pack_raw_bytes" : false,
"allowed_request_headers": ["x-forwarded-for"],
"allowed_authorization_headers" : ["x-org-auth-tenantid", "x-token"]
}
name: extauthz-filter
type: http_filter_extauthz
EOF
This defines a destination service for external authorization in namespace ext-authz-ns
to service ext-auth
running on port 8443
over https
The detailed configuration options for the above service can be found in the External Authorization Filter reference.
Enable the External Authorization filter for service
kubectl edit -n httpbin gatewayhosts.enroute.saaras.io httpbin-80-gatewayhost
5 apiVersion: enroute.saaras.io/v1
6 kind: GatewayHost
7 metadata:
8 annotations:
13 labels:
14 app: httpbin
16 name: httpbin-80-gatewayhost
17 namespace: httpbin
20 spec:
21 routes:
22 - conditions:
23 - header:
24 contains: auth-disabled-route
25 name: X-auth-hint
26 - prefix: /post
27 disableExtauth: true
28 filters:
29 - name: httpbin-80-rl2
30 type: route_filter_ratelimit
31 services:
32 - healthCheck:
33 healthyThresholdCount: 3
34 host: hc
35 intervalSeconds: 5
36 path: /
37 timeoutSeconds: 3
38 unhealthyThresholdCount: 3
39 name: httpbin
40 port: 80
41 - conditions:
42 - header:
43 contains: auth-enabled-route
44 name: X-auth-hint
45 - prefix: /post
46 filters:
47 - name: httpbin-80-rl2
48 type: route_filter_ratelimit
49 services:
50 - healthCheck:
51 healthyThresholdCount: 3
52 host: hc
53 intervalSeconds: 5
54 path: /
55 timeoutSeconds: 3
56 unhealthyThresholdCount: 3
57 name: httpbin
58 port: 80
59 virtualhost:
60 filters:
61 - name: httpbin-80-luatestfilter
62 type: http_filter_lua
63 - name: extauthz-filter
64 type: http_filter_extauthz
65 fqdn: '*'
Note the lines 63-64
above that attaches the filter to GatewayHost
Note on line 27
external authorization is explicitly disabled (using disableExtauth: true
directive) for a request with incoming header X-auth-hint: auth-disabled-route
Verify invocation of external authorization service
The external authentication service for this example when invoked sets three headers -
"X-Org-Auth-Tenantid": "eC1hdXRoLWFjY291bnRJZAo=",
"X-Token": "eC1hdXRoLXRva2VuCg==",
If the request was sent to the external authentication service, the above three headers would be set.
To send a request
curl -vv -X POST -H 'X-auth-hint: "auth-disabled-route"' -H 'Content-Type: application/json' -d '{"auth":"disabled"}' 212.2.241.255/post
{
"args": {},
"data": "{\auth\":\"disabled\"}",
"files": {},
"form": {},
"headers": {
"Accept": "*/*",
"Content-Length": "26",
"Content-Type": "application/json",
"Host": "212.2.241.255",
"User-Agent": "curl/7.68.0",
"X-Envoy-Expected-Rq-Timeout-Ms": "15000",
"X-Envoy-External-Address": "192.168.1.6",
"X-Stamp": "\"prod2\""
},
"json": {
"auth": "disabled"
},
"origin": "152.70.114.65,192.168.1.6",
"url": "http://212.2.241.255/post"
}
Now lets sent a request that will be authenticated by an external auth service
curl -vv -X POST -H 'X-auth-hint: "auth-enabled-route"' -H 'Content-Type: application/json' -d '{"auth":"enabled"}' 212.2.241.255/post
{
"args": {},
"data": "{\"auth\":\"enabled\"}",
"files": {},
"form": {},
"headers": {
"Accept": "*/*",
"Content-Length": "26",
"Content-Type": "application/json",
"Ext-Authz-Example-Header": "ext-authz-example-header-value",
"Host": "212.2.241.255",
"User-Agent": "curl/7.68.0",
"X-Org-Auth-Tenantid": "eC1hdXRoLWFjY291bnRJZAo=",
"X-Token": "eC1hdXRoLXRva2VuCg==",
"X-Envoy-Expected-Rq-Timeout-Ms": "15000",
"X-Envoy-External-Address": "192.168.1.6",
"X-Stamp": "\"prod1\""
},
"json": {
"auth": "enabled"
},
"origin": "152.70.114.65,192.168.1.6",
"url": "http://212.2.241.255/post"
}
Conclusion
This howto quickly covers how to configure and enable an external authorization service for authenticating services at Ingress