# Copyright 2016 The Tulsi 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.

"""Skylark rules supporting Tulsi.

This file provides Bazel aspects used to obtain information about a given
project and pass it back to Tulsi.
"""

load(
    ":tulsi_aspects_paths.bzl",
    "AppleBundleInfo",
    "AppleTestInfo",
    "IosExtensionBundleInfo",
    "SwiftInfo",
)
load("@bazel_tools//tools/cpp:toolchain_utils.bzl", "find_cpp_toolchain")

# Defensive list of features that can appear in the C++ toolchain, but that we
# definitely don't want to enable (meaning we don't want them to contribute
# command line flags).
UNSUPPORTED_FEATURES = [
    "thin_lto",
    "module_maps",
    "use_header_modules",
    "fdo_instrument",
    "fdo_optimize",
]

# List of all of the attributes that can link from a Tulsi-supported rule to a
# Tulsi-supported dependency of that rule.
# For instance, an ios_application's "binary" attribute might link to an
# objc_binary rule which in turn might have objc_library's in its "deps"
# attribute.
_TULSI_COMPILE_DEPS = [
    "binary",
    "bundles",
    "deps",
    "extension",
    "extensions",
    "frameworks",
    "settings_bundle",
    "srcs",  # To propagate down onto rules which generate source files.
    "tests",  # for test_suite when the --noexpand_test_suites flag is used.
    "_implicit_tests",  # test_suites without a `tests` attr have an '$implicit_tests' attr instead.
    "test_bundle",
    "test_host",
    # Special attribute name which serves as an escape hatch intended for custom
    # rule creators who use non-standard attribute names for rule dependencies
    # and want those dependencies to show up in Xcode.
    "tulsi_deps",
    "watch_application",
    "xctest_app",
]

# These are attributes that contain bundles but should not be considered as
# embedded bundles. For example, test bundles depend on app bundles
# to be test hosts in bazel semantics, but in reality, Xcode treats the test
# bundles as an embedded bundle of the app.
_TULSI_NON_EMBEDDEDABLE_ATTRS = [
    "test_host",
    "xctest_app",
]

# List of all attributes whose contents should resolve to "support" files; files
# that are used by Bazel to build but do not need special handling in the
# generated Xcode project. For example, Info.plist and entitlements files.
_SUPPORTING_FILE_ATTRIBUTES = [
    "app_icons",
    "entitlements",
    "infoplist",
    "infoplists",
    "resources",
    "strings",
    "structured_resources",
    "storyboards",
    "xibs",
]

# List of rules whose outputs should be treated as generated sources.
_SOURCE_GENERATING_RULES = [
    "j2objc_library",
]

# List of rules whose outputs should be treated as generated sources that do not
# use ARC.
_NON_ARC_SOURCE_GENERATING_RULES = [
    "objc_proto_library",
]

# Whitelist of all extensions to include when scanning target.files for generated
# files. This helps avoid but not prevent the following:
#
# _tulsi-include maps generated files from multiple configurations into one
# directory for inclusion in the generated project. This can cause issues when
# conflicting files are generated, e.g.
#
# library/subpath/foobar (an executable)
# library/subpath/foobar/dependency/dep_lib.a
#
# Tulsi would fail trying to copy both of these as it would require `foobar` to
# be both a file and directory. As a partial workaround, we only copy in files
# that we believe to be 'source files' and thus unlikely to also be folders.
_GENERATED_SOURCE_FILE_EXTENSIONS = [
    "c",
    "cc",
    "cpp",
    "h",
    "hpp",
    "m",
    "mm",
    "swift",
    "swiftmodule",
]

TulsiSourcesAspectInfo = provider(
    fields = {
        "transitive_info_files": """
The file actions used to save this rule's info and that of all of its transitive dependencies as
well as any Info plists required for extensions.
""",
        "inheritable_attributes": """
The inheritable attributes of this rule, expressed as a dict instead of a struct to allow easy
joining.
""",
        "transitive_attributes": """
Transitive attributes that should be applied to every rule that depends on this rule.
""",
        "artifacts": """
Artifacts from this rule.
""",
        "filtering_info": """
Filtering information for this target. Only for test target, otherwise is None.
""",
    },
)

TulsiOutputAspectInfo = provider(
    fields = {
        "transitive_generated_files": "Depset of tulsi generated files.",
        "transitive_embedded_bundles": "Depset of all bundles embedded into this target.",
    },
)

def _dict_omitting_none(**kwargs):
    """Creates a dict from the args, dropping keys with None or [] values."""
    return {
        name: kwargs[name]
        for name in kwargs
        # Skylark doesn't support "is"; comparison is explicit for correctness.
        # pylint: disable=g-equals-none,g-explicit-bool-comparison
        if kwargs[name] != None and kwargs[name] != []
    }

