def run_goal_rules( self, *, options_bootstrapper: OptionsBootstrapper, union_membership: UnionMembership, options: Options, goals: Iterable[str], specs: Specs, ) -> int: """Runs @goal_rules sequentially and interactively by requesting their implicit Goal products. For retryable failures, raises scheduler.ExecutionError. :returns: An exit code. """ global_options = options.for_global_scope() console = Console( use_colors=global_options.colors, session=self.scheduler_session if global_options.get("v2_ui") else None, ) workspace = Workspace(self.scheduler_session) interactive_runner = InteractiveRunner(self.scheduler_session) for goal in goals: goal_product = self.goal_map[goal] # NB: We no-op for goals that have no V2 implementation because no relevant backends are # registered. This allows us to safely set `--v1 --v2`, even if no V2 backends are registered. # Once V1 is removed, we might want to reconsider the behavior to instead warn or error when # trying to run something like `./pants run` without any backends registered. is_implemented = union_membership.has_members_for_all( goal_product.subsystem_cls.required_union_implementations) if not is_implemented: continue params = Params( specs.provided_specs, options_bootstrapper, console, workspace, interactive_runner, ) logger.debug( f"requesting {goal_product} to satisfy execution of `{goal}` goal" ) try: exit_code = self.scheduler_session.run_goal_rule( goal_product, params) finally: console.flush() if exit_code != PANTS_SUCCEEDED_EXIT_CODE: return exit_code return PANTS_SUCCEEDED_EXIT_CODE
def get_all_help_info( cls, options: Options, union_membership: UnionMembership, consumed_scopes_mapper: ConsumedScopesMapper, registered_target_types: RegisteredTargetTypes, ) -> AllHelpInfo: scope_to_help_info = {} name_to_goal_info = {} for scope_info in sorted(options.known_scope_to_info.values(), key=lambda x: x.scope): options.for_scope(scope_info.scope) # Force parsing. subsystem_cls = scope_info.subsystem_cls if not scope_info.description: cls_name = ( f"{subsystem_cls.__module__}.{subsystem_cls.__qualname__}" if subsystem_cls else "") raise ValueError( f"Subsystem {cls_name} with scope `{scope_info.scope}` has no description. " f"Add a class property `help`.") is_goal = subsystem_cls is not None and issubclass( subsystem_cls, GoalSubsystem) oshi = HelpInfoExtracter( scope_info.scope).get_option_scope_help_info( scope_info.description, options.get_parser(scope_info.scope), is_goal) scope_to_help_info[oshi.scope] = oshi if is_goal: goal_subsystem_cls = cast(Type[GoalSubsystem], subsystem_cls) is_implemented = union_membership.has_members_for_all( goal_subsystem_cls.required_union_implementations) name_to_goal_info[scope_info.scope] = GoalHelpInfo( goal_subsystem_cls.name, scope_info.description, is_implemented, consumed_scopes_mapper(scope_info.scope), ) name_to_target_type_info = { alias: TargetTypeHelpInfo.create(target_type, union_membership=union_membership) for alias, target_type in registered_target_types.aliases_to_types.items() if (not alias.startswith("_") and target_type.removal_version is None and alias != target_type.deprecated_alias) } return AllHelpInfo( scope_to_help_info=scope_to_help_info, name_to_goal_info=name_to_goal_info, name_to_target_type_info=name_to_target_type_info, )
def run_goal_rules( self, *, options_bootstrapper: OptionsBootstrapper, union_membership: UnionMembership, goals: Iterable[str], specs: Specs, poll: bool = False, poll_delay: Optional[float] = None, ) -> int: """Runs @goal_rules sequentially and interactively by requesting their implicit Goal products. For retryable failures, raises scheduler.ExecutionError. :returns: An exit code. """ workspace = Workspace(self.scheduler_session) interactive_runner = InteractiveRunner(self.scheduler_session) for goal in goals: goal_product = self.goal_map[goal] # NB: We no-op for goals that have no implementation because no relevant backends are # registered. We might want to reconsider the behavior to instead warn or error when # trying to run something like `./pants run` without any backends registered. is_implemented = union_membership.has_members_for_all( goal_product.subsystem_cls.required_union_implementations) if not is_implemented: continue # NB: Keep this in sync with the method `goal_consumed_types`. params = Params(specs, options_bootstrapper, self.console, workspace, interactive_runner) logger.debug( f"requesting {goal_product} to satisfy execution of `{goal}` goal" ) try: exit_code = self.scheduler_session.run_goal_rule( goal_product, params, poll=poll, poll_delay=poll_delay) finally: self.console.flush() if exit_code != PANTS_SUCCEEDED_EXIT_CODE: return exit_code return PANTS_SUCCEEDED_EXIT_CODE
def get_all_help_info( cls, options: Options, union_membership: UnionMembership, consumed_scopes_mapper: ConsumedScopesMapper, ) -> AllHelpInfo: scope_to_help_info = {} name_to_goal_info = {} for scope_info in sorted(options.known_scope_to_info.values(), key=lambda x: x.scope): options.for_scope(scope_info.scope) # Force parsing. optionable_cls = scope_info.optionable_cls if not scope_info.description: cls_name = ( f"{optionable_cls.__module__}.{optionable_cls.__qualname__}" if optionable_cls else "" ) raise ValueError( f"Subsystem {cls_name} with scope `{scope_info.scope}` has no description. " f"Add a docstring or implement get_description()." ) is_goal = optionable_cls is not None and issubclass(optionable_cls, GoalSubsystem) oshi: OptionScopeHelpInfo = HelpInfoExtracter( scope_info.scope ).get_option_scope_help_info( scope_info.description, options.get_parser(scope_info.scope), is_goal ) scope_to_help_info[oshi.scope] = oshi if is_goal: goal_subsystem_cls = cast(Type[GoalSubsystem], optionable_cls) is_implemented = union_membership.has_members_for_all( goal_subsystem_cls.required_union_implementations ) name_to_goal_info[scope_info.scope] = GoalHelpInfo( goal_subsystem_cls.name, scope_info.description, is_implemented, consumed_scopes_mapper(scope_info.scope), ) return AllHelpInfo( scope_to_help_info=scope_to_help_info, name_to_goal_info=name_to_goal_info )