Throttling In WSO2 API Manager

This post is about the ThrottleHandler in WSO2 APIM 2.6.0.

Java class : org.wso2.carbon.apimgt.gateway.handlers.throttling.ThrottleHandler

“DoThrottle” method will initialize throttle flow in ThrottleHandler class.

private boolean doThrottle(MessageContext messageContext)

If this returns true, that means the message flow need to continue(message not throttled) and pass the requests to next handler. If this is false, that means the message is throttled out.

Let us explore the implementation logic of the ThrottleHandler (what happens in the DoThrottle call and subsequent methods).

As the first step, this will validate if the authentication is successful. For that, it will retrieve the AuthenticationContext information from the request.

Once that is confirmed, the handler will initialize the throttle for subscription level spike arrest (initThrottleForSubscriptionLevelSpikeArrest in ThrottleHandler class)

That method will create throttle context for incoming message (only if it is not created previously).

After that operation, the call will go to “doRoleBasedAccessThrottlingWithCEP” method.

This is where application, subscription and resource level throttling will happen.

The following throttle keys will be used here.

  • Application level throttle key : combination of {applicationId}:{authorizedUser}
  • Subscription level throttle key : combination of {applicationId}:{apiContext}:{apiVersion}
  • Resource level throttle key : combination of {apiContext}/ {apiVersion}{resourceUri}:{httpMethod}
  • API level throttle key : combination of {apiContext}:{apiVersion}

Note : The code will only proceed with throttling if and only if the AuthenticationContext is set (not null).

Then it will check if the request is blocked (if there are blocking conditions present : IP level blocking or app level blocking).

If the request is blocked, then it will be marked as throttled (i.e – isThrottled = true). The flow will abort.

The code will check for API level tier. If it is not present, it moves to resource level tiers.

In other words, if API level throttle policy is present, no resource level policy will apply for it.

Suppose resource level policy is applicable. In that case, the code will check if unlimited tier is present. If so, throttling will not be applied at resource level

log.debug("Resource level throttling set as unlimited and request will pass resource level");

The below debug log will indicate this (enable debug logs for : org.wso2.carbon.apimgt.gateway.handlers.throttling.ThrottleHandler)

If some other policy is used (not the unlimited tier), then there are few checks to be done.

Evaluating conditional groups : A map is used to store the conditional groups and it will be passed to the throttle condition evaluator (along with the request) and checks if the request is throttled based on the conditional groups.

After that, if it is not throttled at API level, it checks for resource level throttling. If it is throttled, request will be stopped.

Suppose the request is not throttled at resource level, then it will be checked for subscription level throttling.

If the request is not throttled even at subscription level, the check will proceed to application level throttling.

This is the final check. If the request is not throttled even at application level, it means the request was not throttled at any level.

If that happens (i.e – successful API call), publish an event to global policy server. There, it will check for the hard limit. If that is also passed, then the event will be published as a non throttled event.

Note : If “stopOnQuotaReach” is false, that means the request can pass even after throttle limit is reached. Here, this is considered as a successful call.

Leave a comment

This site uses Akismet to reduce spam. Learn how your comment data is processed.