On 8 dec, 14:28, James Reeves <
weavejes...@googlemail.com> wrote:
> On Dec 8, 4:30 am, Lance Carlson <
lancecarl...@gmail.com> wrote:
>
> > Couldn't you make your http framework event based? Then you could do
> > both without too much re-engineering.
>
> Yes, I could create a web framework that does both, but I don't think
> it's a good idea to do so.
>
> Firstly, you can't generate a thread per connection if you want your
> application to be performant. You'd quickly run out of threads, as
> they're relatively expensive (we're talking less than 10,000
> simultaneous connections). Long-polling servers tend to use non-
> blocking IO, so you'd need to write something using java.nio.
>
> This means you'd have to drop Ring compatibility and Java servlet
> compatibility.
>
> Next you'd need to design your framework around a streaming, event-
> based model. In a resource-based model, you need one function that
> takes in a request and returns a response. An event-based model is
> obviously more complex, as you need to be able to assign many
> functions to various events, such as connection, disconnection, data
> received, etc. This would be tying yourself to a single Java HTTP
> server, or writing your own.
I'm not convinced that it would be all that more difficult to write an
event-based web server that would handle typical request/response
cycles and long-lasting connections equally well. Yes, you'd probably
have to give up the servlet API and definitely the one-thread-per-
connection model, but IMO both are mistakes anyway. AFAIK there's no
clojure-based event system right now, but one could probably be
written, and I suspect it could work pretty well even if you'd
probably have to take more care about how to handle your state; though
"typical functional" clojure's is pretty close to what you'd need,
there's some nooks and crannies that don't seem to support event-
based, multiple-interleaved-actions-in-a-single-thread much - like the
ref-type synchronization mechanisms, which all seem to assume that
each task/transaction runs in its own thread. Still, I think for a
network server, you don't really need all that much shared state
anyway.
As for compojure, there's two things that currently make this kind of
scheme an uneasy match:
One is the use of dynamic variables (*errors* and *params* are the two
that stand out most) - but I'm already writing my code to keep the use
of them to a minimum, and I think it wouldn't be too hard to get rid
of them completely with only minimal extra code and a couple of useful
macros.
The other is the aforementioned lack (in both Java and clojure) of a
generic event framework for web servers, meaning it would probably be
hard to port from one server to the next (although I don't think there
even are all that many event-based webservers for Java, and personally
I don't really care that much about portability anyway if I can get a
single good server to work with). If you're willing to submit to a
single implementation for the time being, I think many of the features
in compojure could be kept intact or would only need minimal changes,
since most of it pretty much functional anyway, but the core request/
response "simple function call" interface would have to go in favor of
some kind of event/callback mechanism.
If all this comes across as condescending to compojure, I want to
assure all of you that wasn't my intention. As a matter of fact I'm
working on a compojure-based project right now and it's the most fun
I've had in a year. :)
As an aside,
http://mina.apache.org/ looks sort of interesting to me,
though I've not researched it much yet.
Cheers,
Joost Diepenmaat.