I have a Spring Boot application that is pushing JSON messages to a queue, and in the other place it is consuming those JSON messages using #JmsListener. Those messages are then send via HTTP Post request. The response code might be 200 and that's OK, but I would like to handle situations when client is down or just simply response code is different than 200.
Is there any mechanism that I could use for retrying the messages? Maybe I could push back the message at the end of the queue and retry them for lets say 3 times? Is there any internal ActiveMQ mechanism for doing that after message was actually dequeued?
Sounds like you are looking for a transaction between the consumer and HTTP Post. JMS won't acknowledge the message off the queue until your code calls session.commit(). You can then call up to one HTTP endpoint and maintain reasonable transaction and single message delivery quality of service.
The key to making this self-healing is to detect invalid message payloads (ie bad JSON format or bad data) and move those messages into a DLQ.
Look into adding JMS local transaction support instead of using AUTO_ACKNOWLEDGE
connection.createSession(true, Session.SESSION_TRANSACTED);
Then in your psuedo-code:
Message message = session.receive ..
.. do valid message checks
.. call HTTP endpoint..
// now take action based on HTTP return code
switch(httpReturnCode)
case 200:
session.commit();
case .. invalid message returned from HTTP:
.. produce message to DLQ for inspection
session.commit();
case .. http not available..:
.. do some time delay, retry to http endpoint
Related
I need to write an API, when client invoke that API it publish message on request topic of MQTT and wait for response on response topic. If response topic doesn't return anything then API should return default response.
My problem is while consuming message from topic. I am able to publish but how I can wait for response (to consuming message) for a specific topic and send it as response or after specific time send default response of API.
I am using Spring 4, Java.
You can implement steps:
Your HTTP server receive a request and publish a request message with an unique correlation-id to MQTT, and create event loop E to wait message response
Consumer C1 consume the message and handle, then response (publish) a message with the same correlation-id to MQTT
Consumer C2 in your HTTP server consume the response message and give it to event loop E
Event loop E break a loop and return message response to HTTP client
I am using Java servlets using Apache tomcat.
I've configured a threadpool and am dealing with each request.
My page is taking in many GET requests at the same time, I'm wondering if I can respond to the server after each get request before any of the logic happens?
So server gives me a request -> I respond with either 'good send another' or 'bad send another' before I start my queueing.
Any help would be much appreciated!
EDIT
Sorry that was terribly written :(
What I'm asking for is a way to send a Header to the client (in this case it's a server which sends me lots of requests). The response would just be 200 or error based on the information I get sent.
What my program is doing:
My servlet gets sent lots of GET requests from one client. (over 100,000) Which I am using tomcat to queue and put into a threadpool. It is then assigned to a worker thread which processes it and puts it into a database.
I've been told to do is send a request back to that server saying 'ok received it'. I think I can use a header response but I don't have the URL of that client (and the client can change for different campaigns). So was wondering what the best way would be to send that response.
After doing some more research I think what I'm looking for is ServletOutputStream.
response.setContentType("text/html");
ServletOutputStream output = response.getOutputStream();
output.flush();
output.close();
Using servlet output stream where do I set the <head><body> tag? and insert the header response afterwards.
The simple answer is "sure".
If these are get requests from a web page for a web page, include a refresh timer and send back some token that can be used to identify the difference between a first-time-request and an I-requested-earlier-are-you-done request. In this case the refresh timer can be set via a meta refresh tag.
If the get requests are part of a REST API then you can define "got it and I'm working" into the protocol. For instance, return a 202 to indicate "got it but not done" and return 200 to indicate "done". As with the html page, consider sending some token back with the 202 that identifies the pending request.
I'm implementing a http client app with Netty. The task is to send the same request to several endpoints and collect the answers for further processing. Many such requests can be sent concurrently to the same endpoints. The problem is to match responses received from one endpoint to requests.
One possible solution is to create a new handler (and pipeline) for each request as describe here https://stackoverflow.com/a/7905761/4926576. In this case request can be mapped to handler and handler can store the response. But this means creating new connection for each request which will degrade the performance.
I also don't want to change the protocol and include request ids in requests/responses only for the purpose of matching.
If both the client and server are respecting HTTP pipelining semantics, then the server must respond to requests in order. Therefore, for each connection, you can maintain a queue of requests. Each new request goes on the back of the queue and each response pops it's matching request from the front of the queue.
In the event of connection failure the queue also provides you with the list of requests that were sent but for which you have not received a response. You can then take appropriate error correcting action for each request.
I'm reading the OSCWCD books by Charles Lyon on section about asynchoronous request. It says that in a asynchronous cycle, one can dispatch even when a response has been committed. I don't understand why so? Any insight would be great!
The general approach for asynchronous approach is that client will open a new channel to receive the asynchronous response and will provide the handle of that channel to the server. The asynchronous response is not sent on the intial client request/response channel, rather it is sent on a different channel, which remains active till the client does not receive the asynchronous response.
If client is not able to provide any channel for the server to send the asynchronous response, then another approach is to use the polling. In this case, server as part of the intial request response, will provide a polling URL. The client can poll it periodicall, and when server has the response ready, will return the response. When server does not have a response, it should return a meaningful in-progress message.
Is it possible to make GET & POST requests in Java or another language such that you don't care about what is returned?
As in just sending the requests but not wanting to receive any responses?
Whether you care about the response or not, it will be sent. The HTTP protocol specifications say that it must be.
If you don't care about the response, your client could just close the connection immediately after sending the request. But the chances are that you do want to know that the request was processed (i.e. the response status) even if you don't want to look at the contents of the response message.
So maybe you could send the request and request body, and read the response status and then close the connection without reading the response body. However, this has a downside. It means that you can't reuse the HTTP connection to make further requests. The next request to the same server has to open a new connection.
You could use anynchronous HTTP requests if you don't care about the responses (that way your worker thread will not have to wait for the response to come back). See http://www.javaworld.com/javaworld/jw-03-2008/jw-03-asynchhttp.html for some details on Asynchronous/Synchronous HTTP queries in Java. Then you can control if the anychronous thread does or does not handle the response (or any failure flagged on the communication) - as long as there were no TCP level failures on the request the connection will still be opened.
You can't control whether or not the server returns a response. Your code is free to ignore any response it receives.
It's pretty hard to not get responses because they're part of the HTTP protocol. but you can certainly ignore the responses.