def _struct_omitting_none(**kwargs):
    """Creates a struct from the args, dropping keys with None or [] values."""
    return struct(**_dict_omitting_none(**kwargs))

def _convert_outpath_to_symlink_path(path):
    """Converts full output paths to their tulsi-symlink equivalents.

    Bazel output paths are unstable, prone to change with architecture,
    platform or flag changes. Therefore we can't rely on them to supply to Xcode.
    Instead, we will root all outputs under a stable tulsi dir,
    and the bazel_build.py script will link the artifacts into the correct
    location under it.

    Tulsi root is located at WORKSPACE/bazel-exec-root-link/_tulsi-includes/x/x/.
    The two "x" directories are stubs to match the number of path components, so
    that relative paths work with the new location. Some Bazel outputs, like
    module maps, use relative paths to reference other files in the build.

    The leading underscore in _tulsi-includes is present as Bazel will clear
    all directories that don't start with '.', '_', or 'bazel-' when it builds.
    Otherwise, upon a build failure, _tulsi-includes would be removed and
    indexing and auto-completion for generated files would no longer work until
    the next successful build.

    In short, this method will transform
      bazel-out/ios-x86_64-min7.0/genfiles/foo
    to
      _tulsi-includes/x/x/foo

    This is currently enabled for everything although it will only affect
    generated files.

    Args:
      path: path to transform

    Returns:
      A string that is the original path modified according to the rules.
    """

    # Transform paths of the form:
    #   bazel-[whatever]/[platform-config]/symlink[/.*]
    # to:
    #   _tulsi-includes/x/x/symlink[/.*]
    first_dash = path.find("-")
    components = path.split("/")
    if (len(components) > 2 and
        first_dash >= 0 and
        first_dash < len(components[0])):
        return "_tulsi-includes/x/x/" + "/".join(components[3:])
    return path

def _is_bazel_external_file(f):
    """Returns True if the given file is a Bazel external file."""
    return f.path.startswith("external/")

def _file_metadata(f):
    """Returns metadata about a given File."""
    if not f:
        return None

    # Special case handling for Bazel external files which have a path that starts
    # with 'external/' but their short_path and root.path have no mention of being
    # external.
    out_path = f.path if _is_bazel_external_file(f) else f.short_path
    if not f.is_source:
        root_path = f.root.path
        symlink_path = _convert_outpath_to_symlink_path(root_path)
        if symlink_path == root_path:
            # The root path should always be bazel-out/... and thus is expected to be
            # updated.
            print('Unexpected root path "%s". Please report.' % root_path)
            root_execution_path_fragment = root_path
        else:
            root_execution_path_fragment = symlink_path
    else:
        root_execution_path_fragment = None

    # At the moment (Oct. 2016), Bazel disallows most files without extensions.
    # As a temporary hack, Tulsi treats File instances pointing at extension-less
    # paths as directories. This is extremely fragile and must be replaced with
    # logic properly homed in Bazel.
    is_dir = (f.basename.find(".") == -1)

    return _struct_omitting_none(
        path = out_path,
        src = f.is_source,
        root = root_execution_path_fragment,
        is_dir = is_dir,
    )

def _file_metadata_by_replacing_path(f, new_path, new_is_dir = None):
    """Returns a copy of the f _file_metadata struct with the given path."""
    root_path = _get_opt_attr(f, "rootPath")
    if new_is_dir == None:
        new_is_dir = f.is_dir

    return _struct_omitting_none(
        path = new_path,
        src = f.src,
        root = root_path,
        is_dir = new_is_dir,
    )

def _depset_to_file_metadata_list(a_depset):
    """"Converts a depset of files into a list of _file_metadata structs."""
    return [_file_metadata(f) for f in a_depset.to_list()]

def _collect_artifacts(obj, attr_path):
    """Returns a list of Artifact objects for the attr_path in obj."""
    return [
        f
        for src in _getattr_as_list(obj, attr_path)
        for f in _get_opt_attr(src, "files").to_list()
    ]

def _collect_files(obj, attr_path, convert_to_metadata = True):
    """Returns a list of artifact_location's for the attr_path in obj."""
    if convert_to_metadata:
        return [_file_metadata(f) for f in _collect_artifacts(obj, attr_path)]
    else:
        return _collect_artifacts(obj, attr_path)

def _collect_first_file(obj, attr_path):
    """Returns a the first artifact_location for the attr_path in obj."""
    files = _collect_files(obj, attr_path)
    if not files:
        return None
    return files[0]

def _collect_supporting_files(rule_attr, convert_to_metadata = True):
    """Extracts 'supporting' files from the given rule attributes."""
    all_files = []
    for attr in _SUPPORTING_FILE_ATTRIBUTES:
        all_files += _collect_files(
            rule_attr,
            attr,
            convert_to_metadata = convert_to_metadata,
        )
    return all_files

