# Copyright 2017 The Bazel Authors. All rights reserved.
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
#    http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.

load(
    "@bazel_gazelle_is_bazel_module//:defs.bzl",
    "GAZELLE_IS_BAZEL_MODULE",
)
load(
    "@bazel_skylib//lib:shell.bzl",
    "shell",
)
load(
    "//internal:gazelle_binary.bzl",
    _gazelle_binary = "gazelle_binary_wrapper",
)
load(
    "//internal:go_repository.bzl",
    _go_repository = "go_repository",
)
load(
    "//internal:overlay_repository.bzl",
    _git_repository = "git_repository",
    _http_archive = "http_archive",
)
load(
    "//internal/generationtest:generationtest.bzl",
    _gazelle_generation_test = "gazelle_generation_test",
)

go_repository = _go_repository
git_repository = _git_repository
http_archive = _http_archive
gazelle_binary = _gazelle_binary
gazelle_generation_test = _gazelle_generation_test

DEFAULT_LANGUAGES = [
    Label("//language/proto:go_default_library"),
    Label("//language/go:go_default_library"),
]

def _valid_env_variable_name(name):
    """ Returns if a string is in the regex [a-zA-Z_][a-zA-Z0-9_]*

    Given that bazel lacks support of regex, we need to implement
    a poor man validation
    """
    if not name:
        return False
    for i, c in enumerate(name.elems()):
        if c.isalpha() or c == "_" or (i > 0 and c.isdigit()):
            continue
        return False
    return True

def _rlocation_path(ctx, file):
    if file.short_path.startswith("../"):
        return file.short_path[3:]
    else:
        return ctx.workspace_name + "/" + file.short_path

def _gazelle_runner_attr_factory(test_runner = False):
    attrs = {
        "gazelle": attr.label(
            allow_single_file = True,
            default = "//cmd/gazelle",
            executable = True,
            cfg = "target",
        ),
        "command": attr.string(
            values = [
                "fix",
                "update",
                "update-repos",
            ],
            default = "update",
        ),
        "mode": attr.string(
            values = ["", "print", "fix", "diff"],
            default = "",
        ),
        "external": attr.string(
            values = ["", "external", "static", "vendored"],
            default = "",
        ),
        "build_tags": attr.string_list(),
        "prefix": attr.string(),
        "extra_args": attr.string_list(),
        "data": attr.label_list(allow_files = True),
        "env": attr.string_dict(),
        "_repo_config": attr.label(
            default = "@bazel_gazelle_go_repository_config//:WORKSPACE" if GAZELLE_IS_BAZEL_MODULE else None,
            allow_single_file = True,
        ),
        "_template": attr.label(
            default = "//internal:gazelle.bash.in",
            allow_single_file = True,
        ),
    }
    if test_runner:
        attrs.update({
            "workspace": attr.label(
                allow_single_file = True,
                doc = "Label of the WORKSPACE file",
                mandatory = True,
            ),
            "mode": attr.string(
                values = ["diff"],
                default = "diff",
            ),
        })
    return attrs

