On Tue, Jun 5, 2012 at 10:35 PM, Willy Tarreau <[email protected]> wrote: > Hi David,
as usual, great response willy. it got me thinking how great it would be if we could bury links in the manual (or a copy of it) to public urls to these discussions. it doesn't fit to have the conversational tone in a manual, but to link out to this discussion would be so awesome. maybe this what stackexchange could be used for, but it'd require us to copy and replay the whole discussion. > > On Tue, Jun 05, 2012 at 06:17:15PM -0700, David Birdsong wrote: >> Is there a way to set the maxqueu for an entire backend? > > No. When I developped the server maxqueue, I remember having done the same > for the backend (it even ended up in the doc, causing later confusion), but > I removed it during tests because I noticed it was totally useless the way > it worked. Initially the goal was to limit the queue in the backend, not > counting the servers, which did not make much sense since it depends whether > the clients have a cookie or not. Then I figured that we'd have to count all > the queues of all servers, and I did not want to do that for each connection > since it's always expensive for just a few use cases. So I removed it before > ever releasing it. > >> I set maxqueu >> on default-server to 1, and on the frontend ACL required that >> connslots be greater than 1. I expected connslots to be maxconn * num >> server + 1 * num servers (connections + queue slots). >> >> I found that the backend still queued requests. My ACL could check the >> current queue size of the backend and route away from that backend if >> it's gt 0, but I figured connslots was the more correct approach. What >> am I doing or understanding wrongly? > > You're not necessarily doing anything wrong, there are a wide number of > reasons for deciding not to queue in a specific way, and that's the first > thing to define. If you have maxconn on servers, you need some queues. > The server queues are only for requests which target a specific server. > If the request has no cookie set, it will remain in the backend queue so > that any server may pick it. So as you can see, you *need* to support > queues both in the backend and servers whenever you use maxconn. > > If you would prevent the backend from queueing any connections, you would > constantly emit 503 to some visitors, because traffic is never perfectly > smooth (which is observed by your backend queue inflating). i my case, i have another backend fully capable of serving the requests, so if haproxy can route away accurately, the requests could land in a capable backend. is the 503 only because haproxy can't know ahead of time before choosing the backend what will happen in the future and so enforching no queue is technically not reasonable? > > The best way I found to manage queues is the avg_queue ACL. It returns > the average number of queued connections per active server. This means > that wherever the connections are queued, they're accounted for, and > divided by the number of servers. The result is an average queue length > for the backend, which translates in an average wait time for visitors. > cool, i'll use it. is it expensive to calc on every request? > I think it's the most efficient way of taking decisions based on queue > length because you don't need to consider any difference between new and > past visitors, and you don't care whether a server has a deeper queue > than another one. This way you can safely remove the maxqueue parameter > from your servers and only decide to switch to another backend based on > the avg_queue. > > BTW, what I'd suggest if you use this is to split the traffic depending > on the persistence cookie : stop sending new visitors to a backend which > has too many queued connections, but still send existing ones there. You > will see that the load on the servers will then regulate itself very well > and become extremely smooth. And that way you can finely control your > response times. In short this looks like this : > in this case, requests are completely stateless. we have a pool of 40 api servers capable of handling paths at /v2/*. the api servers are a java jetty app. i'm experimenting with carving up the urls space to send the same requests to the same servers to see if garbage collection is slightly more efficient if the servers don't see all of the api namespace and can 'specialize'. > frontend pub > acl bk_full avg_queue(bk_www) gt 10 > acl has_cook cook_len(SRV) gt 0 > use_backend bk_sorry if bk_full !has_cook > default_backend bk_www > > backend bk_www > cookie SRV insert indirect nocache > server s1 1.1.1.1:80 cookie 1 maxconn 50 > ... > > backend bk_sorry > server sorry 127.0.0.1:8080 > > Regards, > Willy >

