When RHEL5 went EOL we talked about dropping the prohibition on
modules using the requests library (directly.... many modules use
requests indirectly through their dependencies) but someone said
"there's other distros than RHEL5 using 1.x versions of requests."
(and according to that person, the 1.x version of requests is
different enough that code that can use both requests versions
wouldn't be portable.)
If the premise is correct, we still should figure out what our
criteria is for allowing modules to make use of requests. We don't
disallow other libraries **cough**docker**cough** just because their
API is unstable. We simply tell people what version of the library is
needed for the module to run. So what criteria needs to be met so
that we can do that for requests?
I've always encouraged module authors to avoid requests due to 1.x but
even 2.x version incompatibilities, but I was unaware we banned them
until this thread was started (we should update the docs).
Even though the development of 'requests' has been much more stable
for the last few years, the 'installed base' has a very long memory
and not everyone can update to the latest from pip, which is what most
developers target/test. This is also why I insist on 'version
checking' when i see `import requests` on any module or it stated as a
dependency .. the same goes for docker.py, anyone that has looked at
those modules can see the proliferation of version comparison
statements. There are a few libraries that fall into this category,
mostly due to rapidly changing landscapes in tech.
Another thing to consider is that the controller tends to be much
newer OS/Software than the targets (user workstation vs servers) and
that even those versions might differ vastly, so modules/plugins that
require requests on the controller should be less problematic than
those that execute on the remote target. We already have plenty of
modules/plugins that depend on requests, but mostly due to depending
on an API specific library that uses requests internally.
I'm not a fan of banning, but I can see @sivel's point on avoiding
unnecessary dependencies when we have alternatives that cover the same
needs.
For those that were not already using related tools and had the
libraries already installed, installing new dependencies manually is
already a burden, I would prefer not to add to it.
Should we then expand this criteria to any/all libraries? What is the
threshold?
Taken to the absurd extreme, every library can be eliminated as a
dependency until we get into C bindings and such .. even then we can
work around those by using 'pure python' implementations.
Whatever we decide, we should also clearly document it, not just add a
check that makes it fail in CI.
In the end, I'm fine with removing the ban. I would still 'strongly
recommend' to any authors on review to use the existing alternative,
specially if they want to be included in Ansible's distribution. And,
if they cannot avoid it, be very clear about the versions required,
both in code and in docs.
My major complaint is that the version argument is disingenuous and
reflects poorly upon us every time we make it. (Internally, someone
said that prior to requests-2.1.0, the API was unstable. 2.1.0 was
released in 2013-12-05, about the time Ansible-1.5 was released.
RHEL6 and Debian Jessie both have newer releases (2.6.0 and 2.4.3
respectively).
If we can agree to stop making that argument (at least, as a project
member... I wouldn't object to someone making clear that api
incompatibility of older versions was their personal pet peeve like:
"The project doesn't allow requests because open_url works fine for
almost all use cases. Personally, I can never forget that they
changed their API 5 years ago so I don't use it myself".) that would
satisfy me.
For your point, though, the API is both well known to developers and
much better designed than open_url/fetch_url. requests is available
most places due to being a dep in so many third party libraries
(including libraries which Ansible users will be installing for other
Ansible modules) so it's not an extra dependency in many environments.
I think the unnecessary dep argument is enough to prohibit it in core
modules and discourage it in community modules doing simple things.
I'm unsure if we should outright ban it there, though. I'm also
leaning towards the view that even if we ban it for simple things, we
shouldn't ban it in community modules doing complex things.... The API
of requests makes complex things much easier to code than
open_url/fetch_url and I don't think we want to spend a lot of time
making open_url/fetch_url's API better....
It is not a question about pet peeves, its a question about the installed base.
Python 2.7 was released much longer than 5 yrs ago and we still
support it and even 2.6, not because we like to, but because the
existing install base still has those versions.
The requests lib has been present for a long time, used by many apps
and installed in many systems, a less popular library is not even as
close to be as problematic.
I don't see that as disingenuous, just dealing with the reality that
production systems don't get updated at anything close to the
frequency developers update their workstations and development
environments. This has always been a frustration that has affected
developers and administrators, 1/2 the reason everyone
virtualizes/jails/contains applications, but as a system tool we don't
have the luxury to control the execution environment, so we need to
balance the existing base vs the maintainability and the feature set
we want to provide.
That said, I never thought an outright ban was reasonable and I'm
still a firm believer on being specific about versions, at the very
least in the documentation. Not just on requests, but any library that
has an installed base that will conflict with the latest version being
used. Thankfully that tends to be a short list, mostly related to
technology that is still in its 'fast evolution' phase.
For your point, though, the API is both well known to developers and
much better designed than open_url/fetch_url
I’m not necessarily disagreeing here, but do you have something specific you are referring to? What about requests is much better than open_url/fetch_url.
Note that we recently added a new Request class in urls.py that aims to address some usability concerns, such as functionality somewhat similar to the Session class of requests.
For your point, though, the API is both well known to developers and
much better designed than open_url/fetch_url
I'm not necessarily disagreeing here, but do you have something specific you
are referring to? What about requests is much better than
open_url/fetch_url.
Note that we recently added a new `Request` class in urls.py that aims to
address some usability concerns, such as functionality somewhat similar to
the Session class of requests.
Nice, the API of the Request class looks a lot better than what we
had. The only thing I'm seeing right off the bat is that the
exceptions are probably still the same mess as open_url() had? That's
not the end of the world, though.