# Copyright 2017 The ChromiumOS Authors
# Use of this source code is governed by a BSD-style license that can be
# found in the LICENSE file.

"""cros tryjob: Schedule a tryjob."""

import logging
import os
import time

from chromite.third_party.google.protobuf import json_format

from chromite.cbuildbot import trybot_patch_pool
from chromite.cli import command
from chromite.lib import config_lib
from chromite.lib import constants
from chromite.lib import cros_build_lib
from chromite.lib import git
from chromite.lib import request_build
from chromite.scripts import cbuildbot as cbuildbot_lib
from chromite.utils import pformat


REMOTE = "remote"
INFRA_TESTING = "infra-testing"
LOCAL = "local"
CBUILDBOT = "cbuildbot"


def ConfigsToPrint(site_config, production, build_config_fragments):
    """Select a list of buildbot configs to print out.

    Args:
        site_config: config_lib.SiteConfig containing all config info.
        production: Display tryjob or production configs?.
        build_config_fragments: List of strings to filter config names with.

    Returns:
        List of config_lib.BuildConfig objects.
    """
    configs = site_config.values()

    def optionsMatch(config):
        # In this case, build_configs are config name fragments. If the config
        # name doesn't contain any of the fragments, filter it out.
        for build_config in build_config_fragments:
            if build_config not in config.name:
                return False

        return config_lib.isTryjobConfig(config) != production

    # All configs, filtered by optionsMatch.
    configs = [config for config in configs if optionsMatch(config)]

    # Sort build type, then board.
    # 'daisy-paladin-tryjob' -> ['tryjob', 'paladin', 'daisy']
    configs.sort(key=lambda c: list(reversed(c.name.split("-"))))

    return configs


def PrintKnownConfigs(site_config, production, build_config_fragments):
    """Print a list of known buildbot configs.

    Args:
        site_config: config_lib.SiteConfig containing all config info.
        production: Display tryjob or production configs?.
        build_config_fragments: List of strings to filter config names with.
    """
    configs = ConfigsToPrint(site_config, production, build_config_fragments)

    COLUMN_WIDTH = max([0] + [len(c.name) for c in configs]) + 1
    if production:
        print("Production configs:")
    else:
        print("Tryjob configs:")

    print("config".ljust(COLUMN_WIDTH), "description")
    print("------".ljust(COLUMN_WIDTH), "-----------")
    for config in configs:
        desc = config.description or ""
        print(config.name.ljust(COLUMN_WIDTH), desc)


def CbuildbotArgs(options):
    """Function to generate cbuildbot command line args.

    This are pre-api version filtering.

    Args:
        options: Parsed cros tryjob tryjob arguments.

    Returns:
        List of strings in ['arg1', 'arg2'] format
    """
    args = []

    if options.where in (REMOTE, INFRA_TESTING):
        if options.production:
            args.append("--buildbot")
        else:
            args.append("--remote-trybot")

    elif options.where == LOCAL:
        args.extend(
            (
                "--buildroot",
                options.buildroot,
                "--git-cache-dir",
                options.git_cache_dir,
                "--no-buildbot-tags",
            )
        )

        if options.production:
            # This is expected to fail on workstations without an explicit
            # --debug.
            args.append("--buildbot")
        else:
            args.append("--debug")

    elif options.where == CBUILDBOT:
        args.extend(
            (
                "--buildroot",
                os.path.join(options.buildroot, "repository"),
                "--workspace",
                os.path.join(options.buildroot, "workspace"),
                "--git-cache-dir",
                options.git_cache_dir,
                "--debug",
                "--nobootstrap",
                "--noreexec",
                "--no-buildbot-tags",
            )
        )

        if options.production:
            # This is expected to fail on workstations without an explicit
            # --debug.
            args.append("--buildbot")

    else:
        raise Exception("Unknown options.where: %s" % (options.where,))

    if options.branch:
        args.extend(("-b", options.branch))

    for g in options.gerrit_patches:
        args.extend(("-g", g))

    if options.hwtest_dut_dimensions:
        args.extend(
            ("--hwtest_dut_dimensions", " ".join(options.hwtest_dut_dimensions))
        )

    if options.passthrough:
        args.extend(options.passthrough)

    if options.passthrough_raw:
        args.extend(options.passthrough_raw)

    return args


