pypa/pip

--extra-index-url in requirements.txt

survivorbat opened this issue ยท 14 comments

Environment

  • pip version: 20.0.2 / 20.0.2
  • Python version: 3.6.9 / 3.8.0
  • OS: Linux Mint / MacOS
  • keyring package: 21.2.0 / 21.2.0
  • artifacts-keyring package: 0.2.9 / 0.2.9

Description
We are using an Azure DevOps artifact feed to provide our users with a 'mypackage' package. We're currently building applicationB that has this mypackage package as a dependency in the requirements.txt.

To add the azure artifacts index to the install command, we've added --extra-index-url https://pkgs.dev.azure.com/<org>/_packaging/mypackage/pypi/simple/ at the top of the requirements.txt file and added the mypackage package to the requirements.txt list.

Running pip install -r requirements.txt gives me the following error:

Looking in indexes: https://pypi.org/simple, https://pkgs.dev.azure.com/<org>/_packaging/mypackage/pypi/simple/
ERROR: Could not find a version that satisfies the requirement mypackage>=1.0.0 (from -r requirements.txt (line 2)) (from versions: none)
ERROR: No matching distribution found for mypackage>=1.0.0 (from -r requirements.txt (line 2))

Installing this package with an explicit --extra-index-url like so: pip install -r requirements.txt --extra-index-url https://pkgs.dev.azure.com/<org>/_packaging/mypackage/pypi/simple/ however, works perfectly and installs the packages like it should.

Installing it also works when I add the extra index url to my global pip.conf settings.

Expected behavior
I expect all the dependencies (pypi and private azure artifacts feed) to be installed without issues using the pip install -r requirements.txt and without having to explicitly configure the index url in my pip configuration.

How to Reproduce

  1. Set up a requirements.txt file with a link to a private pypi repository (azure artifacts?)
    For example:

    --extra-index-url https://pkgs.dev.azure.com/<org>/_packaging/mypackage/pypi/simple/
    mypackage>=1.0.0
    requests
    
  2. Then run pip install -r requirements.txt

  3. An error occurs.

Output

Looking in indexes: https://pypi.org/simple, https://pkgs.dev.azure.com/<org>/_packaging/mypackage/pypi/simple/
ERROR: Could not find a version that satisfies the requirement mypackage>=1.0.0 (from -r requirements.txt (line 2)) (from versions: none)
ERROR: No matching distribution found for mypackage>=1.0.0 (from -r requirements.txt (line 2))

There's something inconsistent here. You state that requirements.txt contains

--extra-index-url https://pkgs.dev.azure.com/<org>/_packaging/mypackage/pypi/simple/ mypackage==1.0.0 requests

But your output shows

ERROR: Could not find a version that satisfies the requirement mypackage>=1.6.1 (from -r requirements.txt (line 2))

Where did the requirement for 1.6.1 or greater come from?

@pfmoore You're right! I forgot to remove the version number, I fixed the error logs.

Hmm, OK. I'm not 100% sure why you needed to edit the version (generally, having as close a copy/paste of the actual situation where the error occurs is really helpful, because there can be key bits of information that might not be obvious at first glance) but I can't see why changing the version would be relevant here, so it's not a big deal.

Can you post the full log when running pip with -vvv added to the options, so we can see the complete logs and any information/debug output? Thanks.

Without extra index url in command options:

Created temporary directory: /tmp/pip-ephem-wheel-cache-6y85e8_9
Created temporary directory: /tmp/pip-req-tracker-b_tf3zns
Initialized build tracking at /tmp/pip-req-tracker-b_tf3zns
Created build tracker: /tmp/pip-req-tracker-b_tf3zns
Entered build tracker: /tmp/pip-req-tracker-b_tf3zns
Created temporary directory: /tmp/pip-install-fvd2fpmn
Looking in indexes: https://pypi.org/simple, https://pkgs.dev.azure.com/<org>/_packaging/mypackage/pypi/simple/
2 location(s) to search for versions of mypackage:
* https://pypi.org/simple/mypackage/
* https://pkgs.dev.azure.com/<org>/_packaging/mypackage/pypi/simple/mypackage/
Fetching project page and analyzing links: https://pypi.org/simple/mypackage/
Getting page https://pypi.org/simple/mypackage/
Found index url https://pypi.org/simple
Getting credentials from keyring for https://pypi.org/simple
Getting credentials from keyring for pypi.org
Looking up "https://pypi.org/simple/mypackage/" in the cache
Request header has "max_age" as 0, cache bypassed
Starting new HTTPS connection (1): pypi.org:443
https://pypi.org:443 "GET /simple/mypackage/ HTTP/1.1" 404 13
Status code 404 not in (200, 203, 300, 301)
Could not fetch URL https://pypi.org/simple/mypackage/: 404 Client Error: Not Found for url: https://pypi.org/simple/mypackage/ - skipping
Fetching project page and analyzing links: https://pkgs.dev.azure.com/<org>/_packaging/mypackage/pypi/simple/mypackage/
Getting page https://pkgs.dev.azure.com/<org>/_packaging/mypackage/pypi/simple/mypackage/
Getting credentials from keyring for pkgs.dev.azure.com
Looking up "https://pkgs.dev.azure.com/<org>/_packaging/mypackage/pypi/simple/mypackage/" in the cache
Request header has "max_age" as 0, cache bypassed
Starting new HTTPS connection (1): pkgs.dev.azure.com:443
https://pkgs.dev.azure.com:443 "GET /<org>/_packaging/mypackage/pypi/simple/mypackage/ HTTP/1.1" 302 593
Status code 302 not in (200, 203, 300, 301)
Looking up "https://spsprodweu4.vssps.visualstudio.com/_signin?realm=pkgs.dev.azure.com&reply_to=https%3A%2F%2Fpkgs.dev.azure.com%2F<org>%2F_packaging%2Fmypackage%2Fpypi%2Fsimple%2Fmypackage%2F&redirect=1&hid=<token>" in the cache
Request header has "max_age" as 0, cache bypassed
Starting new HTTPS connection (1): spsprodweu4.vssps.visualstudio.com:443
https://spsprodweu4.vssps.visualstudio.com:443 "GET /_signin?realm=pkgs.dev.azure.com&reply_to=https%3A%2F%2Fpkgs.dev.azure.com%2F<org>%2F_packaging%2Fmypackage%2Fpypi%2Fsimple%2Fmypackage%2F&redirect=1&hid=<token> HTTP/1.1" 203 15654
Updating cache with response from "https://spsprodweu4.vssps.visualstudio.com/_signin?realm=pkgs.dev.azure.com&reply_to=https%3A%2F%2Fpkgs.dev.azure.com%2F<org>%2F_packaging%2Fmypackage%2Fpypi%2Fsimple%2Fmypackage%2F&redirect=1&hid=<token>"
Response header has "no-store"
  Skipping link: not a file: https://spsprodweu4.vssps.visualstudio.com/go/profile (from https://spsprodweu4.vssps.visualstudio.com/_signin?realm=pkgs.dev.azure.com&reply_to=https%3A%2F%2Fpkgs.dev.azure.com%2F<org>%2F_packaging%2Fmypackage%2Fpypi%2Fsimple%2Fmypackage%2F&redirect=1&hid=<token>#ctx=eyJTaWduSW5Db29raWVEb21haW5zIjpbImh0dHBzOi8vbG9naW4ud2luZG93cy5uZXQiXX01)
  Skipping link: not a file: https://spsprodweu4.vssps.visualstudio.com/_signout (from https://spsprodweu4.vssps.visualstudio.com/_signin?realm=pkgs.dev.azure.com&reply_to=https%3A%2F%2Fpkgs.dev.azure.com%2F<org>%2F_packaging%2Fmypackage%2Fpypi%2Fsimple%2Fmypackage%2F&redirect=1&hid=68f47bca-fbc6-48e0-81db-6958e3f16b5b&context=eyJodCI6MiwiaGlkIjoiZDZhOTRkYTYtOTVkYS00NjViLTg2Y2UtINGCNDkzNWIzNTQ1M2RlIiwicXMiOnt9LCJyciI6IiIsInZoIjoiIiwiY3YiOiIiLCJjcyI6IiJ90#ctx=eyJTaWduSW5Db29raWVEb21haW5zIjpbImh0dHBzOi8vbG9naW4ud2luZG93cy5uZXQiXX01)