def _collect_bundle_paths(rule_attr, bundle_attributes, bundle_ext):
    """Extracts subpaths with the given bundle_ext for the given attributes."""
    discovered_paths = dict()
    bundles = []
    if not bundle_ext.endswith("/"):
        bundle_ext += "/"
    bundle_ext_len = len(bundle_ext) - 1

    for attr in bundle_attributes:
        for f in _collect_files(rule_attr, attr):
            end = f.path.find(bundle_ext)
            if end < 0:
                continue
            end += bundle_ext_len

            path = f.path[:end]
            root_path = _get_opt_attr(f, "rootPath")
            full_path = str(root_path) + ":" + path
            if full_path in discovered_paths:
                continue

            # Using the 'discovered_paths' as a set, we will only be checking for the existence of a
            # key, the actual value does not matter so assign it 'None'.
            discovered_paths[full_path] = None

            # Generally Xcode treats bundles as special files so they should not be
            # flagged as directories.
            bundles.append(_file_metadata_by_replacing_path(f, path, False))
    return bundles

def _collect_asset_catalogs(rule_attr):
    """Extracts xcassets directories from the given rule attributes."""
    attrs = ["app_asset_catalogs", "asset_catalogs"]
    bundles = _collect_bundle_paths(rule_attr, attrs, ".xcassets")
    bundles.extend(_collect_bundle_paths(rule_attr, attrs, ".xcstickers"))

    return bundles

def _collect_bundle_imports(rule_attr):
    """Extracts bundle directories from the given rule attributes."""
    return _collect_bundle_paths(
        rule_attr,
        ["bundle_imports", "settings_bundle"],
        ".bundle",
    )

def _collect_framework_imports(rule_attr):
    """Extracts framework directories from the given rule attributes."""
    return _collect_bundle_paths(
        rule_attr,
        ["framework_imports"],
        ".framework",
    )

def _collect_xcdatamodeld_files(obj, attr_path):
    """Returns artifact_location's for xcdatamodeld's for attr_path in obj."""
    files = _collect_files(obj, attr_path)
    if not files:
        return []
    discovered_paths = dict()
    datamodelds = []
    for f in files:
        end = f.path.find(".xcdatamodel/")
        if end < 0:
            continue
        end += 12

        path = f.path[:end]
        root_path = _get_opt_attr(f, "rootPath")
        full_path = str(root_path) + ":" + path
        if full_path in discovered_paths:
            continue

        # Using the 'discovered_paths' as a set, we will only be checking for the existence of a
        # key, the actual value does not matter so assign it 'None'.
        discovered_paths[full_path] = None
        datamodelds.append(_file_metadata_by_replacing_path(f, path, False))
    return datamodelds

def _collect_dependencies(rule_attr, attr_name):
    """Collects Bazel targets for a dependency attr.

    Args:
      rule_attr: The Bazel rule.attr whose dependencies should be collected.
      attr_name: attribute name to inspect for dependencies.

    Returns:
      A list of the Bazel target dependencies of the given rule.
    """
    return [
        dep
        for dep in _getattr_as_list(rule_attr, attr_name)
        if type(dep) == "Target" and
           (TulsiSourcesAspectInfo in dep or TulsiOutputAspectInfo in dep)
    ]

def _collect_dependency_labels(rule, filter, attr_list):
    """Collects Bazel labels for a list of dependency attributes.

    Args:
      rule: The Bazel rule whose dependencies should be collected.
      filter: Filter to apply when gathering dependencies.
      attr_list: List of attribute names potentially containing Bazel labels for
          dependencies of the given rule.

    Returns:
      A list of the Bazel labels of dependencies of the given rule.
    """
    attr = rule.attr
    deps = [
        dep
        for attribute in attr_list
        for dep in _filter_deps(
            filter,
            _collect_dependencies(attr, attribute),
        )
    ]
    return [dep.label for dep in deps if hasattr(dep, "label")]

def _get_opt_attr(obj, attr_path):
    """Returns the value at attr_path on the given object if it is set."""
    attr_path = attr_path.split(".")
    for a in attr_path:
        if not obj or not hasattr(obj, a):
            return None
        obj = getattr(obj, a)
    return obj

def _get_label_attr(obj, attr_path):
    """Returns the value at attr_path as a label string if it is set."""
    label = _get_opt_attr(obj, attr_path)
    return str(label) if label else None

def _getattr_as_list(obj, attr_path):
    """Returns the value at attr_path as a list.

    This handles normalization of attributes containing a single value for use in
    methods expecting a list of values.

    Args:
      obj: The struct whose attributes should be parsed.
      attr_path: Dotted path of attributes whose value should be returned in
          list form.

    Returns:
      A list of values for obj at attr_path or [] if the struct has
      no such attribute.
    """
    val = _get_opt_attr(obj, attr_path)
    if not val:
        return []

    if type(val) == "list":
        return val
    return [val]

