Skip to content

Commit

Permalink
Merge pull request #585 from qwcode/userscheme_pt6
Browse files Browse the repository at this point in the history
--user fixes part 6 #573
  • Loading branch information
pnasrat committed Jun 30, 2012
2 parents 6ed502c + 0708447 commit d82816c
Show file tree
Hide file tree
Showing 3 changed files with 48 additions and 13 deletions.
5 changes: 4 additions & 1 deletion pip/req.py
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@
from pip.util import display_path, rmtree
from pip.util import ask, ask_path_exists, backup_dir
from pip.util import is_installable_dir, is_local, dist_is_local, dist_in_usersite
from pip.util import renames, normalize_path, egg_link_path
from pip.util import renames, normalize_path, egg_link_path, dist_in_site_packages
from pip.util import make_path_relative
from pip.util import call_subprocess
from pip.backwardcompat import (urlparse, urllib,
Expand Down Expand Up @@ -685,6 +685,9 @@ def check_if_exists(self):
if self.use_user_site:
if dist_in_usersite(existing_dist):
self.conflicts_with = existing_dist
elif running_under_virtualenv() and dist_in_site_packages(existing_dist):
raise InstallationError("Will not install to the user site because it will lack sys.path precedence to %s in %s"
%(existing_dist.project_name, existing_dist.location))
else:
self.conflicts_with = existing_dist
return True
Expand Down
6 changes: 6 additions & 0 deletions pip/util.py
Original file line number Diff line number Diff line change
Expand Up @@ -303,6 +303,12 @@ def dist_in_usersite(dist):
else:
return False

def dist_in_site_packages(dist):
"""
Return True if given Distribution is installed in distutils.sysconfig.get_python_lib().
"""
return normalize_path(dist_location(dist)).startswith(normalize_path(site_packages))


def get_installed_distributions(local_only=True, skip=('setuptools', 'pip', 'python')):
"""
Expand Down
50 changes: 38 additions & 12 deletions tests/test_user_site.py
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,14 @@
from tests.test_pip import here, reset_env, run_pip, pyversion


patch_dist_in_site_packages = """
def dist_in_site_packages(dist):
return False
import pip
pip.util.dist_in_site_packages=dist_in_site_packages
"""


def test_install_curdir_usersite_fails_in_old_python():
"""
Test --user option on older Python versions (pre 2.6) fails intelligibly
Expand Down Expand Up @@ -111,15 +119,21 @@ def test_install_user_conflict_in_usersite(self):
assert not isfile(initools_v3_file), initools_v3_file


def test_install_user_conflict_in_site(self):
def test_install_user_conflict_in_globalsite(self):
"""
Test user install with conflict in site ignores site and installs to usersite
Test user install with conflict in global site ignores site and installs to usersite
"""

#the test framework only supports testing using virtualenvs
#this test will use a --system_site_packages virtualenv to achieve the conflict scenario.
# the test framework only supports testing using virtualenvs
# the sys.path ordering for virtualenvs with --system-site-packages is this: virtualenv-site, user-site, global-site
# this test will use 2 modifications to simulate the user-site/global-site relationship
# 1) a monkey patch which will make it appear INITools==0.2 is not in in the virtualenv site
# if we don't patch this, pip will return an installation error: "Will not install to the usersite because it will lack sys.path precedence..."
# 2) adding usersite to PYTHONPATH, so usersite as sys.path precedence over the virtualenv site

env = reset_env(system_site_packages=True, sitecustomize=patch_dist_in_site_packages)
env.environ["PYTHONPATH"] = env.root_path / env.user_site

env = reset_env(system_site_packages=True)
result1 = run_pip('install', 'INITools==0.2')
result2 = run_pip('install', '--user', 'INITools==0.1')

Expand All @@ -141,14 +155,14 @@ def test_install_user_conflict_in_globalsite_and_usersite(self):
Test user install with conflict in globalsite and usersite ignores global site and updates usersite.
"""

#the test framework only supports testing using virtualenvs
#this test will use a --system_site_packages virtualenv to achieve the conflict scenario.

env = reset_env(system_site_packages=True)
# the test framework only supports testing using virtualenvs.
# the sys.path ordering for virtualenvs with --system-site-packages is this: virtualenv-site, user-site, global-site.
# this test will use 2 modifications to simulate the user-site/global-site relationship
# 1) a monkey patch which will make it appear INITools==0.2 is not in in the virtualenv site
# if we don't patch this, pip will return an installation error: "Will not install to the usersite because it will lack sys.path precedence..."
# 2) adding usersite to PYTHONPATH, so usersite as sys.path precedence over the virtualenv site

# the sys.path ordering for virtualenvs with --system-site-packages is this: virtualenv site, usersite, global site
# given this ordering you *can't* use it to simulate the scenario for this test.
# this test will add the usersite to PYTHONPATH to simulate the desired ordering
env = reset_env(system_site_packages=True, sitecustomize=patch_dist_in_site_packages)
env.environ["PYTHONPATH"] = env.root_path / env.user_site

result1 = run_pip('install', 'INITools==0.2')
Expand All @@ -166,3 +180,15 @@ def test_install_user_conflict_in_globalsite_and_usersite(self):
initools_folder = env.root_path / env.site_packages / 'initools'
assert isdir(egg_info_folder)
assert isdir(initools_folder)


def test_install_user_in_global_virtualenv_with_conflict_fails(self):
"""
Test user install in --system-site-packages virtualenv with conflict in site fails.
"""
env = reset_env(system_site_packages=True)
result1 = run_pip('install', 'INITools==0.2')
result2 = run_pip('install', '--user', 'INITools==0.1', expect_error=True)
assert result2.stdout.startswith("Will not install to the user site because it will lack sys.path precedence to %s in %s"
%('INITools',env.root_path / env.site_packages)), result2.stdout

0 comments on commit d82816c

Please sign in to comment.