#!/usr/bin/env python3
# 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.
"""
Example usage:
$ fx set ...
$ scripts/gn/trim_visibility.py --target="//build/config:Wno-conversion"

The output is useful for instance if you have a visibility allowlist for
a deprecation and you'd like to trim it for stale values.
"""

import argparse
import itertools
import os
import re
import subprocess
import sys
import unittest

TARGET_DIR_PART = re.compile(r"\/\/([\w\-_]*(?:\/[\w\-_]+)*)")


def run_command(command):
    return subprocess.check_output(
        command, stderr=subprocess.STDOUT, encoding="utf8")


# TODO(shayba): consider supporting local labels (not just absolutes)
def target_to_dir(target):
    """Returns likely directory path for a target's BUILD.gn file."""
    m = TARGET_DIR_PART.match(target)
    return m.group(1)


# TODO(shayba): consider supporting local labels (not just absolutes)
def is_visible_to(target, visibility):
    """Returns whether dst_target is visible to src_target."""
    target_dirs, _, target_label = target.partition(":")
    visibility_dirs, _, visibility_label = visibility.partition(":")
    for target_dir, visibility_dir in itertools.zip_longest(
            target_dirs.split("/"), visibility_dirs.split("/")):
        if visibility_dir == "*":
            return True
        if target_dir != visibility_dir:
            return False
    if visibility_label == "*":
        return True
    return target_label == visibility_label


def main():
    parser = argparse.ArgumentParser(
        description=
        "Prints which of a target's given visibility list entries are actually needed."
    )
    parser.add_argument("--target", help="Target with visibility")
    parser.add_argument(
        "--verbose",
        action="store_true",
        default=False,
        help="Print progress and stats")
    args = parser.parse_args()

    if not args.target:
        return unittest.main()

    def verbose(*vargs, **kwargs):
        if args.verbose:
            print(*vargs, **kwargs)

    verbose("Getting visibility list...")
    target_visibility = (
        run_command(
            ["fx", "gn", "desc", "out/default", args.target,
             "visibility"]).strip().splitlines())
    verbose(f"Found {len(target_visibility)} elements in list.")

    # Unfortunately we can't rely on `gn refs` to find all references to the
    # target if it's a config.
    # https://bugs.chromium.org/p/gn/issues/detail?id=203
    # Instead we hope that we can translate visibility labels to BUILD.gn files
    # correctly, and then wing it by looking for any valid *.gn file under the
    # given subdirectory.
    # This approach is not expected to be accurate.

    used_visibility = set()
    for vis in target_visibility:
        found_usage = False
        for root, _, files in os.walk(target_to_dir(vis)):
            for filename in files:
                if os.path.splitext(filename)[1] == ".gn":
                    # This has some false positives, but is better than parsing
                    # GN files or relying on `gn desc` for the target, each of
                    # which is a whole can of worms.
                    if args.target in open(os.path.join(root, filename)).read():
                        used_visibility.add(vis)
                        found_usage = True
                        break
            if found_usage:
                break

    verbose("Used visibility:")
    for used in sorted(used_visibility):
        print(f'"{used}",')

    return 0


class Test(unittest.TestCase):

    def test_target_to_dir(self):

        def expect(target, build_dir):
            self.assertTrue(target_to_dir(target), build_dir)

        expect(r"//build/config:Wno-conversion", "build/config")
        expect(r"//foo/bar/*", "foo/bar")
        expect(r"//foo:bar", "foo/bar")

    def test_is_visible_to(self):

        def is_visible(src, dst):
            self.assertTrue(is_visible_to(src, dst))

        def not_visible(src, dst):
            self.assertFalse(is_visible_to(src, dst))

        is_visible("//foo:bar", "*")
        is_visible("//foo:bar", "//foo/*")
        is_visible("//foo:bar", "//foo:bar")
        is_visible("//foo:bar", "//foo:*")
        not_visible("//foo:bar", "//foo:baz")
        not_visible("//foo:bar", "//foo/baz")
        not_visible("//foo/bar:baz", "//foo/bar")


if __name__ == "__main__":
    sys.exit(main())