def _extract_defines_from_option_list(lst):
    """Extracts preprocessor defines from a list of -D strings."""
    defines = []
    for item in lst:
        if item.startswith("-D"):
            defines.append(item[2:])
    return defines

def _extract_compiler_defines(ctx):
    """Extracts preprocessor defines from compiler fragments."""
    defines = []

    cpp_fragment = _get_opt_attr(ctx.fragments, "cpp")

    # Enabled in Bazel 0.17
    if hasattr(cpp_fragment, "copts"):
        cc_toolchain = find_cpp_toolchain(ctx)
        copts = cpp_fragment.copts
        cxxopts = cpp_fragment.cxxopts
        conlyopts = cpp_fragment.conlyopts

        feature_configuration = cc_common.configure_features(
            cc_toolchain = cc_toolchain,
            requested_features = ctx.features,
            unsupported_features = ctx.disabled_features + UNSUPPORTED_FEATURES,
        )
        c_variables = cc_common.create_compile_variables(
            feature_configuration = feature_configuration,
            cc_toolchain = cc_toolchain,
            user_compile_flags = depset(copts + conlyopts),
        )
        cpp_variables = cc_common.create_compile_variables(
            feature_configuration = feature_configuration,
            cc_toolchain = cc_toolchain,
            add_legacy_cxx_options = True,
            user_compile_flags = depset(copts + cxxopts),
        )
        c_options = cc_common.get_memory_inefficient_command_line(
            feature_configuration = feature_configuration,
            # TODO(hlopko): Replace with action_name once Bazel >= # 0.16 is assumed
            action_name = "c-compile",
            variables = c_variables,
        )
        cpp_options = cc_common.get_memory_inefficient_command_line(
            feature_configuration = feature_configuration,
            # TODO(hlopko): Replace with action_name once Bazel >= # 0.16 is assumed
            action_name = "c++-compile",
            variables = cpp_variables,
        )
        defines += _extract_defines_from_option_list(c_options)
        defines += _extract_defines_from_option_list(cpp_options)
    elif cpp_fragment:
        c_options = _get_opt_attr(cpp_fragment, "c_options")
        defines += _extract_defines_from_option_list(c_options)

        compiler_options = cpp_fragment.compiler_options([])
        defines += _extract_defines_from_option_list(compiler_options)

        unfiltered = cpp_fragment.unfiltered_compiler_options([])
        defines += _extract_defines_from_option_list(unfiltered)

        cxx = cpp_fragment.cxx_options([])
        defines += _extract_defines_from_option_list(cxx)

    objc_fragment = _get_opt_attr(ctx.fragments, "objc")
    if objc_fragment:
        objc_copts = _get_opt_attr(objc_fragment, "copts")
        defines += _extract_defines_from_option_list(objc_copts)

    return defines

def _collect_secondary_artifacts(target, ctx):
    """Returns a list of file metadatas for implicit outputs of 'target'."""
    artifacts = []
    if AppleBundleInfo in target:
        infoplist = target[AppleBundleInfo].infoplist

        if infoplist:
            artifacts.append(_file_metadata(infoplist))

    return artifacts

def _extract_generated_sources(target):
    """Returns (source_metadatas, includes) generated by the given target."""
    file_metadatas = []
    objc_provider = _get_opt_attr(target, "objc")
    if hasattr(objc_provider, "source") and hasattr(objc_provider, "header"):
        all_files = depset(transitive = [objc_provider.source, objc_provider.header])
        file_metadatas = _depset_to_file_metadata_list(all_files)

    return file_metadatas

def _get_deployment_info(target, ctx):
    """Returns (platform_type, minimum_os_version) for the given target."""
    platform_type = _get_platform_type(ctx)

    if AppleBundleInfo in target:
        apple_bundle_provider = target[AppleBundleInfo]
        minimum_os_version = apple_bundle_provider.minimum_os_version
        return (platform_type, minimum_os_version)
    return (platform_type, _minimum_os_for_platform(ctx, platform_type))

def _get_xcode_version(ctx):
    """Returns the current Xcode version as a string."""
    return str(ctx.attr._tulsi_xcode_config[apple_common.XcodeVersionConfig].xcode_version())

def _get_platform_type(ctx):
    """Return the current apple_common.platform_type as a string."""
    current_platform = (_get_opt_attr(ctx, "rule.attr.platform_type") or
                        _get_opt_attr(ctx, "rule.attr._platform_type"))
    if not current_platform:
        apple_frag = _get_opt_attr(ctx.fragments, "apple")
        current_platform = str(apple_frag.single_arch_platform.platform_type)
    return current_platform

