Coro::LWP - make LWP non-blocking - as much as possible
use Coro::LWP; # afterwards LWP should not block
Over the years, a number of less-invasive alternatives have popped up, which you
might find more acceptable than this rather invasive and fragile module. All
of them only support HTTP (and sometimes HTTPS).
- AnyEvent::HTTP
- Works fine without Coro. Requires using a very different
API than LWP. Probably the best choice iff you can do with a
completely different event-based API.
- LWP::Protocol::AnyEvent::http
- Makes LWP use AnyEvent::HTTP. Does not make LWP
event-based, but allows Coro threads to schedule unimpeded through its
AnyEvent integration.
Lets you use the LWP API normally.
- LWP::Protocol::Coro::http
- Basically the same as above, distinction unclear. :)
- AnyEvent::HTTP::LWP::UserAgent
- A different user agent implementation, not completely
transparent to users, requires Coro.
This module is an AnyEvent user, you need to make sure that you use and run a
supported event loop.
This module tries to make LWP non-blocking with respect to other coroutines as
much as possible, and with whatever means it takes.
LWP really tries very hard to be blocking (and relies on a lot of undocumented
functionality in IO::Socket), so this module had to be very invasive and must
be loaded very early to take the proper effect.
Note that the module AnyEvent::HTTP might offer an alternative to the full LWP
that is designed to be non-blocking.
Here is what it currently does (future versions of LWP might require different
tricks):
- It loads Coro::Select, overwriting the perl
"select" builtin globally.
- This is necessary because LWP calls select quite often for
timeouts and who-knows-what.
Impact: everybody else uses this (slower) version of select, too. It should
be quite compatible to perls builtin select, though.
- It overwrites Socket::inet_aton with
Coro::Util::inet_aton.
- This is necessary because LWP might (and does) try to
resolve hostnames this way.
Impact: some code might not expect coroutine semantics, for example, when
you fork you might prefer the blocking variant because other coroutines
shouldn't actually run.
- It replaces the base class of Net::HTTP, Net::FTP,
Net::NNTP.
- This is necessary because LWP does not always use select to
see whether a filehandle can be read/written without blocking, so the base
class "IO::Socket::INET" needs to be replaced by
"Coro::Socket".
Impact: Coro::Socket is not at all compatible to IO::Socket::INET. While it
duplicates some undocumented functionality required by LWP, it does not
have all the methods of IO::Socket::INET and might act quite differently
in practise. Also, protocols other than the above mentioned will still
block, at least some of the time.
All this likely makes other libraries than just LWP not block, but that's just a
side effect you cannot rely on.
Increases parallelism is not supported by all libraries, some might cache data
globally.
Marc A. Lehmann <[email protected]>
http://software.schmorp.de/pkg/Coro.html