# Copyright 2021 The gRPC Authors
#
# 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.

"""
This module contains build rules relating to gRPC Objective-C.
"""

load("@rules_proto//proto:defs.bzl", "ProtoInfo")
load(
    "//bazel:protobuf.bzl",
    "get_include_directory",
    "get_plugin_args",
    "proto_path_to_generated_filename",
)
load(":grpc_util.bzl", "to_upper_camel_with_extension")

_GRPC_PROTO_HEADER_FMT = "{}.pbrpc.h"
_GRPC_PROTO_SRC_FMT = "{}.pbrpc.m"
_PROTO_HEADER_FMT = "{}.pbobjc.h"
_PROTO_SRC_FMT = "{}.pbobjc.m"
_GENERATED_PROTOS_DIR = "_generated_protos"

_GENERATE_HDRS = 1
_GENERATE_SRCS = 2
_GENERATE_NON_ARC_SRCS = 3

def _generate_objc_impl(ctx):
    """Implementation of the generate_objc rule."""
    protos = [
        f
        for src in ctx.attr.deps
        for f in src[ProtoInfo].transitive_imports.to_list()
    ]

    target_package = _join_directories([ctx.label.workspace_root, ctx.label.package])

    files_with_rpc = [_label_to_full_file_path(f, target_package) for f in ctx.attr.srcs]

    outs = []
    for proto in protos:
        outs.append(_get_output_file_name_from_proto(proto, _PROTO_HEADER_FMT))
        outs.append(_get_output_file_name_from_proto(proto, _PROTO_SRC_FMT))

        file_path = _get_full_path_from_file(proto)
        if file_path in files_with_rpc:
            outs.append(_get_output_file_name_from_proto(proto, _GRPC_PROTO_HEADER_FMT))
            outs.append(_get_output_file_name_from_proto(proto, _GRPC_PROTO_SRC_FMT))

    out_files = [ctx.actions.declare_file(out) for out in outs]
    dir_out = _join_directories([
        str(ctx.genfiles_dir.path),
        target_package,
        _GENERATED_PROTOS_DIR,
    ])

    arguments = []
    tools = []
    if ctx.executable.plugin:
        arguments += get_plugin_args(
            ctx.executable.plugin,
            [],
            dir_out,
            False,
        )
        tools = [ctx.executable.plugin]
    arguments.append("--objc_out=" + dir_out)

    arguments.append("--proto_path=.")
    arguments += [
        "--proto_path={}".format(get_include_directory(i))
        for i in protos
    ]

    # Include the output directory so that protoc puts the generated code in the
    # right directory.
    arguments.append("--proto_path={}".format(dir_out))
    arguments += ["--proto_path={}".format(_get_directory_from_proto(proto)) for proto in protos]
    arguments += [_get_full_path_from_file(proto) for proto in protos]

    # create a list of well known proto files if the argument is non-None
    well_known_proto_files = []
    if ctx.attr.use_well_known_protos:
        f = ctx.attr.well_known_protos.files.to_list()[0].dirname

        # go two levels up so that #import "google/protobuf/..." is correct
        arguments.append("-I{0}".format(f + "/../.."))
        well_known_proto_files = ctx.attr.well_known_protos.files.to_list()
    ctx.actions.run(
        inputs = protos + well_known_proto_files,
        tools = tools,
        outputs = out_files,
        executable = ctx.executable._protoc,
        arguments = arguments,
    )

    return struct(files = depset(out_files))  # buildifier: disable=rule-impl-return

def _label_to_full_file_path(src, package):
    if not src.startswith("//"):
        # Relative from current package
        if not src.startswith(":"):
            # "a.proto" -> ":a.proto"
            src = ":" + src
        src = "//" + package + src

    # Converts //path/to/package:File.ext to path/to/package/File.ext.
    src = src.replace("//", "")
    src = src.replace(":", "/")
    if src.startswith("/"):
        # "//:a.proto" -> "/a.proto" so remove the initial slash
        return src[1:]
    else:
        return src

def _get_output_file_name_from_proto(proto, fmt):
    return proto_path_to_generated_filename(
        _GENERATED_PROTOS_DIR + "/" +
        _get_directory_from_proto(proto) + _get_slash_or_null_from_proto(proto) +
        to_upper_camel_with_extension(_get_file_name_from_proto(proto), "proto"),
        fmt,
    )

def _get_file_name_from_proto(proto):
    return proto.path.rpartition("/")[2]

def _get_slash_or_null_from_proto(proto):
    """Potentially returns empty (if the file is in the root directory)"""
    return proto.path.rpartition("/")[1]

def _get_directory_from_proto(proto):
    return proto.path.rpartition("/")[0]

def _get_full_path_from_file(file):
    gen_dir_length = 0

    # if file is generated, then prepare to remote its root
    # (including CPU architecture...)
    if not file.is_source:
        gen_dir_length = len(file.root.path) + 1

    return file.path[gen_dir_length:]

def _join_directories(directories):
    massaged_directories = [directory for directory in directories if len(directory) != 0]
    return "/".join(massaged_directories)

generate_objc = rule(
    attrs = {
        "deps": attr.label_list(
            mandatory = True,
            allow_empty = False,
            providers = [ProtoInfo],
        ),
        "plugin": attr.label(
            default = "@com_github_grpc_grpc//src/compiler:grpc_objective_c_plugin",
            executable = True,
            providers = ["files_to_run"],
            cfg = "exec",
        ),
        "srcs": attr.string_list(
            mandatory = False,
            allow_empty = True,
        ),
        "use_well_known_protos": attr.bool(
            mandatory = False,
            default = False,
        ),
        "well_known_protos": attr.label(
            default = "@com_google_protobuf//:well_known_type_protos",
        ),
        "_protoc": attr.label(
            default = Label("//external:protocol_compiler"),
            executable = True,
            cfg = "exec",
        ),
    },
    output_to_genfiles = True,
    implementation = _generate_objc_impl,
)

def _group_objc_files_impl(ctx):
    suffix = ""
    if ctx.attr.gen_mode == _GENERATE_HDRS:
        suffix = "h"
    elif ctx.attr.gen_mode == _GENERATE_SRCS:
        suffix = "pbrpc.m"
    elif ctx.attr.gen_mode == _GENERATE_NON_ARC_SRCS:
        suffix = "pbobjc.m"
    else:
        fail("Undefined gen_mode")
    out_files = [
        file
        for file in ctx.attr.src.files.to_list()
        if file.basename.endswith(suffix)
    ]
    return struct(files = depset(out_files))  # buildifier: disable=rule-impl-return

generate_objc_hdrs = rule(
    attrs = {
        "src": attr.label(
            mandatory = True,
        ),
        "gen_mode": attr.int(
            default = _GENERATE_HDRS,
        ),
    },
    implementation = _group_objc_files_impl,
)

generate_objc_srcs = rule(
    attrs = {
        "src": attr.label(
            mandatory = True,
        ),
        "gen_mode": attr.int(
            default = _GENERATE_SRCS,
        ),
    },
    implementation = _group_objc_files_impl,
)

generate_objc_non_arc_srcs = rule(
    attrs = {
        "src": attr.label(
            mandatory = True,
        ),
        "gen_mode": attr.int(
            default = _GENERATE_NON_ARC_SRCS,
        ),
    },
    implementation = _group_objc_files_impl,
)
