An application programming interface (API) is a piece of code that allows two software programs to interact with one another. An API specifies how a developer may request services from an operating system (OS) or other programme, as well as disclose data in various contexts and through many channels.
Semaphores are synchronization objects that limit the number of simultaneous accesses to a shared resource. You can use a semaphore to control concurrency and prioritize API requests. Each priority level can have its own semaphore.
In the case of applications that call resources of various formats (for example, JSON or XML), API prioritization allows you to specify which calls should be considered for priority and be sent to the origin during situations in which there is high demand. When you configure your rules based on information found in the inbound request, you get a list of calls that are prioritized based on the information given. The different levels of priority that your API requests can have. For example, you might have high, medium, and low priority levels.
To prioritize an API using the semaphore concept, you can assign different levels of priority to your requests, such as high, medium, and low. Then, create separate semaphores for each priority level, where the number of permits in each semaphore represents the maximum number of simultaneous requests allowed. When a request arrives, it tries to acquire a permit from the appropriate semaphore based on its priority. If no permits are available, the request waits. Once a permit is acquired, the request is processed, and upon completion, the permit is released, allowing another waiting request to proceed. This way, higher-priority requests are given precedence while controlling the concurrency of API requests through the semaphore mechanism. By using this concept, we can prioritize our api and reduce the workload
from odoo import http
from odoo.http import request, Response
import json
class ApiUsingSemaphore(http.Controller):
@http.route('/cybro/RestApi/semaphore', type='http', auth='public',
method=['POST'], csrf=False)
def api_using_semaphore(self, *args, **kwargs):
try:
semaphore_count = int(request.env[
'ir.config_parameter'].sudo().get_param(
'semaphore_count', default='0'))
semaphore_count += 1
Request.env[
'ir.config_parameter'].sudo().set_param(
'semaphore_count', str(semaphore_count))
if request.httprequest.method == 'POST':
semaphore_count -= 1
Request.env[
'ir.config_parameter'].sudo().set_param(
'semaphore_count', str(semaphore_count))
response_data = {
"Status": "good",
"Message": "Everything working fine"
}
return Response(json.dumps(
response_data), headers={
'Content-Type': 'application/json'})
except Exception as e:
response_data = {
"Status": "error",
"Message": str(e)
}
return Response(json.dumps(
response_data), headers={'Content-Type':'application/json'})
The code you have mentioned involves the usage of a field named "semaphore_count" in the "ir.config_parameter" model. This field serves as a counter, incrementing each time an API call is received and decrementing when the API processing is completed. Here's how it works:
The "semaphore_count" field in the "ir.config_parameter" model is used to store the current count of API calls in progress. When an API request is received, the code retrieves the current count from the "semaphore_count" field using get_param. If no value is found, it defaults to 0.the code increments the count by 1 using count = int(get_semaphore) + 1. If the current count is equal to or greater than 0, it means there are ongoing API calls. In this case, the incremented count is saved back to the "semaphore_count" field using set_param.
If the current count is less than 0 or False, indicating no ongoing API calls, the count is set to 1 using set_param.
Inside the POST request block, the count is decremented by 1 using count = int(get_semaphore) - 1. Which means an api is completed.the decremented count is saved back to the "semaphore_count" field using set_param.the API response is generated with a JSON message indicating the status and result of the API call.
In case of any exceptions during API processing, an error response is generated with a relevant error message. The count is updated to reflect the completion of the API call, ensuring that the count accurately represents the number of ongoing API calls.
Utilizing the "semaphore_count" field in the "ir.config_parameter" model effectively tracks the count of ongoing API calls, allowing for proper handling and control of concurrent API access.
def check_semaphore_count(self):
semaphore_count = int(request.env['ir.config_parameter'].sudo().get_param('semaphore_count', default='0')
If semaphore_count != 0
# Waiting for 300ms to complete an API request
time.sleep(0.3)
If you have a long function that takes too much time to process, you can split that function into smaller functions. When every small function is complete, check that the semaphore_count is not zero. If the semaphore count is not zero, wait 300 ms to complete your first or hAPI request. (300 ms is just an example:compute how much time it takes to complete your one API.)