Given no hashes to check 0 links for project 'mypackage': discarding no candidates
ERROR: Could not find a version that satisfies the requirement mypackage>=1.6.1 (from -r requirements.txt (line 2)) (from versions: none)
Cleaning up...
Removed build tracker: '/tmp/pip-req-tracker-b_tf3zns'
ERROR: No matching distribution found for mypackage>=1.6.1 (from -r requirements.txt (line 2))
Exception information:
Traceback (most recent call last):
  File "/home/maarten/dev/mypackage/venv/lib/python3.6/site-packages/pip/_internal/cli/base_command.py", line 186, in _main
    status = self.run(options, args)
  File "/home/maarten/dev/mypackage/venv/lib/python3.6/site-packages/pip/_internal/commands/install.py", line 331, in run
    resolver.resolve(requirement_set)
  File "/home/maarten/dev/mypackage/venv/lib/python3.6/site-packages/pip/_internal/legacy_resolve.py", line 177, in resolve
    discovered_reqs.extend(self._resolve_one(requirement_set, req))
  File "/home/maarten/dev/mypackage/venv/lib/python3.6/site-packages/pip/_internal/legacy_resolve.py", line 333, in _resolve_one
    abstract_dist = self._get_abstract_dist_for(req_to_install)
  File "/home/maarten/dev/mypackage/venv/lib/python3.6/site-packages/pip/_internal/legacy_resolve.py", line 281, in _get_abstract_dist_for
    req.populate_link(self.finder, upgrade_allowed, require_hashes)
  File "/home/maarten/dev/mypackage/venv/lib/python3.6/site-packages/pip/_internal/req/req_install.py", line 249, in populate_link
    self.link = finder.find_requirement(self, upgrade)
  File "/home/maarten/dev/mypackage/venv/lib/python3.6/site-packages/pip/_internal/index/package_finder.py", line 927, in find_requirement
    'No matching distribution found for %s' % req
pip._internal.exceptions.DistributionNotFound: No matching distribution found for mypackage>=1.6.1 (from -r requirements.txt (line 2))

When appending the --extra-index-url to the pip install command it asks me to login to azure and afterwards it installs the package like normal. In these logs I kept the version number in.

It looks like it might be getting a signin page and treating it as an index. That's likely your problem, for some reason with --extra-index-url in the requirements file, the keyring stuff isn't kicking in properly.

I suspect that the PipSession being built is only being populated with the index URLs from the command line, not the ones from the requirements file, and the keyring handling is hooked into that part of the process. But I don't know enough about the keyring support in pip to be sure.

@zooba what's your view here, as you implemented the keyring support?

Apologies for hijacking but seems like the same happens with -f inside requirements.txt.

# requirements.txt
torch==1.5.0+cpu -f https://download.pytorch.org/whl/torch_stable.html

pip install -r requirements.txt

Exception information:
Traceback (most recent call last):
  File "D:\Tools\conda\envs\u8-test\lib\site-packages\pip\_internal\cli\base_command.py", line 188, in _main
    status = self.run(options, args)
  File "D:\Tools\conda\envs\u8-test\lib\site-packages\pip\_internal\cli\req_command.py", line 185, in wrapper
    return func(self, options, args)
  File "D:\Tools\conda\envs\u8-test\lib\site-packages\pip\_internal\commands\install.py", line 333, in run
    reqs, check_supported_wheels=not options.target_dir
  File "D:\Tools\conda\envs\u8-test\lib\site-packages\pip\_internal\resolution\legacy\resolver.py", line 179, in resolve
discovered_reqs.extend(self._resolve_one(requirement_set, req))
  File "D:\Tools\conda\envs\u8-test\lib\site-packages\pip\_internal\resolution\legacy\resolver.py", line 362, in _resolve_one
