I am working on a MVC application using asp.net which contains 4 portion which need to be updated in real-time.
I started this with having different hub classes in signalR. But it turns out that signalR is making 4 different connection one for each portion to support this which is increasing the load over server and sometime it is not at all possible to have more than 2 connection.
Curious to know if there exist any way by which I can handle using only one connection.
In short,
One application -> 4 signalR portion need to be handle by 1 signalR connection.
One page can connect to multiple hubs without issue. It will be over one connection, so nothing to worry about. It's dead easy with the generated proxy (see http://www.asp.net/signalr/overview/guide-to-the-api/hubs-api-guide-javascript-client#genproxy).
You will get a different connectionId for each hub, but that shouldn't be a problem.
Related
We're planning on adding SignalR to several differnet web applications. The applications are targeted different aspects of an order. When something happens to an order, all users working with the order across all web applications should be notitfied.
Changes to an order are availible asa message on a servicebus.
We could implement the following logic in all web applications:
Subscribe to a topic (one subscription per webapp)
OnMessage -> Send orderId to hub
Hub would notify clients working on the orderId
Question is: Could we implement all this common functionality in a separate application, and all web apps would reference the same signalr scripts?
All applications live on the same domain, and it would give us a lot of benefit not having to implement signalr in every app.
Good idea, or am I missing something important here?
Edit: Put in other words: I have WebAppA, WebAppB and WebAppC all without SignalR. I'm asking if its possible to create a WebappD that talks to clients in WebApp A,B,C
Second Solution is very good. it will move signalr load (espcially memory) from your main web apps to WebAppD(signalr web app). And all your main web apps will not be dependent to signalr.
Drawbacks: You don't have any authentication on WebAppD. Because clients are authenticated on the other WebApps. You should let the WebAppD knows about orderId. That's why, you should send message to server (WebAppD) from clients(Javascript).
Because of enable cross domain settings, anyone can send message to server. Even they don't need to be connected WebAppA,WebAppB or WebAppC. Even if you solve this problem (virtual path etc), Someone is connected but not authenticated on WebAppA,WebAppB,WebAppC can sends message. Because WebAppD just get the message and it doesn't know this client is authenticated or not so it will serve this message to all others. In Short: Someone can send fake messages to other clients.
So you should share your authentication like this (or some other logic) between your web app and signalr webapp.
Other than this I couldn't see any drawback.
I am running a site in which I am using SignalR with a custom scaleout backplane that allows us to push out real-time data to users connected to any of our load balanced web servers.
I recently found out that the Kendo UI components for MVC (which we use for other site features) can be configured to use SignalR rather than AJAX for binding with the data model. It seems like using web sockets via SignalR could potentially offer a performance boost over using AJAX as we are now. However, I would ideally like to let our kendo components access a SignalR instance that only uses whatever web server they connect to rather than using the instance with the scaleout backplane since that would involve a lot of overgead that isn't necessary for that data binding.
I should mention that there would be cases where we would have one page with one partial view that uses one SignalR configuration and another partial view that uses the other.
Is this something that can be done? If so, are there recommended ways of going about doing so?
I am not entirely certain about your approach but you can of course have 2 SignalR servers using different kinds of backplanes and connect to the 2 servers from a client. You would have to though look into how to handle cross-domain requests with SignalR.
I'm developing an application that has various types of Notifications. Examples of notifications:
Message Created
Listing Submitted
Listing Approved
I'd like to tie all of these up to SignalR so that any connected clients get updates in real-time.
As far as architecture goes - right now the application is entirely within a single solution hosted on an Azure Website. The triggers for each of these notification types live within this application.
When a trigger is hit, I'd like to tell signalR, "Hey, send this message to the following clients" along with a list of userIds. I'm assuming that it's possible to identify connected clients based on userId... and I'm assuming that the process of send message to clients should be executed outside of the web application, so as to not slow down the MVC app or risk losing data in a broken async call. First question - are these assumptions correct?
Assuming so, this means that I'll need something like a dedicated web/worker role to be sending messages to clients. I could pass messages from my web application directly to this process, but what happens if the process dies? The resiliency concerns lead me to believe that the proper way to pass messages would be via a queue of some sort. Second question - is this a valid train of thought?
Assuming so, this means that I can either use a good ol' Azure SQL database as a queue, but it seems like there are some specialized (and maybe cheaper) services to handle message queueing, such as this:
http://www.windowsazure.com/en-us/develop/net/how-to-guides/queue-service/
Third question: Should this be used as a queueing mechanism for signalR? I'm interested in using Redis for caching in the future... would Redis be better or worse than the queue service?
Final Question:
I've attempted to illustrate my proposed architecture here:
What I'm most unclear on here is how the MVC app will know when to queue, or how the SignalR processes will know when to broadcast. Should the MVC app queue blindly, without caring about connected clients? This seems to introduce a lot of wasted space on the queue, and wasted cycles in the worker roles, since a very small percentage of clients will ever be connected.
The only other approach I can think of is to somehow give the MVC app visibility into the SignalR processes to see if the client is connected... and if they are, then Enqueue. This makes me uncomfortable though because it means I have to hit that red line on the diagram for every trigger that gets hit, which - even if done async - gets me worrying about performance and reliability.
What is the recommended architecture for scalable, performant SignalR message broadcasting? Performance is top priority, followed closely by cost.
Bonus question:
What if some messages are of higher priority than others? Should two queues be used, one of which always gets checked before the other?
If you want to target some users, you'll have to come up with a mechanism, off the top of my head I can give an example, if any user hits a page, you can create a group for that page and push to all users in that group/in that page.
It's not clear to me why you need the queues. Usually users subscribe to some events when hitting a page or by some action like join a chat room, and the server pushes data using those events/functions when appropriate.
For scalability, you can run signalr in different servers, in which case you should use sql server, or service bus or redis as a backplane.
Firstly you need to create a SignalR server to which all the users can connect to. This SignalR server can be created either in the web role or worker role. If you have a huge user base then its better to create the SignalR server on a separate role.
Then wherever the trigger is hit and you want to send messages to users, you have to create a SignalR client (.NET or javascript) and then connect to SignalR server. Then you can send the message to SignalR server which in turn will broadcast to all the other users connected. After that you can disconnect the connection with SignalR server. This way you dont have to use queues to communicate with the SignalR role.
And also to send messages to specific users you can store the socket id's along with their user id's in a table (azure table storage should do) when they connect to SignalR server. Then using socket id you can send messages to specific user.
I've downloaded the last Signalr.Redis package (v0.1) and I've compiled the last Redis source code (2.4.26).
I tried to run Redis on my local pc (server and client work well) but when I start SignalR with Redis as a message broadcaster, it seems that signalr wants to start multiple connection to server (same server=localhost but multiple port number).
I know that Redis integration with SignalR is new and perphaps buggy, but is it possible to work with redis+signalr on local machine or is not a supported scenario?
Thanks.
SignalR will attempt to make a variety of connections to the server in order to keep an open connection. For most browsers it ends up long polling the server (which results in multiple requests regardless). What I ended up doing was using allowing SignalR to connect in a normal fashion to my MVC app and then call actions on my controllers which in turn communicated with Redis. This gives me the added benefit of being able to perform business logic in between. Not sure I answered your question, but I just wanted to share how its worked for me.
I have an existing complex website built using ASP.NET MVC, including a database backend, data layer, as well as the Web UI layer. Rebuilding this website in another language is not a feasible option.
There are some UI elements on some views (client side) which would benefit from live interactivity, involving both push and pull, so rather than implement some kind of custom long polling or websocket server in asp.net, I am looking to leverage node.js for Windows, and Socket.io.
My problem is that I need two way communication between both applications. Each user should only be able to receive data once they are authorised on the ASP.NET website, so I first need communication for this. Secondly, once certain events occur on the ASP.NET website I want to immediately push this data to the Node server, to be broadcast to specific users or groups of users. Thirdly, I would like any data sent to the node.js server to be pushed to the ASP.NET website for processing, as this is where all our business logic lies. The sole reason for adding Node.js is to have the possibility to push data directly to the client, I do not want to build any business logic into it (or as little as possible).
I would like to know what the fastest method of two-way push communication is between Node.Js and ASP.NET. The only good option I'm aware of so far is to create a special listener on a specific port on the node.js server and connect to that, but I was wondering if there's a more elegant or more efficient method? I also know that you could use a database inbetween but surely this would need to be polled and would be less efficient? Both servers will be running on the same server under a Visual Studio project.
Many thanks for any help you can provide.
I'm not an ASP.NET expert, but I think there are multiple ways you can achieve this:
1) As you said, you could make Node listen on a specific port for data and then react based on the data received (TCP)
2) You can make POST requests to Node.js (HTTP) and also send an auth-key in the process to be extra-secure. Like on 1) Node would react to the data you send.
3) Use something like Redis for pub-sub, send messages from ASP.NET (pub) and get them on the Node.js part (sub). This is even better if you want to scale your app across multiple machines etc.
The only good option I'm aware of so far is to create a special
listener on a specific port on the node.js server and connect to that,
but I was wondering if there's a more elegant or more efficient
method?
You can try to look at redis pub/sub model where ASP.NET MVC application and node.js would communicate through separate channels in order to achieve full-duplex communication. Or you can also try to use CouchDB change nofitications.
I also know that you could use a database inbetween but surely this
would need to be polled and would be less efficient?
Former techniques do not require you to poll for changes, but instead they will notify you when the changes happens or channel message arrives.