def do_test(dirname): envdir = os.path.join(dirname, "myenv") # don't specify a python version so we use the one we already have # in the root env, otherwise this might take forever. conda_api.create(prefix=envdir, pkgs=['python']) assert os.path.isdir(envdir) assert os.path.isdir(os.path.join(envdir, "conda-meta")) # test that we can install a package via pip assert not os.path.exists(os.path.join(envdir, FLAKE8_BINARY)) pip_api.install(prefix=envdir, pkgs=['flake8']) assert os.path.exists(os.path.join(envdir, FLAKE8_BINARY)) # list what was installed installed = pip_api.installed(prefix=envdir) assert 'flake8' in installed assert installed['flake8'][0] == 'flake8' assert installed['flake8'][1] is not None # test that we can remove it again pip_api.remove(prefix=envdir, pkgs=['flake8']) assert not os.path.exists(os.path.join(envdir, FLAKE8_BINARY)) # no longer in the installed list installed = pip_api.installed(prefix=envdir) assert 'flake8' not in installed
def do_test(dirname): envdir = os.path.join(dirname, 'myenv') conda_api.create(prefix=envdir, pkgs=['python=3.8']) pip_api.install(prefix=envdir, pkgs=['chardet==3']) pip_packages = conda_api.installed_pip(envdir) assert pip_packages == ['chardet==3.0.0']
def fix_environment_deviations(self, prefix, spec, deviations=None, create=True): if deviations is None: deviations = self.find_environment_deviations(prefix, spec) if deviations.unfixable: raise CondaManagerError("Unable to update environment at %s" % prefix) if os.path.isdir(os.path.join(prefix, 'conda-meta')): to_update = list(set(deviations.missing_packages + deviations.wrong_version_packages)) if len(to_update) > 0: specs = spec.specs_for_conda_package_names(to_update) assert len(specs) == len(to_update) spec.apply_pins(prefix, specs) try: conda_api.install( prefix=prefix, pkgs=specs, channels=spec.channels, stdout_callback=self._on_stdout, stderr_callback=self._on_stderr) except conda_api.CondaError as e: raise CondaManagerError("Failed to install packages: {}: {}".format(", ".join(specs), str(e))) finally: spec.remove_pins(prefix) elif create: # Create environment from scratch command_line_packages = set(spec.conda_packages_for_create) # conda won't let us create a completely empty environment if len(command_line_packages) == 0: command_line_packages = set(['python']) try: conda_api.create( prefix=prefix, pkgs=list(command_line_packages), channels=spec.channels, stdout_callback=self._on_stdout, stderr_callback=self._on_stderr) except conda_api.CondaError as e: raise CondaManagerError("Failed to create environment at %s: %s" % (prefix, str(e))) else: raise CondaManagerError("Conda environment at %s does not exist" % (prefix)) # now add pip if needed missing = list(deviations.missing_pip_packages) if len(missing) > 0: specs = spec.specs_for_pip_package_names(missing) assert len(specs) == len(missing) try: pip_api.install(prefix=prefix, pkgs=specs) except pip_api.PipError as e: raise CondaManagerError("Failed to install missing pip packages: {}: {}".format( ", ".join(missing), str(e))) # write a file to tell us we can short-circuit next time self._write_timestamp_file(prefix, spec)
def do_test(dirname): envdir = os.path.join(dirname, "myenv") conda_api.create(prefix=envdir, pkgs=['python']) # no packages to install with pytest.raises(TypeError) as excinfo: pip_api.install(prefix=envdir, pkgs=[]) assert 'must specify a list' in repr(excinfo.value) # no packages to remove with pytest.raises(TypeError) as excinfo: pip_api.remove(prefix=envdir, pkgs=[]) assert 'must specify a list' in repr(excinfo.value) # pip command not installed from os.path import exists as real_exists def mock_exists(path): if path.endswith("pip") or path.endswith("pip.exe"): return False else: return real_exists(path) monkeypatch.setattr('os.path.exists', mock_exists) with pytest.raises(pip_api.PipNotInstalledError) as excinfo: pip_api.install(prefix=envdir, pkgs=['foo']) assert 'command is not installed in the environment' in repr( excinfo.value) installed = pip_api.installed(prefix=envdir) assert dict( ) == installed # with pip not installed, no packages are listed. # pip command exits nonzero error_script = """from __future__ import print_function import sys print("TEST_ERROR", file=sys.stderr) sys.exit(1) """ def get_failed_command(prefix, extra_args): return tmp_script_commandline(error_script) monkeypatch.setattr( 'anaconda_project.internal.pip_api._get_pip_command', get_failed_command) with pytest.raises(pip_api.PipError) as excinfo: pip_api.install(prefix=envdir, pkgs=['flake8']) assert 'TEST_ERROR' in repr(excinfo.value) # pip command exits zero printing stuff on stderr error_message_but_success_script = """from __future__ import print_function import sys print("TEST_ERROR", file=sys.stderr) sys.exit(0) """ def get_failed_command(prefix, extra_args): return tmp_script_commandline(error_message_but_success_script) monkeypatch.setattr( 'anaconda_project.internal.pip_api._get_pip_command', get_failed_command) pip_api.install(prefix=envdir, pkgs=['flake8']) # cannot exec pip def mock_popen(args, stdout=None, stderr=None): raise OSError("failed to exec") monkeypatch.setattr('subprocess.Popen', mock_popen) with pytest.raises(pip_api.PipError) as excinfo: pip_api.install(prefix=envdir, pkgs=['flake8']) assert 'failed to exec' in repr(excinfo.value)
def fix_environment_deviations(self, prefix, spec, deviations=None, create=True): if deviations is None: deviations = self.find_environment_deviations(prefix, spec) if deviations.unfixable: raise CondaManagerError("Unable to update environment at %s" % prefix) conda_meta = os.path.join(prefix, 'conda-meta') packed = os.path.join(conda_meta, '.packed') install_pip = True if os.path.isdir(conda_meta) and os.path.exists(packed): with open(packed) as f: packed_arch = f.read().strip() matched = packed_arch == conda_api.current_platform() if matched: if 'win' in conda_api.current_platform(): unpack_script = [ 'python', os.path.join(prefix, 'Scripts', 'conda-unpack-script.py') ] else: unpack_script = os.path.join(prefix, 'bin', 'conda-unpack') try: subprocess.check_call(unpack_script) os.remove(packed) install_pip = False except (subprocess.CalledProcessError, OSError) as e: self._log_info( 'Warning: conda-unpack could not be run: \n{}\n' 'The environment will be recreated.'.format(str(e))) create = True shutil.rmtree(prefix) else: self._log_info( 'Warning: The unpacked env does not match the current architecture. ' 'It will be recreated.') create = True shutil.rmtree(prefix) if os.path.isdir(conda_meta): to_update = list( set(deviations.missing_packages + deviations.wrong_version_packages)) if len(to_update) > 0: specs = spec.specs_for_conda_package_names(to_update) assert len(specs) == len(to_update) spec.apply_pins(prefix, specs) try: conda_api.install(prefix=prefix, pkgs=specs, channels=spec.channels, stdout_callback=self._on_stdout, stderr_callback=self._on_stderr) except conda_api.CondaError as e: raise CondaManagerError( "Failed to install packages: {}: {}".format( ", ".join(specs), str(e))) finally: spec.remove_pins(prefix) elif create: # Create environment from scratch command_line_packages = set(spec.conda_packages_for_create) try: conda_api.create(prefix=prefix, pkgs=list(command_line_packages), channels=spec.channels, stdout_callback=self._on_stdout, stderr_callback=self._on_stderr) except conda_api.CondaError as e: raise CondaManagerError( "Failed to create environment at %s: %s" % (prefix, str(e))) else: raise CondaManagerError("Conda environment at %s does not exist" % (prefix)) # now add pip if needed missing = list(deviations.missing_pip_packages) if (len(missing) > 0) and install_pip: specs = spec.specs_for_pip_package_names(missing) assert len(specs) == len(missing) try: pip_api.install(prefix=prefix, pkgs=specs, stdout_callback=self._on_stdout, stderr_callback=self._on_stderr) except pip_api.PipError as e: raise CondaManagerError( "Failed to install missing pip packages: {}: {}".format( ", ".join(missing), str(e))) # write a file to tell us we can short-circuit next time self._write_timestamp_file(prefix, spec)