"""Tests for the Bazel java_binary rule"""

load("@bazel_features//private:util.bzl", _bazel_version_ge = "ge")
load("@rules_testing//lib:analysis_test.bzl", "analysis_test", "test_suite")
load("@rules_testing//lib:truth.bzl", "matching")
load("@rules_testing//lib:util.bzl", "util")
load("//java:java_binary.bzl", "java_binary")
load("//test/java/testutil:helper.bzl", "always_passes")
load("//test/java/testutil:java_info_subject.bzl", "java_info_subject")
load("//test/java/testutil:rules/template_var_info_rule.bzl", "template_var_info_rule")

def _test_java_binary_cross_compilation_to_unix(name):
    # A Unix platform that:
    # - has a JDK
    # - does not require a launcher
    # - is not supported by the default C++ toolchain
    util.helper_target(
        native.platform,
        name = name + "/platform",
        constraint_values = [
            "@platforms//os:linux",
            "@platforms//cpu:s390x",
        ],
    )

    util.helper_target(
        java_binary,
        name = name + "/bin",
        srcs = ["java/C.java"],
        main_class = "C",
    )

    analysis_test(
        name = name,
        impl = _test_java_binary_cross_compilation_to_unix_impl,
        target = name + "/bin",
        config_settings = {
            "//command_line_option:platforms": [Label(name + "/platform")],
        },
        # Requires the launcher_maker toolchain.
        attr_values = {"tags": ["min_bazel_9"]},
    )

def _test_java_binary_cross_compilation_to_unix_impl(env, target):
    # The main assertion is that analysis succeeds, but verify the absence of a
    # binary launcher for good measure. We do this by checking that the output
    # executable is the stub script, and not a bespoke launcher
    executable = target[DefaultInfo].files_to_run.executable.short_path
    assert_action = env.expect.that_target(target).action_generating(executable)
    assert_action.mnemonic().equals("TemplateExpand")
    assert_action.substitutions().keys().contains("%jvm_flags%")
    assert_action.inputs().contains_exactly(["java/bazel/rules/java_stub_template.txt"])

def _test_java_binary_excludes_build_data(name):
    if not _bazel_version_ge("8.0.0"):
        always_passes(name)
        return

    util.helper_target(
        java_binary,
        name = name + "/bin",
        srcs = ["Main.java"],
        exclude_build_data = True,
    )

    analysis_test(
        name = name,
        impl = _test_java_binary_excludes_build_data_impl,
        target = name + "/bin",
        attr_values = {"tags": ["min_bazel_8"]},
    )

def _test_java_binary_excludes_build_data_impl(env, target):
    assert_deploy_jar_action = env.expect.that_target(target).action_generating(
        "{package}/{name}_deploy.jar",
    )

    assert_deploy_jar_action.argv().contains("--normalize")
    assert_deploy_jar_action.argv().contains("--exclude_build_data")
    assert_deploy_jar_action.argv().not_contains("--build_info_file")
    assert_deploy_jar_action.inputs().not_contains_predicate(
        matching.file_basename_equals("non_volatile_file.properties"),
    )
    assert_deploy_jar_action.inputs().not_contains_predicate(
        matching.file_basename_equals("redacted_file.properties"),
    )

def _test_java_binary_stamping_enabled_build_data_excluded_fails(name):
    if not _bazel_version_ge("8.0.0"):
        always_passes(name)
        return

    util.helper_target(
        java_binary,
        name = name + "/bin",
        srcs = ["Main.java"],
        exclude_build_data = True,
        stamp = 1,
    )

    analysis_test(
        name = name,
        impl = _test_java_binary_stamping_enabled_build_data_excluded_fails_impl,
        target = name + "/bin",
        expect_failure = True,
        attr_values = {"tags": ["min_bazel_8"]},
    )

def _test_java_binary_stamping_enabled_build_data_excluded_fails_impl(env, target):
    env.expect.that_target(target).failures().contains_predicate(
        matching.str_matches("Enabling stamping has no effect with exclude_build_data enabled"),
    )

def _test_java_binary_javacopts_make_variable_expansion(name):
    util.helper_target(
        template_var_info_rule,
        name = name + "/vars",
        vars = {
            "MY_CUSTOM_OPT": "MY_OPT_VALUE",
        },
    )
    util.helper_target(
        java_binary,
        name = name + "/bin",
        srcs = ["java/A.java"],
        javacopts = ["$(MY_CUSTOM_OPT)"],
        toolchains = [name + "/vars"],
    )

    analysis_test(
        name = name,
        impl = _test_java_binary_javacopts_make_variable_expansion_impl,
        target = name + "/bin",
        # Broken by Starlarkification in the embedded rules in Bazel 7
        attr_values = {"tags": ["min_bazel_8"]},
    )

def _test_java_binary_javacopts_make_variable_expansion_impl(env, target):
    assert_java_info = java_info_subject.from_target(env, target)
    assert_java_info.compilation_info().javac_options().not_contains("$(MY_CUSTOM_OPT)")
    assert_java_info.compilation_info().javac_options().contains("MY_OPT_VALUE")

def _test_java_binary_javacopts_location_expansion(name):
    util.helper_target(
        java_binary,
        name = name + "/bin",
        srcs = ["A.java"],
        javacopts = ["-XepOpt:foo=$(location :A.java)"],
    )

    analysis_test(
        name = name,
        impl = _test_java_binary_javacopts_location_expansion_impl,
        target = name + "/bin",
    )

def _test_java_binary_javacopts_location_expansion_impl(env, target):
    assert_java_info = java_info_subject.from_target(env, target)
    assert_java_info.compilation_info().javac_options().contains(
        "-XepOpt:foo={package}/A.java",
    )

def _test_java_binary_resource_strip_prefix(name):
    util.helper_target(
        java_binary,
        name = name + "/bin",
        srcs = ["Foo.java"],
        main_class = "Foo",
        resource_strip_prefix = native.package_name() + "/path/to/strip",
        resources = ["path/to/strip/bar.props"],
    )

    analysis_test(
        name = name,
        impl = _test_java_binary_resource_strip_prefix_impl,
        target = name + "/bin",
    )

def _test_java_binary_resource_strip_prefix_impl(env, target):
    env.expect.that_target(target).action_generating("{package}/{name}.jar").contains_flag_values([
        ("--resources", "{package}/path/to/strip/bar.props:bar.props"),
    ])

def _test_java_binary_empty_srcs(name):
    analysis_test(
        name = name,
        impl = _test_java_binary_empty_srcs_impl,
        target = "//test/bazel:bin_without_srcs",  # need a target not under a `/java/` segment
        expect_failure = True,
    )

def _test_java_binary_empty_srcs_impl(env, target):
    env.expect.that_target(target).failures().contains_predicate(matching.str_matches(
        "need at least one of 'main_class' or Java source files",
    ))

def java_binary_tests(name):
    test_suite(
        name = name,
        tests = [
            _test_java_binary_cross_compilation_to_unix,
            _test_java_binary_excludes_build_data,
            _test_java_binary_stamping_enabled_build_data_excluded_fails,
            _test_java_binary_javacopts_make_variable_expansion,
            _test_java_binary_javacopts_location_expansion,
            _test_java_binary_resource_strip_prefix,
            _test_java_binary_empty_srcs,
        ],
    )