def CreateBuildrootIfNeeded(buildroot):
    """Create the buildroot is it doesn't exist with confirmation prompt.

    Args:
        buildroot: The buildroot path to create as a string.

    Returns:
        boolean: Does the buildroot now exist?
    """
    if os.path.exists(buildroot):
        return True

    prompt = "Create %s as buildroot" % buildroot
    if not cros_build_lib.BooleanPrompt(prompt=prompt, default=False):
        print(
            "Please specify a different buildroot via the --buildroot option."
        )
        return False

    os.makedirs(buildroot)
    return True


def RunLocal(options):
    """Run a local tryjob.

    Args:
        options: Parsed cros tryjob tryjob arguments.

    Returns:
        Exit code of build as an int.
    """
    if cros_build_lib.IsInsideChroot():
        cros_build_lib.Die("Local tryjobs cannot be started inside the chroot.")

    args = CbuildbotArgs(options)

    if not CreateBuildrootIfNeeded(options.buildroot):
        return 1

    # Define the command to run.
    launcher = constants.CHROMITE_DIR / "scripts" / "cbuildbot_launch"
    cmd = [launcher] + args + options.build_configs

    # Run the tryjob.
    result = cros_build_lib.run(
        cmd, debug_level=logging.CRITICAL, check=False, cwd=options.buildroot
    )
    return result.returncode


def RunCbuildbot(options):
    """Run a cbuildbot build.

    Args:
        options: Parsed cros tryjob tryjob arguments.

    Returns:
        Exit code of build as an int.
    """
    if cros_build_lib.IsInsideChroot():
        cros_build_lib.Die(
            "cbuildbot tryjobs cannot be started inside the chroot."
        )

    args = CbuildbotArgs(options)

    if not CreateBuildrootIfNeeded(options.buildroot):
        return 1

    # Define the command to run.
    cbuildbot = constants.CHROMITE_BIN_DIR / "cbuildbot"
    cmd = [cbuildbot] + args + options.build_configs

    # Run the tryjob.
    result = cros_build_lib.run(
        cmd, debug_level=logging.CRITICAL, check=False, cwd=options.buildroot
    )
    return result.returncode


def DisplayLabel(site_config, options, build_config_name):
    """Decide which display_label to use.

    Args:
        site_config: config_lib.SiteConfig containing all config info.
        options: Parsed command line options for cros tryjob.
        build_config_name: Name of the build config we are scheduling.

    Returns:
        String to use as the cbb_build_label value.
    """
    # Production tryjobs always display as production tryjobs.
    if options.production:
        return config_lib.DISPLAY_LABEL_PRODUCTION_TRYJOB

    # Our site_config is only valid for the current branch. If the build
    # config is known and has an explicit display_label, use it.
    # to be 'main'.
    if (
        options.branch == "main"
        and build_config_name in site_config
        and site_config[build_config_name].display_label
    ):
        return site_config[build_config_name].display_label

    # Fall back to default.
    return config_lib.DISPLAY_LABEL_TRYJOB


def FindUserEmail(options):
    """Decide which email address is submitting the job.

    Args:
        options: Parsed command line options for cros tryjob.

    Returns:
        Email address for the tryjob as a string.
    """

    if options.committer_email:
        return options.committer_email

    cwd = os.path.dirname(os.path.realpath(__file__))
    return git.GetProjectUserEmail(cwd)


def PushLocalPatches(local_patches, user_email, dryrun=False):
    """Push local changes to a remote ref, and generate args to send.

    Args:
        local_patches: patch_pool.local_patches from verified patch_pool.
        user_email: Unique id for user submitting this tryjob.
        dryrun: Is this a dryrun? If so, don't really push.

    Returns:
        List of strings to pass to builder to include these patches.
    """
    manifest = git.ManifestCheckout.Cached(constants.SOURCE_ROOT)

    current_time = str(int(time.time()))
    ref_base = os.path.join("refs/tryjobs", user_email, current_time)

    extra_args = []
    for patch in local_patches:
        # Isolate the name; if it's a tag or a remote, let through.
        # Else if it's a branch, get the full branch name minus refs/heads.
        local_branch = git.StripRefsHeads(patch.ref, False)
        ref_final = os.path.join(ref_base, local_branch, patch.sha1)

        checkout = patch.GetCheckout(manifest)
        checkout.AssertPushable()
        print("Uploading patch %s" % patch)
        patch.Upload(checkout["push_url"], ref_final, dryrun=dryrun)

        # TODO(crbug/216095): Pass in the remote instead of tag.
        tag = constants.EXTERNAL_PATCH_TAG
        if checkout["remote"] == config_lib.GetSiteParams().INTERNAL_REMOTE:
            tag = constants.INTERNAL_PATCH_TAG

        extra_args.append(
            "--remote-patches=%s:%s:%s:%s:%s"
            % (
                patch.project,
                local_branch,
                ref_final,
                patch.tracking_branch,
                tag,
            )
        )

    return extra_args


