__init__.py 2.7 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394
  1. import collections
  2. import logging
  3. from typing import Generator, List, Optional, Sequence, Tuple
  4. from pip._internal.utils.logging import indent_log
  5. from .req_file import parse_requirements
  6. from .req_install import InstallRequirement
  7. from .req_set import RequirementSet
  8. __all__ = [
  9. "RequirementSet",
  10. "InstallRequirement",
  11. "parse_requirements",
  12. "install_given_reqs",
  13. ]
  14. logger = logging.getLogger(__name__)
  15. class InstallationResult:
  16. def __init__(self, name: str) -> None:
  17. self.name = name
  18. def __repr__(self) -> str:
  19. return f"InstallationResult(name={self.name!r})"
  20. def _validate_requirements(
  21. requirements: List[InstallRequirement],
  22. ) -> Generator[Tuple[str, InstallRequirement], None, None]:
  23. for req in requirements:
  24. assert req.name, f"invalid to-be-installed requirement: {req}"
  25. yield req.name, req
  26. def install_given_reqs(
  27. requirements: List[InstallRequirement],
  28. install_options: List[str],
  29. global_options: Sequence[str],
  30. root: Optional[str],
  31. home: Optional[str],
  32. prefix: Optional[str],
  33. warn_script_location: bool,
  34. use_user_site: bool,
  35. pycompile: bool,
  36. ) -> List[InstallationResult]:
  37. """
  38. Install everything in the given list.
  39. (to be called after having downloaded and unpacked the packages)
  40. """
  41. to_install = collections.OrderedDict(_validate_requirements(requirements))
  42. if to_install:
  43. logger.info(
  44. "Installing collected packages: %s",
  45. ", ".join(to_install.keys()),
  46. )
  47. installed = []
  48. with indent_log():
  49. for req_name, requirement in to_install.items():
  50. if requirement.should_reinstall:
  51. logger.info("Attempting uninstall: %s", req_name)
  52. with indent_log():
  53. uninstalled_pathset = requirement.uninstall(auto_confirm=True)
  54. else:
  55. uninstalled_pathset = None
  56. try:
  57. requirement.install(
  58. install_options,
  59. global_options,
  60. root=root,
  61. home=home,
  62. prefix=prefix,
  63. warn_script_location=warn_script_location,
  64. use_user_site=use_user_site,
  65. pycompile=pycompile,
  66. )
  67. except Exception:
  68. # if install did not succeed, rollback previous uninstall
  69. if uninstalled_pathset and not requirement.install_succeeded:
  70. uninstalled_pathset.rollback()
  71. raise
  72. else:
  73. if uninstalled_pathset and requirement.install_succeeded:
  74. uninstalled_pathset.commit()
  75. installed.append(InstallationResult(req_name))
  76. return installed