def _minimum_os_for_platform(ctx, platform_type_str):
    """Extracts the minimum OS version for the given apple_common.platform."""
    min_os = _get_opt_attr(ctx, "rule.attr.minimum_os_version")
    if min_os:
        return min_os

    platform_type = getattr(apple_common.platform_type, platform_type_str)
    min_os = (ctx.attr._tulsi_xcode_config[apple_common.XcodeVersionConfig].minimum_os_for_platform_type(platform_type))

    if not min_os:
        return None

    # Convert the DottedVersion to a string suitable for inclusion in a struct.
    return str(min_os)

def _collect_swift_modules(target):
    """Returns a depset of Swift modules found on the given target."""
    if SwiftInfo in target:
        swift_info = target[SwiftInfo]
        if hasattr(swift_info, "transitive_swiftmodules"):
            return swift_info.transitive_swiftmodules
    return depset()

def _collect_module_maps(target):
    """Returns a depset of Clang module maps found on the given target."""
    if SwiftInfo in target and apple_common.Objc in target:
        objc = target[apple_common.Objc]
        if hasattr(objc, "module_map"):
            return objc.module_map
    return depset()

# TODO(b/64490743): Add these files to the Xcode project.
def _collect_swift_header(target):
    """Returns a depset of Swift generated headers found on the given target."""

    # swift_* targets put the generated header into their objc provider HEADER
    # field.
    if SwiftInfo in target and apple_common.Objc in target:
        return target[apple_common.Objc].header
    return depset()

def _target_filtering_info(ctx):
    """Returns filtering information for test rules."""
    rule = ctx.rule

    # TODO(b/72406542): Clean this up to use a test provider if possible.
    if rule.kind.endswith("_test"):
        # Note that a test's size is considered a tag for filtering purposes.
        size = _getattr_as_list(rule, "attr.size")
        tags = _getattr_as_list(rule, "attr.tags")
        return struct(tags = tags + size)
    else:
        return None