def RunRemote(
    site_config, options, patch_pool, infra_testing=False, production=False
):
    """Schedule remote tryjobs."""
    logging.info(
        "Scheduling remote tryjob(s): %s", ", ".join(options.build_configs)
    )

    luci_builder = None
    if infra_testing:
        luci_builder = config_lib.LUCI_BUILDER_INFRA_TESTING
    # Production tryjobs actually execute in the Release group
    elif production:
        luci_builder = config_lib.LUCI_BUILDER_RELEASE

    user_email = FindUserEmail(options)

    # Figure out the cbuildbot command line to pass in.
    args = CbuildbotArgs(options)
    args += PushLocalPatches(patch_pool.local_patches, user_email)

    if options.debug:
        # default_debug template used to test email templates before they go
        # live.
        email_template = "default_debug"
    else:
        email_template = "tryjob"

    logging.info("Submitting tryjob...")
    results = []
    for build_config in options.build_configs:
        tryjob = request_build.RequestBuild(
            build_config=build_config,
            luci_builder=luci_builder,
            display_label=DisplayLabel(site_config, options, build_config),
            branch=options.branch,
            extra_args=args,
            user_email=user_email,
            email_template=email_template,
        )
        results.append(tryjob.Submit(dryrun=False))

    if options.json:
        # Convert Buildbucket Build object to dict, output as json.
        print(pformat.json([json_format.MessageToDict(r) for r in results]))
    else:
        print("Tryjob submitted!")
        print("To view your tryjobs, visit:")
        for r in results:
            print(f"{constants.CHROMEOS_MILO_HOST}{r.id}")


