Date | Commit message (Collapse) |
|
Small fixes and documentation are the focus of this release.
James Golick reported and helped me track down a bug that caused
SIGHUP to drop the default listener (0.0.0.0:8080) if and only
if listeners were completely unspecified in both the
command-line and Unicorn config file. The Unicorn config file
remains the recommended option for specifying listeners as it
allows fine-tuning of the :backlog, :rcvbuf, :sndbuf,
:tcp_nopush, and :tcp_nodelay options.
There are some documentation (and resulting website)
improvements. setup.rb users will notice the new section 1
manpages for `unicorn` and `unicorn_rails`, Rubygems users
will have to install manpages manually or use the website.
The HTTP parser got a 3rd-party code review which resulted in
some cleanups and one insignificant bugfix as a result.
Additionally, the HTTP parser compiles, runs and passes unit
tests under Rubinius. The pure-Ruby parts still do not work yet
and we currently lack the resources/interest to pursue this
further but help will be gladly accepted.
The website now has an Atom feed for new release announcements.
Those unfamiliar with Atom or HTTP may finger unicorn@bogomips.org
for the latest announcements.
|
|
When SIGHUP reloads the config, we didn't account for the case
where the listen socket was completely unspecified. Thus the
default listener (0.0.0.0:8080), did not get preserved and
re-injected into the config properly.
Note that relying on the default listen or specifying listeners
on the command-line means it's /practically/ impossible to
_unbind_ those listeners with a configuration file reload. We
also need to preserve the (unspecified) default listener across
upgrades that later result in SIGHUP, too; so the easiest way is
to inject the default listener into the command-line for
upgrades.
Many thanks to James Golick for reporting and helping me track
down the bug since this behavior is difficult to write reliable
automated tests for.
Signed-off-by: Eric Wong <normalperson@yhbt.net>
|
|
This gives applications more rope to play with in case they have
any reasons for changing some values of the default constants.
Freezing strings for Hash assignments still speeds up MRI, so
we'll keep on doing that for now (and as long as MRI supports
frozen strings, I expect them to always be faster for Hashes
though I'd be very happy to be proven wrong...)
|
|
We may add support for the Gopher protocol in the future...
|
|
We used to try it on every listener, but then rarely-used
listener ports used mainly for monitoring/debugging would have
accept() unnecessary called, getting unnecessarily expensive
inside the kernel.
|
|
This can hide bugs in Rack applications/middleware. Most other
Rack handlers/servers seem to follow this route as well, so
this helps ensure broken things will break loudly and more
consistently across all Rack-enabled servers :)
|
|
This ensures any string literals that pop up in *our* code will
just be a bag of bytes. This shouldn't affect/fix/break
existing apps in most cases, but most constants will always have
the "correct" encoding (none!) to be consistent with HTTP/socket
expectations. Since this comment affects things only on a
per-source basis, it won't affect existing apps with the
exception of strings we pass to the Rack application.
This will eventually allow us to get rid of that Unicorn::Z
constant, too.
|
|
|
|
Avoid potential issues that can arise from logging any weird
characters that may not be supported in the current encoding.
|
|
HTTP/0.9 GET requests expect responses without headers. Some
weird applications/tools still use the ancient HTTP/0.9
protocol for weird reasons, so we'll support them.
ref: rfc 1945, section 4.1
|
|
Otherwise errors in the Unicorn-specific config files can get
error messages swallowed up when daemonizing.
|
|
the docs for the TeeInput class was clobbering the Unicorn
module documentation instead.
|
|
|
|
Since Rack permits body objects to have #close called on
them, we can safely close our pipe readers immediately
instead of waiting on the GC to close them (like we do for
TeeInput tempfiles).
|
|
Rack is autoload-based and so are we.
|
|
|
|
This lets clients can pass through newly-invented status codes
that Rack does not know about.
|
|
|
|
TeeInput being needed is now (once again) an uncommon code path
so there's no point in relying on global constants. While we're
at it, allow StringIO to be used in the presence of small
inputs; too.
|
|
This makes a noticeable difference on light GET/HEAD requests.
Heck, even the tests run a few seconds faster.
|
|
This method is strictly a filter, it does no I/O so "read"
is not an appropriate name to give it.
|
|
This should be more robust, faster and easier to deal
with than the ugly proof-of-concept regexp-based ones.
|
|
|
|
"/dev/null" must be opened in binary mode for Rack-compliance.
Additionally, avoid '' to create an empty string and use
Unicorn::Z instead.
Conflicts:
lib/unicorn/app/exec_cgi.rb
|
|
With the 1.9.2preview1 release (and presumably 1.9.1 p243), the
Ruby core team has decided that bending over backwards to
support crippled operating/file systems was necessary and that
files must be closed before unlinking.
Regardless, this is more efficient than using Tempfile because:
1) no delegation is necessary, this is a real File object
2) no mkdir is necessary for locking, we can trust O_EXCL
to work properly without unnecessary FS activity
3) no finalizer is needed to unlink the file, we unlink
it as soon as possible after creation.
|
|
Regexps can be run against nil just fine
|
|
Anything that calls close on a rack.input body is violating
Rack::Lint; so don't waste cycles supporting them. Being
liberal in things we accept tolerates bad behavior and Unicorn
doesn't have a large userbase that would scream bloody murder if
we stopped supporting broken behavior.
|
|
This simplifies chunked_reader substantially with a slight
increase in tee_input complexity. This is beneficial because
chunked_reader is more complex to begin with and more likely
to experience correctness issues.
|
|
We couldn't do proper namespacing for the C module so there was
a potential conflict with Init_http11() in Mongrel. This was
needed because Mongrel's HTTP parser could be used in some
applications and we may be unfortunate enough need to support
them.
|
|
* maint:
unicorn 0.8.2
always set FD_CLOEXEC on sockets post-accept()
Minor cleanups to core
Re-add support for non-portable socket options
Retry listen() on EADDRINUSE 5 times ever 500ms
Unbind listeners as before stopping workers
Conflicts:
CHANGELOG
lib/unicorn.rb
lib/unicorn/configurator.rb
lib/unicorn/const.rb
|
|
|
|
FD_CLOEXEC is not guaranteed to be inherited by the accept()-ed
descriptors even if the listener socket has this set. This can
be a problem with applications that fork+exec long running
background processes.
Thanks to Paul Sponagl for helping me find this.
|
|
(cherry picked from commit ec70433f84664af0dff1336845ddd51f50a714a3)
|
|
Now that we support tunnelling arbitrary protocols over HTTP as
well as "100 Continue" responses, TCP_NODELAY actually becomes
useful to us. TCP_NODELAY is actually reasonably portable
nowadays; even.
While we're adding non-portable options, TCP_CORK/TCP_NOPUSH can
be enabled, too. Unlike some other servers, these can't be
disabled explicitly/intelligently to force a flush, however.
However, these may still improve performance with "normal" HTTP
applications (Mongrel has always had TCP_CORK enabled in Linux).
While we're adding OS-specific features, we might as well
support TCP_DEFER_ACCEPT in Linux and FreeBSD the "httpready"
accept filter to prevent abuse.
These options can all be enabled on a per-listener basis.
(cherry picked from commit 563d03f649ef31d2aec3505cbbed1e015493b8fc)
|
|
This number of retries and delay taken directly from nginx
(cherry picked from commit d247b5d95a3ad2de65cc909db21fdfbc6194b4c9)
|
|
This allows another process to take our listeners
sooner rather than later.
(cherry picked from commit 8c2040127770e40e344a927ddc187bf801073e33)
|
|
|
|
There's a small memory reduction to be had when forking
oodles of processes and the Perl hacker in me still
gets confused into thinking those are arrays...
|
|
Array#+= creates a new array before assigning, Array#concat just
appends one array to another without an intermediate one.
|
|
|
|
This change gives applications full control to deny clients
from uploading unwanted message bodies. This also paves the
way for doing things like upload progress notification within
applications in a Rack::Lint-compatible manner.
Since we don't support HTTP keepalive, so we have more freedom
here by being able to close TCP connections and deny clients the
ability to write to us (and thus wasting our bandwidth).
While I could've left this feature off by default indefinitely
for maximum backwards compatibility (for arguably broken
applications), Unicorn is not and has never been about
supporting the lowest common denominator.
|
|
This was causing the first part of the body to be missing when
an HTTP client failed to delay between sending the header and
body in the request.
|
|
This gives the app ability to deny clients with 417 instead of
blindly making the decision for the underlying application. Of
course, apps must be made aware of this.
|
|
Now that we support tunnelling arbitrary protocols over HTTP as
well as "100 Continue" responses, TCP_NODELAY actually becomes
useful to us. TCP_NODELAY is actually reasonably portable
nowadays; even.
While we're adding non-portable options, TCP_CORK/TCP_NOPUSH can
be enabled, too. Unlike some other servers, these can't be
disabled explicitly/intelligently to force a flush, however.
However, these may still improve performance with "normal" HTTP
applications (Mongrel has always had TCP_CORK enabled in Linux).
While we're adding OS-specific features, we might as well
support TCP_DEFER_ACCEPT in Linux and FreeBSD the "httpready"
accept filter to prevent abuse.
These options can all be enabled on a per-listener basis.
|
|
This number of retries and delay taken directly from nginx
|
|
This allows another process to take our listeners
sooner rather than later.
|
|
Support for the "Trailer:" header and associated Trailer
lines should be reasonably well supported now
|
|
|
|
We can actually just use one IO and file descriptor here and
simplify the code while we're at it.
|
|
I'd honestly be more comfortable doing this in C (and possibly
adapting the code from the libcurl internals since that code has
been very well-tested).
|