I know HTML 5 includes support for WebSockets, but I feel it is too soon to rely on them, as the spec is not yet finished and the web clients and servers are really still experimenting with the protocol. Applications have been successfully using the long running request (or worse, polling) to essentially produce the "push" functionality desired. There is a protocol Comet that I have read a little about, and I would consider using it if someone endorsed a great implementation of it that they have used or seen used successfully with an ASP.NET/IIS7 server side implementation.
But it seems not so terribly difficult to do on my own, although I see certain technical challenges that must be dealt with.
- Users must be logged on to use my service. I planned to keep state information in Session variables, most likely tied to SQL Server rather than in memory, so that sessions stay "alive" even if IIS recycles or the thread pool recycles. This is not a "public" app, it will have limited users and limited traffic, so the speed penalty of storing state in the DB should not be a critical issue.
I believe, though, that if my "long running" request accesses the Session, even just to read who is logged on before starting, it establishes a "read lock" that I cannot see how to unlock. So while my long running query is executing, any other concurrent request from the same session (there will be many) that read the Session will be OK, but if any needs to write to the Session variables, they will be blocked until my long running request finishes, as a write lock must wait for all prior read locks to complete. So therefore it seems that I must create my own "Session" in my own database. And I guess I'll need to handle the locks myself if I want. I'm pretty sure my implementation will need just a simple short term lock, for reading or writing, which will simply use a static class object and the "lock" C# keyword (using the Monitor class). I don't anticipate needing to implement both read and write locks for my application.
- 2) Storing state in a database will require me to do my own processing of "expired" sessions.
- 3) I plan to use ASP.NET's IHttpAsyncHandler, which will spin off a thread not in the thread pool to wait until there is data to be sent back to the client. This way long running requests will not exhaust IIS's thread pool. I think a thread per request would be ok, although I should be able to simply register the request in a way that would allow a single background / non-pooled thread to handle all the outstanding requests. I’ve not fully worked out the best way to approach this. I like the single thread idea, I just need to figure out the best place to create this background thread, so it is always there when I need it.
As you can see, I am in the early stages, figuring out the best architecture, finding and reviewing examples and anticipating issues I’ll need to resolve in my design. If anyone knows of a good example of this sort of thing, or has any suggestions based on experience, I’d love to hear it.
The best solution I've found is a product called WebSync. It works in all browsers, using the best technology available in that browser to accomplish the task. If WebSockets are supported, it will use pure HTML5 capabilities, but if not, there are "long running query" capabilities they utilize. The API is a pretty simple "Publish"/"Subscribe" model. Great for .NET developers (it runs in IIS)