abstract_dist = self._get_abstract_dist_for(req_to_install)
  File "D:\Tools\conda\envs\u8-test\lib\site-packages\pip\_internal\resolution\legacy\resolver.py", line 313, in _get_abstract_dist_for
self._populate_link(req)
  File "D:\Tools\conda\envs\u8-test\lib\site-packages\pip\_internal\resolution\legacy\resolver.py", line 279, in _populate_link
req.link = self.finder.find_requirement(req, upgrade)
  File "D:\Tools\conda\envs\u8-test\lib\site-packages\pip\_internal\index\package_finder.py", line 930, in find_requirement
req)
pip._internal.exceptions.DistributionNotFound: No matching distribution found for torch==1.5.0+cpu

While this works:

pip install -r requirements.txt -f https://download.pytorch.org/whl/torch_stable.html

Is the syntax perhaps different?

torch==1.5.0+cpu -f https://download.pytorch.org/whl/torch_stable.html

@radujica You should put -f https://download.pytorch.org/whl/torch_stable.html in a seperate line:

-f https://download.pytorch.org/whl/torch_stable.html
torch==1.5.0+cpu

I wasn't able to reproduce this.

Environment

Ubuntu 18.04

python -VV
Python 3.8.0 (default, Jan  4 2020, 14:08:19)
[GCC 7.5.0]
pip freeze
artifacts-keyring==0.2.9
bleach==3.1.5
certifi==2020.6.20
cffi==1.14.0
chardet==3.0.4
colorama==0.4.3
cryptography==2.9.2
distro==1.5.0
docutils==0.16
dotnetcore2==2.1.14
example==0.1.0
idna==2.10
jeepney==0.4.3
keyring==21.2.1
packaging==20.4
pkginfo==1.5.0.1
pycparser==2.20
Pygments==2.6.1
pyparsing==2.4.7
readme-renderer==26.0
requests==2.24.0
requests-toolbelt==0.9.1
rfc3986==1.4.0
SecretStorage==3.1.2
six==1.15.0
tqdm==4.47.0
twine==3.2.0
urllib3==1.25.9
webencodings==0.5.1
pip debug
WARNING: This command is only meant for debugging. Do not use this with automation for parsing and getting these details, since the output and options of this command may change without notice.
pip version: pip 20.1.1 from /tmp/user/1000/tmp.vegDNlec6T/env/lib/python3.8/site-packages/pip (python 3.8)
sys.version: 3.8.0 (default, Jan  4 2020, 14:08:19)
[GCC 7.5.0]
sys.executable: /tmp/user/1000/tmp.vegDNlec6T/env/bin/python
sys.getdefaultencoding: utf-8
sys.getfilesystemencoding: utf-8
locale.getpreferredencoding: UTF-8
sys.platform: linux
sys.implementation:
  name: cpython
'cert' config value: global
REQUESTS_CA_BUNDLE: None
CURL_CA_BUNDLE: None
pip._vendor.certifi.where(): /tmp/user/1000/tmp.vegDNlec6T/env/lib/python3.8/site-packages/pip/_vendor/certifi/cacert.pem
pip._vendor.DEBUNDLED: False
vendored library versions:
  appdirs==1.4.3
  CacheControl==0.12.6
  colorama==0.4.3
  contextlib2==0.6.0.post1 (Unable to locate actual module version, using vendor.txt specified version)
  distlib==0.3.0
  distro==1.5.0 (Unable to locate actual module version, using vendor.txt specified version)
  html5lib==1.0.1
  ipaddress==1.0.23
  msgpack==1.0.0 (Unable to locate actual module version, using vendor.txt specified version)
  packaging==20.3
  pep517==0.8.2
  progress==1.5
  pyparsing==2.4.7
  requests==2.23.0
  certifi==2020.04.05.1
  chardet==3.0.4
  idna==2.9
  urllib3==1.25.8
  resolvelib==0.3.0
  retrying==1.3.3 (Unable to locate actual module version, using vendor.txt specified version)
  setuptools==44.0.0 (Unable to locate actual module version, using vendor.txt specified version)
  six==1.14.0
  toml==0.10.0
  webencodings==0.5.1 (Unable to locate actual module version, using vendor.txt specified version)
