# Copyright 2019 The Fuchsia Authors. All rights reserved.
# Use of this source code is governed by a BSD-style license that can be
# found in the LICENSE file.
"""Recipe for updating the code search super manifest project."""

from PB.recipes.fuchsia.code_search import InputProperties

PYTHON_VERSION_COMPATIBILITY = "PY3"

DEPS = [
    "fuchsia/checkout",
    "fuchsia/git",
    "fuchsia/git_checkout",
    "fuchsia/jiri",
    "fuchsia/status_check",
    "recipe_engine/context",
    "recipe_engine/file",
    "recipe_engine/properties",
    "recipe_engine/raw_io",
    "recipe_engine/step",
]

PROPERTIES = InputProperties

GENERATE_SCRIPT = "setup.sh"

LOCAL_BRANCH_NAME = "latest"


def RunSteps(api, props):
    checkout = api.checkout.fuchsia_with_options(
        manifest=props.manifest,
        remote=props.remote,
        fetch_packages=False,
    )

    if props.preserve_root:
        with api.context(cwd=checkout.root_dir):
            api.git.raw_checkout(branch=LOCAL_BRANCH_NAME)

    with api.step.nest("checkout super manifest project"):
        super_manifest_project_path = checkout.root_dir.join("super")
        api.file.ensure_directory("make dirs", super_manifest_project_path)

        _, base_revision = api.git_checkout(
            props.super_manifest_project,
            path=super_manifest_project_path,
            submodules=False,
            ignore_build_input=True,
        )

    with api.context(cwd=super_manifest_project_path):
        with api.step.nest("reset submodule state"):
            submodule_configs = (
                api.git.config(
                    "--name-only",
                    "--null",
                    "--file",
                    ".gitmodules",
                    "--get-regexp",
                    "submodule.*path",
                    step_name="get submodule configs",
                    stdout=api.raw_io.output_text(),
                    step_test_data=lambda: api.raw_io.test_api.stream_output_text(
                        "\x00".join(
                            [
                                "submodule.a.path",
                                "submodule.b.path",
                            ]
                        )
                    ),
                )
                .stdout.rstrip("\x00")
                .split("\x00")
            )
            for submodule_config in submodule_configs:
                submodule_path = api.git.config(
                    "--null",
                    "--file",
                    ".gitmodules",
                    "--get",
                    submodule_config,
                    step_name="get submodule path",
                    stdout=api.raw_io.output_text(),
                    step_test_data=lambda: api.raw_io.test_api.stream_output_text(
                        "path/to/submodule\x00"
                    ),
                ).stdout.rstrip("\x00")
                api.git(
                    "rm %s" % submodule_path,
                    "rm",
                    "--cached",
                    "--",
                    submodule_path,
                    ok_ret="any",
                )
                submodule_section_name = submodule_config[: -len(".path")]
                api.git.config(
                    "--file",
                    ".gitmodules",
                    "--remove-section",
                    submodule_section_name,
                    step_name="remove section %s" % submodule_section_name,
                )
                api.git.add(add_all=True, force=True)

        # For details, see:
        # https://fuchsia.googlesource.com/jiri/+/main/cmd/jiri/generate-gitmodules.go
        generate_script_path = super_manifest_project_path.join(GENERATE_SCRIPT)
        api.jiri.generate_gitmodules(
            ".gitmodules",
            generate_script=generate_script_path,
            redirect_root=not props.preserve_root,
        )

        api.step("run %s" % GENERATE_SCRIPT, [generate_script_path])
        api.file.remove("remove %s" % GENERATE_SCRIPT, generate_script_path)

        api.git.add(add_all=True, force=True)
        # Only commit if we have a diff, otherwise commit fails.
        if api.git.diff(
            ref_base=base_revision, cached=True, exit_code=True, ok_ret="any"
        ).retcode:
            api.git.commit(
                message="Update submodules to %s" % checkout.integration_revision
            )

        if props.preserve_root:
            # Add our local fuchsia.git checkout as a new remote of the super
            # manifest project's Git repo, and merge in the history.
            source_remote = "local-upstream"
            api.git.remote_add(source_remote, checkout.root_dir)
            api.git.fetch(source_remote)
            api.git(
                "git merge",
                "merge",
                "-m",
                "merge upstream changes",
                "-X",
                "theirs",
                "--allow-unrelated-histories",
                "%s/%s" % (source_remote, LOCAL_BRANCH_NAME),
            )
        # Only push if we have a diff.
        if api.git.diff(
            step_name="check for push",
            ref_base=base_revision,
            cached=True,
            exit_code=True,
            ok_ret="any",
        ).retcode:
            # Skip pushing entirely instead of setting --dry-run because a dry
            # run push may fail if it races with a production build.
            if not props.dry_run:
                api.git.push(
                    "HEAD:main",
                    options=["nokeycheck", "skip-validation"],
                )


def GenTests(api):
    source_info = [
        {
            "name": "integration",
            "remote": "https://fuchsia.googlesource.com/integration",
            "revision": "a491082dc1b632bbcd60ba3618d20b503c2de738",
            "relativePath": "integration",
        },
    ]

    def props(**kwargs):
        return api.properties(
            remote="https://fuchsia.googlesource.com/integration",
            manifest="flower",
            super_manifest_project="https://fuchsia.googlesource.com/super",
            **kwargs
        )

    yield api.status_check.test("no_diff") + props() + api.checkout.source_info(
        source_info
    )

    yield api.status_check.test("yes_diff") + props() + api.step_data(
        "git diff", retcode=1
    ) + api.checkout.source_info(source_info) + api.step_data(
        "check for push", retcode=1
    )

    yield api.status_check.test("dry_run") + props(dry_run=True) + api.step_data(
        "git diff", retcode=1
    ) + api.checkout.source_info(source_info) + api.step_data(
        "check for push", retcode=1
    )

    yield api.status_check.test("preserve_root") + props(
        preserve_root=True
    ) + api.checkout.source_info(source_info)