def _tulsi_sources_aspect(target, ctx):
    """Extracts information from a given rule, emitting it as a JSON struct."""
    rule = ctx.rule
    target_kind = rule.kind
    rule_attr = _get_opt_attr(rule, "attr")
    filter = _filter_for_rule(rule)

    transitive_info_files = []
    transitive_attributes = dict()
    for attr_name in _TULSI_COMPILE_DEPS:
        deps = _collect_dependencies(rule_attr, attr_name)
        for dep in _filter_deps(filter, deps):
            if TulsiSourcesAspectInfo in dep:
                transitive_info_files.append(dep[TulsiSourcesAspectInfo].transitive_info_files)
                transitive_attributes += dep[TulsiSourcesAspectInfo].transitive_attributes

    artifacts = _get_opt_attr(target, "files")
    if artifacts:
        # Ignore any generated Xcode projects as they are not useful to Tulsi.
        artifacts = [
            _file_metadata(f)
            for f in artifacts.to_list()
            if not f.short_path.endswith("project.pbxproj")
        ]
    else:
        # artifacts may be an empty set type, in which case it must be explicitly
        # set to None to allow Skylark's serialization to work.
        artifacts = None

    srcs = (_collect_files(rule, "attr.srcs") +
            _collect_files(rule, "attr.hdrs") +
            _collect_files(rule, "attr.textual_hdrs"))
    generated_files = []
    generated_non_arc_files = []
    if target_kind in _SOURCE_GENERATING_RULES:
        generated_files = _extract_generated_sources(target)
    elif target_kind in _NON_ARC_SOURCE_GENERATING_RULES:
        generated_non_arc_files = _extract_generated_sources(target)

    swift_transitive_modules = depset(
        _depset_to_file_metadata_list(_collect_swift_modules(target)),
    )

    # Collect ObjC module maps dependencies for Swift targets.
    objc_module_maps = depset(
        _depset_to_file_metadata_list(_collect_module_maps(target)),
    )

    # Collect the dependencies of this rule, dropping any .jar files (which may be
    # created as artifacts of java/j2objc rules).
    dep_labels = _collect_dependency_labels(rule, filter, _TULSI_COMPILE_DEPS)
    compile_deps = [str(d) for d in dep_labels if not d.name.endswith(".jar")]

    binary_rule = _get_opt_attr(rule_attr, "binary")
    if binary_rule and type(binary_rule) == "list":
        binary_rule = binary_rule[0]

    supporting_files = (_collect_supporting_files(rule_attr) +
                        _collect_asset_catalogs(rule_attr) +
                        _collect_bundle_imports(rule_attr))

    copts_attr = _get_opt_attr(rule_attr, "copts")
    is_swift_library = target_kind == "swift_library"

    # Keys for attribute and inheritable_attributes keys must be kept in sync
    # with defines in Tulsi's RuleEntry.
    attributes = _dict_omitting_none(
        binary = _get_label_attr(binary_rule, "label"),
        copts = None if is_swift_library else copts_attr,
        swiftc_opts = copts_attr if is_swift_library else None,
        datamodels = _collect_xcdatamodeld_files(rule_attr, "datamodels"),
        supporting_files = supporting_files,
        xctest_app = _get_label_attr(rule_attr, "xctest_app.label"),
        test_host = _get_label_attr(rule_attr, "test_host.label"),
        test_bundle = _get_label_attr(rule_attr, "test_bundle.label"),
    )

    # Inheritable attributes are pulled up through dependencies of type 'binary'
    # to simplify handling in Tulsi (so it appears as though bridging_header is
    # defined on an ios_application rather than its associated objc_binary, for
    # example).
    inheritable_attributes = _dict_omitting_none(
        bridging_header = _collect_first_file(rule_attr, "bridging_header"),
        compiler_defines = _extract_compiler_defines(ctx),
        enable_modules = _get_opt_attr(rule_attr, "enable_modules"),
        launch_storyboard = _collect_first_file(rule_attr, "launch_storyboard"),
        pch = _collect_first_file(rule_attr, "pch"),
    )

    # Merge any attributes on the "binary" dependency into this container rule.
    binary_attributes = _get_opt_attr(binary_rule, "inheritable_attributes")
    if binary_attributes:
        inheritable_attributes = binary_attributes + inheritable_attributes

    # Collect extensions for bundled targets.
    extensions = []
    if AppleBundleInfo in target:
        extensions = [str(t.label) for t in _getattr_as_list(rule_attr, "extensions")]

    # Tulsi considers WatchOS apps and extensions as an "extension"
    if target_kind == "watchos_application":
        watch_ext = _get_label_attr(rule_attr, "extension.label")
        extensions.append(watch_ext)
    if target_kind == "ios_application":
        watch_app = _get_label_attr(rule_attr, "watch_application.label")
        if watch_app:
            extensions.append(watch_app)

    # Record the Xcode version used for all targets, although it will only be used by bazel_build.py
    # for targets that are buildable in the xcodeproj.
    xcode_version = _get_xcode_version(ctx)

    # Collect bundle related information and Xcode version only for runnable targets.
    if AppleBundleInfo in target:
        apple_bundle_provider = target[AppleBundleInfo]

        bundle_name = apple_bundle_provider.bundle_name
        bundle_id = apple_bundle_provider.bundle_id
        product_type = apple_bundle_provider.product_type

        # We only need the infoplist from iOS extension targets.
        infoplist = apple_bundle_provider.infoplist if IosExtensionBundleInfo in target else None
    else:
        bundle_name = None
        product_type = None
        infoplist = None

        # For macos_command_line_application, which does not have a
        # AppleBundleInfo provider but does have a bundle_id attribute for use
        # in the Info.plist.
        if target_kind == "macos_command_line_application":
            bundle_id = _get_opt_attr(rule_attr, "bundle_id")
        else:
            bundle_id = None

    # Collect Swift related attributes.
    swift_defines = []

    if SwiftInfo in target:
        swift_info = target[SwiftInfo]
        attributes["has_swift_info"] = True
        transitive_attributes["swift_language_version"] = swift_info.swift_version
        transitive_attributes["has_swift_dependency"] = True
        swift_defines = swift_info.transitive_defines.to_list()

    all_attributes = attributes + inheritable_attributes + transitive_attributes

    objc_provider = _get_opt_attr(target, "objc")
    objc_defines = []
    target_includes = []

    if objc_provider:
        target_includes = [
            _convert_outpath_to_symlink_path(x)
            for x in objc_provider.include
        ]
        objc_defines = objc_provider.define.to_list()

    platform_type, os_deployment_target = _get_deployment_info(target, ctx)
    non_arc_srcs = _collect_files(rule, "attr.non_arc_srcs")

    # Collect test information.
    if AppleTestInfo in target:
        provider = target[AppleTestInfo]
        srcs = _depset_to_file_metadata_list(provider.sources)
        non_arc_srcs = _depset_to_file_metadata_list(provider.non_arc_sources)
        target_includes = [_convert_outpath_to_symlink_path(x) for x in provider.includes.to_list()]
        swift_transitive_modules = _depset_to_file_metadata_list(provider.swift_modules)
        objc_module_maps = _depset_to_file_metadata_list(provider.module_maps)
        test_deps = provider.deps.to_list()
        module_name = provider.module_name
    else:
        swift_transitive_modules = swift_transitive_modules.to_list()
        objc_module_maps = objc_module_maps.to_list()
        test_deps = None
        module_name = None

    info = _struct_omitting_none(
        artifacts = artifacts,
        attr = _struct_omitting_none(**all_attributes),
        build_file = ctx.build_file_path,
        bundle_id = bundle_id,
        bundle_name = bundle_name,
        objc_defines = objc_defines,
        swift_defines = swift_defines,
        deps = compile_deps,
        test_deps = test_deps,
        extensions = extensions,
        framework_imports = _collect_framework_imports(rule_attr),
        generated_files = generated_files,
        generated_non_arc_files = generated_non_arc_files,
        includes = target_includes,
        os_deployment_target = os_deployment_target,
        label = str(target.label),
        non_arc_srcs = non_arc_srcs,
        secondary_product_artifacts = _collect_secondary_artifacts(target, ctx),
        srcs = srcs,
        swift_transitive_modules = swift_transitive_modules,
        objc_module_maps = objc_module_maps,
        module_name = module_name,
        type = target_kind,
        infoplist = infoplist.basename if infoplist else None,
        platform_type = platform_type,
        product_type = product_type,
        xcode_version = xcode_version,
    )

    # Create an action to write out this target's info.
    output = ctx.new_file(target.label.name + ".tulsiinfo")
    ctx.file_action(output, info.to_json())
    output_files = [output]

    if infoplist:
        output_files.append(infoplist)

    info_files = depset(output_files, transitive = transitive_info_files)
    artifacts_depset = depset(artifacts) if artifacts else depset()

    return [
        OutputGroupInfo(tulsi_info = info_files),
        TulsiSourcesAspectInfo(
            transitive_info_files = info_files,
            inheritable_attributes = inheritable_attributes,
            transitive_attributes = transitive_attributes,
            artifacts = artifacts_depset,
            filtering_info = _target_filtering_info(ctx),
        ),
    ]

