def test_invalid_variable() -> None:
    pants_env = PantsEnvironment()

    with pytest.raises(ValueError) as exc:
        pants_env.get_subset(["3INVALID=doesn't matter"])
    assert (
        "An invalid variable was requested via the --test-extra-env-var mechanism: 3INVALID"
        in str(exc)
    )
Exemple #2
0
    def _init_graph_session(
        cls,
        options_bootstrapper: OptionsBootstrapper,
        build_config: BuildConfiguration,
        options: Options,
        scheduler: Optional[GraphScheduler] = None,
    ) -> GraphSession:
        native = Native()
        native.set_panic_handler()
        graph_scheduler_helper = scheduler or EngineInitializer.setup_graph(
            options_bootstrapper, build_config)

        try:
            global_scope = options.for_global_scope()
        except UnknownFlagsError as err:
            cls._handle_unknown_flags(err, options_bootstrapper)
            raise

        stream_workunits = len(
            options.for_global_scope().streaming_workunits_handlers) != 0
        return graph_scheduler_helper.new_session(
            RunTracker.global_instance().run_id,
            dynamic_ui=global_scope.dynamic_ui,
            use_colors=global_scope.get("colors", True),
            should_report_workunits=stream_workunits,
            session_values=SessionValues({
                OptionsBootstrapper:
                options_bootstrapper,
                PantsEnvironment:
                PantsEnvironment(os.environ),
            }),
        )
Exemple #3
0
    def _init_graph_session(
        cls,
        options_bootstrapper: OptionsBootstrapper,
        build_config: BuildConfiguration,
        run_id: str,
        options: Options,
        scheduler: Optional[GraphScheduler] = None,
        cancellation_latch: Optional[PySessionCancellationLatch] = None,
    ) -> GraphSession:
        native = Native()
        native.set_panic_handler()
        graph_scheduler_helper = scheduler or EngineInitializer.setup_graph(
            options_bootstrapper, build_config
        )

        try:
            global_scope = options.for_global_scope()
        except UnknownFlagsError as err:
            cls._handle_unknown_flags(err, options_bootstrapper)
            raise

        return graph_scheduler_helper.new_session(
            run_id,
            dynamic_ui=global_scope.dynamic_ui,
            use_colors=global_scope.get("colors", True),
            session_values=SessionValues(
                {
                    OptionsBootstrapper: options_bootstrapper,
                    PantsEnvironment: PantsEnvironment(os.environ),
                }
            ),
            cancellation_latch=cancellation_latch,
        )
Exemple #4
0
def get_filtered_environment(
    test_subsystem: TestSubsystem, pants_env: PantsEnvironment
) -> TestExtraEnv:
    env = (
        pants_env.get_subset(test_subsystem.extra_env_vars)
        if test_subsystem.extra_env_vars
        else FrozenDict({})
    )
    return TestExtraEnv(env)
Exemple #5
0
    def __init__(
        self,
        *,
        rules: Optional[Iterable] = None,
        target_types: Optional[Iterable[Type[Target]]] = None,
        objects: Optional[Dict[str, Any]] = None,
        context_aware_object_factories: Optional[Dict[str, Any]] = None,
    ) -> None:
        self.build_root = os.path.realpath(mkdtemp(suffix="_BUILD_ROOT"))
        safe_mkdir(self.build_root, clean=True)
        safe_mkdir(self.pants_workdir)
        BuildRoot().path = self.build_root

        # TODO: Redesign rule registration for tests to be more ergonomic and to make this less
        #  special-cased.
        all_rules = (
            *(rules or ()),
            *source_root.rules(),
            *pants_environment.rules(),
            QueryRule(WrappedTarget, (Address,)),
        )
        build_config_builder = BuildConfiguration.Builder()
        build_config_builder.register_aliases(
            BuildFileAliases(
                objects=objects, context_aware_object_factories=context_aware_object_factories
            )
        )
        build_config_builder.register_rules(all_rules)
        build_config_builder.register_target_types(target_types or ())
        self.build_config = build_config_builder.create()

        options_bootstrapper = create_options_bootstrapper()
        global_options = options_bootstrapper.bootstrap_options.for_global_scope()
        local_store_dir = global_options.local_store_dir
        local_execution_root_dir = global_options.local_execution_root_dir
        named_caches_dir = global_options.named_caches_dir

        graph_session = EngineInitializer.setup_graph_extended(
            pants_ignore_patterns=[],
            use_gitignore=False,
            local_store_dir=local_store_dir,
            local_execution_root_dir=local_execution_root_dir,
            named_caches_dir=named_caches_dir,
            native=Native(),
            options_bootstrapper=options_bootstrapper,
            build_root=self.build_root,
            build_configuration=self.build_config,
            execution_options=ExecutionOptions.from_bootstrap_options(global_options),
        ).new_session(
            build_id="buildid_for_test",
            session_values=SessionValues(
                {OptionsBootstrapper: options_bootstrapper, PantsEnvironment: PantsEnvironment()}
            ),
            should_report_workunits=True,
        )
        self.scheduler = graph_session.scheduler_session
