shashank created CAMEL-24926:
--------------------------------

             Summary: throttle(n).concurrentRequestsMode() lets more than n 
exchanges in when one of them takes longer than 10 seconds
                 Key: CAMEL-24926
                 URL: https://issues.apache.org/jira/browse/CAMEL-24926
             Project: Camel
          Issue Type: Bug
          Components: camel-core
            Reporter: shashank


With {{throttle(1).concurrentRequestsMode()}}, two exchanges can be inside the 
throttled part of the route at the same time:

# Exchange X passes the throttle and completes. Returning its permit schedules 
a cleanup of the throttler state 10 seconds later.
# Exchange A takes the permit and runs for 15 seconds.
# The cleanup runs while A is still being processed and removes the state (the 
semaphore).
# Exchange B arrives. There is no state for the key anymore, so a new one with 
all permits is created, and B passes the throttle while A still holds its 
permit.

Observed with a route whose processor sleeps for slow messages:
{noformat}
t= 0.25s enter X (inside: 1)
t= 0.26s leave X
t= 0.77s enter A (inside: 1)
t=11.28s enter B (inside: 2)
t=12.28s leave B
t=15.78s leave A
max concurrent exchanges inside throttle(1).concurrentRequestsMode() = 2 
(expected 1)
{noformat}
Any exchange that holds a permit for longer than 10 seconds after the previous 
permit was returned breaks the limit, which is a typical case for this mode (a 
slow backend that only accepts n connections).

Cause: {{ConcurrentRequestsThrottler.ThrottlingState.release()}} schedules 
{{clean()}} after {{CLEAN_PERIOD}} (10 s), and {{clean()}} calls 
{{states.remove(key)}} without checking whether a permit was taken in the 
meantime. Taking a permit does not cancel the scheduled cleanup.

Proposed fix: only remove the state in {{clean()}} when all permits are 
available and nobody is waiting for one. To close the remaining window where an 
exchange has looked up the state just before it was removed, mark the state as 
removed (under the state lock), and have an exchange that took a permit from a 
removed state give it back and take one from the current state instead.



--
This message was sent by Atlassian Jira
(v8.20.10#820010)

Reply via email to