I'd like to hear your opinion, what will be the best option to implement websocket queue using Spring and STOMP protocol, when there is no user session (stateless, restful web app).
Based on this explanation: https://stackoverflow.com/a/31577152/3076403 I know that Spring will use the queue when we use simpMessagingTemplate.convertAndSendToUser(...) method and pass the username associated with session id. Otherwise it will use a topic, where all subscribed clients will eventually read the same message returned from the server.
In my case, I have a RESTful app with Angular UI part. I want to implement the progress bar on the UI side. Initially UI sends the message to the server, with given ID that was determined earlier, ex: {id: 20}.
Then, the UI have to listen on the changes of the returned model for the particular ID and calculate the progress of internal processing. The message back can look like this: {id: 20, timeLeft: 30, totalTime: 60}
So for each Angular app that will subscribe to the websocket channel on the server, it should give different results.
As I have no session in the app and have to implement the websocket queue on the server, do you know other solutions using Spring and STOMP protocol different from that one I recently came up with:
Spring: simpMessagingTemplate.convertAndSend("/ui/progress/"+id, ...)
UI ng-stomp: $stomp.subscribe("/ui/progress/"+id, function(...))
I know that this will be a "fake" topic, rather than queue. Any comments and ideas appreciated.
Related
I would like to allow to external service consume my RabbitMQ queues, the question is that I don´t want to give direct access connect to RabbitMQ I would like to expose through a Gateway / API Manager / Rest Endpoint.
I´m not sure if this is possible, but I would like to know some way to leave events in a queue that can be consumed by external services exposed in a security way or centralized like Gateway.
Thank you everybody that response : )
You might try to create a callback service.
What the system will do is it will accept (or even store) POST URLs. When your own queue consumer consumes a message, what it will do is just send the queue message (maybe with add-on data) as a callback to the URLs you have stored. Then the servers the URL belongs to will do whatever they need to the messages sent by your callback service.
As answered by #KaNa0011, callbacks can be a solutions but this put some more responsibility on the producer (what if the receiver is not available ?)
Another approach is to expose your events as an Atom feed, this is something that is explained here by Oliver Gierke in his talk "Refactoring to a System of System" : https://youtu.be/MEySjYD86PQ?t=5487
I have a RESTful web Service that provide function of returning some data whenever a client send GET requests to ask for it:
#GET
#Path("/{deviceId}")
#Produces(MediaType.TEXT_PLAIN)
public String getDataResource(#PathParam("deviceId") long id){
return dataService.getData(id);
}
And the flow for this case would be the client sends request -> the web service returns value. But I want to ask that is it possible that the web service will automatically send response to the client when ever it has new data change inside of it? That means it not need to wait for the client to send request to ask for it. Because I would like to establish a communication between a client and some services running on an Application Server so that the client can always receives the newest data from the Application Server, so I think RESTful web Service can be a solution for it. And in oder to be ensure that the newest data will be transfered to the client side, so the server has to send to the client, not wait for the client to ask for it. Is RESTful web service provides any function like this?
Thank you all!
Is RESTful web service provides any function like this?
No. Not in the context you're asking for.
As answered before, the client could periodically poll for updates on the server. This is usually common option.
Another option - the original server posting updated on the "client". The client then becomes server itself. Viable, if you can expose services on the "client" side.
Maybe what are you looking for are web sockets. It is a long-lasting connection from client, where the server could keep returning data as they come.
There are some books around but you could search the net for more resources depending on the framework you use
You can implement notification system(observer pattern), so that client will poll the server in certain interval and any state change, it can get the result.
You may use the Schedulers to push the data to the client in a certain intervals.
I am trying to implement a web socket session manager and I have just encountered a road block that I hope someone can assist me with.
Basically a client will initiate a web socket session with my websocket server endpoint and I will take the HTTP request parameters, parse it and subscribe to web service producer endpoint. The Web service will return a response containing a subscription identifier of which will use as a key mapping (along with the HTTP session ID) to add to a java map cache with the session object. The proceed to send data to my published webservice consumer endpoint. My application will then take the data received from the producer, use the subscription id that comes with each packet and find the right session in the map caches to send the data back to.
Here is my problem..
I noticed that if the client opens another tab in the browser and sends a second subscription request, it would still be sent with the same HTTP Session ID yet tomcat will still be able to stream the data to the correct tab. This implies that the tomcat websocket implementation has a built in multiplex handling mechanism.
To exclude some unnecessary details unless asked, I want to to also be able identify all the channels that were multiplexed under the same session id. But I can't find any way in the API to identify it. As I need to be able to look up my map caches and remove sessions for tabs that have been closed (which triggers a close method in my web socket endpoint), but I'm not going to be able to do that as there could be many sockets/channels associated with the same HTTP Session ID.
The websocket framework does not provide any such implementation. Every tab opens a new socket. You can maintain a session info through adding a key in the request while initiating the websocket and on message check for that key(eg JSESSION id value) in the server and serve the request accordingly.
I am quite new to web services, JAX-WS etc. so maybe noob question...
So, I want to implement a web service to make two systems communicate. The "client" system is interested in events that are generated on the "server" system. But the "client system" is itself a server for a different app. The server is Java (WAR in tomcat). The client is .Net.
There should be just one client system, but several client processes inside the client system, each interested in distinct categories of events.
I will implement the server-side, and a test client. Somebody else will implement the .Net code.
The running sequence should be along this line :
Server is running...
Client initiates conversation, "registers" to the server, and requests some initial data.
Server keeps a list of registered clients' endpoints
In the server there is a listener that is notified when certain events happen. It will then go through the list of registered clients and forwards the event to each of them
At some point, the client can "unregister" no notify the server that it doesn't want to receive events any more.
First, does it sound like something reasonably doable ?
And is there a standard built-in mechanism, using SOAP (JAX-WS on the server, whatever is available with .Net n the client) - that the server can use to obtain a callback endpoint from the client ?
For example, I did something very similar using RMI, in this case the client can just send a remote reference to itself, that the server can just store ant refer to later.
Finally, is there a standard library to store endpoints references, make (collective) callbacks, and maybe keep the list up-to-date, removing the clients that don't respond so some "ping" call ?
Note for clarity : I need more than just asynchronous method with callback: one message from the client will generate many callback messages from server to client.
Seems you wish to implement a notification facility to inform arbitrary anonymous clients.
I suggest you first consider how you would pass the information using SOAP messages. Then you can consider how to achieve this using java - JAX-WS or additional non-standard libraries. The point is there may be significant limitations or assumptions required to transfer SOAP messages. E.g. firewalls might block your HTTP messages, clients might "just clients" with no ability to act in a server role to recieve SOAP notification requests
Note: An async callback mechanism is defined in JAX-WS 2.0, where the service obtains the endpoint reference of the client. This is the same sort of functionality provided by WebLogic/Fusion proprietary solution described by Deepak Bala. Websphere has a similar proprietary async solution. None of these meet your requirements, because they only allow a single response per request.
SOAP Options:
Proprietary SOAP messages - the "100% Do-It-Yourself Option"
You design full SOAP payload schemas and message exchange pattern.
You can push the notification from the server to the client if you know the client's SOAP endpoint address. The client can transfer it's SOAP endpoint address within original SOAP request payload. Sometime later the server can send a SOAP request to the client.
Problems/Assumptions: (1) need a SOAP/HTTP communication path for requests from server-to-client - not guaranteed when firewalls exist; (2) the client needs to be aware of your notification schema - in fact the client needs to act as a Service endpoint to recieve the SOAP notification request. That's two big assumptions IF you are trying to support arbitrary anonymous clients - that's not something SOAP "just supports" both ends need to design all this in detail. In fact to do this in a service typesafe manner, the client should actually declare it's own service WSDL interface so that you can invoke it. (3) As hinted earlier, many clients are "just clients" - they might not have a HTTP server to accept SOAP requests.
So for proprietary "push" notifications to work, both sides need to servers and both need to publish their SOA interfaces.
Alternatively, you can pull the notification to the client. The client can use a notification request to the server that is either blocking or polling. The server can respond with the notification or nothing or error.
Problems/Assumptions: (1) HTTP servers (i.e. the SOAP server) do not support blocking requests, as a rule, meaning you must poll; (2) the client needs to be aware of your notification schema - in fact the client needs to act as a Service endpoint to recieve the SOAP notification request. That's two very big assumptions for an arbitrary anonymous client - that's not something SOAP "just supports" both ends need to design all this in detail. In fact to do this in a service typesafe manner, the client should actually declare it's own service WSDL interface so that you can invoke it.
Same as above, but make include WS-addressing data in SOAP headers to inform either side of the other's endpoint address.
Basically the same Problems/Assumptions as the first option. WS-addressing addresses will help you intelligently route SOAP messages to the right URL address, but no more.
Use WS-notification
This spec was designed for your scenario.
WS-BaseNotification sub-standard would meet your needs. It provides WSDL port definitions for notification producers and consumers. It provides a WS- standards compliant solution for subscription from a consumer to a producer, and a notification from producers to consumers.
Problems/Limitations: (1) It does NOT define the format of notification payloads. The Notification payload is application-domain specific (proprietary design). The standard does not define any “standard” or “built-in” notification situations or messages. (2) It has the same problems with HTTP notifications passing through firewalls as mentioned above.
(3) WS-Notification is not a supported standard of Java EE/JAX-WS (but there are plenty of app servers, open source and commercial, that support it as an extension).
Use a message queuing solution (e.g. JMS) with traffic encapsulated in HTTP
This requires proprietary design of payloads passing between client and server and back - forming contracts between the two sides. An advantage is that the client can be a pure client, with a message listener invoked in a thread when a message is recieved.
Problems/Limitations: (1) It has the same problems with HTTP notifications passing through firewalls as mentioned above. (2) Is a do-it-yourself implementation. (3) Uses more technology then you currently use.
End Result:
You need at least part of your solution to be a proprietary design - the SOAP/WS standards do not meet your full requirements. In theory this proprietary design could leverage a product to provide much of the legwork, BUT the notification schema design would need to be created and integrated by you.
IF you wish to push notifications, you need some sort of contract for notifications passing to the client, the client needs to act as a SOA server, and you need the firewalls openned for your traffic. Most corporations disallow HTTP requests leaving a server and passing to a client - you normally need an extremely good reason to open firewall ports and even then, many corporations will disallow it...
IF you wish to have clients polling for notifications, you just need a basic WSDL interface on the server side that can be called frequently by clients.
Future Option: HTML5 Web Sockets
IF your client is a HTML5 app, then web sockets enabled servers can push traffic to the browser - and there is some chance corporations will open firewalls. SOAP messages could travel over HTTP web sockets, enabling you to push notifications.
Async clients are supported for WSDL based services through the use of polling and callbacks. In your case I think the requirement is relatively more complicated.
The Oracle fusion middleware doc page has a scenario outlined that will help you. It details a method that allows clients to send requests which generate a HTTP 202 (accepted) and the clients then wait for a response on message queues. In your case the scenario can be tweaked from the one shown below.
Initiate several response queues for each category of callback. The clients can filter them by supplying a client and category ID for the queue. This will serve as a callback mechanism for each client or the processes that are governed under each client. The MDB can be backed by a file store or DB store to ensure reliability and one-time delivery.
Of course you do not need Oracle fusionware to implement this. You can use RabbitMQ or Redis (with transactions) to acknowledge receipt of a message on the client. If your client wishes to un-register it make a call and stop listening to the queue.
I'm unaware of any industry standard that will fit your scenario, but I believe this solution should work well for you.
Have you considered the simpler approach of "pub-sub" using a messaging product ?
(Such as MQ, EMS, or ActiveMQ)
The requirements you describe does not seem to fit "classic" request/reply sync/async SOAP Web Service scenarios.
In a Pub/Sub solution, the client(s) subscribe to a topic once, and the publisher(s) (in your case, the Server) can post any number of relevant messages to all subscribers.
As a bonus, most messaging products include support for "durable subscribers", so the client can be off-line at times and receive all messages after re-connection.
In your case, the server could house a (free) ActiveMQ Server... Providing most of the feature you seem to seek.
If you go that way, I suggest you pick a JMS compliant product with support for .Net.
For those getting here from search engines:
You can use a WebHook for Web APIs nowadays, which works essentially as OP described.
In REST for example, the client will have an HTTP endpoint itself that is dedicated to receiving POST events/notifications from the actual server. The client registers his endpoint with the actual server by giving it an URI on his notification endpoint. From that point on, the actual server can POST to the client’s notification endpoint. It is essentially a convoluted callback, if you are familiar with async terminology.
Maybe Java or .Net have libraries for WebHooks by now.
That said, SSE and Websockets standards provide actual push and real-time messages while being compatible with HTTP and most browsers.
Long polling variations were also used in the past, and are now sometimes called Comet as an aggregate.
For a web service application, I would like for the server to be able to notify the clients about some events. When a client is launched, he calls one of the WS methods to get some information it needs. Then the server, that stores this information, listens continuously for changes on these information and if there is a change, it notifies the concerned client.
I don't know if a web service is a good solution to my problem? I don't know how it may work concerning the TCP connections, since the server may notify a client after a very long time.
What would be the best architecture to solve this kind of issue?
Thanks
EDIT: I've looked at some discussions that propose to use Comet, but if you think there are simpler and more convenient solution, please let me know. Since I'm starting this project from scratch, I have no limitations.
I can also use a polling model where the clients periodically poll the server for the information they need, but then I need to take into account the load that this model may create on the server. I don't know if web services can support such a load when there are a lot of clients.
I've also looked at the asynchronous functionality provided by Servlet 3.0 but I don't know how it may solve my problem.
Without polling: sockets
With polling and webservices: u should use etag (html).
When a client polls he sends a request with an etag. webservice responds either with 200(ok) and data or 304(not modified). 304 has no body => less trafic
Instead of client polling the server, you could implement a callback method on the client so that when ever server want to publish some changes to the client, the server can use the callback method provided by the client.
I can think of one the two approaches below using web services solution:
Callback: When client invokes the server it leaves its call back url and a id, say correlation id. When the server wants to respond back to the client it will just use the call back url to notify. The Server can use a variety of approaches to process the request asynchronously. Your client need not be a webservice for this, but it should be capable of accepting requests (callback). It can be a servlet etc.
Polling: When client makes a request to the server it receives back a id, say requestid. After specified interval client polls the server with this request id to fetch a response. A reasonable timeout and polling interval based on the processing time would be required.