diff --git a/src/python/pants/backend/awslambda/python/rules.py b/src/python/pants/backend/awslambda/python/rules.py index 9bba08d1fae..3219bc75ebf 100644 --- a/src/python/pants/backend/awslambda/python/rules.py +++ b/src/python/pants/backend/awslambda/python/rules.py @@ -4,14 +4,13 @@ import logging from dataclasses import dataclass -from pants.backend.awslambda.python.lambdex import Lambdex, LambdexLockfileSentinel +from pants.backend.awslambda.python.lambdex import Lambdex from pants.backend.awslambda.python.target_types import ( PythonAwsLambdaHandlerField, PythonAwsLambdaRuntime, ResolvedPythonAwsHandler, ResolvePythonAwsHandlerRequest, ) -from pants.backend.experimental.python.lockfile import PythonLockfileRequest from pants.backend.python.util_rules import pex_from_targets from pants.backend.python.util_rules.pex import ( Pex, @@ -87,15 +86,10 @@ async def package_python_awslambda( ], ) - lockfile_hex_digest = None - if lambdex.lockfile != "": - lockfile_request = await Get(PythonLockfileRequest, LambdexLockfileSentinel()) - lockfile_hex_digest = lockfile_request.requirements_hex_digest - lambdex_request = PexRequest( output_filename="lambdex.pex", internal_only=True, - requirements=lambdex.pex_requirements(lockfile_hex_digest), + requirements=lambdex.pex_requirements(), interpreter_constraints=lambdex.interpreter_constraints, main=lambdex.main, ) diff --git a/src/python/pants/backend/codegen/protobuf/python/rules.py b/src/python/pants/backend/codegen/protobuf/python/rules.py index 796e29e9fd6..4e25829615d 100644 --- a/src/python/pants/backend/codegen/protobuf/python/rules.py +++ b/src/python/pants/backend/codegen/protobuf/python/rules.py @@ -7,12 +7,10 @@ from pants.backend.codegen.protobuf.python.additional_fields import PythonSourceRootField from pants.backend.codegen.protobuf.python.grpc_python_plugin import GrpcPythonPlugin from pants.backend.codegen.protobuf.python.python_protobuf_subsystem import ( - MypyProtobufLockfileSentinel, PythonProtobufMypyPlugin, PythonProtobufSubsystem, ) from pants.backend.codegen.protobuf.target_types import ProtobufGrpcToggle, ProtobufSources -from pants.backend.experimental.python.lockfile import PythonLockfileRequest from pants.backend.python.target_types import PythonSources from pants.backend.python.util_rules import pex from pants.backend.python.util_rules.pex import PexRequest, PexResolveInfo, VenvPex, VenvPexRequest @@ -97,18 +95,13 @@ async def generate_python_from_protobuf( target_stripped_sources_request, ) - lockfile_hex_digest = None - if python_protobuf_mypy_plugin.lockfile != "": - lockfile_request = await Get(PythonLockfileRequest, MypyProtobufLockfileSentinel()) - lockfile_hex_digest = lockfile_request.requirements_hex_digest - protoc_gen_mypy_script = "protoc-gen-mypy" protoc_gen_mypy_grpc_script = "protoc-gen-mypy_grpc" mypy_pex = None mypy_request = PexRequest( output_filename="mypy_protobuf.pex", internal_only=True, - requirements=python_protobuf_mypy_plugin.pex_requirements(lockfile_hex_digest), + requirements=python_protobuf_mypy_plugin.pex_requirements(), interpreter_constraints=python_protobuf_mypy_plugin.interpreter_constraints, ) diff --git a/src/python/pants/backend/experimental/python/lockfile.py b/src/python/pants/backend/experimental/python/lockfile.py index 30952f89422..eb0feee7fa2 100644 --- a/src/python/pants/backend/experimental/python/lockfile.py +++ b/src/python/pants/backend/experimental/python/lockfile.py @@ -132,7 +132,7 @@ async def generate_lockfile( PexRequest( output_filename="poetry.pex", internal_only=True, - requirements=poetry_subsystem.pex_requirements(expected_lockfile_hex_digest=None), + requirements=poetry_subsystem.pex_requirements(), interpreter_constraints=poetry_subsystem.interpreter_constraints, main=EntryPoint(PurePath(POETRY_LAUNCHER.path).stem), sources=launcher_digest, diff --git a/src/python/pants/backend/python/goals/coverage_py.py b/src/python/pants/backend/python/goals/coverage_py.py index fc602de8d8f..5aa2022a5b0 100644 --- a/src/python/pants/backend/python/goals/coverage_py.py +++ b/src/python/pants/backend/python/goals/coverage_py.py @@ -334,17 +334,12 @@ class CoverageSetup: @rule async def setup_coverage(coverage: CoverageSubsystem) -> CoverageSetup: - lockfile_hex_digest = None - if coverage.lockfile != "": - lockfile_request = await Get(PythonLockfileRequest, CoveragePyLockfileSentinel()) - lockfile_hex_digest = lockfile_request.requirements_hex_digest - pex = await Get( VenvPex, PexRequest( output_filename="coverage.pex", internal_only=True, - requirements=coverage.pex_requirements(lockfile_hex_digest), + requirements=coverage.pex_requirements(), interpreter_constraints=coverage.interpreter_constraints, main=coverage.main, ), diff --git a/src/python/pants/backend/python/goals/pytest_runner.py b/src/python/pants/backend/python/goals/pytest_runner.py index 68d678f36db..b8923d55596 100644 --- a/src/python/pants/backend/python/goals/pytest_runner.py +++ b/src/python/pants/backend/python/goals/pytest_runner.py @@ -6,17 +6,12 @@ from dataclasses import dataclass from typing import Optional -from pants.backend.experimental.python.lockfile import PythonLockfileRequest from pants.backend.python.goals.coverage_py import ( CoverageConfig, CoverageSubsystem, PytestCoverageData, ) -from pants.backend.python.subsystems.pytest import ( - PyTest, - PytestLockfileSentinel, - PythonTestFieldSet, -) +from pants.backend.python.subsystems.pytest import PyTest, PythonTestFieldSet from pants.backend.python.util_rules.interpreter_constraints import InterpreterConstraints from pants.backend.python.util_rules.pex import Pex, PexRequest, VenvPex, VenvPexProcess from pants.backend.python.util_rules.pex_from_targets import PexFromTargetsRequest @@ -174,11 +169,6 @@ async def setup_pytest_for_target( interpreter_constraints = InterpreterConstraints.create_from_targets(all_targets, python_setup) - lockfile_hex_digest = None - if pytest.lockfile != "": - lockfile_request = await Get(PythonLockfileRequest, PytestLockfileSentinel()) - lockfile_hex_digest = lockfile_request.requirements_hex_digest - requirements_pex_get = Get( Pex, PexFromTargetsRequest, @@ -188,7 +178,7 @@ async def setup_pytest_for_target( Pex, PexRequest( output_filename="pytest.pex", - requirements=pytest.pex_requirements(lockfile_hex_digest), + requirements=pytest.pex_requirements(), interpreter_constraints=interpreter_constraints, internal_only=True, ), diff --git a/src/python/pants/backend/python/goals/repl.py b/src/python/pants/backend/python/goals/repl.py index 2e9f4ce944d..8514e0e68f1 100644 --- a/src/python/pants/backend/python/goals/repl.py +++ b/src/python/pants/backend/python/goals/repl.py @@ -1,8 +1,7 @@ # Copyright 2020 Pants project contributors (see CONTRIBUTORS.md). # Licensed under the Apache License, Version 2.0 (see LICENSE). -from pants.backend.experimental.python.lockfile import PythonLockfileRequest -from pants.backend.python.subsystems.ipython import IPython, IPythonLockfileSentinel +from pants.backend.python.subsystems.ipython import IPython from pants.backend.python.util_rules.pex import Pex, PexRequest from pants.backend.python.util_rules.pex_environment import PexEnvironment from pants.backend.python.util_rules.pex_from_targets import PexFromTargetsRequest @@ -76,17 +75,12 @@ async def create_ipython_repl_request( PythonSourceFiles, PythonSourceFilesRequest(repl.targets, include_files=True) ) - lockfile_hex_digest = None - if ipython.lockfile != "": - lockfile_request = await Get(PythonLockfileRequest, IPythonLockfileSentinel()) - lockfile_hex_digest = lockfile_request.requirements_hex_digest - ipython_request = Get( Pex, PexRequest( output_filename="ipython.pex", main=ipython.main, - requirements=ipython.pex_requirements(lockfile_hex_digest), + requirements=ipython.pex_requirements(), interpreter_constraints=requirements_pex_request.interpreter_constraints, internal_only=True, ), diff --git a/src/python/pants/backend/python/goals/setup_py.py b/src/python/pants/backend/python/goals/setup_py.py index f5be1d7ffe6..ff6a4f95dd3 100644 --- a/src/python/pants/backend/python/goals/setup_py.py +++ b/src/python/pants/backend/python/goals/setup_py.py @@ -13,13 +13,8 @@ from functools import partial from typing import Any, DefaultDict, Dict, List, Mapping, Set, Tuple, cast -from pants.backend.experimental.python.lockfile import PythonLockfileRequest from pants.backend.python.macros.python_artifact import PythonArtifact -from pants.backend.python.subsystems.setuptools import ( - PythonDistributionFieldSet, - Setuptools, - SetuptoolsLockfileSentinel, -) +from pants.backend.python.subsystems.setuptools import PythonDistributionFieldSet, Setuptools from pants.backend.python.target_types import ( PythonDistributionEntryPointsField, PythonProvidesField, @@ -420,17 +415,12 @@ async def run_setup_py(req: RunSetupPyRequest, setuptools: Setuptools) -> RunSet # Note that this pex has no entrypoint. We use it to run our generated setup.py, which # in turn imports from and invokes setuptools. - lockfile_hex_digest = None - if setuptools.lockfile != "": - lockfile_request = await Get(PythonLockfileRequest, SetuptoolsLockfileSentinel()) - lockfile_hex_digest = lockfile_request.requirements_hex_digest - setuptools_pex = await Get( VenvPex, PexRequest( output_filename="setuptools.pex", internal_only=True, - requirements=setuptools.pex_requirements(lockfile_hex_digest), + requirements=setuptools.pex_requirements(), interpreter_constraints=req.interpreter_constraints, ), ) diff --git a/src/python/pants/backend/python/lint/bandit/rules.py b/src/python/pants/backend/python/lint/bandit/rules.py index 1d57eef48e2..0736b33917d 100644 --- a/src/python/pants/backend/python/lint/bandit/rules.py +++ b/src/python/pants/backend/python/lint/bandit/rules.py @@ -4,12 +4,7 @@ from dataclasses import dataclass from typing import Tuple -from pants.backend.experimental.python.lockfile import PythonLockfileRequest -from pants.backend.python.lint.bandit.subsystem import ( - Bandit, - BanditFieldSet, - BanditLockfileSentinel, -) +from pants.backend.python.lint.bandit.subsystem import Bandit, BanditFieldSet from pants.backend.python.util_rules import pex from pants.backend.python.util_rules.interpreter_constraints import InterpreterConstraints from pants.backend.python.util_rules.pex import PexRequest, VenvPex, VenvPexProcess @@ -46,17 +41,13 @@ def generate_argv(source_files: SourceFiles, bandit: Bandit) -> Tuple[str, ...]: @rule(level=LogLevel.DEBUG) async def bandit_lint_partition(partition: BanditPartition, bandit: Bandit) -> LintResult: - lockfile_hex_digest = None - if bandit.lockfile != "": - lockfile_request = await Get(PythonLockfileRequest, BanditLockfileSentinel()) - lockfile_hex_digest = lockfile_request.requirements_hex_digest bandit_pex_get = Get( VenvPex, PexRequest( output_filename="bandit.pex", internal_only=True, - requirements=bandit.pex_requirements(lockfile_hex_digest), + requirements=bandit.pex_requirements(), interpreter_constraints=partition.interpreter_constraints, main=bandit.main, ), diff --git a/src/python/pants/backend/python/lint/black/rules.py b/src/python/pants/backend/python/lint/black/rules.py index a1b26a1ae47..ffac61c0b8f 100644 --- a/src/python/pants/backend/python/lint/black/rules.py +++ b/src/python/pants/backend/python/lint/black/rules.py @@ -4,9 +4,8 @@ from dataclasses import dataclass from typing import Tuple -from pants.backend.experimental.python.lockfile import PythonLockfileRequest from pants.backend.python.lint.black.skip_field import SkipBlackField -from pants.backend.python.lint.black.subsystem import Black, BlackLockfileSentinel +from pants.backend.python.lint.black.subsystem import Black from pants.backend.python.lint.python_fmt import PythonFmtRequest from pants.backend.python.target_types import InterpreterConstraintsField, PythonSources from pants.backend.python.util_rules import pex @@ -89,17 +88,12 @@ async def setup_black( else black.interpreter_constraints ) - lockfile_hex_digest = None - if black.lockfile != "": - lockfile_request = await Get(PythonLockfileRequest, BlackLockfileSentinel()) - lockfile_hex_digest = lockfile_request.requirements_hex_digest - black_pex_get = Get( VenvPex, PexRequest( output_filename="black.pex", internal_only=True, - requirements=black.pex_requirements(lockfile_hex_digest), + requirements=black.pex_requirements(), interpreter_constraints=tool_interpreter_constraints, main=black.main, ), diff --git a/src/python/pants/backend/python/lint/docformatter/rules.py b/src/python/pants/backend/python/lint/docformatter/rules.py index 8a1078ce6f1..b27a9a2b7b0 100644 --- a/src/python/pants/backend/python/lint/docformatter/rules.py +++ b/src/python/pants/backend/python/lint/docformatter/rules.py @@ -4,12 +4,8 @@ from dataclasses import dataclass from typing import Tuple -from pants.backend.experimental.python.lockfile import PythonLockfileRequest from pants.backend.python.lint.docformatter.skip_field import SkipDocformatterField -from pants.backend.python.lint.docformatter.subsystem import ( - Docformatter, - DocformatterLockfileSentinel, -) +from pants.backend.python.lint.docformatter.subsystem import Docformatter from pants.backend.python.lint.python_fmt import PythonFmtRequest from pants.backend.python.target_types import PythonSources from pants.backend.python.util_rules import pex @@ -61,17 +57,13 @@ def generate_args( @rule(level=LogLevel.DEBUG) async def setup_docformatter(setup_request: SetupRequest, docformatter: Docformatter) -> Setup: - lockfile_hex_digest = None - if docformatter.lockfile != "": - lockfile_request = await Get(PythonLockfileRequest, DocformatterLockfileSentinel()) - lockfile_hex_digest = lockfile_request.requirements_hex_digest docformatter_pex_get = Get( VenvPex, PexRequest( output_filename="docformatter.pex", internal_only=True, - requirements=docformatter.pex_requirements(lockfile_hex_digest), + requirements=docformatter.pex_requirements(), interpreter_constraints=docformatter.interpreter_constraints, main=docformatter.main, ), diff --git a/src/python/pants/backend/python/lint/flake8/rules.py b/src/python/pants/backend/python/lint/flake8/rules.py index a6be62cdd1f..ad757e2e305 100644 --- a/src/python/pants/backend/python/lint/flake8/rules.py +++ b/src/python/pants/backend/python/lint/flake8/rules.py @@ -4,12 +4,7 @@ from dataclasses import dataclass from typing import Tuple -from pants.backend.experimental.python.lockfile import PythonLockfileRequest -from pants.backend.python.lint.flake8.subsystem import ( - Flake8, - Flake8FieldSet, - Flake8LockfileSentinel, -) +from pants.backend.python.lint.flake8.subsystem import Flake8, Flake8FieldSet from pants.backend.python.util_rules import pex from pants.backend.python.util_rules.interpreter_constraints import InterpreterConstraints from pants.backend.python.util_rules.pex import PexRequest, VenvPex, VenvPexProcess @@ -46,17 +41,12 @@ def generate_argv(source_files: SourceFiles, flake8: Flake8) -> Tuple[str, ...]: @rule(level=LogLevel.DEBUG) async def flake8_lint_partition(partition: Flake8Partition, flake8: Flake8) -> LintResult: - lockfile_hex_digest = None - if flake8.lockfile != "": - lockfile_request = await Get(PythonLockfileRequest, Flake8LockfileSentinel()) - lockfile_hex_digest = lockfile_request.requirements_hex_digest - flake8_pex_get = Get( VenvPex, PexRequest( output_filename="flake8.pex", internal_only=True, - requirements=flake8.pex_requirements(lockfile_hex_digest), + requirements=flake8.pex_requirements(), interpreter_constraints=partition.interpreter_constraints, main=flake8.main, ), diff --git a/src/python/pants/backend/python/lint/isort/rules.py b/src/python/pants/backend/python/lint/isort/rules.py index 1adbaed4670..88fee76ea1d 100644 --- a/src/python/pants/backend/python/lint/isort/rules.py +++ b/src/python/pants/backend/python/lint/isort/rules.py @@ -4,9 +4,8 @@ from dataclasses import dataclass from typing import Tuple -from pants.backend.experimental.python.lockfile import PythonLockfileRequest from pants.backend.python.lint.isort.skip_field import SkipIsortField -from pants.backend.python.lint.isort.subsystem import Isort, IsortLockfileSentinel +from pants.backend.python.lint.isort.subsystem import Isort from pants.backend.python.lint.python_fmt import PythonFmtRequest from pants.backend.python.target_types import PythonSources from pants.backend.python.util_rules import pex @@ -78,17 +77,12 @@ def generate_argv( @rule(level=LogLevel.DEBUG) async def setup_isort(setup_request: SetupRequest, isort: Isort) -> Setup: - lockfile_hex_digest = None - if isort.lockfile != "": - lockfile_request = await Get(PythonLockfileRequest, IsortLockfileSentinel()) - lockfile_hex_digest = lockfile_request.requirements_hex_digest - isort_pex_get = Get( VenvPex, PexRequest( output_filename="isort.pex", internal_only=True, - requirements=isort.pex_requirements(lockfile_hex_digest), + requirements=isort.pex_requirements(), interpreter_constraints=isort.interpreter_constraints, main=isort.main, ), diff --git a/src/python/pants/backend/python/lint/pylint/rules.py b/src/python/pants/backend/python/lint/pylint/rules.py index ac11c222c41..75db43fcb53 100644 --- a/src/python/pants/backend/python/lint/pylint/rules.py +++ b/src/python/pants/backend/python/lint/pylint/rules.py @@ -5,12 +5,10 @@ from dataclasses import dataclass from typing import Iterable, List, Tuple -from pants.backend.experimental.python.lockfile import PythonLockfileRequest from pants.backend.python.lint.pylint.subsystem import ( Pylint, PylintFieldSet, PylintFirstPartyPlugins, - PylintLockfileSentinel, ) from pants.backend.python.target_types import InterpreterConstraintsField from pants.backend.python.util_rules import pex_from_targets @@ -82,11 +80,6 @@ def generate_argv(source_files: SourceFiles, pylint: Pylint) -> Tuple[str, ...]: async def pylint_lint_partition( partition: PylintPartition, pylint: Pylint, first_party_plugins: PylintFirstPartyPlugins ) -> LintResult: - lockfile_hex_digest = None - if pylint.lockfile != "": - lockfile_request = await Get(PythonLockfileRequest, PylintLockfileSentinel()) - lockfile_hex_digest = lockfile_request.requirements_hex_digest - requirements_pex_get = Get( Pex, PexFromTargetsRequest, @@ -108,7 +101,6 @@ async def pylint_lint_partition( internal_only=True, requirements=pylint.pex_requirements( extra_requirements=first_party_plugins.requirement_strings, - expected_lockfile_hex_digest=lockfile_hex_digest, ), interpreter_constraints=partition.interpreter_constraints, ), diff --git a/src/python/pants/backend/python/lint/yapf/rules.py b/src/python/pants/backend/python/lint/yapf/rules.py index afc9e6541e9..dbf56b57d8b 100644 --- a/src/python/pants/backend/python/lint/yapf/rules.py +++ b/src/python/pants/backend/python/lint/yapf/rules.py @@ -4,10 +4,9 @@ from dataclasses import dataclass from typing import Tuple -from pants.backend.experimental.python.lockfile import PythonLockfileRequest from pants.backend.python.lint.python_fmt import PythonFmtRequest from pants.backend.python.lint.yapf.skip_field import SkipYapfField -from pants.backend.python.lint.yapf.subsystem import Yapf, YapfLockfileSentinel +from pants.backend.python.lint.yapf.subsystem import Yapf from pants.backend.python.target_types import PythonSources from pants.backend.python.util_rules import pex from pants.backend.python.util_rules.pex import PexRequest, VenvPex, VenvPexProcess @@ -68,17 +67,12 @@ def generate_argv(source_files: SourceFiles, yapf: Yapf, check_only: bool) -> Tu @rule(level=LogLevel.DEBUG) async def setup_yapf(setup_request: SetupRequest, yapf: Yapf) -> Setup: - lockfile_hex_digest = None - if yapf.lockfile != "": - lockfile_request = await Get(PythonLockfileRequest, YapfLockfileSentinel()) - lockfile_hex_digest = lockfile_request.requirements_hex_digest - yapf_pex_get = Get( VenvPex, PexRequest( output_filename="yapf.pex", internal_only=True, - requirements=yapf.pex_requirements(lockfile_hex_digest), + requirements=yapf.pex_requirements(), interpreter_constraints=yapf.interpreter_constraints, main=yapf.main, ), diff --git a/src/python/pants/backend/python/subsystems/python_tool_base.py b/src/python/pants/backend/python/subsystems/python_tool_base.py index 3182813f482..2eb82ddb463 100644 --- a/src/python/pants/backend/python/subsystems/python_tool_base.py +++ b/src/python/pants/backend/python/subsystems/python_tool_base.py @@ -6,12 +6,14 @@ import importlib.resources from typing import ClassVar, Iterable, Sequence, cast +from pants.backend.experimental.python.lockfile_metadata import calculate_invalidation_digest from pants.backend.python.target_types import ConsoleScript, EntryPoint, MainSpecification from pants.backend.python.util_rules.interpreter_constraints import InterpreterConstraints from pants.backend.python.util_rules.pex import PexRequirements from pants.engine.fs import FileContent from pants.option.errors import OptionsError from pants.option.subsystem import Subsystem +from pants.util.ordered_set import FrozenOrderedSet class PythonToolRequirementsBase(Subsystem): @@ -119,7 +121,6 @@ def all_requirements(self) -> tuple[str, ...]: def pex_requirements( self, - expected_lockfile_hex_digest: str | None, *, extra_requirements: Iterable[str] = (), ) -> PexRequirements: @@ -128,8 +129,14 @@ def pex_requirements( If the tool supports lockfiles, the returned type will install from the lockfile rather than `all_requirements`. """ - if not self.register_lockfile or self.lockfile == "": - return PexRequirements((*self.all_requirements, *extra_requirements)) + + requirements = (*self.all_requirements, *extra_requirements) + + if not self.uses_lockfile: + return PexRequirements(requirements) + + hex_digest = calculate_invalidation_digest(FrozenOrderedSet(requirements)) + if self.lockfile == "": assert self.default_lockfile_resource is not None return PexRequirements( @@ -137,14 +144,14 @@ def pex_requirements( f"{self.options_scope}_default_lockfile.txt", importlib.resources.read_binary(*self.default_lockfile_resource), ), - lockfile_hex_digest=expected_lockfile_hex_digest, + lockfile_hex_digest=hex_digest, ) return PexRequirements( file_path=self.lockfile, file_path_description_of_origin=( f"the option `[{self.options_scope}].experimental_lockfile`" ), - lockfile_hex_digest=expected_lockfile_hex_digest, + lockfile_hex_digest=hex_digest, ) @property @@ -155,6 +162,10 @@ def lockfile(self) -> str: """ return cast(str, self.options.experimental_lockfile) + @property + def uses_lockfile(self) -> bool: + return self.register_lockfile and self.lockfile != "" + @property def interpreter_constraints(self) -> InterpreterConstraints: """The interpreter constraints to use when installing and running the tool. diff --git a/src/python/pants/backend/python/typecheck/mypy/rules.py b/src/python/pants/backend/python/typecheck/mypy/rules.py index 5789fe956c3..6c2a91c9fb3 100644 --- a/src/python/pants/backend/python/typecheck/mypy/rules.py +++ b/src/python/pants/backend/python/typecheck/mypy/rules.py @@ -143,7 +143,6 @@ async def mypy_typecheck_partition( internal_only=True, main=mypy.main, requirements=mypy.pex_requirements( - expected_lockfile_hex_digest=None, extra_requirements=first_party_plugins.requirement_strings, ), interpreter_constraints=tool_interpreter_constraints,