def _gazelle_runner_impl_factory(ctx, test_runner = False):
    args = [ctx.attr.command]
    if ctx.attr.mode:
        args.extend(["-mode", ctx.attr.mode])
    if ctx.attr.external:
        args.extend(["-external", ctx.attr.external])
    if ctx.attr.prefix:
        args.extend(["-go_prefix", ctx.attr.prefix])
    if ctx.attr.build_tags:
        args.extend(["-build_tags", ",".join(ctx.attr.build_tags)])
    if GAZELLE_IS_BAZEL_MODULE:
        args.append("-bzlmod")
    args.extend([ctx.expand_location(arg, ctx.attr.data) for arg in ctx.attr.extra_args])

    for key in ctx.attr.env:
        if not _valid_env_variable_name(key):
            fail("Invalid environmental variable name: '%s'" % key)

    env = "\n".join(["export %s=%s" % (x, shell.quote(y)) for (x, y) in ctx.attr.env.items()])

    out_file = ctx.actions.declare_file(ctx.label.name + ".bash")
    go_tool = ctx.toolchains["@io_bazel_rules_go//go:toolchain"].sdk.go
    repo_config = ctx.file._repo_config
    substitutions = {
        "@@ARGS@@": shell.array_literal(args),
        "@@GAZELLE_PATH@@": shell.quote(_rlocation_path(ctx, ctx.executable.gazelle)),
        "@@GENERATED_MESSAGE@@": """
# Generated by {label}
# DO NOT EDIT
""".format(label = str(ctx.label)),
        "@@GOTOOL@@": shell.quote(_rlocation_path(ctx, go_tool)),
        "@@ENV@@": env,
        "@@REPO_CONFIG_PATH@@": shell.quote(_rlocation_path(ctx, repo_config)) if repo_config else "",
        "@@WORKSPACE@@": ctx.file.workspace.path if test_runner else "",
    }
    ctx.actions.expand_template(
        template = ctx.file._template,
        output = out_file,
        substitutions = substitutions,
        is_executable = True,
    )
    runfiles = ctx.runfiles(files = [
        ctx.executable.gazelle,
        go_tool,
    ] + ([repo_config] if repo_config else []) + ([ctx.file.workspace] if test_runner else [])).merge(
        ctx.attr.gazelle[DefaultInfo].default_runfiles,
    )
    for d in ctx.attr.data:
        runfiles = runfiles.merge(d[DefaultInfo].default_runfiles)
    return [DefaultInfo(
        files = depset([out_file]),
        runfiles = runfiles,
        executable = out_file,
    )]

def _gazelle_runner_impl(ctx):
    return _gazelle_runner_impl_factory(ctx)

def _gazelle_test_runner_impl(ctx):
    return _gazelle_runner_impl_factory(ctx, test_runner = True)

_gazelle_runner = rule(
    implementation = _gazelle_runner_impl,
    attrs = _gazelle_runner_attr_factory(),
    executable = True,
    toolchains = ["@io_bazel_rules_go//go:toolchain"],
)

_gazelle_test_runner = rule(
    implementation = _gazelle_test_runner_impl,
    attrs = _gazelle_runner_attr_factory(test_runner = True),
    executable = True,
    toolchains = ["@io_bazel_rules_go//go:toolchain"],
)

def _gazelle_kwargs_prepare(name, kwargs):
    if "args" in kwargs:
        # The args attribute has special meaning for executable rules, but we
        # always want extra_args here instead.
        if "extra_args" in kwargs:
            fail("{}: both args and extra_args were provided".format(name))
        kwargs["extra_args"] = kwargs["args"]
        kwargs.pop("args")

    visibility = kwargs.pop("visibility", default = None)
    return name + "-runner", visibility

def gazelle(name, **kwargs):
    runner_name, visibility = _gazelle_kwargs_prepare(name, kwargs)

    _gazelle_runner(
        name = runner_name,
        **kwargs
    )
    tags_set = {t: "" for t in kwargs.pop("tags", [])}
    tags_set["manual"] = ""
    tags = tags_set.keys()
    native.sh_binary(
        name = name,
        tags = tags,
        srcs = [runner_name],
        visibility = visibility,
        deps = ["@bazel_tools//tools/bash/runfiles"],
        data = kwargs["data"] if "data" in kwargs else [],
    )

def gazelle_test(name, **kwargs):
    runner_name, visibility = _gazelle_kwargs_prepare(name, kwargs)

    _gazelle_test_runner(
        name = runner_name,
        **kwargs
    )

    # Note: the "external" tag is a workaround for
    # https://github.com/bazelbuild/bazel/issues/15516.
    tags_set = {t: "" for t in kwargs.pop("tags", [])}
    tags_set["no-sandbox"] = ""
    tags_set["no-cache"] = ""
    tags_set["external"] = ""
    tags = tags_set.keys()
    native.sh_test(
        name = name,
        srcs = [runner_name],
        visibility = visibility,
        tags = tags,
        deps = ["@bazel_tools//tools/bash/runfiles"],
        data = kwargs["data"] if "data" in kwargs else [],
    )