def VerifyOptions(options, site_config):
    """Verify that our command line options make sense.

    Args:
        options: Parsed cros tryjob tryjob arguments.
        site_config: config_lib.SiteConfig containing all config info.
    """
    # Handle --list before checking that everything else is valid.
    if options.list:
        PrintKnownConfigs(
            site_config, options.production, options.build_configs
        )
        raise cros_build_lib.DieSystemExit(0)  # Exit with success code.

    # Validate specified build_configs.
    if not options.build_configs:
        cros_build_lib.Die("At least one build_config is required.")

    on_branch = options.branch != "main"

    if not (options.yes or on_branch):
        unknown_build_configs = [
            b for b in options.build_configs if b not in site_config
        ]
        if unknown_build_configs:
            prompt = (
                "Unknown build configs; are you sure you want to schedule "
                "for %s?" % ", ".join(unknown_build_configs)
            )
            if not cros_build_lib.BooleanPrompt(prompt=prompt, default=False):
                cros_build_lib.Die("No confirmation.")

    unsupported_tryjobs = []
    for build_config in options.build_configs:
        for suffix in ("-release", "-payloads", "-full"):
            if suffix in build_config:
                unsupported_tryjobs.append(build_config)
                break

    # The user may have specified a --version but not a --branch, need to check
    # both to determine `cros tryjob` support.
    specified_version = None
    if options.passthrough:
        for i, val in enumerate(options.passthrough):
            if val.startswith("--version"):
                if "=" in val:
                    specified_version = val.split("=", 1)[-1]
                else:
                    specified_version = options.passthrough[i + 1]
    if unsupported_tryjobs:
        unsupported_branch = False
        version = specified_version
        if not version and on_branch:
            tokens = options.branch.split("-")
            if tokens[0] in ("release", "stabilize", "firmware"):
                version = tokens[-1]
        if version:
            if int(version.split(".")[0]) >= 15183:
                unsupported_branch = True
        if (not on_branch and not specified_version) or unsupported_branch:
            cros_build_lib.Die(
                "`cros tryjob` is unsupported for %s on milestones >= 108, "
                "please use `cros try`.",
                ",".join(unsupported_tryjobs),
            )

    # Ensure that production configs are only run with --production.
    if not (on_branch or options.production or options.where == CBUILDBOT):
        # We can't know if branched configs are tryjob safe.
        # It should always be safe to run a tryjob config with --production.
        prod_configs = []
        for b in options.build_configs:
            if b in site_config and not config_lib.isTryjobConfig(
                site_config[b]
            ):
                prod_configs.append(b)

        if prod_configs:
            # Die, and explain why.
            alternative_configs = ["%s-tryjob" % b for b in prod_configs]
            msg = (
                "These configs are not tryjob safe:\n"
                "  %s\n"
                "Consider these configs instead:\n"
                "  %s\n"
                "See go/cros-explicit-tryjob-build-configs-psa."
                % (", ".join(prod_configs), ", ".join(alternative_configs))
            )

            if options.branch == "main":
                # On main branch, we know the status of configs for sure.
                cros_build_lib.Die(msg)
            elif not options.yes:
                # On branches, we are just guessing. Let people override.
                prompt = "%s\nAre you sure you want to continue?" % msg
                if not cros_build_lib.BooleanPrompt(
                    prompt=prompt, default=False
                ):
                    cros_build_lib.Die("No confirmation.")

    patches_given = options.gerrit_patches or options.local_patches
    if options.production:
        # Make sure production builds don't have patches.
        if patches_given and not options.debug:
            cros_build_lib.Die(
                "Patches cannot be included in production builds."
            )
    elif options.where != CBUILDBOT:
        # Ask for confirmation if there are no patches to test.
        if not patches_given and not options.yes:
            prompt = (
                "No patches were provided; are you sure you want to just "
                "run a build of %s?"
                % (options.branch if options.branch else "ToT")
            )
            if not cros_build_lib.BooleanPrompt(prompt=prompt, default=False):
                cros_build_lib.Die("No confirmation.")

    if options.where in (REMOTE, INFRA_TESTING):
        if options.buildroot:
            cros_build_lib.Die("--buildroot is not used for remote tryjobs.")

        if options.git_cache_dir:
            cros_build_lib.Die(
                "--git-cache-dir is not used for remote tryjobs."
            )
    else:
        if options.json:
            cros_build_lib.Die("--json can only be used for remote tryjobs.")

    if options.hwtest_dut_dimensions:
        has_board = has_model = has_pool = False
        for dim in options.hwtest_dut_dimensions:
            if dim.startswith(cbuildbot_lib.BOARD_DIM_LABEL):
                has_board = True
            elif dim.startswith(cbuildbot_lib.MODEL_DIM_LABEL):
                has_model = True
            elif dim.startswith(cbuildbot_lib.POOL_DIM_LABEL):
                has_pool = True

        if not (has_board and has_model and has_pool):
            cros_build_lib.Die(
                "HWTest DUT dimensions must include board, model, and "
                "pool (given %s)." % options.hwtest_dut_dimensions
            )


