Prashanta Kumar Pal
Prashanta Kumar Pal

Reputation: 15

How to make a thread safe rest endpoint

Could you please suggest how to make a rest end point thread safe without doing that method as synchronized?

The problem I am facing is,

Suppose I have some rows in a table in database like below,

table1
id     name    status
---    -----   --------
1      abc     assigned
2      abc     ready
3      abc     ready

and so on.

Now in my PUT call, request body is the name (i.e. abc in this case). I am just selecting the row from that table and updating the status like below,

select id from table1 where name='abc' and status='ready' order by id limit 1;

update table1 set status='assigned' where id = [id from above select query].

If multiple client calling that PUT end point in same time, same id (say "2") is getting returned to more than two clients. The requirement is same id can not be send to more than one client.

Upvotes: 0

Views: 4532

Answers (3)

Pospolita Nikita
Pospolita Nikita

Reputation: 665

I think you should encapsulate you DB logic into another service. Then make this method "Transactional". (If you use Spring: https://docs.spring.io/spring-framework/docs/current/javadoc-api/org/springframework/transaction/annotation/Transactional.html) Your question is not about thread-safe, it's about transactions.

Upvotes: 4

duffymo
duffymo

Reputation: 308763

Your pooled JDBC connections are single threaded. You need to worry about locking and isolation.

Set the isolation level of your database connections to SERIALIZABLE. It will be the least performant setting, but it'll guarantee that there are no dirty reads or writes.

Another choice to consider is non-blocking IO. Your typical Java HTTP listener queues up HTTP requests as they come in, to be handled by a pool of listeners. If the load is heavy, the blocking dequeue will wait until a listener is freed up to process the next request.

You can write your own NIO listener using Netty or vert.x. Incoming requests are handled serially by a single thread, which puts them on an event bus for processing.

Upvotes: 0

JB Nizet
JB Nizet

Reputation: 691715

Just use the following query:

update table1 set status = 'assigned' where name = 'abc' and status = 'ready'

Upvotes: 2

Related Questions