5/14/2023

Secure API Access using APISIX Gateway and Keycloak

 





The purpose of this post is to explain how we can secure APIs using APISIX API Gateway and Keycloak. 

We are going to use Keycloak for authentication and authorization as an identity provider.


The Key Takeaways



  1. This approach is that the application doesn’t have to handle authentication and authorization for APIs since it’s managed by API Gateway.


  1. Also since it’s cloud native API Gateway, we can manage and use it, the same way Kubernetes artifacts manage and use.


  1. With this kind of a platform, we can deploy applications developed in any programming language since the platform itself manages non-functional features that need to be there, such as security.

https://i.stack.imgur.com/qaogh.png




To get an idea about Keycloak RBAC, please see the diagram below.


.








https://images.app.goo.gl/g9oixvSgQ9virLBf8


This post is inspired by the example below but I had to fix some of the configurations since it’s already outdated.

https://www.youtube.com/watch?v=xjDQ9Gm234c


You can find the customized repo from below location

https://github.com/dhanuka84/apisix-summit-material


  • Please note that you have to replace 192.168.59.106 with minikube ip in your minikube cluster.


Steps for setting up the platform


  1. Install minikube addons



In this local setup we are using minikube. Now we need to install a few addons related to our poc.


  1. Run this command to install three add-ons.


minikube addons enable storage-provisioner default-storageclass ingress ingress-dns


  1. Install metalLB load balancer

Please follow the below reference to install metalLB load balancer for minikube.

https://kubebyexample.com/learning-paths/metallb/install


  1. Load application images to minikube


        docker pull docker.io/jpgouin/front-app:1.0-rc4

        docker pull jpgouin/app-go-api:1.0-rc1


        minikube image load docker.io/jpgouin/front-app:1.0-rc4

                        minikube image load jpgouin/app-go-api:1.0-rc1


  2.  Install APISIX APIGateway



helm repo add apisix https://charts.apiseven.com

helm repo add bitnami https://charts.bitnami.com/bitnami


helm repo update

kubectl create ns ingress-apisix


helm install apisix apisix/apisix \

  --set gateway.type=LoadBalancer \

  --set ingress-controller.enabled=true \

  --namespace ingress-apisix \

  --set ingress-controller.config.apisix.serviceNamespace=ingress-apisix






3. Install Keycloak


kubectl create ns keycloak


kubectl create -f https://raw.githubusercontent.com/keycloak/keycloak-quickstarts/latest/kubernetes-examples/keycloak.yaml -n keycloak


wget -q -O - https://raw.githubusercontent.com/keycloak/keycloak-quickstarts/latest/kubernetes-examples/keycloak-ingress.yaml | \

sed "s/KEYCLOAK_HOST/keycloak.$(minikube ip).nip.io/" | \

kubectl create -f -  -n keycloak


  • You can verify the installation with below commands


$ kubectl get ing  -n keycloak

NAME       CLASS   HOSTS                            ADDRESS          PORTS     AGE

keycloak   nginx   keycloak.192.168.59.106.nip.io   192.168.59.106   80, 443   54m




$ KEYCLOAK_URL=https://keycloak.$(minikube ip).nip.io &&
> echo "" &&
echo "Keycloak:                 $KEYCLOAK_URL" &&
echo "Keycloak Admin Console:   $KEYCLOAK_URL/admin" &&
echo "Keycloak Account Console: $KEYCLOAK_URL/realms/myrealm/account" &&
echo ""
Keycloak:                 https://keycloak.192.168.59.106.nip.io
Keycloak Admin Console:   https://keycloak.192.168.59.106.nip.io/admin
Keycloak Account Console: https://keycloak.192.168.59.106.nip.io/realms/myrealm/account
$ kubectl get all -n keycloak
NAME                            READY   STATUS    RESTARTS   AGE
pod/keycloak-7c7444bcf5-fwdsc   1/1     Running   0          44m
NAME               TYPE           CLUSTER-IP       EXTERNAL-IP     PORT(S)          AGE
service/keycloak   LoadBalancer   10.109.145.178   192.168.59.24   8080:31190/TCP   44m
NAME                       READY   UP-TO-DATE   AVAILABLE   AGE
deployment.apps/keycloak   1/1     1            1           44m
NAME                                  DESIRED   CURRENT   READY   AGE
replicaset.apps/keycloak-7c7444bcf5   1         1         1       44m





4. Deploying the applications


  • Front-end application


kubectl create ns poc-front-appsvc




  • Back-end application




5. APISIX routes configuration







  • Please note that, demo-api.demo.jpgouin.pro is the backend app host path.


  • Add below entry to /etc/hosts file for DNS mapping



You can see that the API Gateway load balancer external ip is 192.168.59.25


dhanuka84@dhanuka84:~/research/apim$ cat  /etc/hosts


192.168.59.25 book-app.demo.jpgouin.pro demo-api.demo.jpgouin.pro



6. Testing



Go to the website using the URL below.


http://book-app.demo.jpgouin.pro/


This will display a site without the below data. So you can add authors and books as below.


  • Make sure that the author first and last name is same.






7. Applying RBAC for the APIs exposed by microservices applications.


  1. Create a routing for the keycloak, by doing this we can access keycloak through API Gateway.

    kubectl apply -f https://raw.githubusercontent.com/dhanuka84/apisix-summit-material/master/configuration/keycloak-route.yaml




  1. To create RBAC configuration in keycloak , you can login to the keycloak admin dashboard with below url then entering both username and password as admin .


https://keycloak.192.168.59.106.nip.io/



Then just follow the same 7 steps mentioned in this readme file: https://raw.githubusercontent.com/dhanuka84/apisix-summit-material/master/Readme.md



Or else you can upload a realm-export.json file to keycloak.


  • Create a realm by selecting the Create Realm button.




  • Browse to resource file (realm-export.json) .




  • Finally you can check the configuration as below.



8. Apply OAuth2/OpenID configuration to API Gateway routes.

Change application route configuration as below.

kubectl apply -f https://raw.githubusercontent.com/dhanuka84/apisix-summit-material/master/scenario/Step-2a-front-route-secure.yaml


kubectl apply -f https://raw.githubusercontent.com/dhanuka84/apisix-summit-material/master/scenario/Step-2b-back-route-secure.yaml



  • Now the front-end application router will use openid-connect plugin with given configuration.

  • Expected behavior is when we enter the web-application URL it will direct to keycloak username and password login page.

  • If you login as Jhon, he can create authors but can’t create books

  • If you login as Franck, he can create a book entry but can’t create an author record.

  • Both users can view the data created by them.



9. Testing




Once you login as Franck, you can’t create authors and will get 403 error code.



He still can enter the book record.


  • This way we can secure APIs based resources and restrict actions based on configured RBAC.

No comments:

Post a Comment