Lets get our hands dirty and dig into the procedure step by step.

Step 1: Deploying the API Operator for Kubernetes

API Operator for Kubernetes is a handy tool to deploy your micro-services as managed APIs in Kubernetes and manage them with business plans and security plans without any hassle. Here, I will be using the API Operator for Kubernetes to deploy our micro-service as a managed API in Kubernetes and apply a business plan to limit the number of API requests for a resource.

Navigate to the api-k8s-crds-1.0.0 directory in the extracted zip in prerequisite 4 Deploy the artifacts related to the API Operator

kubectl apply -f apim-operator/controller-artifacts/

3. The API Operator for Kubernetes makes your managed API image reusable from another cluster by pushing it to the DockerHub. You can enter your DockerHub information as below and deploy the controller configurations.

Open apim-operator/controller-configs/controller_conf.yaml and update user’s docker registry.

dockerRegistry: <username-docker-registry>

Open apim-operator/controller-configs/docker_secret_template.yaml.

Enter the base 64 encoded username and password of the Docker-Hub account

data:

username: ENTER YOUR BASE64 ENCODED USERNAME

password: ENTER YOUR BASE64 ENCODED PASSWORD

Execute the following command to deploy controller configurations.

kubectl apply -f apim-operator/controller-configs/

4. Configure the API Controller, which is a comprehensive command line tool to handle operations related to API Operator.

Extract the API controller distribution, and navigate inside the extracted folder using the command-line tool

Add the location of the extracted folder to your system’s $PATH variable to be able to access the executable from anywhere.

Set the API Controller’s mode to Kubernetes

apictl set --mode k8s

Step 2: Deploy your business plan in the cluster

You can define your business plan using the RateLimiting kind and deploy it in the cluster.

There are 3 RateLimiting types: advance, subscription and application; which allows you to limit the number of API requests on different bases. In this blog we will be discussing the advance type, which actually is the simplest type, which allows you to limit the number of API requests from all the users to a particular resource or an API.

Lets define our business policy to allow only 3 requests per minute.

apiVersion: wso2.com/v1alpha1

kind: RateLimiting

metadata:

name: advancethreepolicy

spec:

type: advance

description: Allow 3 requests per minute # optional

timeUnit: min

unitTime: 1

requestCount:

limit: 3

Lets deploy this in the kubernetes cluster. (rlpolicy.yaml is the file name with the above policy)

apictl apply -f rlpolicy.yaml

Architecture of Rate Limiting Controller

When you deploy the ratelimiting CRD with your business plan, the ratelimiting controller creates a configmap with all the policies you had deployed.

Step 3: Refer your business plan in the swagger definition

You can define your managed API with your business plan policy, security policy and endpoint of your micro-service using a swagger definition.

You can find an example swagger definition here. I have defined the policy to be applied to the whole API with the extension “x-wso2-throttling-tier”. If you want to limit the number of API requests to a resource, you can define it the same way in the resource level.

x-wso2-throttling-tier: advancethreepolicy

In the example swagger file, I have used the sample Petstore from swagger.io.

You can use the endpoint of your micro-service deployed in kubernetes in the same way with the “x-wso2-production-endpoints” extension.

Step 4: Deploy your managed API using the swagger

As the final step lets deploy our managed API in the Kubernetes.

apictl add api -n adpetstore --from-file=swagger.yaml

The API Operator will run a kaniko job to create an image of the micro-gateway with the given swagger file and the policy configmap created in step 2.

It will take some time for the API service to be available. After the API Service is available we can invoke the API and test if our business plan is applied.

TOKEN=eyJ0eXAiOiJKV1QiLCJhbGciOiJSUzI1NiIsIng1dCI6IlpqUm1ZVE13TlRKak9XVTVNbUl6TWpnek5ESTNZMkl5TW1JeVkyRXpNamRoWmpWaU1qYzBaZz09In0.eyJhdWQiOiJodHRwOlwvXC9vcmcud3NvMi5hcGltZ3RcL2dhdGV3YXkiLCJzdWIiOiJhZG1pbkBjYXJib24uc3VwZXIiLCJhcHBsaWNhdGlvbiI6eyJvd25lciI6ImFkbWluIiwidGllciI6IlVubGltaXRlZCIsIm5hbWUiOiJzYW1wbGUtY3JkLWFwcGxpY2F0aW9uIiwiaWQiOjMsInV1aWQiOm51bGx9LCJzY29wZSI6ImFtX2FwcGxpY2F0aW9uX3Njb3BlIGRlZmF1bHQiLCJpc3MiOiJodHRwczpcL1wvd3NvMmFwaW06MzIwMDFcL29hdXRoMlwvdG9rZW4iLCJ0aWVySW5mbyI6e30sImtleXR5cGUiOiJQUk9EVUNUSU9OIiwic3Vic2NyaWJlZEFQSXMiOltdLCJjb25zdW1lcktleSI6IjNGSWlUM1R3MWZvTGFqUTVsZjVVdHVTTWpsUWEiLCJleHAiOjM3MTk3Mzk4MjYsImlhdCI6MTU3MjI1NjE3OSwianRpIjoiZDI3N2VhZmUtNTZlOS00MTU2LTk3NzUtNDQwNzA3YzFlZWFhIn0.W0N9wmCuW3dxz5nTHAhKQ-CyjysR-fZSEvoS26N9XQ9IOIlacB4R5x9NgXNLLE-EjzR5Si8ou83mbt0NuTwoOdOQVkGqrkdenO11qscpBGCZ-Br4Gnawsn3Yw4a7FHNrfzYnS7BZ_zWHPCLO_JqPNRizkWGIkCxvAg8foP7L1T4AGQofGLodBMtA9-ckuRHjx3T_sFOVGAHXcMVwpdqS_90DeAoT4jLQ3darDqSoE773mAyDIRz6CAvNzzsWQug-i5lH5xVty2kmZKPobSIziAYes-LPuR-sp61EIjwiKxnUlSsxtDCttKYHGZcvKF12y7VF4AqlTYmtwYSGLkXXXw

Now lets invoke the API with the default JWT token which allows all the users.

curl -X GET "https://<external IP of LB service>:9095/petstoreadvance/v1/pet/55" -H "accept: application/xml" -H "Authorization:Bearer $TOKEN" -k

If you are using GKE clusters you can use the external IP of the managed API service we deployed (adpetstore). If you are using minikube you can use the NodePort the service is exposed along with the minikube IP.

As an example you can see the below command I used in minikube.

curl -X GET "https://192.168.99.121:32111/petstoreadvance/v1/pet/55?[1-4]" -H "accept: application/xml" -H "Authorization:Bearer $TOKEN" -k

Since we applied our business plan to allow only 3 requests per minute for our micro-service, from the below screenshot you can see that the 4th request has been throttled out.

In this blog, we were able to apply a business plan in 4 simple steps for our micro-service to allow only 3 requests per minute.