0% found this document useful (0 votes)
14 views4 pages

Semaphore Bulkhead in Microservices

The document discusses mechanisms provided by Resilience4j for building fault-tolerant microservices, focusing on the Bulkhead pattern. It explains two types of Bulkheads: Semaphore Bulkhead, which limits concurrent calls using a counter, and Thread Pool Bulkhead, which assigns dedicated thread pools for each service to prevent blocking. Additionally, it covers the Time Limiter, which prevents asynchronous calls from hanging indefinitely.

Uploaded by

Muni Msd
Copyright
© All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PDF, TXT or read online on Scribd
0% found this document useful (0 votes)
14 views4 pages

Semaphore Bulkhead in Microservices

The document discusses mechanisms provided by Resilience4j for building fault-tolerant microservices, focusing on the Bulkhead pattern. It explains two types of Bulkheads: Semaphore Bulkhead, which limits concurrent calls using a counter, and Thread Pool Bulkhead, which assigns dedicated thread pools for each service to prevent blocking. Additionally, it covers the Time Limiter, which prevents asynchronous calls from hanging indefinitely.

Uploaded by

Muni Msd
Copyright
© All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PDF, TXT or read online on Scribd

Bulkhead: Fault-Tolerant Microservice (Part-2)

Wednesday, 16 July 2025 5:50 AM

To build Fault tolerant microservices: Resilience4j provides below


mechanisms

(already covered in Part-1)


Rate Limiter

Retry Bulkhead
Resilience4j

Circuit Breaker Time Limiter

Lets see in depth of:


Bulkhead:

Rate Limiter:
• Protects our application from our clients by limiting how many requests we accept within a
specific time window from them.
• also Rate limiter never talks about the concurrency.
Ex: let say our application is "Order".

Req at 1st sec

Client Req at 2nd sec Order


Req at 3rd sec
Req at 4th sec
Product
Req at 5th sec

Too many
requests, request
limit is 4 in 5sec.

Bulkhead:
• It helps to control how many concurrent requests can go to downstream service.

Ex: let say our application is "Order"

Use-Case: Let say, "Product" is small and light weight service and can only handle 3 concurrent
request.

(3 calls at same time)


Client Order

Product

Only 3 concurrent request is allowed, 4th


request will be either blocked or rejected
until one of the previous ones completes.

Above use case is resolved through "Semaphore


Bulkhead"

• It also protects our application from our downstream services by limiting how many threads
we allocate to them.

Use-Case: Let say our Order Service has 2 APIs (endpoints)

API 1 : make a downstream call to Product service.


API 2 : make a downstream call to Payment service.

Product service takes ~100 milliseconds to process a request (Fast Service)


and
Payment service takes ~5second to process a request (Slow service)

What if there is a sudden spike in API 2 traffic and more and more calls are made to Payment service (say calls are not
concurrent).

Since Payment service is slow, it holds or blocks the thread longer( for ~5seconds) and its possible that all the threads of Order
service now blocked (by Payment service only).

Now even the Order service fast endpoint (API 1) becomes unavailable as there is no threads available.
Order
Product (fast service)
Client API1
No more
threads
available

API2 Payment (slow service)

(all threads blocked because of slow service)

Above use case is resolved through "Thread Pool


Bulkhead"

Bulkhead

Semaphore Bulkhead Thread Pool Bulkhead

Semaphore Bulkhead:

• Limits the number of concurrent calls using


counter.

• If the limit is reached, further calls are


rejected immediately or blocked for specific
wait time.

it limits the number of concurrency call, via Semaphore Lock.


I have already explained in depth about Semaphores in
Multithreading topic of Java playlist. Have a look if there is
any doubt with Semaphore locks.

[Link] dependency

[Link]

Accepted values for maxWaitDuration: It accepts values in the following format:

<number><time-unit>

Supported time units:


• ms — milliseconds
• s — seconds
• m — minutes
• h — hours
• d — days (not typical, but valid)

Example:
[Link]=0 # Reject immediately
[Link]=300ms # Wait 300 milliseconds
[Link]=2s # Wait 2 seconds
[Link]=1m # Wait 1 minute
Thread Pool Bulkhead:

• Assign a dedicated thread pool for each service.

• Only that pool is used to call the downstream.

If you have any doubts, how Thread Pools and Thread Pool Executor works, kindly have a look at this video in
Java playlist, I have already discussed in depth.

• The AOP proxy intercepts your method call.


• It submits your method to the Bulkhead's thread pool (configured via [Link]).
[Link](() -> {
return ourMethodLogic(); // The whole method body runs here
}, bulkheadThreadPoolExecutor);

• It returns a CompletableFuture to the caller for async response.


• Inside your method, [Link](...) just wraps the result in a completed future — it does
NOT run anything in a thread pool.

[Link]

ThreadPool for productService will be created with these configurations.

Testing the Output:

Just added [Link] for testing purpose.

Output:
Max thread pool size is = 3 and Queue size is = 2

Invoked the API 6 times, lets see the output:

Thread1, RQ1
Thread2, RQ2
Thread3, RQ3 and RQ4 and RQ5 is inserted into the queue
RQ6 is rejected, as there is no thread available and no space in queue
Thread1 becomes free and picked RQ4 from queue
Thread2 becomes free and picked RQ5 from queue
Time Limiter:

• Time Limiter is used to prevent async call from hanging indefinitely.


• Time Limiter is non blocking in Resilience4j.
• Means, it is mainly designed for asynchronous operations, that returns a reactive type like
Mono, Flux etc.

But currently we have covered Blocking calls like RestTemplate, RestClient and
FeignClient.
And we have already covered how to control the time out of the blocking calls.

Feign Client example:

Time Limiter context is same but for reactive calls. Will cover TimeLimiter, when will start Spring Web
flux (reactive programming)

You might also like