@command.command_decorator("tryjob")
class TryjobCommand(command.CliCommand):
    """Schedule a tryjob."""

    EPILOG = """
Remote Examples:
  cros tryjob -g 123 lumpy-compile-only-pre-cq
  cros tryjob -g 123 -g 456 lumpy-compile-only-pre-cq daisy-pre-cq
  cros tryjob -g *123 --hwtest daisy-paladin-tryjob
  cros tryjob -p chromiumos/chromite lumpy-compile-only-pre-cq
  cros tryjob -p chromiumos/chromite:foo_branch lumpy-paladin-tryjob

Local Examples:
  cros tryjob --local -g 123 daisy-paladin-tryjob
  cros tryjob --local --buildroot /my/cool/path -g 123 daisy-paladin-tryjob

Production Examples (danger, can break production if misused):
  cros tryjob --production --branch release-R61-9765.B asuka-release
  cros tryjob --production --version 9795.0.0 --channel canary  lumpy-payloads

List Examples:
  cros tryjob --list
  cros tryjob --production --list
  cros tryjob --list lumpy
  cros tryjob --list lumpy vmtest
"""

    @classmethod
    def AddParser(cls, parser):
        """Adds a parser."""
        super(cls, TryjobCommand).AddParser(parser)
        parser.add_argument(
            "build_configs", nargs="*", help="One or more configs to build."
        )
        parser.add_argument(
            "-b",
            "--branch",
            default="main",
            help="The manifest branch to test.  The branch to "
            "check the buildroot out to.",
        )
        parser.add_argument(
            "--profile",
            dest="passthrough",
            action="append_option_value",
            help="Name of profile to sub-specify board variant.",
        )
        parser.add_argument(
            "--yes",
            action="store_true",
            default=False,
            help="Never prompt to confirm.",
        )
        parser.add_argument(
            "--production",
            action="store_true",
            default=False,
            help="This is a production build, NOT a test build. "
            "Confirm with Chrome OS deputy before use.",
        )
        parser.add_argument(
            "--pass-through",
            dest="passthrough_raw",
            action="append",
            help="Arguments to pass to cbuildbot. To be avoided."
            "Confirm with Chrome OS deputy before use.",
        )
        parser.add_argument(
            "--json",
            action="store_true",
            default=False,
            help="Return details of remote tryjob in script friendly output.",
        )

        # Do we build locally, on on a trybot builder?
        where_group = parser.add_argument_group(
            "Where", description="Where do we run the tryjob?"
        )
        where_ex = where_group.add_mutually_exclusive_group()
        where_ex.add_argument(
            "--remote",
            dest="where",
            action="store_const",
            const=REMOTE,
            default=REMOTE,
            help="Run the tryjob on a remote builder. (default)",
        )
        where_ex.add_argument(
            "--infra-testing",
            dest="where",
            action="store_const",
            const=INFRA_TESTING,
            help="Run the tryjob against the infra-testing swarming pool.",
        )
        where_ex.add_argument(
            "--swarming",
            dest="where",
            action="store_const",
            const=REMOTE,
            help="Run the tryjob on a swarming builder. (deprecated)",
        )
        where_ex.add_argument(
            "--local",
            dest="where",
            action="store_const",
            const=LOCAL,
            help="Run the tryjob on your local machine.",
        )
        where_ex.add_argument(
            "--cbuildbot",
            dest="where",
            action="store_const",
            const=CBUILDBOT,
            help="Run special local build from current checkout in buildroot.",
        )
        where_group.add_argument(
            "-r",
            "--buildroot",
            type="path",
            help="Root directory to use for the local tryjob. "
            "NOT the current checkout.",
        )
        where_group.add_argument(
            "--git-cache-dir",
            type="path",
            help="Git cache directory to use for local tryjobs.",
        )

        # What patches do we include in the build?
        what_group = parser.add_argument_group(
            "Patch",
            description="Which patches should be included with the tryjob?",
        )
        what_group.add_argument(
            "-g",
            "--gerrit-patches",
            action="split_extend",
            default=[],
            metavar="Id1 *int_Id2...IdN",
            help="Space-separated list of short-form Gerrit "
            "Change-Id's or change numbers to patch. "
            "Please prepend '*' to internal Change-Id's",
        )
        # We have to format metavar poorly to workaround an argparse bug.
        # https://bugs.python.org/issue11874
        what_group.add_argument(
            "-p",
            "--local-patches",
            action="split_extend",
            default=[],
            metavar="'<project1>[:<branch1>] ... <projectN>[:<branchN>] '",
            help="Space-separated list of project branches with "
            "patches to apply.  Projects are specified by name. "
            "If no branch is specified the current branch of the "
            "project will be used.  NOTE: -p is known to be buggy; "
            "prefer using -g instead (see https://crbug.com/806963 "
            "and https://crbug.com/807834).",
        )

        # Identifing the request.
        who_group = parser.add_argument_group(
            "Requestor", description="Who is submitting the jobs?"
        )
        who_group.add_argument(
            "--committer-email", help="Override default git committer email."
        )

        # Modify the build.
        how_group = parser.add_argument_group(
            "Modifiers", description="How do we modify build behavior?"
        )
        how_group.add_argument(
            "--latest-toolchain",
            dest="passthrough",
            action="append_option",
            help="Use the latest toolchain.",
        )
        how_group.add_argument(
            "--nochromesdk",
            dest="passthrough",
            action="append_option",
            help="Don't run the ChromeSDK stage which builds "
            "Chrome outside of the chroot.",
        )
        how_group.add_argument(
            "--timeout",
            dest="passthrough",
            action="append_option_value",
            help="Specify the maximum amount of time this job "
            "can run for, at which point the build will be "
            "aborted.  If set to zero, then there is no "
            "timeout.",
        )
        how_group.add_argument(
            "--confidence-check-build",
            dest="passthrough",
            action="append_option",
            help="Run the build as a confidence check build.",
        )
        how_group.add_argument(
            "--chrome_version",
            dest="passthrough",
            action="append_option_value",
            help="Used with SPEC logic to force a particular "
            "git revision of chrome rather than the latest. "
            "HEAD is a valid value.",
        )
        how_group.add_argument(
            "--debug-cidb",
            dest="passthrough",
            action="append_option",
            help="Force Debug CIDB to be used.",
        )
        how_group.add_argument(
            "--no-publish-prebuilt-confs",
            dest="passthrough",
            action="append_option",
            help="Force the tryjob to not publish commits to prebuilt.conf or "
            "sdk_version.conf, even if run in production.",
        )

        # Overrides for the build configs testing behaviors.
        test_group = parser.add_argument_group(
            "Testing Flags", description="How do we change testing behavior?"
        )
        test_group.add_argument(
            "--hwtest",
            dest="passthrough",
            action="append_option",
            help="Enable hwlab testing. Default false.",
        )
        test_group.add_argument(
            "--hwtest_dut_dimensions",
            action="split_extend",
            default=None,
            help="Space-separated list of key:val Swarming bot "
            "dimensions to run each builders SkylabHWTest "
            "stages against (this overrides the configured "
            "DUT dimensions for each test). Requires at least "
            '"label-board", "label-model", and "label-pool".',
        )
        test_group.add_argument(
            "--notests",
            dest="passthrough",
            action="append_option",
            help="Override values from buildconfig, run no "
            "tests, and build no autotest artifacts.",
        )
        test_group.add_argument(
            "--novmtests",
            dest="passthrough",
            action="append_option",
            help="Override values from buildconfig, run no vmtests.",
        )
        test_group.add_argument(
            "--noimagetests",
            dest="passthrough",
            action="append_option",
            help="Override values from buildconfig and run no image tests.",
        )

        # <board>-payloads tryjob specific options.
        payloads_group = parser.add_argument_group(
            "Payloads", description="Options only used by payloads tryjobs."
        )
        payloads_group.add_argument(
            "--version",
            dest="passthrough",
            action="append_option_value",
            help="Specify the release version for payload regeneration. "
            "Ex: 9799.0.0",
        )
        payloads_group.add_argument(
            "--channel",
            dest="passthrough",
            action="append_option_value",
            help="Specify a channel for a payloads trybot. Can "
            "be specified multiple times. No valid for "
            "non-payloads configs.",
        )

        configs_group = parser.add_argument_group(
            "Configs",
            description="Options for displaying available build configs.",
        )
        configs_group.add_argument(
            "-l",
            "--list",
            action="store_true",
            dest="list",
            default=False,
            help="List the trybot configs (adjusted by --production).",
        )

    @classmethod
    def ProcessOptions(cls, parser, options):
        """Post process options."""
        if options.where == CBUILDBOT:
            options.buildroot = options.buildroot or os.path.join(
                os.path.dirname(constants.SOURCE_ROOT), "cbuild"
            )

        if options.where == LOCAL:
            options.buildroot = options.buildroot or os.path.join(
                os.path.dirname(constants.SOURCE_ROOT), "tryjob"
            )

        if options.buildroot:
            options.git_cache_dir = options.git_cache_dir or os.path.join(
                options.buildroot, ".git_cache"
            )

    def Run(self):
        """Runs `cros tryjob`."""
        site_config = config_lib.GetConfig()

        VerifyOptions(self.options, site_config)

        logging.info("Verifying patches...")
        patch_pool = trybot_patch_pool.TrybotPatchPool.FromOptions(
            gerrit_patches=self.options.gerrit_patches,
            local_patches=self.options.local_patches,
            sourceroot=constants.SOURCE_ROOT,
            remote_patches=[],
        )

        if self.options.where == REMOTE:
            return RunRemote(site_config, self.options, patch_pool)
        elif self.options.where == INFRA_TESTING:
            return RunRemote(
                site_config, self.options, patch_pool, infra_testing=True
            )
        elif self.options.production:
            return RunRemote(
                site_config, self.options, patch_pool, production=True
            )
        elif self.options.where == LOCAL:
            return RunLocal(self.options)
        elif self.options.where == CBUILDBOT:
            return RunCbuildbot(self.options)
        else:
            raise Exception("Unknown options.where: %s" % (self.options.where,))