Exemple #6
0
 def _resolve_plugins(
     self, options_bootstrapper: OptionsBootstrapper
 ) -> ResolvedPluginDistributions:
     session = self._scheduler.scheduler.new_session(
         "plugin_resolver",
         session_values=SessionValues({
             OptionsBootstrapper:
             options_bootstrapper,
             PantsEnvironment:
             PantsEnvironment(dict(options_bootstrapper.env_tuples)),
         }),
     )
     return cast(
         ResolvedPluginDistributions,
         session.product_request(ResolvedPluginDistributions,
                                 [self._interpreter_constraints])[0],
     )
Exemple #7
0
    def run_goal_rule(
        self,
        goal: Type[Goal],
        *,
        global_args: Optional[Iterable[str]] = None,
        args: Optional[Iterable[str]] = None,
        env: Optional[Mapping[str, str]] = None,
    ) -> GoalRuleResult:
        options_bootstrapper = create_options_bootstrapper(
            args=(*(global_args or []), goal.name, *(args or [])),
            env=env,
        )

        raw_specs = options_bootstrapper.get_full_options([
            *GlobalOptions.known_scope_infos(),
            *goal.subsystem_cls.known_scope_infos()
        ]).specs
        specs = SpecsParser(self.build_root).parse_specs(raw_specs)

        stdout, stderr = StringIO(), StringIO()
        console = Console(stdout=stdout, stderr=stderr)

        session = self.scheduler.scheduler.new_session(
            build_id="buildid_for_test",
            should_report_workunits=True,
            session_values=SessionValues({
                OptionsBootstrapper:
                options_bootstrapper,
                PantsEnvironment:
                PantsEnvironment(env)
            }),
        )

        exit_code = session.run_goal_rule(
            goal,
            Params(
                specs,
                console,
                Workspace(self.scheduler),
                InteractiveRunner(self.scheduler),
            ),
        )

        console.flush()
        return GoalRuleResult(exit_code, stdout.getvalue(), stderr.getvalue())
Exemple #8
0
    def set_options(self, args: Iterable[str], *, env: Optional[Mapping[str, str]] = None) -> None:
        """Update the engine session with new options and/or environment variables.

        The environment variables will be used to set the `PantsEnvironment`, which is the
        environment variables captured by the parent Pants process. Some rules use this to be able
        to read arbitrary env vars. Any options that start with `PANTS_` will also be used to set
        options.

        This will override any previously configured values.
        """
        options_bootstrapper = create_options_bootstrapper(args=args, env=env)
        self.scheduler = self.scheduler.scheduler.new_session(
            build_id="buildid_for_test",
            should_report_workunits=True,
            session_values=SessionValues(
                {OptionsBootstrapper: options_bootstrapper, PantsEnvironment: PantsEnvironment(env)}
            ),
        )
