diff options
Diffstat (limited to 'examples')
23 files changed, 526 insertions, 0 deletions
diff --git a/examples/BUILD b/examples/BUILD new file mode 100644 index 0000000..4d93f01 --- /dev/null +++ b/examples/BUILD @@ -0,0 +1 @@ +# rules_license examples diff --git a/examples/README.md b/examples/README.md new file mode 100644 index 0000000..0afb5ca --- /dev/null +++ b/examples/README.md @@ -0,0 +1,16 @@ +# Examples for rules_license + +This set of files provides an example of how license rules can be used. + +Terminology +- Organization: A company, organization or other entity that wants to use + license rules to enforce their particular compliance needs. These examples + use the work organization throughout. +- SCM: source code management system. These examples assume that + an organization has a SCM that can enforce ownership restrictions on + specific folder trees. Targets are divided into BUILD files that are + reviewed by engineers vs. those that are reviewed by an organization's + compliance team. + +## Overview + diff --git a/examples/my_org/compliance/BUILD b/examples/my_org/compliance/BUILD new file mode 100644 index 0000000..074b21e --- /dev/null +++ b/examples/my_org/compliance/BUILD @@ -0,0 +1,31 @@ +# Example license policy definitions. + +load("@rules_license//rules:license_policy.bzl", "license_policy") + +package(default_visibility = ["//examples:__subpackages__"]) + +# license_policy rules generally appear in a central location per workspace. They +# are intermingled with normal target build rules +license_policy( + name = "production_service", + conditions = [ + "notice", + "restricted_if_statically_linked", + ], +) + +license_policy( + name = "mobile_application", + conditions = [ + "notice", + ], +) + +license_policy( + name = "special_whitelisted_app", + # There could be a whitelist of targets here. + conditions = [ + "notice", + "whitelist:acme_corp_paid", + ], +) diff --git a/examples/my_org/licenses/BUILD b/examples/my_org/licenses/BUILD new file mode 100644 index 0000000..d9d5c25 --- /dev/null +++ b/examples/my_org/licenses/BUILD @@ -0,0 +1,58 @@ +# Example license kind definitions. + +# We expect that all license_kind rules used by an organization exist in a +# central place in their source repository. +# +# - This allows centralized audit and, with suport from the SCM, an assurance +# that individual developers are not adding new license kinds to the code +# base without authorization. +# - When third party packages are used, they might come with license rules +# pointing to well known license_kinds from @rules_license/licenses. +# At import time, users can mechanically transform those target paths from +# @rules_license to their own license_kind repository. +# - The conditions for each license_kind may be customized for the organzation's +# needs, and not match the conditions used by the canonical versions from +# @rules_license. +# - In rare cases, a third_party project will define their own license_kinds. +# There is no reasonable automatic handling of that. Organizations will have +# to hand inspect the license text to see if it matches the conditions, and +# then will have to hand import it to their private license_kind repository. + +load("@rules_license//rules:license_kind.bzl", "license_kind") + +package(default_visibility = ["//examples:__subpackages__"]) + +# license_kind rules generally appear in a central location per workspace. They +# are intermingled with normal target build rules +license_kind( + name = "generic_notice", + conditions = [ + "notice", + ], +) + +license_kind( + name = "generic_restricted", + conditions = [ + "restricted", + ], +) + +license_kind( + name = "unencumbered", + conditions = [], # none +) + +license_kind( + name = "lgpl_like", + conditions = [ + "restricted_if_statically_linked", + ], +) + +license_kind( + name = "acme_corp_paid", + conditions = [ + "whitelist:acme_corp_paid", + ], +) diff --git a/examples/src/BUILD b/examples/src/BUILD new file mode 100644 index 0000000..be415fc --- /dev/null +++ b/examples/src/BUILD @@ -0,0 +1,64 @@ +# Examples of applications and interactions with licenses + +load("@rules_license//examples/vendor/constant_gen:defs.bzl", "constant_gen") +load("@rules_license//rules:compliance.bzl", "check_license", "licenses_used") +load("@rules_license//rules:license_policy_check.bzl", "license_policy_check") +load("@rules_license//tools:test_helpers.bzl", "golden_test") + +cc_binary( + name = "my_server", + srcs = ["server.cc"], + deps = [ + ":message", + "@rules_license//examples/vendor/libhhgttg", + ], +) + +# Sample +constant_gen( + name = "message", + text = "Hello, world.", + var = "server_message", +) + +license_policy_check( + name = "check_server", + policy = "@rules_license//examples/my_org/compliance:production_service", + target = ":my_server", +) + +cc_binary( + name = "my_violating_server", + srcs = ["server.cc"], + deps = [ + ":message", + "@rules_license//examples/vendor/acme", + "@rules_license//examples/vendor/libhhgttg", + ], +) + +license_policy_check( + name = "check_violating_server", + policy = "@rules_license//examples/my_org/compliance:production_service", + tags = [ + "manual", + "notap", + ], + target = ":my_violating_server", +) + +# +# Verify the licenses are what we expect. The golden output shows that +# :my_server only uses the unencumbered license type. + +licenses_used( + name = "server_licenses", + out = "server_licenses.json", + deps = [":my_server"], +) + +golden_test( + name = "verify_server_licenses_test", + golden = "server_licenses.golden", + subject = ":server_licenses.json", +) diff --git a/examples/src/mobile.cc b/examples/src/mobile.cc new file mode 100644 index 0000000..d15090f --- /dev/null +++ b/examples/src/mobile.cc @@ -0,0 +1,20 @@ +// Copyright 2020 Google LLC +// +// 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 +// +// https://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. + + +#include <iostream> + +int main(int argc, char* argv[]) { + std::cout << "Hello world" << std::endl; +} diff --git a/examples/src/server.cc b/examples/src/server.cc new file mode 100644 index 0000000..8f7990e --- /dev/null +++ b/examples/src/server.cc @@ -0,0 +1,22 @@ +// Copyright 2020 Google LLC +// +// 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 +// +// https://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. + +#include <iostream> + +extern const char* server_message; + +int main(int argc, char* argv[]) { + std::cout << server_message << std::endl; + return 0; +} diff --git a/examples/src/server_licenses.golden b/examples/src/server_licenses.golden new file mode 100644 index 0000000..a8f388b --- /dev/null +++ b/examples/src/server_licenses.golden @@ -0,0 +1,28 @@ +[ + { + "rule": "//examples/vendor/constant_gen:license_for_emitted_code", + "license_kinds": [ + { + "target": "@//examples/my_org/licenses:unencumbered", + "name": "unencumbered", + "conditions": [] + } + ], + "copyright_notice": "", + "package_name": "Trivial Code Generator Output", + "license_text": "examples/vendor/constant_gen/LICENSE" + }, + { + "rule": "//examples/vendor/libhhgttg:license", + "license_kinds": [ + { + "target": "@//examples/my_org/licenses:generic_notice", + "name": "generic_notice", + "conditions": ["notice"] + } + ], + "copyright_notice": "", + "package_name": "", + "license_text": "examples/vendor/libhhgttg/LICENSE" + } +] diff --git a/examples/src/server_report.golden b/examples/src/server_report.golden new file mode 100644 index 0000000..6d322b1 --- /dev/null +++ b/examples/src/server_report.golden @@ -0,0 +1,3 @@ += @rules_license//examples/vendor/constant_gen:license_for_emitted_code + kind: @@rules_license//examples/my_org/licenses:unencumbered + conditions: [] diff --git a/examples/vendor/README.md b/examples/vendor/README.md new file mode 100644 index 0000000..273dea6 --- /dev/null +++ b/examples/vendor/README.md @@ -0,0 +1,6 @@ +# Third party packges used by your project. + +Note that these are presumed to be vendored in to your source tree. +These examples to not try to address the concerns of organizations +that wish to use license software without first examining the license +and preserving their own copy and audit trail. diff --git a/examples/vendor/acme/ACME_LICENSE b/examples/vendor/acme/ACME_LICENSE new file mode 100644 index 0000000..53a5daf --- /dev/null +++ b/examples/vendor/acme/ACME_LICENSE @@ -0,0 +1,3 @@ +Acme Novelty & Software provides a license to this software under terms laid +out in specific contracts. Unless you have purchased a license from us, you may +not use this software for any purpose. diff --git a/examples/vendor/acme/BUILD b/examples/vendor/acme/BUILD new file mode 100644 index 0000000..488af62 --- /dev/null +++ b/examples/vendor/acme/BUILD @@ -0,0 +1,22 @@ +# A package with a commercial license. + +load("@rules_license//rules:license.bzl", "license") + +package( + default_applicable_licenses = [":license"], + default_visibility = ["//visibility:public"], +) + +# The default license for an entire package is typically named "license". +license( + name = "license", + license_kinds = [ + "@rules_license//examples/my_org/licenses:acme_corp_paid", + ], + license_text = "ACME_LICENSE", +) + +cc_library( + name = "acme", + srcs = ["coyote.cc"], +) diff --git a/examples/vendor/acme/coyote.cc b/examples/vendor/acme/coyote.cc new file mode 100644 index 0000000..e1e8083 --- /dev/null +++ b/examples/vendor/acme/coyote.cc @@ -0,0 +1,17 @@ +// Copyright 2020 Google LLC +// +// 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 +// +// https://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. + +bool caught_road_runner() { + return false; +} diff --git a/examples/vendor/constant_gen/BUILD b/examples/vendor/constant_gen/BUILD new file mode 100644 index 0000000..e837fd1 --- /dev/null +++ b/examples/vendor/constant_gen/BUILD @@ -0,0 +1,69 @@ +# An example of a code generator with a distinct license for the generated code. + +load(":defs.bzl", "constant_gen") +load("@rules_license//rules:compliance.bzl", "licenses_used") +load("@rules_license//rules:license.bzl", "license") +load("@rules_license//tools:test_helpers.bzl", "golden_test") + +package( + default_applicable_licenses = [":license"], + default_visibility = ["//visibility:public"], +) + +# The default license for an entire package is typically named "license". +license( + name = "license", + package_name = "Trivial Code Generator", + license_kinds = [ + "@rules_license//examples/my_org/licenses:generic_restricted", + ], + license_text = "LICENSE", +) + +license( + name = "license_for_emitted_code", + package_name = "Trivial Code Generator Output", + license = "LICENSE.on_output", + license_kinds = [ + "@rules_license//examples/my_org/licenses:unencumbered", + ], +) + +# The generator itself will be licensed under :license +py_binary( + name = "constant_generator", + srcs = ["constant_generator.py"], + python_version = "PY3", +) + +# Sample: This target will be licensed under :license_for_emitted_code +constant_gen( + name = "libhello", + text = "Hello, world.", + var = "hello_world", +) + +# Verify the licenses are what we expect +licenses_used( + name = "generator_licenses", + out = "generator_licenses.json", + deps = [":constant_generator"], +) + +golden_test( + name = "verify_generator_licenses", + golden = "generator_licenses.golden", + subject = ":generator_licenses.json", +) + +licenses_used( + name = "generated_code_licenses", + # Note: using default output file name + deps = [":libhello"], +) + +golden_test( + name = "verify_generated_code_licenses", + golden = "generated_code_licenses.golden", + subject = ":generated_code_licenses.json", +) diff --git a/examples/vendor/constant_gen/LICENSE b/examples/vendor/constant_gen/LICENSE new file mode 100644 index 0000000..861da0d --- /dev/null +++ b/examples/vendor/constant_gen/LICENSE @@ -0,0 +1 @@ +This code is provided under a license which contains some restrictions. diff --git a/examples/vendor/constant_gen/LICENSE.on_output b/examples/vendor/constant_gen/LICENSE.on_output new file mode 100644 index 0000000..b699638 --- /dev/null +++ b/examples/vendor/constant_gen/LICENSE.on_output @@ -0,0 +1 @@ +The generated output from constant_gen has no license encumberances. diff --git a/examples/vendor/constant_gen/constant_generator.py b/examples/vendor/constant_gen/constant_generator.py new file mode 100644 index 0000000..6bd92b2 --- /dev/null +++ b/examples/vendor/constant_gen/constant_generator.py @@ -0,0 +1,33 @@ +# Copyright 2020 Google LLC +# +# 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 +# +# https://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. + +# Lint as: python3 +"""A trivial tool to turn a string into a C++ constant. + +This is not meant to be useful. It is only to provide an example of a tool that +generates code. +""" + +import sys + + +def main(argv): + if len(argv) != 4: + raise Exception('usage: constant_generator out_file var_name text') + with open(argv[1], 'w') as out: + out.write('const char* %s = "%s";\n' % (argv[2], argv[3])) + + +if __name__ == '__main__': + main(sys.argv) diff --git a/examples/vendor/constant_gen/defs.bzl b/examples/vendor/constant_gen/defs.bzl new file mode 100644 index 0000000..f979664 --- /dev/null +++ b/examples/vendor/constant_gen/defs.bzl @@ -0,0 +1,59 @@ +"""A trivial rule to turn a string into a C++ constant.""" + +# Copyright 2020 Google LLC +# +# 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 +# +# https://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. + +def _constant_gen_impl(ctx): + # Turn text into a C++ constant. + outputs = [ctx.outputs.src_out] + ctx.actions.run( + mnemonic = "GenerateConstant", + progress_message = "Generating %s" % ctx.attr.var, + outputs = outputs, + executable = ctx.executable._generator, + arguments = [ctx.outputs.src_out.path, ctx.attr.var, ctx.attr.text], + ) + return [DefaultInfo(files = depset(outputs))] + +_constant_gen = rule( + implementation = _constant_gen_impl, + attrs = { + "src_out": attr.output(mandatory = True), + "text": attr.string(mandatory = True), + "var": attr.string(mandatory = False), + "_generator": attr.label( + default = Label("@rules_license//examples/vendor/constant_gen:constant_generator"), + executable = True, + allow_files = True, + cfg = "host", + ), + }, +) + +def constant_gen(name, text, var): + # Generate the code + _constant_gen( + name = name + "_src_", + src_out = name + "_src_.cc", + text = text, + var = var, + applicable_licenses = ["@rules_license//examples/vendor/constant_gen:license_for_emitted_code"], + ) + + # And turn it into a library we can link against + native.cc_library( + name = name, + srcs = [name + "_src_"], + applicable_licenses = ["@rules_license//examples/vendor/constant_gen:license_for_emitted_code"], + ) diff --git a/examples/vendor/constant_gen/generated_code_licenses.golden b/examples/vendor/constant_gen/generated_code_licenses.golden new file mode 100644 index 0000000..a37723a --- /dev/null +++ b/examples/vendor/constant_gen/generated_code_licenses.golden @@ -0,0 +1,15 @@ +[ + { + "rule": "//examples/vendor/constant_gen:license_for_emitted_code", + "license_kinds": [ + { + "target": "@//examples/my_org/licenses:unencumbered", + "name": "unencumbered", + "conditions": [] + } + ], + "copyright_notice": "", + "package_name": "Trivial Code Generator Output", + "license_text": "examples/vendor/constant_gen/LICENSE" + } +] diff --git a/examples/vendor/constant_gen/generator_licenses.golden b/examples/vendor/constant_gen/generator_licenses.golden new file mode 100644 index 0000000..164b00b --- /dev/null +++ b/examples/vendor/constant_gen/generator_licenses.golden @@ -0,0 +1,15 @@ +[ + { + "rule": "//examples/vendor/constant_gen:license", + "license_kinds": [ + { + "target": "@//examples/my_org/licenses:generic_restricted", + "name": "generic_restricted", + "conditions": ["restricted"] + } + ], + "copyright_notice": "", + "package_name": "Trivial Code Generator", + "license_text": "examples/vendor/constant_gen/LICENSE" + } +] diff --git a/examples/vendor/libhhgttg/BUILD b/examples/vendor/libhhgttg/BUILD new file mode 100644 index 0000000..c5da389 --- /dev/null +++ b/examples/vendor/libhhgttg/BUILD @@ -0,0 +1,25 @@ +# A package with all code under a single license. This is the most common case +# we expect to see. + +load("@rules_license//rules:license.bzl", "license") + +# Using a package wide default ensure that all targets are associated with the +# license. +package( + default_applicable_licenses = [":license"], + default_visibility = ["//visibility:public"], +) + +# The default license for an entire package is typically named "license". +license( + name = "license", + license_kinds = [ + "@rules_license//examples/my_org/licenses:generic_notice", + ], + license_text = "LICENSE", +) + +cc_library( + name = "libhhgttg", + srcs = ["answer.cc"], +) diff --git a/examples/vendor/libhhgttg/LICENSE b/examples/vendor/libhhgttg/LICENSE new file mode 100644 index 0000000..660e329 --- /dev/null +++ b/examples/vendor/libhhgttg/LICENSE @@ -0,0 +1,2 @@ +You can do whatever you want with this software. Just incude this license +with your distribution. diff --git a/examples/vendor/libhhgttg/answer.cc b/examples/vendor/libhhgttg/answer.cc new file mode 100644 index 0000000..8b78f90 --- /dev/null +++ b/examples/vendor/libhhgttg/answer.cc @@ -0,0 +1,15 @@ +// Copyright 2020 Google LLC +// +// 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 +// +// https://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. + +int answer = 42; |