def _collect_bundle_info(target):
    """Returns Apple bundle info for the given target, None if not a bundle."""
    if AppleBundleInfo in target:
        apple_bundle = target[AppleBundleInfo]
        has_dsym = (apple_common.AppleDebugOutputs in target)
        return struct(
            archive_root = apple_bundle.archive_root,
            bundle_name = apple_bundle.bundle_name,
            bundle_extension = apple_bundle.bundle_extension,
            has_dsym = has_dsym,
        )

    return None

# Due to b/71744111 we have to manually re-create tag filtering for test_suite
# rules.
def _tags_conform_to_filter(tags, filter):
    """Mirrors Bazel tag filtering for test_suites.

    This makes sure that the target has all of the required tags and none of
    the excluded tags before we include them within a test_suite.

    For more information on filtering inside Bazel, see
    com.google.devtools.build.lib.packages.TestTargetUtils.java.

    Args:
      tags: all of the tags for the test target
      filter: a struct containing excluded_tags and required_tags

    Returns:
      True if this target passes the filter and False otherwise.

    """

    # None of the excluded tags can be present.
    for exclude in filter.excluded_tags:
        if exclude in tags:
            return False

    # All of the required tags must be present.
    for required in filter.required_tags:
        if required not in tags:
            return False

    # All filters have been satisfied.
    return True

def _filter_for_rule(rule):
    """Returns a filter for test_suite rules and None for other rules."""
    if rule.kind != "test_suite":
        return None

    excluded_tags = []
    required_tags = []

    tags = _getattr_as_list(rule, "attr.tags")

    for tag in tags:
        if tag.startswith("-"):
            excluded_tags.append(tag[1:])
        elif tag.startswith("+"):
            required_tags.append(tag[1:])
        elif tag == "manual":
            # The manual tag is treated specially; it is ignored for filters.
            continue
        else:
            required_tags.append(tag)
    return struct(
        excluded_tags = excluded_tags,
        required_tags = required_tags,
    )

def _filter_deps(filter, deps):
    """Filters dep targets based on tags."""
    if not filter:
        return deps

    kept_deps = []
    for dep in deps:
        info = None
        if TulsiSourcesAspectInfo in dep:
            info = dep[TulsiSourcesAspectInfo].filtering_info

        # Only attempt to filter targets that support filtering.
        # test_suites in a test_suite are not filtered, but their
        # tests are.
        if not info or _tags_conform_to_filter(info.tags, filter):
            kept_deps.append(dep)
    return kept_deps