Exemple #9
0
    def request(self, output_type: Type["TestBase._O"],
                inputs: Iterable[Any]) -> "TestBase._O":
        # TODO: Update all callsites to pass this explicitly via session values.
        session = self.scheduler
        for value in inputs:
            if type(value) == OptionsBootstrapper:
                session = self.scheduler.scheduler.new_session(
                    build_id="buildid_for_test",
                    should_report_workunits=True,
                    session_values=SessionValues({
                        OptionsBootstrapper:
                        value,
                        PantsEnvironment:
                        PantsEnvironment()
                    }),
                )

        result = assert_single_element(
            session.product_request(output_type, [Params(*inputs)]))
        return cast(TestBase._O, result)
def test_pants_environment(input_strs: List[str], expected: Dict[str, str]) -> None:
    pants_env = PantsEnvironment({"A": "a", "B": "b", "C": "c"})

    subset = pants_env.get_subset(input_strs)
    assert dict(subset) == expected
def get_subprocess_environment(
        subproc_env: SubprocessEnvironment,
        pants_env: PantsEnvironment) -> SubprocessEnvironmentVars:
    return SubprocessEnvironmentVars(
        pants_env.get_subset(subproc_env.env_vars_to_pass_to_subprocesses,
                             allowed=SETTABLE_ENV_VARS))
Exemple #12
0
def pants_environment(session_values: SessionValues) -> PantsEnvironment:
    # TODO: The @deprecated decorator seems to obscure type information.
    return cast(PantsEnvironment, PantsEnvironment(session_values[CompleteEnvironment]))
Exemple #13
0
    def __init__(
        self,
        *,
        rules: Iterable | None = None,
        target_types: Iterable[type[Target]] | None = None,
        objects: dict[str, Any] | None = None,
        context_aware_object_factories: dict[str, Any] | None = None,
        isolated_local_store: bool = False,
        ca_certs_path: str | None = None,
    ) -> None:
        self.build_root = os.path.realpath(mkdtemp(suffix="_BUILD_ROOT"))
        safe_mkdir(self.build_root, clean=True)
        safe_mkdir(self.pants_workdir)
        BuildRoot().path = self.build_root

        # TODO: Redesign rule registration for tests to be more ergonomic and to make this less
        #  special-cased.
        all_rules = (
            *(rules or ()),
            *source_root.rules(),
            *pants_environment.rules(),
            QueryRule(WrappedTarget, [Address]),
            QueryRule(UnionMembership, []),
        )
        build_config_builder = BuildConfiguration.Builder()
        build_config_builder.register_aliases(
            BuildFileAliases(
                objects=objects,
                context_aware_object_factories=context_aware_object_factories))
        build_config_builder.register_rules(all_rules)
        build_config_builder.register_target_types(target_types or ())
        self.build_config = build_config_builder.create()

        self.options_bootstrapper = create_options_bootstrapper()
        options = self.options_bootstrapper.full_options(self.build_config)
        global_options = self.options_bootstrapper.bootstrap_options.for_global_scope(
        )
        local_store_dir = (os.path.realpath(safe_mkdtemp())
                           if isolated_local_store else
                           global_options.local_store_dir)
        local_execution_root_dir = global_options.local_execution_root_dir
        named_caches_dir = global_options.named_caches_dir

        graph_session = EngineInitializer.setup_graph_extended(
            pants_ignore_patterns=GlobalOptions.compute_pants_ignore(
                self.build_root, global_options),
            use_gitignore=False,
            local_store_dir=local_store_dir,
            local_execution_root_dir=local_execution_root_dir,
            named_caches_dir=named_caches_dir,
            native=Native(),
            build_root=self.build_root,
            build_configuration=self.build_config,
            executor=_EXECUTOR,
            execution_options=ExecutionOptions.from_options(options),
            ca_certs_path=ca_certs_path,
            native_engine_visualize_to=None,
        ).new_session(
            build_id="buildid_for_test",
            session_values=SessionValues({
                OptionsBootstrapper: self.options_bootstrapper,
                PantsEnvironment: PantsEnvironment(),
            }),
        )
        self.scheduler = graph_session.scheduler_session