networking - What are the benefits of java.nio for a web server? -
i know recurrent question , have read articles following 1 http://www.mailinator.com/tymapaulmultithreaded.pdf saying not true nio scales better io.
but struggling see how java nio scales better when developing web server traditional acceptor/worker threads architecture ? let me explain:
usually java web servers use following pattern handle connections:
a few acceptor threads limited number of cores block on serversocket's accept() method:
while (true) { socket = serversocket.accept(); // handlerequest submits socket queue handlerequest(socket); socket.close(); }when client socket retrieved submitted non-blocking queue , processed worker thread pool of worker threads. number of worker threads depending on duration of io operations being performed.
how using java.nio make architecture more scalable ?
i mean still need have worker threads process request blocking operations (access database or filesystem, invoke external services). if backend operations not performed asynchronously in node.js, still need worked threads limit overall scalability vs 1 or 2 event dispatcher threads.
i paul tyma's article on issue, in-depth. i'd see 2 main points in article:
- you can better throughput traditional, blocking io (he measured it)
- traditional, blocking io makes server logic way less complex -- state of client-server dialogue implicitly defined in thread flow.
the main reason use non-blocking nio when have many, many simultaneous, idle requests. reason is: nio can serve multiple requests same thread, , better.
ok, can read everywhere. now... why better?
there 2 main reasons, related 2 different kinds of overhead come each thread:
- when scheduler changes thread processor executing, there's "context switch", can expensive operation (ie, thread has state in processor -- values in registers, tons of data loaded in l1, l2, l3 caches, etc -- has "saved" somewhere when thread stops , "reloaded" when thread continues executing; also, when lose contents of l1, l2, l3 caches, possibly tons of cache misses, bad (or not, depends on workload))
- each thread has allocate own, independent stack (which used store local variables , return addresses of function calls)
so, each thread comes more "wasted" memory , possibly "wasted" processor cycles (to perform "context switch").
now, let's have chat server, clients make http connections requesting new messages, , server answer them when there new messages client (so clients instantly receive new messages). suppose have 10k such clients. in traditional, blocking, thread-per-connection model, you'd have 10k threads. in java, typical standard value thread stack size (-xss) 256kb. 10k threads, automatically using 2gb memory!!!!!!!! worse: if there's no activity @ on chat server, no messages being sent, clients still making waste 2gb. add tons of context switches, , see have problem.
in situation, you'd better off using non-blocking nio, in fewer threads (eventually 1!) enough handle 10k clients, you'd save context switches (ie, cpu time) , thread stacks (ie, memory), @ expense of more complex code, side-effect of using non-blocking nio.
Comments
Post a Comment