Skip to content

Commit

Permalink
Disambiguate binary and lambda output. (pantsbuild#10735)
Browse files Browse the repository at this point in the history
Previously we named them after the target name, which might
not be unique across the repo. Now we use the entire target
address. The new name is `path.to.target.dir/target_name.pex/zip`.
This seems like a good compromise between completely flat
and overstructured. It also preserves the existing filenames,
for less confusion.

[ci skip-rust]
  • Loading branch information
benjyw authored Sep 4, 2020
1 parent a403445 commit fbf17ae
Show file tree
Hide file tree
Showing 6 changed files with 59 additions and 6 deletions.
2 changes: 1 addition & 1 deletion build-support/bin/bootstrap_pants_pex.sh
Original file line number Diff line number Diff line change
Expand Up @@ -15,4 +15,4 @@ source "${REPO_ROOT}/build-support/pants_venv"
source "${REPO_ROOT}/build-support/bin/native/bootstrap_code.sh"

./pants binary src/python/pants/bin:pants_local_binary || exit 1
mv dist/pants_local_binary.pex pants.pex
mv dist/src.python.pants.bin/pants_local_binary.pex pants.pex
2 changes: 2 additions & 0 deletions pants.toml
Original file line number Diff line number Diff line change
@@ -1,6 +1,8 @@
[GLOBAL]
print_exception_stacktrace = true

pants_distdir_legacy_paths = false

# Enable our custom loose-source plugins.
pythonpath = ["%(buildroot)s/pants-plugins"]
backend_packages.add = [
Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,8 @@
# Copyright 2019 Pants project contributors (see CONTRIBUTORS.md).
# Licensed under the Apache License, Version 2.0 (see LICENSE).

import logging
import os
from dataclasses import dataclass

from pants.backend.awslambda.common.awslambda_common_rules import (
Expand Down Expand Up @@ -30,8 +32,11 @@
from pants.engine.process import ProcessResult
from pants.engine.rules import Get, collect_rules, rule
from pants.engine.unions import UnionRule
from pants.option.global_options import GlobalOptions
from pants.util.logging import LogLevel

logger = logging.getLogger(__name__)


@dataclass(frozen=True)
class PythonAwsLambdaFieldSet(AWSLambdaFieldSet):
Expand All @@ -48,10 +53,23 @@ class LambdexSetup:

@rule(desc="Create Python AWS Lambda", level=LogLevel.DEBUG)
async def create_python_awslambda(
field_set: PythonAwsLambdaFieldSet, lambdex_setup: LambdexSetup
field_set: PythonAwsLambdaFieldSet, lambdex_setup: LambdexSetup, global_options: GlobalOptions
) -> CreatedAWSLambda:
# Lambdas typically use the .zip suffix, so we use that instead of .pex.
pex_filename = f"{field_set.address.target_name}.zip"
disambiguated_pex_filename = os.path.join(
field_set.address.spec_path.replace(os.sep, "."), f"{field_set.address.target_name}.zip"
)
if global_options.options.pants_distdir_legacy_paths:
pex_filename = f"{field_set.address.target_name}.zip"
logger.warning(
f"Writing to the legacy subpath: {pex_filename}, which may not be unique. An "
f"upcoming version of Pants will switch to writing to the fully-qualified subpath: "
f"{disambiguated_pex_filename}. You can effect that switch now (and silence this "
f"warning) by setting `pants_distdir_legacy_paths = false` in the [GLOBAL] section of "
f"pants.toml."
)
else:
pex_filename = disambiguated_pex_filename
# We hardcode the platform value to the appropriate one for each AWS Lambda runtime.
# (Running the "hello world" lambda in the example code will report the platform, and can be
# used to verify correctness of these platform strings.)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,7 @@ def create_python_awslambda(rule_runner: RuleRunner, addr: str) -> Tuple[str, by
args=[
"--backend-packages=pants.backend.awslambda.python",
"--source-root-patterns=src/python",
"--pants-distdir-legacy-paths=false",
]
)
target = rule_runner.get_target(Address.parse(addr), bootstrapper)
Expand Down Expand Up @@ -83,7 +84,7 @@ def handler(event, context):
zip_file_relpath, content = create_python_awslambda(
rule_runner, "src/python/foo/bar:hello_world_lambda"
)
assert "hello_world_lambda.zip" == zip_file_relpath
assert "src.python.foo.bar/hello_world_lambda.zip" == zip_file_relpath
zipfile = ZipFile(BytesIO(content))
names = set(zipfile.namelist())
assert "lambdex_handler.py" in names
Expand Down
25 changes: 23 additions & 2 deletions src/python/pants/backend/python/goals/create_python_binary.py
Original file line number Diff line number Diff line change
@@ -1,6 +1,8 @@
# Copyright 2019 Pants project contributors (see CONTRIBUTORS.md).
# Licensed under the Apache License, Version 2.0 (see LICENSE).

import logging
import os
from dataclasses import dataclass
from typing import Tuple

Expand Down Expand Up @@ -28,8 +30,11 @@
from pants.engine.rules import Get, collect_rules, rule
from pants.engine.target import HydratedSources, HydrateSourcesRequest
from pants.engine.unions import UnionRule
from pants.option.global_options import GlobalOptions
from pants.util.logging import LogLevel

logger = logging.getLogger(__name__)


@dataclass(frozen=True)
class PythonBinaryFieldSet(BinaryFieldSet, RunFieldSet):
Expand Down Expand Up @@ -67,7 +72,9 @@ def generate_additional_args(

@rule(level=LogLevel.DEBUG)
async def create_python_binary(
field_set: PythonBinaryFieldSet, python_binary_defaults: PythonBinaryDefaults
field_set: PythonBinaryFieldSet,
python_binary_defaults: PythonBinaryDefaults,
global_options: GlobalOptions,
) -> CreatedBinary:
entry_point = field_set.entry_point.value
if entry_point is None:
Expand All @@ -80,7 +87,21 @@ async def create_python_binary(
entry_point = PythonBinarySources.translate_source_file_to_entry_point(
stripped_binary_sources.snapshot.files
)
output_filename = f"{field_set.address.target_name}.pex"

disambiguated_output_filename = os.path.join(
field_set.address.spec_path.replace(os.sep, "."), f"{field_set.address.target_name}.pex"
)
if global_options.options.pants_distdir_legacy_paths:
output_filename = f"{field_set.address.target_name}.pex"
logger.warning(
f"Writing to the legacy subpath: {output_filename}, which may not be unique. An "
f"upcoming version of Pants will switch to writing to the fully-qualified subpath: "
f"{disambiguated_output_filename}. You can effect that switch now (and silence this "
f"warning) by setting `pants_distdir_legacy_paths = false` in the [GLOBAL] section of "
f"pants.toml."
)
else:
output_filename = disambiguated_output_filename
two_step_pex = await Get(
TwoStepPex,
TwoStepPexFromTargetsRequest(
Expand Down
11 changes: 11 additions & 0 deletions src/python/pants/option/global_options.py
Original file line number Diff line number Diff line change
Expand Up @@ -384,6 +384,17 @@ def register_bootstrap_options(cls, register):
default=os.path.join(buildroot, "dist"),
help="Write end-product artifacts to this dir.",
)
# TODO: Change the default to false in 2.1, deprecate the option in 2.2 and remove in 2.3.
register(
"--pants-distdir-legacy-paths",
type=bool,
advanced=True,
default=True,
help="Whether to write binaries to the pre-2.0 paths under distdir. These legacy "
"paths are not qualified by target address, so may be ambiguous. This option "
"is a temporary mechanism for easing transition to 2.0. We recommemd switching "
"to the new, unambiguous paths ASAP, by setting this option to true.",
)
register(
"--pants-subprocessdir",
advanced=True,
Expand Down

0 comments on commit fbf17ae

Please sign in to comment.