diff options
Diffstat (limited to 'tools/bazel_integration_test/bazel_integration_test.bzl')
-rw-r--r-- | tools/bazel_integration_test/bazel_integration_test.bzl | 134 |
1 files changed, 134 insertions, 0 deletions
diff --git a/tools/bazel_integration_test/bazel_integration_test.bzl b/tools/bazel_integration_test/bazel_integration_test.bzl new file mode 100644 index 0000000..c016551 --- /dev/null +++ b/tools/bazel_integration_test/bazel_integration_test.bzl @@ -0,0 +1,134 @@ +# Copyright 2023 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. + +"Define a rule for running bazel test under Bazel" + +load("//:version.bzl", "SUPPORTED_BAZEL_VERSIONS", "bazel_version_to_binary_label") +load("//python:defs.bzl", "py_test") + +BAZEL_BINARY = bazel_version_to_binary_label(SUPPORTED_BAZEL_VERSIONS[0]) + +_ATTRS = { + "bazel_binary": attr.label( + default = BAZEL_BINARY, + doc = """The bazel binary files to test against. + +It is assumed by the test runner that the bazel binary is found at label_workspace/bazel (wksp/bazel.exe on Windows)""", + ), + "bazel_commands": attr.string_list( + default = ["info", "test --test_output=errors ..."], + doc = """The list of bazel commands to run. + +Note that if a command contains a bare `--` argument, the --test_arg passed to Bazel will appear before it. +""", + ), + "bzlmod": attr.bool( + default = False, + doc = """Whether the test uses bzlmod.""", + ), + "workspace_files": attr.label( + doc = """A filegroup of all files in the workspace-under-test necessary to run the test.""", + ), +} + +def _config_impl(ctx): + if len(SUPPORTED_BAZEL_VERSIONS) > 1: + fail(""" + bazel_integration_test doesn't support multiple Bazel versions to test against yet. + """) + if len(ctx.files.workspace_files) == 0: + fail(""" +No files were found to run under integration testing. See comment in /.bazelrc. +You probably need to run + tools/bazel_integration_test/update_deleted_packages.sh +""") + + # Serialize configuration file for test runner + config = ctx.actions.declare_file("%s.json" % ctx.attr.name) + ctx.actions.write( + output = config, + content = """ +{{ + "workspaceRoot": "{TMPL_workspace_root}", + "bazelBinaryWorkspace": "{TMPL_bazel_binary_workspace}", + "bazelCommands": [ {TMPL_bazel_commands} ], + "bzlmod": {TMPL_bzlmod} +}} +""".format( + TMPL_workspace_root = ctx.files.workspace_files[0].dirname, + TMPL_bazel_binary_workspace = ctx.attr.bazel_binary.label.workspace_name, + TMPL_bazel_commands = ", ".join(["\"%s\"" % s for s in ctx.attr.bazel_commands]), + TMPL_bzlmod = str(ctx.attr.bzlmod).lower(), + ), + ) + + return [DefaultInfo( + files = depset([config]), + runfiles = ctx.runfiles(files = [config]), + )] + +_config = rule( + implementation = _config_impl, + doc = "Configures an integration test that runs a specified version of bazel against an external workspace.", + attrs = _ATTRS, +) + +def bazel_integration_test(name, override_bazel_version = None, bzlmod = False, dirname = None, **kwargs): + """Wrapper macro to set default srcs and run a py_test with config + + Args: + name: name of the resulting py_test + override_bazel_version: bazel version to use in test + bzlmod: whether the test uses bzlmod + dirname: the directory name of the test. Defaults to value of `name` after trimming the `_example` suffix. + **kwargs: additional attributes like timeout and visibility + """ + + # By default, we assume sources for "pip_example" are in examples/pip/**/* + dirname = dirname or name[:-len("_example")] + native.filegroup( + name = "_%s_sources" % name, + srcs = native.glob( + ["%s/**/*" % dirname], + exclude = ["%s/bazel-*/**" % dirname], + ), + ) + workspace_files = kwargs.pop("workspace_files", "_%s_sources" % name) + + bazel_binary = BAZEL_BINARY if not override_bazel_version else bazel_version_to_binary_label(override_bazel_version) + _config( + name = "_%s_config" % name, + workspace_files = workspace_files, + bazel_binary = bazel_binary, + bzlmod = bzlmod, + ) + + tags = kwargs.pop("tags", []) + tags.append("integration-test") + + py_test( + name = name, + srcs = [Label("//tools/bazel_integration_test:test_runner.py")], + main = "test_runner.py", + args = [native.package_name() + "/_%s_config.json" % name], + deps = [Label("//python/runfiles")], + data = [ + bazel_binary, + "//:distribution", + "_%s_config" % name, + workspace_files, + ], + tags = tags, + **kwargs + ) |