# Copyright 2020 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 running Tricium analyzers."""

import collections

from recipe_engine.config import ConfigList, ConfigGroup, Single
from recipe_engine.recipe_api import Property

PYTHON_VERSION_COMPATIBILITY = 'PY3'

DEPS = [
    "fuchsia/git",
    "fuchsia/tricium_analyze",
    "recipe_engine/buildbucket",
    "recipe_engine/cipd",
    "recipe_engine/context",
    "recipe_engine/path",
    "recipe_engine/platform",
    "recipe_engine/properties",
    "recipe_engine/raw_io",
    "recipe_engine/step",
    "recipe_engine/tricium",
]

PROPERTIES = {
    "cipd_packages":
        Property(
            help="CIPD packages containing necessary binaries.",
            kind=ConfigList(
                lambda: ConfigGroup(
                    # Package name.
                    name=Single(str),
                    # Version.
                    version=Single(str),
                    # Language subdirectory (e.g. clang) in which to put the package. The Tricium modules assume a Fuchsia prebuilts-like layout.
                    subdir=Single(str),
                )
            ),
            default={},
        ),
}

# Namedtuple to simulate a class generated by jiri checkout because flutter is
# not using jiri.
_CheckoutResult = collections.namedtuple(
    '_CheckoutResult', ['root_dir', 'release_version']
)


def RunSteps(api, cipd_packages):  # pragma: no cover
  # TODO(godofredoc): Fix tricium recipe.
  return

  with api.context(infra_steps=True):
    checkout_root = api.path["start_dir"]
    checkout_path = api.path['start_dir'].join('recipes')
    # tricium is expecting a dictionary as a checkout.
    checkout = _CheckoutResult(checkout_path, '')

    bb_input = api.buildbucket.build.input
    if bb_input.gerrit_changes:
      api.git.checkout_cl(bb_input.gerrit_changes[0], checkout_path)

  # If specified, download CIPD packages.
  if cipd_packages:
    with api.step.nest("ensure_packages"):
      with api.context(infra_steps=True):
        cipd_dir = checkout_root.join("cipd")
        pkgs = api.cipd.EnsureFile()
        for package in cipd_packages:
          pkgs.add_package(
              package["name"], package["version"], subdir=package["subdir"]
          )
          api.cipd.ensure(cipd_dir, pkgs)
          platform = "%s-%s" % (
              api.platform.name.replace("win", "windows"),
              {
                  "intel": {
                      32: "386",
                      # Note that this is different from the CIPD norm (this is how
                      # //prebuilt/third_party is laid out).
                      64: "x64",
                  },
                  "arm": {
                      32: "armv6",
                      64: "arm64",
                  },
              }[api.platform.arch][api.platform.bits],
          )
          # Only these tools are being downloaded from CIPD, so directly set the
          # paths if cipd_packages is defined.
          api.tricium_analyze.black = cipd_dir.join("black")
          api.tricium_analyze.yapf = cipd_dir.join("yapf")

  with api.context(cwd=checkout_path):
    # --diff-filter=d excludes deleted files, because we don't want to
    # check those.
    paths = api.git(
        "get changed files",
        "diff-tree",
        "--no-commit-id",
        "--name-only",
        "--diff-filter=d",
        "-r",
        "HEAD",
        stdout=api.raw_io.output_text(),
    ).stdout.splitlines()

    api.tricium_analyze.checkout = checkout
    for path in paths:
      # TODO(haowei): fxb/44823 Call git-check-attr on all files at once to speed it up
      attr_result = api.git(
          "check attr of %s" % path,
          "check-attr",
          "tricium",
          "--",
          path,
          stdout=api.raw_io.output_text(),
      ).stdout.strip()
      if attr_result.endswith(": unset"):
        continue
      api.tricium_analyze([path])
  api.tricium.write_comments()


def GenTests(api):
  # TODO(godofredoc): Fix tricium recipe.
  return

  DIFF = """diff --git a/{0} b/{0}
index e684c1e..a76a10e 100644
--- a/{0}
+++ b/{0}
@@ -1,2 +1,4 @@
+  foo
+  bar
"""

  changed_files_data = lambda files: api.step_data(
      "get changed files",
      api.raw_io.stream_output_text("\n".join(files)),
  )
  get_changed_files_data = lambda files: api.step_data(
      "analyze %s.get changed files" % files[0],
      api.raw_io.stream_output_text("\n".join(DIFF.format(f) for f in files)),
  )

  formatted_files_data = lambda files: api.step_data(
      "analyze %s.get formatted files" % files[0],
      api.raw_io.stream_output_text("\n".join(DIFF.format(f) for f in files)),
  )

  try_build = api.buildbucket.try_build(
      git_repo="https://flutter.googlesource.com/recipes"
  )
  basic_properties = api.properties(ref="refs/changes/12345/2",)

  yield (
      api.test("default") + try_build + basic_properties +
      api.properties(analyses=["Yapf"],) + changed_files_data(["flutter.py"]) +
      get_changed_files_data(["flutter.py"]) +
      formatted_files_data(["flutter.py"])
  )

  yield (
      api.test("with_cipd_packages") + try_build + basic_properties +
      api.properties(
          analyses=["Yapf"],
          cipd_packages=[{
              "name": "fuchsia/go/${platform}",
              "version": "integration",
              "subdir": "go",
          }],
      ) + changed_files_data(["flutter.py"]) +
      get_changed_files_data(["flutter.py"]) +
      formatted_files_data(["flutter.py"])
  )

  yield (
      api.test("attribute disable") + try_build + basic_properties +
      api.properties(analyses=["ClangFormat", "GNFormat"],) +
      changed_files_data(["BUILD.gn", "hello.go"]) + api.step_data(
          "check attr of BUILD.gn",
          api.raw_io.stream_output_text("BUILD.gn: tricium: unset\n"),
      )
  )