def _tulsi_outputs_aspect(target, ctx):
    """Collects outputs of each build invocation."""

    rule = ctx.rule
    target_kind = rule.kind
    rule_attr = _get_opt_attr(rule, "attr")
    transitive_generated_files = []

    # A collective list of bundle infos that has been gathered by each dependency of this target.
    # We intentionally do not collect info about _current_ target to exclude the
    # root target, which will be covered by other structs in this aspect, from the
    # list.
    transitive_embedded_bundles = []

    # A list of bundle infos corresponding to the dependencies of this target.
    direct_embedded_bundles = []

    for attr_name in _TULSI_COMPILE_DEPS:
        deps = _collect_dependencies(rule_attr, attr_name)
        for dep in deps:
            if TulsiOutputAspectInfo in dep:
                transitive_generated_files.append(dep[TulsiOutputAspectInfo].transitive_generated_files)
                transitive_embedded_bundles.append(dep[TulsiOutputAspectInfo].transitive_embedded_bundles)

            # Retrieve the bundle info for embeddable attributes.
            if attr_name not in _TULSI_NON_EMBEDDEDABLE_ATTRS:
                dep_bundle_info = _collect_bundle_info(dep)
                if dep_bundle_info:
                    direct_embedded_bundles.append(dep_bundle_info)

    embedded_bundles = depset(direct_embedded_bundles, transitive = transitive_embedded_bundles)

    artifact = None
    bundle_name = None
    archive_root = None
    bundle_dir = None
    infoplist = None
    if AppleBundleInfo in target:
        bundle_info = target[AppleBundleInfo]

        artifact = bundle_info.archive.path
        archive_root = bundle_info.archive_root
        infoplist = bundle_info.infoplist

        bundle_name = bundle_info.bundle_name
        bundle_dir = bundle_info.bundle_dir
    elif target_kind == "macos_command_line_application":
        # Special support for macos_command_line_application which does not have an
        # AppleBundleInfo provider.

        # Both the dSYM binary and executable binary don't have an extension, so
        # pick the first extension-less file not in a DWARF folder.
        artifacts = [
            x.path
            for x in target.files.to_list()
            if x.extension == "" and
               "Contents/Resources/DWARF" not in x.path
        ]
        if len(artifacts) > 0:
            artifact = artifacts[0]

    # Collect generated files for bazel_build.py to copy under Tulsi root.
    all_files_depsets = []
    if target_kind in _SOURCE_GENERATING_RULES + _NON_ARC_SOURCE_GENERATING_RULES:
        objc_provider = _get_opt_attr(target, "objc")
        if hasattr(objc_provider, "source") and hasattr(objc_provider, "header"):
            all_files_depsets.append(objc_provider.source)
            all_files_depsets.append(objc_provider.header)

    all_files_depsets.append(_collect_swift_header(target))
    all_files_depsets.append(_collect_swift_modules(target))
    all_files_depsets.append(_collect_module_maps(target))

    source_files = [
        x
        for x in target.files.to_list()
        if x.extension.lower() in _GENERATED_SOURCE_FILE_EXTENSIONS
    ]
    if infoplist:
        source_files.append(infoplist)

    source_files.extend(_collect_artifacts(rule, "attr.srcs"))
    source_files.extend(_collect_artifacts(rule, "attr.hdrs"))
    source_files.extend(_collect_artifacts(rule, "attr.textual_hdrs"))
    source_files.extend(_collect_supporting_files(rule_attr, convert_to_metadata = False))

    all_files = depset(source_files, transitive = all_files_depsets)

    generated_files = depset(
        [x for x in all_files.to_list() if not x.is_source],
        transitive = transitive_generated_files,
    )

    has_dsym = False
    if hasattr(ctx.fragments, "objc"):
        # Check the fragment directly, as macos_command_line_application does not
        # propagate apple_common.AppleDebugOutputs.
        has_dsym = ctx.fragments.objc.generate_dsym

    info = _struct_omitting_none(
        artifact = artifact,
        bundle_dir = bundle_dir,
        archive_root = archive_root,
        generated_sources = [(x.path, x.short_path) for x in generated_files],
        bundle_name = bundle_name,
        embedded_bundles = embedded_bundles.to_list(),
        has_dsym = has_dsym,
    )

    output = ctx.new_file(target.label.name + ".tulsiouts")
    ctx.file_action(output, info.to_json())

    return [
        OutputGroupInfo(tulsi_outputs = [output]),
        TulsiOutputAspectInfo(
            transitive_generated_files = generated_files,
            transitive_embedded_bundles = embedded_bundles,
        ),
    ]

tulsi_sources_aspect = aspect(
    attr_aspects = _TULSI_COMPILE_DEPS,
    attrs = {
        "_tulsi_xcode_config": attr.label(default = configuration_field(
            name = "xcode_config_label",
            fragment = "apple",
        )),
        "_cc_toolchain": attr.label(default = Label(
            "@bazel_tools//tools/cpp:current_cc_toolchain",
        )),
    },
    fragments = [
        "apple",
        "cpp",
        "objc",
    ],
    implementation = _tulsi_sources_aspect,
)

# This aspect does not propagate past the top-level target because we only need
# the top target outputs.
tulsi_outputs_aspect = aspect(
    attr_aspects = _TULSI_COMPILE_DEPS,
    attrs = {
        "_cc_toolchain": attr.label(
            default = Label("@bazel_tools//tools/cpp:current_cc_toolchain"),
        ),
    },
    fragments = [
        "apple",
        "cpp",
        "objc",
    ],
    implementation = _tulsi_outputs_aspect,
)