Compatible tags: 87
  cp38-cp38-manylinux2014_x86_64
  cp38-cp38-manylinux2010_x86_64
  cp38-cp38-manylinux1_x86_64
  cp38-cp38-linux_x86_64
  cp38-abi3-manylinux2014_x86_64
  cp38-abi3-manylinux2010_x86_64
  cp38-abi3-manylinux1_x86_64
  cp38-abi3-linux_x86_64
  cp38-none-manylinux2014_x86_64
  cp38-none-manylinux2010_x86_64
  ...
  [First 10 tags shown. Pass --verbose to show all.]

Steps

  1. Navigated to dev.azure.com
  2. Selected "Sign in to Azure DevOps"
  3. Signed in
  4. Created a new project in Azure DevOps
  5. Navigated to the Artifacts page of the new project
  6. Created a new feed
  7. Created a virtual environment in the console, and installed wheel into it
  8. Created a dummy package locally from a setup.py containing from setuptools import setup; setup(name="example", version="0.1.0"), and executing ./env/bin/python setup.py sdist bdist_wheel
  9. On the feed page, clicked "Connect to feed", then "twine" and followed the instructions for integration, including installing twine keyring artifacts-keyring in my environment, upgrading pip, and adding the repository details to ~/.pypirc
  10. executed twine upload, followed the console instructions to navigate to https://microsoft.com/devicelogin and enter a code, signed into my Microsoft account, and switched back to the console to see the upload succeed

Following that, in the same environment with keyring, and artifacts-keyring (per the pip integration instructions), I was able to successfully install with:

  1. ./env/bin/python -m pip install example --index-url https://pkgs.dev.azure.com/chrahunt/example1/_packaging/abc/pypi/simple/
    which are from their instructions verbatim

  2. ./env/bin/python -m pip install example --extra-index-url https://pkgs.dev.azure.com/chrahunt/example1/_packaging/abc /pypi/simple/
    which are not from their instructions, but should behave the same

  3. ./env/bin/python -m pip install -r requirements.txt, where requirements.txt contained

    --extra-index-url https://pkgs.dev.azure.com/chrahunt/example1/_packaging/abc/pypi/simple/
    example
    

Can you please try the same and revert back to us if you can reproduce it, with similar instructions and environment information?

Unfortunately I'm no longer working on this project and don't have access to the code. I'll pass this issue to one of my colleagues.

I wasn't able to repro this issue (i.e. get the error message specified in the original post). However, --extra-index-url indeed doesn't have exactly same effect when specified in the command line and in requirements file (issue #8640). This is visible, for instance, when using a private feed hosted in Azure DevOps which requires authentication.

It's possible that @chrahunt didn't get any error because he used a DevOps project with visibility set to Public (auth needed for uploading packages using twine, but not for downloading packages using pip).

Please note that the error provided in the original post:

ERROR: Could not find a version that satisfies the requirement mypackage>=1.0.0 (from -r requirements.txt (line 2)) (from versions: none)
ERROR: No matching distribution found for mypackage>=1.0.0 (from -r requirements.txt (line 2))

will be reported if the Azure DevOps package feed doesn't exist (e.g. a typo in extra-index-url) or the user doesn't have permissions to access it. In either case, the authentication was successful and the issue has nothing to do with pip or keyring.

I would suggest closing this issue.

In what version the fix in #8522 was introduced? I believe I am using the latest pip and I am still facing this issue. If the private feed is indeed private for download, artifacts-keyring won't pick the --extra-index-url in the requirements.txt and won't try to get credentials for it.

In what version the fix in #8522 was introduced? I believe I am using the latest pip and I am still facing this issue. If the private feed is indeed private for download, artifacts-keyring won't pick the --extra-index-url in the requirements.txt and won't try to get credentials for it.

I just checked and the change will only be introduced in pip 20.3
Sadly it is not out yet, but will be soon ๐Ÿ˜„