Repository: salesforce/rules_spring Branch: main Commit: d774f923d79f Files: 311 Total size: 1.4 MB Directory structure: gitextract_43sa_2ka/ ├── .aspect/ │ └── bazelrc/ │ ├── README.md │ ├── automatic_updates.md │ ├── bazel6.bazelrc │ ├── bazel7.bazelrc │ ├── bazel8.bazelrc │ ├── ci.bazelrc │ ├── convenience.bazelrc │ ├── correctness.bazelrc │ ├── debug.bazelrc │ ├── intro.md │ ├── java.bazelrc │ ├── javascript.bazelrc │ ├── performance.bazelrc │ └── usage.md ├── .bazelrc ├── .bazelversion ├── .gitignore ├── BUILD ├── CODEOWNERS ├── CODE_OF_CONDUCT.md ├── LICENSE.txt ├── MODULE.bazel ├── README.md ├── REPO.bazel ├── SECURITY.md ├── examples/ │ ├── README.md │ ├── demoapp/ │ │ ├── BUILD │ │ ├── README.md │ │ ├── application-dev.properties │ │ ├── application.properties │ │ ├── author.txt │ │ ├── config/ │ │ │ └── application.properties │ │ ├── custom_bazelrun_script.sh │ │ ├── demoapp_classpath.idx │ │ ├── demoapp_dupeclass_allowlist.txt │ │ ├── example_data.txt │ │ ├── generate-build-info.bzl │ │ ├── generate-build-info.sh │ │ ├── info.txt │ │ ├── libs/ │ │ │ ├── lib1/ │ │ │ │ ├── BUILD │ │ │ │ └── src/ │ │ │ │ ├── main/ │ │ │ │ │ └── java/ │ │ │ │ │ └── com/ │ │ │ │ │ └── bazel/ │ │ │ │ │ └── demo/ │ │ │ │ │ └── IntentionalDupedClass.java │ │ │ │ └── test/ │ │ │ │ └── java/ │ │ │ │ └── com/ │ │ │ │ └── bazel/ │ │ │ │ └── demo/ │ │ │ │ └── IntentionalDupedClassTest.java │ │ │ ├── lib2/ │ │ │ │ ├── BUILD │ │ │ │ └── src/ │ │ │ │ ├── main/ │ │ │ │ │ └── java/ │ │ │ │ │ └── com/ │ │ │ │ │ └── bazel/ │ │ │ │ │ └── demo/ │ │ │ │ │ └── IntentionalDupedClass.java │ │ │ │ └── test/ │ │ │ │ └── java/ │ │ │ │ └── com/ │ │ │ │ └── bazel/ │ │ │ │ └── demo/ │ │ │ │ └── IntentionalDupedClassTest.java │ │ │ └── lib3_neverlink/ │ │ │ ├── BUILD │ │ │ ├── README.md │ │ │ └── src/ │ │ │ ├── main/ │ │ │ │ └── java/ │ │ │ │ └── com/ │ │ │ │ └── bazel/ │ │ │ │ └── demo/ │ │ │ │ └── NeverLinkedClass.java │ │ │ └── test/ │ │ │ └── java/ │ │ │ └── com/ │ │ │ └── bazel/ │ │ │ └── demo/ │ │ │ └── NeverLinkTest.java │ │ ├── remote_debug.sh │ │ ├── src/ │ │ │ ├── main/ │ │ │ │ ├── java/ │ │ │ │ │ └── com/ │ │ │ │ │ └── sample/ │ │ │ │ │ ├── SampleAutoConfiguration.java │ │ │ │ │ ├── SampleMain.java │ │ │ │ │ └── SampleRest.java │ │ │ │ └── resources/ │ │ │ │ ├── META-INF/ │ │ │ │ │ └── spring/ │ │ │ │ │ └── org.springframework.boot.autoconfigure.AutoConfiguration.imports │ │ │ │ └── application.properties │ │ │ └── test/ │ │ │ ├── java/ │ │ │ │ └── com/ │ │ │ │ ├── salesforce/ │ │ │ │ │ └── rules_spring/ │ │ │ │ │ └── PackagingTest.java │ │ │ │ └── sample/ │ │ │ │ ├── SampleRestFuncTest.java │ │ │ │ └── SampleRestUnitTest.java │ │ │ └── resources/ │ │ │ └── test.properties │ │ └── src_root/ │ │ └── main/ │ │ └── java/ │ │ └── com/ │ │ └── sample/ │ │ └── SampleRootClass.java │ ├── helloworld/ │ │ ├── BUILD │ │ ├── README.md │ │ ├── libs/ │ │ │ ├── lib1/ │ │ │ │ ├── BUILD │ │ │ │ └── src/ │ │ │ │ ├── main/ │ │ │ │ │ └── java/ │ │ │ │ │ └── com/ │ │ │ │ │ └── bazel/ │ │ │ │ │ └── demo/ │ │ │ │ │ └── IntentionalDupedClass.java │ │ │ │ └── test/ │ │ │ │ └── java/ │ │ │ │ └── com/ │ │ │ │ └── bazel/ │ │ │ │ └── demo/ │ │ │ │ └── IntentionalDupedClassTest.java │ │ │ └── lib2/ │ │ │ ├── BUILD │ │ │ └── src/ │ │ │ ├── main/ │ │ │ │ └── java/ │ │ │ │ └── com/ │ │ │ │ └── bazel/ │ │ │ │ └── demo/ │ │ │ │ └── IntentionalDupedClass.java │ │ │ └── test/ │ │ │ └── java/ │ │ │ └── com/ │ │ │ └── bazel/ │ │ │ └── demo/ │ │ │ └── IntentionalDupedClassTest.java │ │ ├── remote_debug.sh │ │ └── src/ │ │ ├── main/ │ │ │ ├── java/ │ │ │ │ └── com/ │ │ │ │ └── sample/ │ │ │ │ ├── SampleAutoConfiguration.java │ │ │ │ ├── SampleMain.java │ │ │ │ └── SampleRest.java │ │ │ └── resources/ │ │ │ ├── META-INF/ │ │ │ │ └── spring/ │ │ │ │ └── org.springframework.boot.autoconfigure.AutoConfiguration.imports │ │ │ └── application.properties │ │ └── test/ │ │ ├── java/ │ │ │ └── com/ │ │ │ └── sample/ │ │ │ ├── SampleRestFuncTest.java │ │ │ └── SampleRestUnitTest.java │ │ └── resources/ │ │ └── test.properties │ └── kotlinapp/ │ └── README.md ├── makerelease.sh ├── maven_install.json ├── springboot/ │ ├── BUILD │ ├── README.md │ ├── addin_end.txt │ ├── attributes.md │ ├── bazelrun.md │ ├── check_dupe_classes.py │ ├── cli.md │ ├── default_bazelrun_script.sh │ ├── deps_filter_rules/ │ │ ├── BUILD │ │ ├── README.md │ │ ├── dependencyset.bzl │ │ ├── dependencyset.md │ │ ├── deps_filter.bzl │ │ └── tests/ │ │ ├── README.md │ │ ├── dependencyset/ │ │ │ ├── external_dependencies/ │ │ │ │ └── compile_and_runtime/ │ │ │ │ ├── BUILD │ │ │ │ ├── compile_and_runtime_test.bzl │ │ │ │ └── src/ │ │ │ │ ├── main/ │ │ │ │ │ └── java/ │ │ │ │ │ └── com/ │ │ │ │ │ └── depsfilter/ │ │ │ │ │ └── A.java │ │ │ │ └── test/ │ │ │ │ └── java/ │ │ │ │ └── com/ │ │ │ │ └── depsfilter/ │ │ │ │ ├── DepsFilterCaseSensitivePatternMatchingTest.java │ │ │ │ ├── DepsFilterCompileDepsOnlyTest.java │ │ │ │ ├── DepsFilterEmptyExclusionsTest.java │ │ │ │ ├── DepsFilterExcludeTransitiveTest.java │ │ │ │ ├── DepsFilterLabelExclusionsTest.java │ │ │ │ ├── DepsFilterMultipleExclusionsWithTransitivesTest.java │ │ │ │ ├── DepsFilterMultipleExclusionsWithoutTransitivesTest.java │ │ │ │ ├── DepsFilterNoFilteringTest.java │ │ │ │ ├── DepsFilterOneCompileOneRuntimeDepTest.java │ │ │ │ ├── DepsFilterPathBasedExclusionsComprehensiveTest.java │ │ │ │ ├── DepsFilterPathExclusionsTest.java │ │ │ │ ├── DepsFilterPathExclusionsWithTransitivesTest.java │ │ │ │ ├── DepsFilterPathPatternsWithSpecialCharactersTest.java │ │ │ │ ├── DepsFilterRuntimeDepsOnlyTest.java │ │ │ │ ├── DepsFilterSingleDepWithExclusionsTest.java │ │ │ │ └── DepsFilterSingleRuntimeDepWithExclusionsTest.java │ │ │ └── internal_dependencies/ │ │ │ ├── compile_and_runtime_1/ │ │ │ │ ├── BUILD │ │ │ │ ├── compile_and_runtime_test.bzl │ │ │ │ └── src/ │ │ │ │ └── main/ │ │ │ │ └── java/ │ │ │ │ └── com/ │ │ │ │ └── depsfilter/ │ │ │ │ ├── A.java │ │ │ │ ├── B.java │ │ │ │ ├── C.java │ │ │ │ ├── D.java │ │ │ │ ├── E.java │ │ │ │ ├── F.java │ │ │ │ ├── G.java │ │ │ │ ├── H.java │ │ │ │ └── I.java │ │ │ ├── compile_and_runtime_2/ │ │ │ │ ├── BUILD │ │ │ │ ├── compile_and_runtime_test.bzl │ │ │ │ └── src/ │ │ │ │ ├── main/ │ │ │ │ │ └── java/ │ │ │ │ │ └── com/ │ │ │ │ │ └── depsfilter/ │ │ │ │ │ ├── A.java │ │ │ │ │ ├── B.java │ │ │ │ │ ├── C.java │ │ │ │ │ ├── D.java │ │ │ │ │ ├── E.java │ │ │ │ │ ├── F.java │ │ │ │ │ ├── G.java │ │ │ │ │ ├── H.java │ │ │ │ │ ├── I.java │ │ │ │ │ └── J.java │ │ │ │ └── test/ │ │ │ │ └── java/ │ │ │ │ └── com/ │ │ │ │ └── depsfilter/ │ │ │ │ ├── DepsFilterEmptyExclusionsTest.java │ │ │ │ ├── DepsFilterExcludeTransitiveTest.java │ │ │ │ ├── DepsFilterFilteredDepsTest.java │ │ │ │ ├── DepsFilterInterfaceImplementationTest.java │ │ │ │ ├── DepsFilterMultipleExclusionsWithTransitiveTest.java │ │ │ │ ├── DepsFilterMultipleExclusionsWithoutTransitiveTest.java │ │ │ │ ├── DepsFilterMultiplePathsTest.java │ │ │ │ ├── DepsFilterPathBasedExclusionsTest.java │ │ │ │ └── DepsFilterTestHelper.java │ │ │ ├── compile_time_only/ │ │ │ │ ├── BUILD │ │ │ │ ├── compile_time_only_test.bzl │ │ │ │ └── src/ │ │ │ │ └── main/ │ │ │ │ └── java/ │ │ │ │ └── com/ │ │ │ │ └── depsfilter/ │ │ │ │ ├── A.java │ │ │ │ ├── B.java │ │ │ │ ├── C.java │ │ │ │ ├── D.java │ │ │ │ ├── E.java │ │ │ │ ├── F.java │ │ │ │ ├── G.java │ │ │ │ ├── H.java │ │ │ │ └── I.java │ │ │ └── runtime_only/ │ │ │ ├── BUILD │ │ │ ├── runtime_only_test.bzl │ │ │ └── src/ │ │ │ └── main/ │ │ │ └── java/ │ │ │ └── com/ │ │ │ └── depsfilter/ │ │ │ ├── A.java │ │ │ ├── B.java │ │ │ ├── C.java │ │ │ ├── D.java │ │ │ ├── E.java │ │ │ ├── F.java │ │ │ ├── G.java │ │ │ ├── H.java │ │ │ └── I.java │ │ ├── depsfilter/ │ │ │ ├── external_dependencies/ │ │ │ │ ├── compile_and_runtime/ │ │ │ │ │ ├── BUILD │ │ │ │ │ ├── compile_and_runtime_test.bzl │ │ │ │ │ └── src/ │ │ │ │ │ └── test/ │ │ │ │ │ └── java/ │ │ │ │ │ └── com/ │ │ │ │ │ └── depsfilter/ │ │ │ │ │ ├── DepsFilterCaseSensitivePatternMatchingTest.java │ │ │ │ │ ├── DepsFilterCompileDepsOnlyTest.java │ │ │ │ │ ├── DepsFilterEmptyExclusionsTest.java │ │ │ │ │ ├── DepsFilterExcludeTransitiveTest.java │ │ │ │ │ ├── DepsFilterLabelExclusionsTest.java │ │ │ │ │ ├── DepsFilterMultipleExclusionsWithTransitivesTest.java │ │ │ │ │ ├── DepsFilterMultipleExclusionsWithoutTransitivesTest.java │ │ │ │ │ ├── DepsFilterNoFilteringTest.java │ │ │ │ │ ├── DepsFilterOneCompileOneRuntimeDepTest.java │ │ │ │ │ ├── DepsFilterPathBasedExclusionsComprehensiveTest.java │ │ │ │ │ ├── DepsFilterPathExclusionsTest.java │ │ │ │ │ ├── DepsFilterPathExclusionsWithTransitivesTest.java │ │ │ │ │ ├── DepsFilterPathPatternsWithSpecialCharactersTest.java │ │ │ │ │ ├── DepsFilterRuntimeDepsOnlyTest.java │ │ │ │ │ ├── DepsFilterSingleDepWithExclusionsTest.java │ │ │ │ │ └── DepsFilterSingleRuntimeDepWithExclusionsTest.java │ │ │ │ └── compile_and_runtime_through_java_library/ │ │ │ │ ├── BUILD │ │ │ │ ├── compile_and_runtime_test.bzl │ │ │ │ └── src/ │ │ │ │ ├── main/ │ │ │ │ │ └── java/ │ │ │ │ │ └── com/ │ │ │ │ │ └── depsfilter/ │ │ │ │ │ └── A.java │ │ │ │ └── test/ │ │ │ │ └── java/ │ │ │ │ └── com/ │ │ │ │ └── depsfilter/ │ │ │ │ ├── DepsFilterCaseSensitivePatternMatchingTest.java │ │ │ │ ├── DepsFilterCompileDepsOnlyTest.java │ │ │ │ ├── DepsFilterEmptyExclusionsTest.java │ │ │ │ ├── DepsFilterExcludeTransitiveTest.java │ │ │ │ ├── DepsFilterLabelExclusionsTest.java │ │ │ │ ├── DepsFilterMultipleExclusionsWithTransitivesTest.java │ │ │ │ ├── DepsFilterMultipleExclusionsWithoutTransitivesTest.java │ │ │ │ ├── DepsFilterNoFilteringTest.java │ │ │ │ ├── DepsFilterOneCompileOneRuntimeDepTest.java │ │ │ │ ├── DepsFilterPathBasedExclusionsComprehensiveTest.java │ │ │ │ ├── DepsFilterPathExclusionsTest.java │ │ │ │ ├── DepsFilterPathExclusionsWithTransitivesTest.java │ │ │ │ ├── DepsFilterPathPatternsWithSpecialCharactersTest.java │ │ │ │ ├── DepsFilterRuntimeDepsOnlyATest.java │ │ │ │ ├── DepsFilterRuntimeDepsOnlyBTest.java │ │ │ │ ├── DepsFilterSingleDepWithExclusionsTest.java │ │ │ │ ├── DepsFilterSingleRuntimeDepWithExclusionsATest.java │ │ │ │ └── DepsFilterSingleRuntimeDepWithExclusionsBTest.java │ │ │ └── internal_dependencies/ │ │ │ ├── compile_and_runtime_1/ │ │ │ │ ├── BUILD │ │ │ │ ├── compile_and_runtime_test.bzl │ │ │ │ └── src/ │ │ │ │ └── main/ │ │ │ │ └── java/ │ │ │ │ └── com/ │ │ │ │ └── depsfilter/ │ │ │ │ ├── A.java │ │ │ │ ├── B.java │ │ │ │ ├── C.java │ │ │ │ ├── D.java │ │ │ │ ├── E.java │ │ │ │ ├── F.java │ │ │ │ ├── G.java │ │ │ │ └── H.java │ │ │ ├── compile_and_runtime_2/ │ │ │ │ ├── BUILD │ │ │ │ ├── compile_and_runtime_test.bzl │ │ │ │ └── src/ │ │ │ │ ├── main/ │ │ │ │ │ └── java/ │ │ │ │ │ └── com/ │ │ │ │ │ └── depsfilter/ │ │ │ │ │ ├── A.java │ │ │ │ │ ├── B.java │ │ │ │ │ ├── C.java │ │ │ │ │ ├── D.java │ │ │ │ │ ├── E.java │ │ │ │ │ ├── F.java │ │ │ │ │ ├── G.java │ │ │ │ │ ├── H.java │ │ │ │ │ ├── I.java │ │ │ │ │ └── J.java │ │ │ │ └── test/ │ │ │ │ └── java/ │ │ │ │ └── com/ │ │ │ │ └── depsfilter/ │ │ │ │ ├── DepsFilterEmptyExclusionsTest.java │ │ │ │ ├── DepsFilterExcludeTransitiveTest.java │ │ │ │ ├── DepsFilterFilteredDepsTest.java │ │ │ │ ├── DepsFilterInterfaceImplementationTest.java │ │ │ │ ├── DepsFilterMultipleExclusionsWithTransitiveTest.java │ │ │ │ ├── DepsFilterMultipleExclusionsWithoutTransitiveTest.java │ │ │ │ ├── DepsFilterMultiplePathsTest.java │ │ │ │ ├── DepsFilterPathBasedExclusionsTest.java │ │ │ │ └── DepsFilterTestHelper.java │ │ │ ├── compile_time_only/ │ │ │ │ ├── BUILD │ │ │ │ ├── compile_time_only_test.bzl │ │ │ │ └── src/ │ │ │ │ └── main/ │ │ │ │ └── java/ │ │ │ │ └── com/ │ │ │ │ └── depsfilter/ │ │ │ │ ├── A.java │ │ │ │ ├── B.java │ │ │ │ ├── C.java │ │ │ │ ├── D.java │ │ │ │ ├── E.java │ │ │ │ ├── F.java │ │ │ │ ├── G.java │ │ │ │ └── H.java │ │ │ └── runtime_only/ │ │ │ ├── BUILD │ │ │ ├── runtime_only_test.bzl │ │ │ └── src/ │ │ │ └── main/ │ │ │ └── java/ │ │ │ └── com/ │ │ │ └── depsfilter/ │ │ │ ├── A.java │ │ │ ├── B.java │ │ │ ├── C.java │ │ │ ├── D.java │ │ │ ├── E.java │ │ │ ├── F.java │ │ │ ├── G.java │ │ │ └── H.java │ │ ├── external_dependencies_testing.md │ │ ├── external_deps/ │ │ │ ├── BUILD │ │ │ └── unmanaged_deps_filter_install.json │ │ ├── internal_dependencies_testing.md │ │ └── test_utils/ │ │ ├── BUILD │ │ ├── dependency_graph.txt │ │ ├── src/ │ │ │ └── test/ │ │ │ └── java/ │ │ │ └── com/ │ │ │ └── depsfilter/ │ │ │ ├── DependencyGraphAnalyzer.java │ │ │ ├── DependencyGraphTestConfig.java │ │ │ └── DepsFilterTestHelper.java │ │ └── verification_utils.bzl │ ├── deps_filter_rules_legacy/ │ │ ├── BUILD │ │ ├── README.md │ │ ├── deps_filter.bzl │ │ ├── deps_filter.md │ │ ├── deps_filter_disable_transitives.bzl │ │ ├── deps_filter_disable_transitives.md │ │ └── src/ │ │ └── test/ │ │ └── java/ │ │ └── com/ │ │ └── depsfilter/ │ │ ├── DepsFilterWithTransitivesExclusionTest.java │ │ ├── DepsFilterWithoutTransitivesExclusionTest.java │ │ ├── TransitiveDepsFilterCaseA.java │ │ ├── TransitiveDepsFilterCaseB.java │ │ ├── TransitiveDepsFilterCaseC.java │ │ └── TransitiveDepsFilterCaseD.java │ ├── deps_filter_transitive.bzl │ ├── detect_javax_classes.py │ ├── empty.txt │ ├── import_bundles/ │ │ ├── BUILD │ │ └── README.md │ ├── javax.md │ ├── springboot.bzl │ ├── springboot_doc.md │ ├── springboot_pkg.sh │ ├── src/ │ │ ├── main/ │ │ │ └── java/ │ │ │ └── com/ │ │ │ └── salesforce/ │ │ │ └── rulesspring/ │ │ │ ├── cli/ │ │ │ │ └── SpringBootInspector.java │ │ │ └── index/ │ │ │ ├── IndexFileType.java │ │ │ ├── IndexOfFiles.java │ │ │ ├── IndexedFile.java │ │ │ ├── SpringBootIndexReporter.java │ │ │ └── SpringBootJarIndexer.java │ │ └── test/ │ │ └── java/ │ │ └── com/ │ │ └── salesforce/ │ │ └── rulesspring/ │ │ └── index/ │ │ └── SpringBootJarIndexerTest.java │ ├── testing_springboot.md │ ├── tests/ │ │ └── check_dupe_classes_test.py │ ├── unwanted_classes.md │ ├── write_bazelrun_env.sh │ ├── write_gitinfo_properties.sh │ └── write_manifest.sh └── tools/ ├── buildstamp/ │ ├── README.md │ └── get_workspace_status ├── codecoverage/ │ └── coverage-report.sh ├── formatter/ │ ├── README.md │ └── format_bazel_files.sh ├── get_github_stats_downloads.py ├── jar_explode/ │ ├── README.md │ └── jar_explode.sh └── license/ ├── BUILD └── licenses_used.bzl ================================================ FILE CONTENTS ================================================ ================================================ FILE: .aspect/bazelrc/README.md ================================================ ## Aspect bazelrc Presets See: - [Aspect Presets](https://github.com/bazel-contrib/bazel-lib/tree/main/.aspect/bazelrc) ================================================ FILE: .aspect/bazelrc/automatic_updates.md ================================================ ## Automatic updates A convenient way to automatically keep your vendored copy up-to-date is to use the `write_aspect_bazelrc_presets` rule in `.aspect/bazelrc/BUILD.bazel`: ```python title=".aspect/bazelrc/BUILD.bazel" "Aspect bazelrc presets; see https://docs.aspect.build/guides/bazelrc" load("@aspect_bazel_lib//lib:bazelrc_presets.bzl", "write_aspect_bazelrc_presets") write_aspect_bazelrc_presets(name = "update_aspect_bazelrc_presets") ``` When `@aspect_bazel_lib` is upgraded in your `WORKSPACE.bazel` or your `MODULE.bazel` file, a `diff_test` stamped out by `write_aspect_bazelrc_presets` will fail if your vendored copy is out-of-date and print the Bazel command to run to update it. For example, `bazel run //.aspect/bazelrc:update_aspect_bazelrc_presets`. See the [bazelrc](https://github.com/aspect-build/bazel-examples/blob/main/bazelrc/.aspect/bazelrc/BUILD.bazel) example in our [bazel-examples](https://github.com/aspect-build/bazel-examples) repository for a working example. ================================================ FILE: .aspect/bazelrc/bazel6.bazelrc ================================================ # Speed up all builds by not checking if external repository files have been modified. # Docs: https://github.com/bazelbuild/bazel/blob/1af61b21df99edc2fc66939cdf14449c2661f873/src/main/java/com/google/devtools/build/lib/bazel/repository/RepositoryOptions.java#L244 build --noexperimental_check_external_repository_files fetch --noexperimental_check_external_repository_files query --noexperimental_check_external_repository_files # Directories used by sandboxed non-worker execution may be reused to avoid unnecessary setup costs. # Save time on Sandbox creation and deletion when many of the same kind of action run during the # build. # Docs: https://bazel.build/reference/command-line-reference#flag--reuse_sandbox_directories build --reuse_sandbox_directories # Avoid this flag being enabled by remote_download_minimal or remote_download_toplevel # See https://meroton.com/blog/bazel-6-errors-build-without-the-bytes/ build --noexperimental_action_cache_store_output_metadata # Speed up all builds by not checking if output files have been modified. Lets you make changes to # the output tree without triggering a build for local debugging. For example, you can modify # [rules_js](https://github.com/aspect-build/rules_js) 3rd party npm packages in the output tree # when local debugging. # Docs: https://github.com/bazelbuild/bazel/blob/1af61b21df99edc2fc66939cdf14449c2661f873/src/main/java/com/google/devtools/build/lib/pkgcache/PackageOptions.java#L185 # NB: This flag is in bazel6.bazelrc as when used in Bazel 7 is has been observed to break # "build without the bytes" --remote_download_outputs=toplevel. See https://github.com/bazel-contrib/bazel-lib/pull/711 # for more info. build --noexperimental_check_output_files fetch --noexperimental_check_output_files query --noexperimental_check_output_files # Don't apply `--noremote_upload_local_results` and `--noremote_accept_cached` to the disk cache. # If you have both `--noremote_upload_local_results` and `--disk_cache`, then this fixes a bug where # Bazel doesn't write to the local disk cache as it treats as a remote cache. # Docs: https://bazel.build/reference/command-line-reference#flag--incompatible_remote_results_ignore_disk # NB: This flag is in bazel6.bazelrc because it became a no-op in Bazel 7 and has been removed # in Bazel 8. build --incompatible_remote_results_ignore_disk # Propagate tags from a target declaration to the actions' execution requirements. # Ensures that tags applied in your BUILD file, like `tags=["no-remote"]` # get propagated to actions created by the rule. # Without this option, you rely on rules authors to manually check the tags you passed # and apply relevant ones to the actions they create. # See https://github.com/bazelbuild/bazel/issues/8830 for details. # Docs: https://bazel.build/reference/command-line-reference#flag--experimental_allow_tags_propagation build --experimental_allow_tags_propagation fetch --experimental_allow_tags_propagation query --experimental_allow_tags_propagation ================================================ FILE: .aspect/bazelrc/bazel7.bazelrc ================================================ # Speed up all builds by not checking if external repository files have been modified. # Docs: https://github.com/bazelbuild/bazel/blob/1af61b21df99edc2fc66939cdf14449c2661f873/src/main/java/com/google/devtools/build/lib/bazel/repository/RepositoryOptions.java#L244 common --noexperimental_check_external_repository_files # Don't report when the root module's lower bound for a dependency happens to be less than the resolved version. # This is expected and should NOT prompt an engineer to update our lower bound to match. # WARNING: For repository 'aspect_bazel_lib', the root module requires module version aspect_bazel_lib@1.30.2, # but got aspect_bazel_lib@1.31.2 in the resolved dependency graph. common --check_direct_dependencies=off # Directories used by sandboxed non-worker execution may be reused to avoid unnecessary setup costs. # Save time on Sandbox creation and deletion when many of the same kind of action run during the # build. # Docs: https://bazel.build/reference/command-line-reference#flag--reuse_sandbox_directories build --reuse_sandbox_directories ================================================ FILE: .aspect/bazelrc/bazel8.bazelrc ================================================ # No Bazel 8 specific flag presets yet. ================================================ FILE: .aspect/bazelrc/ci.bazelrc ================================================ # Set this flag to enable re-tries of failed tests on CI. # When any test target fails, try one or more times. This applies regardless of whether the "flaky" # tag appears on the target definition. # This is a tradeoff: legitimately failing tests will take longer to report, # but we can paper over flaky tests that pass most of the time. # The alternative is to mark every flaky test with the `flaky = True` attribute, but this requires # the buildcop to make frequent code edits. # Not recommended for local builds so that the flakiness is observed during development and thus # is more likely to get fixed. # Note that when passing after the first attempt, Bazel will give a special "FLAKY" status. # Docs: https://bazel.build/docs/user-manual#flaky-test-attempts test --flaky_test_attempts=2 # Announce all announces command options read from the bazelrc file(s) when starting up at the # beginning of each Bazel invocation. This is very useful on CI to be able to inspect what Bazel rc # settings are being applied on each run. # Docs: https://bazel.build/docs/user-manual#announce-rc build --announce_rc # Add a timestamp to each message generated by Bazel specifying the time at which the message was # displayed. # Docs: https://bazel.build/docs/user-manual#show-timestamps build --show_timestamps # Only show progress every 60 seconds on CI. # We want to find a compromise between printing often enough to show that the build isn't stuck, # but not so often that we produce a long log file that requires a lot of scrolling. # https://bazel.build/reference/command-line-reference#flag--show_progress_rate_limit build --show_progress_rate_limit=60 # Use cursor controls in screen output. # Docs: https://bazel.build/docs/user-manual#curses build --curses=yes # Use colors to highlight output on the screen. Set to `no` if your CI does not display colors. # Docs: https://bazel.build/docs/user-manual#color build --color=yes # The terminal width in columns. Configure this to override the default value based on what your CI system renders. # Docs: https://github.com/bazelbuild/bazel/blob/1af61b21df99edc2fc66939cdf14449c2661f873/src/main/java/com/google/devtools/build/lib/runtime/UiOptions.java#L151 build --terminal_columns=143 ###################################### # Generic remote cache configuration # ###################################### # Only download remote outputs of top level targets to the local machine. # Docs: https://bazel.build/reference/command-line-reference#flag--remote_download_toplevel build --remote_download_toplevel # The maximum amount of time to wait for remote execution and cache calls. # https://bazel.build/reference/command-line-reference#flag--remote_timeout build --remote_timeout=3600 # Upload locally executed action results to the remote cache. # Docs: https://bazel.build/reference/command-line-reference#flag--remote_upload_local_results build --remote_upload_local_results # Fall back to standalone local execution strategy if remote execution fails. If the grpc remote # cache connection fails, it will fail the build, add this so it falls back to the local cache. # Docs: https://bazel.build/reference/command-line-reference#flag--remote_local_fallback build --remote_local_fallback # Fixes builds hanging on CI that get the TCP connection closed without sending RST packets. # Docs: https://bazel.build/reference/command-line-reference#flag--grpc_keepalive_time build --grpc_keepalive_time=30s ================================================ FILE: .aspect/bazelrc/convenience.bazelrc ================================================ # Attempt to build & test every target whose prerequisites were successfully built. # Docs: https://bazel.build/docs/user-manual#keep-going build --keep_going # Output test errors to stderr so users don't have to `cat` or open test failure log files when test # fail. This makes the log noisier in exchange for reducing the time-to-feedback on test failures for # users. # Docs: https://bazel.build/docs/user-manual#test-output test --test_output=errors # Show the output files created by builds that requested more than one target. This helps users # locate the build outputs in more cases # Docs: https://bazel.build/docs/user-manual#show-result build --show_result=20 # Bazel picks up host-OS-specific config lines from bazelrc files. For example, if the host OS is # Linux and you run bazel build, Bazel picks up lines starting with build:linux. Supported OS # identifiers are `linux`, `macos`, `windows`, `freebsd`, and `openbsd`. Enabling this flag is # equivalent to using `--config=linux` on Linux, `--config=windows` on Windows, etc. # Docs: https://bazel.build/reference/command-line-reference#flag--enable_platform_specific_config common --enable_platform_specific_config # Output a heap dump if an OOM is thrown during a Bazel invocation # (including OOMs due to `--experimental_oom_more_eagerly_threshold`). # The dump will be written to `/.heapdump.hprof`. # You may need to configure CI to capture this artifact and upload for later use. # Docs: https://bazel.build/reference/command-line-reference#flag--heap_dump_on_oom common --heap_dump_on_oom ================================================ FILE: .aspect/bazelrc/correctness.bazelrc ================================================ # Do not upload locally executed action results to the remote cache. # This should be the default for local builds so local builds cannot poison the remote cache. # It should be flipped to `--remote_upload_local_results` on CI # by using `--bazelrc=.aspect/bazelrc/ci.bazelrc`. # Docs: https://bazel.build/reference/command-line-reference#flag--remote_upload_local_results build --noremote_upload_local_results # Don't allow network access for build actions in the sandbox. # Ensures that you don't accidentally make non-hermetic actions/tests which depend on remote # services. # Developers should tag targets with `tags=["requires-network"]` to opt-out of the enforcement. # Docs: https://bazel.build/reference/command-line-reference#flag--sandbox_default_allow_network build --sandbox_default_allow_network=false # Warn if a test's timeout is significantly longer than the test's actual execution time. # Bazel's default for test_timeout is medium (5 min), but most tests should instead be short (1 min). # While a test's timeout should be set such that it is not flaky, a test that has a highly # over-generous timeout can hide real problems that crop up unexpectedly. # For instance, a test that normally executes in a minute or two should not have a timeout of # ETERNAL or LONG as these are much, much too generous. # Docs: https://bazel.build/docs/user-manual#test-verbose-timeout-warnings test --test_verbose_timeout_warnings # Allow the Bazel server to check directory sources for changes. Ensures that the Bazel server # notices when a directory changes, if you have a directory listed in the srcs of some target. # Recommended when using # [copy_directory](https://github.com/bazel-contrib/bazel-lib/blob/main/docs/copy_directory.md) and # [rules_js](https://github.com/aspect-build/rules_js) since npm package are source directories # inputs to copy_directory actions. # Docs: https://bazel.build/reference/command-line-reference#flag--host_jvm_args startup --host_jvm_args=-DBAZEL_TRACK_SOURCE_DIRECTORIES=1 # Allow exclusive tests to run in the sandbox. Fixes a bug where Bazel doesn't enable sandboxing for # tests with `tags=["exclusive"]`. # Docs: https://bazel.build/reference/command-line-reference#flag--incompatible_exclusive_test_sandboxed test --incompatible_exclusive_test_sandboxed # Use a static value for `PATH` and does not inherit `LD_LIBRARY_PATH`. Doesn't let environment # variables like `PATH` sneak into the build, which can cause massive cache misses when they change. # Use `--action_env=ENV_VARIABLE` if you want to inherit specific environment variables from the # client, but note that doing so can prevent cross-user caching if a shared cache is used. # Docs: https://bazel.build/reference/command-line-reference#flag--incompatible_strict_action_env build --incompatible_strict_action_env # Do not automatically create `__init__.py` files in the runfiles of Python targets. Fixes the wrong # default that comes from Google's internal monorepo by using `__init__.py` to delimit a Python # package. Precisely, when a `py_binary` or `py_test` target has `legacy_create_init` set to `auto (the # default), it is treated as false if and only if this flag is set. See # https://github.com/bazelbuild/bazel/issues/10076. # Docs: https://bazel.build/reference/command-line-reference#flag--incompatible_default_to_explicit_init_py build --incompatible_default_to_explicit_init_py # Set default value of `allow_empty` to `False` in `glob()`. This prevents a common mistake when # attempting to use `glob()` to match files in a subdirectory that is opaque to the current package # because it contains a BUILD file. See https://github.com/bazelbuild/bazel/issues/8195. # Docs: https://bazel.build/reference/command-line-reference#flag--incompatible_disallow_empty_glob common --incompatible_disallow_empty_glob # Always download coverage files for tests from the remote cache. By default, coverage files are not # downloaded on test result cache hits when --remote_download_minimal is enabled, making it impossible # to generate a full coverage report. # Docs: https://bazel.build/reference/command-line-reference#flag--experimental_fetch_all_coverage_outputs # detching remote cache results test --experimental_fetch_all_coverage_outputs ================================================ FILE: .aspect/bazelrc/debug.bazelrc ================================================ ############################################################ # Use `bazel test --config=debug` to enable these settings # ############################################################ # Stream stdout/stderr output from each test in real-time. # Docs: https://bazel.build/docs/user-manual#test-output test:debug --test_output=streamed # Run one test at a time. # Docs: https://bazel.build/reference/command-line-reference#flag--test_strategy test:debug --test_strategy=exclusive # Prevent long running tests from timing out. # Docs: https://bazel.build/docs/user-manual#test-timeout test:debug --test_timeout=9999 # Always run tests even if they have cached results. # Docs: https://bazel.build/docs/user-manual#cache-test-results test:debug --nocache_test_results ================================================ FILE: .aspect/bazelrc/intro.md ================================================ # Aspect bazelrc presets The `.bazelrc` files found here are the source-of-truth for our recommended Bazel presets. They are mirrored on our docsite at https://docs.aspect.build/guides/bazelrc. ================================================ FILE: .aspect/bazelrc/java.bazelrc ================================================ # Aspect recommended Bazel flags when using rules_java and rules_jvm_external # Pin java versions to desired language level # See https://bazel.build/docs/bazel-and-java#java-versions # and https://en.wikipedia.org/wiki/Java_version_history # What version of Java are the source files in this repo? # See https://bazel.build/docs/user-manual#java-language-version common --java_language_version=17 # The Java language version used to build tools that are executed during a build # See https://bazel.build/docs/user-manual#tool-java-language-version common --tool_java_language_version=17 # The version of JVM to use to execute the code and run the tests. # NB: The default value is local_jdk which is non-hermetic. # See https://bazel.build/docs/user-manual#java-runtime-version common --java_runtime_version=remotejdk_17 # The version of JVM used to execute tools that are needed during a build. # See https://bazel.build/docs/user-manual#tool-java-runtime-version common --tool_java_runtime_version=remotejdk_17 # Repository rules, such as rules_jvm_external: put Bazel's JDK on the path. # Avoids non-hermeticity from dependency on a JAVA_HOME pointing at a system JDK # see https://github.com/bazelbuild/rules_jvm_external/issues/445 common --repo_env=JAVA_HOME=../bazel_tools/jdk ================================================ FILE: .aspect/bazelrc/javascript.bazelrc ================================================ # Aspect recommended Bazel flags when using Aspect's JavaScript rules: https://github.com/aspect-build/rules_js # Docs for Node.js flags: https://nodejs.org/en/docs/guides/debugging-getting-started/#command-line-options # Support for debugging Node.js tests. Use bazel run with `--config=debug` to turn on the NodeJS # inspector agent. The node process will break before user code starts and wait for the debugger to # connect. Pass the --inspect-brk option to all tests which enables the node inspector agent. See # https://nodejs.org/de/docs/guides/debugging-getting-started/#command-line-options for more # details. # Docs: https://nodejs.org/en/docs/guides/debugging-getting-started/#command-line-options run:debug -- --node_options=--inspect-brk test:debug --test_env=NODE_OPTIONS=--inspect-brk ================================================ FILE: .aspect/bazelrc/performance.bazelrc ================================================ # Directories used by sandboxed non-worker execution may be reused to avoid unnecessary setup costs. # Save time on Sandbox creation and deletion when many of the same kind of action run during the # build. # No longer experimental in Bazel 6: https://github.com/bazelbuild/bazel/commit/c1a95501a5611878e5cc43a3cc531f2b9e47835b # Docs: https://bazel.build/reference/command-line-reference#flag--reuse_sandbox_directories build --experimental_reuse_sandbox_directories # Do not build runfiles symlink forests for external repositories under # `.runfiles/wsname/external/repo` (in addition to `.runfiles/repo`). This reduces runfiles & # sandbox creation times & prevents accidentally depending on this feature which may flip to off by # default in the future. Note, some rules may fail under this flag, please file issues with the rule # author. # Docs: https://bazel.build/reference/command-line-reference#flag--legacy_external_runfiles build --nolegacy_external_runfiles # Avoid creating a runfiles tree for binaries or tests until it is needed. # Docs: https://bazel.build/reference/command-line-reference#flag--build_runfile_links # See https://github.com/bazelbuild/bazel/issues/6627 # # This may break local workflows that `build` a binary target, then run the resulting program # outside of `bazel run`. In those cases, the script will need to call # `bazel build --build_runfile_links //my/binary:target` and then execute the resulting program. build --nobuild_runfile_links # Needed prior to Bazel 8; see # https://github.com/bazelbuild/bazel/issues/20577 coverage --build_runfile_links ================================================ FILE: .aspect/bazelrc/usage.md ================================================ ## Using Aspect bazelrc presets in your project The `.bazelrc` file can get large, fast. Some settings don't apply everywhere - some options are appropriate only on CI, and some vary depending on the version of Bazel you use or languages used. Bazel rc files can contain `import` statements, which allow you to organize the content better. To use these presets in your project, simply vendor the `*.bazelrc` files from https://github.com/bazel-contrib/bazel-lib/tree/main/.aspect/bazelrc into the `.aspect/bazelrc` folder in your repository and `import` them in your `.bazelrc` file. For example, ```python title=".bazelrc" # Import Aspect bazelrc presets import %workspace%/.aspect/bazelrc/bazel6.bazelrc import %workspace%/.aspect/bazelrc/convenience.bazelrc import %workspace%/.aspect/bazelrc/correctness.bazelrc import %workspace%/.aspect/bazelrc/debug.bazelrc import %workspace%/.aspect/bazelrc/javascript.bazelrc import %workspace%/.aspect/bazelrc/performance.bazelrc ### YOUR PROJECT SPECIFIC OPTIONS GO HERE ### # Load any settings & overrides specific to the current user from `.aspect/bazelrc/user.bazelrc`. # This file should appear in `.gitignore` so that settings are not shared with team members. This # should be last statement in this config so the user configuration is able to overwrite flags from # this file. See https://bazel.build/configure/best-practices#bazelrc-file. try-import %workspace%/.aspect/bazelrc/user.bazelrc ``` ================================================ FILE: .bazelrc ================================================ # # Copyright (c) 2017-2024, salesforce.com, inc. # All rights reserved. # Licensed under the BSD 3-Clause license. # For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause # # ********************************** # ASPECT PRESETS # https://github.com/bazel-contrib/bazel-lib/tree/main/.aspect/bazelrc # ********************************** import %workspace%/.aspect/bazelrc/bazel7.bazelrc import %workspace%/.aspect/bazelrc/convenience.bazelrc import %workspace%/.aspect/bazelrc/correctness.bazelrc # ********************************** # BZLMOD # ********************************** common --enable_bzlmod # ********************************** # ARTIFACT STAMPING # ********************************** # These settings ensure Spring Boot artifacts are built with stamped version info. # The Spring Boot rule uses the stamping information to populate the /manage/info endpoint # refer to our tools/buildstamp/README.md for more details build --stamp build --workspace_status_command tools/buildstamp/get_workspace_status # ********************************** # JAVA COMPILATION # ********************************** # Currently, only the exmaples use Java, so these settings are limited to the examples. # Spring Boot 3 requires JDK17 # Compile and Test/Run JDKs common --java_language_version=17 # used for compilation (version for compiling java sources) common --java_runtime_version=17 # used for execution & testing java binaries # Tools - the jdk used for running tools that get executed during the build common --tool_java_language_version=17 common --tool_java_runtime_version=17 ================================================ FILE: .bazelversion ================================================ 7.4.1 ================================================ FILE: .gitignore ================================================ # # Copyright (c) 2017-2021, salesforce.com, inc. # All rights reserved. # Licensed under the BSD 3-Clause license. # For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause # # bazel build dirs bazel-* # set your user to your public GitHub user in a script like this: # git config --global user.email '#####+username@users.noreply.github.com' # but dont check it in setGitOSSUser.sh # python __pycache__ # //tools/python_interpreter captive_python3 bin # after running the //tools/codecoverage tooling you will be left with this root level folder # it contains your test results, so do not checkin coverage-reports # release zips rules-spring-*.zip .vscode .ijwb .idea ================================================ FILE: BUILD ================================================ # # Copyright (c) 2017-2024, salesforce.com, inc. # All rights reserved. # Licensed under the BSD 3-Clause license. # For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause # load("@rules_license//rules:license.bzl", "license") exports_files([ "LICENSE.txt", ]) # Using a package wide default ensure that all targets are associated with the # license. package( default_applicable_licenses = [":license"], default_visibility = ["//visibility:public"], ) license( name = "license", copyright_notice = "Copyright (c) 2017-2024, Salesforce", license_kinds = [ "@rules_license//licenses/spdx:Apache-2.0", ], license_text = "//:LICENSE.txt", package_name = "@rules_spring", package_url = "https://github.com/salesforce/rules_spring", package_version = "2.4.2", visibility = ["//visibility:public"], ) ================================================ FILE: CODEOWNERS ================================================ # Comment line immediately above ownership line is reserved for related gus information. Please be careful while editing. #ECCN:Open Source ================================================ FILE: CODE_OF_CONDUCT.md ================================================ # Salesforce Open Source Community Code of Conduct ## About the Code of Conduct Equality is a core value at Salesforce. We believe a diverse and inclusive community fosters innovation and creativity, and are committed to building a culture where everyone feels included. Salesforce open-source projects are committed to providing a friendly, safe, and welcoming environment for all, regardless of gender identity and expression, sexual orientation, disability, physical appearance, body size, ethnicity, nationality, race, age, religion, level of experience, education, socioeconomic status, or other similar personal characteristics. The goal of this code of conduct is to specify a baseline standard of behavior so that people with different social values and communication styles can work together effectively, productively, and respectfully in our open source community. It also establishes a mechanism for reporting issues and resolving conflicts. All questions and reports of abusive, harassing, or otherwise unacceptable behavior in a Salesforce open-source project may be reported by contacting the Salesforce Open Source Conduct Committee at ossconduct@salesforce.com. ## Our Pledge In the interest of fostering an open and welcoming environment, we as contributors and maintainers pledge to making participation in our project and our community a harassment-free experience for everyone, regardless of gender identity and expression, sexual orientation, disability, physical appearance, body size, ethnicity, nationality, race, age, religion, level of experience, education, socioeconomic status, or other similar personal characteristics. ## Our Standards Examples of behavior that contributes to creating a positive environment include: * Using welcoming and inclusive language * Being respectful of differing viewpoints and experiences * Gracefully accepting constructive criticism * Focusing on what is best for the community * Showing empathy toward other community members Examples of unacceptable behavior by participants include: * The use of sexualized language or imagery and unwelcome sexual attention or advances * Personal attacks, insulting/derogatory comments, or trolling * Public or private harassment * Publishing, or threatening to publish, others' private information—such as a physical or electronic address—without explicit permission * Other conduct which could reasonably be considered inappropriate in a professional setting * Advocating for or encouraging any of the above behaviors ## Our Responsibilities Project maintainers are responsible for clarifying the standards of acceptable behavior and are expected to take appropriate and fair corrective action in response to any instances of unacceptable behavior. Project maintainers have the right and responsibility to remove, edit, or reject comments, commits, code, wiki edits, issues, and other contributions that are not aligned with this Code of Conduct, or to ban temporarily or permanently any contributor for other behaviors that they deem inappropriate, threatening, offensive, or harmful. ## Scope This Code of Conduct applies both within project spaces and in public spaces when an individual is representing the project or its community. Examples of representing a project or community include using an official project email address, posting via an official social media account, or acting as an appointed representative at an online or offline event. Representation of a project may be further defined and clarified by project maintainers. ## Enforcement Instances of abusive, harassing, or otherwise unacceptable behavior may be reported by contacting the Salesforce Open Source Conduct Committee at ossconduct@salesforce.com. All complaints will be reviewed and investigated and will result in a response that is deemed necessary and appropriate to the circumstances. The committee is obligated to maintain confidentiality with regard to the reporter of an incident. Further details of specific enforcement policies may be posted separately. Project maintainers who do not follow or enforce the Code of Conduct in good faith may face temporary or permanent repercussions as determined by other members of the project's leadership and the Salesforce Open Source Conduct Committee. ## Attribution This Code of Conduct is adapted from the [Contributor Covenant][contributor-covenant-home], version 1.4, available at https://www.contributor-covenant.org/version/1/4/code-of-conduct.html. It includes adaptions and additions from [Go Community Code of Conduct][golang-coc], [CNCF Code of Conduct][cncf-coc], and [Microsoft Open Source Code of Conduct][microsoft-coc]. This Code of Conduct is licensed under the [Creative Commons Attribution 3.0 License][cc-by-3-us]. [contributor-covenant-home]: https://www.contributor-covenant.org (https://www.contributor-covenant.org/) [golang-coc]: https://golang.org/conduct [cncf-coc]: https://github.com/cncf/foundation/blob/master/code-of-conduct.md [microsoft-coc]: https://opensource.microsoft.com/codeofconduct/ [cc-by-3-us]: https://creativecommons.org/licenses/by/3.0/us/ ================================================ FILE: LICENSE.txt ================================================ Copyright (c) 2017-2024, Salesforce 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. ================================================ FILE: MODULE.bazel ================================================ module( name = "rules_spring", version = "2.6.3", compatibility_level = 2, repo_name = "rules_spring", ) # Python for dupe class checking support bazel_dep(name = "rules_python", version = "0.40.0") # For License support bazel_dep(name = "rules_license", version = "1.0.0") # For unittest toolchain bazel_dep(name = "bazel_skylib", version = "1.1.1") # DEV DEPENDENCIES # Maven dependencies for the examples bazel_dep(name = "rules_jvm_external", version = "6.6", dev_dependency = True) maven = use_extension("@rules_jvm_external//:extensions.bzl", "maven", dev_dependency = True) maven.install( artifacts = [ "org.slf4j:slf4j-api:2.0.17", "org.springframework.boot:spring-boot:3.4.4", "org.springframework.boot:spring-boot-actuator:3.4.4", "org.springframework.boot:spring-boot-actuator-autoconfigure:3.4.4", "org.springframework.boot:spring-boot-autoconfigure:3.4.4", "org.springframework.boot:spring-boot-configuration-processor:3.4.4", "org.springframework.boot:spring-boot-loader:3.4.4", "org.springframework.boot:spring-boot-loader-tools:3.4.4", "org.springframework.boot:spring-boot-jarmode-tools:3.4.4", "org.springframework.boot:spring-boot-starter:3.4.4", "org.springframework.boot:spring-boot-starter-actuator:3.4.4", "org.springframework.boot:spring-boot-starter-freemarker:3.4.4", "org.springframework.boot:spring-boot-starter-jdbc:3.4.4", "org.springframework.boot:spring-boot-starter-jetty:3.4.4", "org.springframework.boot:spring-boot-starter-logging:3.4.4", "org.springframework.boot:spring-boot-starter-security:3.4.4", "org.springframework.boot:spring-boot-starter-test:3.4.4", "org.springframework.boot:spring-boot-starter-web:3.4.4", "org.springframework.boot:spring-boot-test:3.4.4", "org.springframework.boot:spring-boot-test-autoconfigure:3.4.4", "org.springframework.boot:spring-boot-starter-thymeleaf:3.4.4", "org.springframework:spring-aop:6.2.5", "org.springframework:spring-aspects:6.2.5", "org.springframework:spring-beans:6.2.5", "org.springframework:spring-context:6.2.5", "org.springframework:spring-context-support:6.2.5", "org.springframework:spring-core:6.2.5", "org.springframework:spring-expression:6.2.5", "org.springframework:spring-jdbc:6.2.5", "org.springframework:spring-test:6.2.5", "org.springframework:spring-tx:6.2.5", "org.springframework:spring-web:6.2.5", "org.springframework:spring-webmvc:6.2.5", # intentionally ancient version annotation-api; in demoapp we use # a filter to exclude this dependency "javax.annotation:javax.annotation-api:1.3.2", # test deps "junit:junit:4.13.2", "org.hamcrest:hamcrest-core:2.2", "org.assertj:assertj-core:3.25.3", ], lock_file = "//:maven_install.json", ) use_repo(maven, "maven") unmanaged_maven = use_extension("@rules_jvm_external//:extensions.bzl", "maven", dev_dependency = True) unmanaged_maven.install( name = "unmanaged_deps_filter", artifacts = [ "org.springframework.boot:spring-boot-starter-data-jpa:3.3.11", "org.springframework.boot:spring-boot-starter-security:3.3.11", "com.fasterxml.jackson.core:jackson-databind:2.17.2", "org.hibernate.orm:hibernate-core:6.4.4.Final", "org.springframework.boot:spring-boot-starter-oauth2-client:3.3.11", "org.springframework.boot:spring-boot-starter-webflux:3.3.11", "org.springframework.boot:spring-boot-starter-actuator:3.3.11", "jakarta.servlet.jsp:jakarta.servlet.jsp-api:3.1.1", "junit:junit:4.13.2", "org.assertj:assertj-core:3.26.0", "io.micrometer:micrometer-commons:1.13.13", "org.slf4j:jul-to-slf4j:2.0.17", ], excluded_artifacts = [ "org.slf4j:slf4j-api", "org.yaml:snakeyaml", ], lock_file = "//springboot/deps_filter_rules/tests/external_deps:unmanaged_deps_filter_install.json", ) use_repo(unmanaged_maven, "unmanaged_deps_filter") ================================================ FILE: README.md ================================================ ## Salesforce Spring Rules for Bazel This repository contains the [Spring Boot](https://spring.io/guides/gs/spring-boot/) rule for the [Bazel](https://bazel.build/) build system. It enables Bazel to build Spring Boot applications and package them as an executable jar file. The executable jar is the best way to deploy your Spring Boot application in production environments. The Salesforce *springboot* rule can be found, along with documentation, in this directory: - [springboot](springboot): a Bazel extension to build and package Spring Boot applications ### Support and Ongoing Development This rule was developed and is supported by Salesforce. If you have any issues with this repository, please create a [GitHub Issue](https://github.com/salesforce/rules_spring/issues). We will try to quickly address problems and answer questions. Note that we do not yet officially support running these [rules on Windows](https://github.com/salesforce/rules_spring/issues/25) but some users have gotten it to work. Ongoing development is planned and tracked using this GitHub repository's [Issues list](https://github.com/salesforce/rules_spring/issues). To see what bug fixes and new features are planned, consult the backlog located there. Generally, we prioritize based on our internal requirements at Salesforce, but if you need something please post a comment on the issue and that will help us prioritize. To see what features/fixes were delivered in a particular release, use the release [version labels](https://github.com/salesforce/rules_spring/issues/labels) and filter on Closed issues. [(example)](https://github.com/salesforce/rules_spring/issues?q=label%3A2.6.1+is%3Aclosed). :octocat: Please do us a **huge favor**. If you think this project could be useful for you, now or in the future, please hit the **Star** button at the top. That helps us advocate for more time and resources on this project. Thanks! ### Loading the Spring Rules in your WORKSPACE Before you can use the rule in your BUILD files, you need to add it to your workspace. **Bzlmod** ```starlark bazel_dep(name = "rules_spring", version = "2.6.3") ``` **WORKSPACE (legacy)** This loads a pre-built version of this rule into your workspace during the build. ```starlark http_archive( name = "rules_spring", sha256 = "2d0805b4096db89b8e407ed0c243ce81c3d20f346e4c259885041d5eabc59436", urls = [ "https://github.com/salesforce/rules_spring/releases/download/2.6.3/rules-spring-2.6.3.zip", ], ) ``` If you choose not to use an official release, you may be tempted to use a *git_repository* workspace rule to point to our *main* branch, Please **do not** do this, as we use *main* for ongoing work. We may check breaking changes into *main* at any time. ### Upgrading to Spring Boot 3 This is largely outside the scope of *rules_spring*. You will need to update your dependencies in your *maven_install* rules, of course. But there are [a ton of other steps](https://github.com/spring-projects/spring-boot/wiki/Spring-Boot-3.0-Migration-Guide). Salesforce has some [docs/tools that will help](https://github.com/salesforce/rules_spring/issues/230) for Bazel users. The one change that you will need to make for *rules_spring* is to choose the Boot3 launcher class. This is because Boot rewrote the launcher for Boot3 and it is available under a different name. The Boot2 launcher is the default for *rules_spring* so as not to break backwards compatibility. Example: ```starlark springboot( name = "helloworld_boot3", boot_app_class = "com.sample.SampleMain", java_library = ":helloworld_lib", # SPRING BOOT 3 # The launcher class changed in Spring Boot 3.2.0, so we provide the # Boot3 launcher class here (the Boot2 one is the default) boot_launcher_class = 'org.springframework.boot.loader.launch.JarLauncher', ) ``` ### Appendix: Alternate Approach for Building and Running Spring Boot Applications If you don't need to create a runnable executable jar file, there is an alternate approach to Spring Boot in the *rules_jvm_external* repository. That approach is sufficient if Bazel and your Bazel workspace (i.e. source code) are available in all environments that launch the application. - [rules_jvm_external Spring Boot example](https://github.com/bazelbuild/rules_jvm_external/tree/master/examples/spring_boot) At Salesforce, Bazel is not available in production environments, and so this alternate approach is not viable. ================================================ FILE: REPO.bazel ================================================ repo( default_package_metadata = ["//:license"], ) ================================================ FILE: SECURITY.md ================================================ ## Security Please report any security issue to [security@salesforce.com](mailto:security@salesforce.com) as soon as it is discovered. This library limits its runtime dependencies in order to reduce the total cost of ownership as much as can be, but all consumers should remain vigilant and have their security stakeholders review all third-party products (3PP) like this one and their dependencies. ================================================ FILE: examples/README.md ================================================ ## Bazel Spring Boot Rule Examples Navigate into our examples directories: - [Hello World](helloworld): bare bones example - [Demo App](demoapp): demonstrates how to use various features in the rule The examples above are coresident with the rule itself, which makes them not precise. Your usage of rules_spring will be as a remote repository. These same examples are availabe in a dedicated repository: - [External Demos](https://github.com/plaird/rules_spring_demoapp) There is also a Kotlin example, which is kept in a separate branch in this repository: - [KotlinApp](https://github.com/salesforce/rules_spring/tree/examples_kotlin) shows how to build and run Spring Boot applications written in Kotlin with *rules_spring* ================================================ FILE: examples/demoapp/BUILD ================================================ # # Copyright (c) 2017-2024, salesforce.com, inc. # All rights reserved. # Licensed under the BSD 3-Clause license. # For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause # # NOTE: # This sample is embedded in the same workspace as the springboot rule. Therefore references # to local path "//springboot" work here. But you will need to change them to: # "@rules_spring//springboot" when you consume the official release via http_archive. load("//springboot:springboot.bzl", "springboot") load("//springboot/deps_filter_rules_legacy:deps_filter.bzl", "deps_filter") load("//tools/license:licenses_used.bzl", "licenses_used") load(":generate-build-info.bzl", "gen_buildinfo_rule") # dependencies from other packages in the workspace deps = [ "//examples/demoapp/libs/lib1", "//examples/demoapp/libs/lib2", # the neverlink example lib is only included at compile time, and not packaged in the jar "//examples/demoapp/libs/lib3_neverlink", ] # create our deps list for Spring Boot springboot_deps = [ "//springboot/import_bundles:springboot_required_deps", "@maven//:org_springframework_boot_spring_boot_starter_jetty", "@maven//:org_springframework_boot_spring_boot_starter_web", "@maven//:org_springframework_boot_spring_boot_loader_tools", "@maven//:org_springframework_boot_spring_boot_jarmode_tools", "@maven//:org_springframework_spring_webmvc", # bring in same dep again as above, but through a different maven_install # rule: the springboot rule does not package duplicate deps, first one wins #"@spring_boot_starter_jetty//:org_springframework_boot_spring_boot_starter_jetty", ] # Sometimes you have a transitive that you don't want. The unwanted_classes.md doc # covers this case, and this snippet shows how to use it: deps_filter( name = "filtered_deps", deps_exclude_labels = [ # tomcat comes in transitively, but we want to use jetty "@maven//:org_apache_tomcat_embed_tomcat_embed_core", "@maven//:org_apache_tomcat_embed_tomcat_embed_el", "@maven//:org_apache_tomcat_embed_tomcat_embed_websocket", # just a demo of excluding a transitive "@maven//:javax_annotation_javax_annotation_api", ], exclude_transitives = True, deps = springboot_deps + deps, # the input list ) # This Java library contains the app code java_library( name = "demoapp_lib", srcs = glob(["src/main/java/**/*.java"]), resources = glob(["src/main/resources/**"]) + [":generate_build_info"], deps = [":filtered_deps"], ) # This is just an example of having a dependency that you want only added to # the springboot jar, not the java_library. This is rare. java_library( name = "rootclassloader_lib", srcs = glob(["src_root/main/java/**/*.java"]), ) test_deps = [ "@maven//:junit_junit", "@maven//:org_hamcrest_hamcrest_core", ] java_test( name = "SampleRestUnitTest", srcs = ["src/test/java/com/sample/SampleRestUnitTest.java"], deps = [":demoapp_lib"] + test_deps, ) filegroup( name = "bazelrun_data_files", srcs = [ "application.properties", "application-dev.properties", "config/application.properties", "example_data.txt", ], ) # Build the app as a Spring Boot executable jar # To launch: bazel run //examples/demoapp springboot( name = "demoapp", # sometimes packagers want to put certain files into the root of the springboot app jar # these addins will be copied into the root of the generated springboot jar addins = [ ":info.txt", ":author.txt", ], # add JVM exports/opens for Java modularization bazelrun_addexports = [ "java.base/java.base=ALL-UNNAMED", "java.base/java.io=ALL-UNNAMED", "java.base/java.nio=ALL-UNNAMED", ], bazelrun_addopens = [ "java.base/java.util.concurrent=ALL-UNNAMED", "java.base/java.util.logging=ALL-UNNAMED", ], # data files can be made available in the working directory for when the app is launched with bazel run bazelrun_data = [":bazelrun_data_files"], # Specify optional environment variables to set when the application is launched with 'bazel run' bazelrun_env_flag_list = [ "PROP1=blue", "PROP2=green", ], bazelrun_jvm_flag_list = [ "-Dcustomprop3=bronze", "-DcustomProp4=copper", ], # new way # Specify optional JVM args to use when the application is launched with 'bazel run' bazelrun_jvm_flags = "-Dcustomprop=gold -DcustomProp2=silver", # old way boot_app_class = "com.sample.SampleMain", # SPRING BOOT 3 # The launcher class changed in between Boot2 and Boot3, so we provide the # Boot3 launcher class here (the Boot2 one is the default) boot_launcher_class = "org.springframework.boot.loader.launch.JarLauncher", # BANNED DEPS # These are dependencies that you never want in your springboot jar. # This is used to detect mistakes in your transitive dependency graph. They # might be test jars, or compile time jars like lombok. The list of strings # is matched against the dependency jar filenames with a 'contains' match. deps_banned = [ "junit", "mockito", "lombok", ], # run the application in the background (command returns immediately) #bazelrun_background = True, # if you have conflicting classes in dependency jar files, you can define the order in which the jars are loaded # https://docs.spring.io/spring-boot/docs/current/reference/html/appendix-executable-jar-format.html#executable-jar-war-index-files-classpath deps_index_file = ":demoapp_classpath.idx", # TO TEST THE DUPE CLASSES FEATURE: # There is an intentionally duplicated class in lib1 and lib2. Do this: # 1. set fail_on_duplicate_classes = True # 2. comment out lib1 or lib2 in demoapp_dupeclass_allowlist.txt # Build should fail due to the duplicate class. dupeclassescheck_enable = True, dupeclassescheck_ignorelist = "demoapp_dupeclass_allowlist.txt", java_library = ":demoapp_lib", # DEPS ARE OPTIONAL HERE # The springboot rule inherits all deps and runtime_deps from the java_library() # but this jar for uncommon reason is just added to the springboot rule. deps = [":rootclassloader_lib"], ) springboottest_deps = [ "@maven//:org_springframework_spring_beans", "@maven//:org_springframework_boot_spring_boot_test", "@maven//:org_springframework_spring_test", ] java_test( name = "SampleRestFuncTest", srcs = ["src/test/java/com/sample/SampleRestFuncTest.java"], resources = glob(["src/test/resources/**"]), deps = [":demoapp_lib"] + test_deps + springboottest_deps, ) java_test( name = "PackagingTest", srcs = ["src/test/java/com/salesforce/rules_spring/PackagingTest.java"], data = [":demoapp"], deps = [":demoapp_lib"] + test_deps, ) licenses_used( name = "demoapp_licenses", out = "demoapp_licenses.json", deps = [":demoapp"], ) # Prove that we can have a second springboot() app in the same BUILD file. # https://github.com/salesforce/rules_spring/issues/139 # To launch: bazel run //examples/demoapp:demoapp-second springboot( name = "demoapp-second", # you may choose to override the launcher script that is used when you invoke 'bazel run //examples/demoapp' bazelrun_script = "custom_bazelrun_script.sh", boot_app_class = "com.sample.SampleMain", boot_launcher_class = "org.springframework.boot.loader.launch.JarLauncher", java_library = ":demoapp_lib", deps = [":rootclassloader_lib"], ) # BuildProperties Support # See the generate-build-info.sh for usage details. exports_files([ "generate-build-info.sh", ]) gen_buildinfo_rule( name = "generate_build_info", ) ================================================ FILE: examples/demoapp/README.md ================================================ ## Demo App Spring Boot Example This example shows how to use many of the features of the Spring Boot rule for Bazel. To build: ```bash bazel build //examples/demoapp ``` To run: ```bash bazel run //examples/demoapp # or to see build data in the endpoint, run like this: bazel run --action_env=BUILD_NUMBER=998 --action_env=BUILD_TAG=green examples/demoapp ``` Endpoints: ``` http://localhost:8080/ http://localhost:8080/actuator/configprops http://localhost:8080/actuator/info ``` For full documentation of rules_spring, see the [//springboot](../../springboot) package documentation. ================================================ FILE: examples/demoapp/application-dev.properties ================================================ demoapp.config.rootdirectory=loaded (via dev profile) ================================================ FILE: examples/demoapp/application.properties ================================================ demoapp.config.rootdirectory=loaded ================================================ FILE: examples/demoapp/author.txt ================================================ Salesforce ================================================ FILE: examples/demoapp/config/application.properties ================================================ demoapp.config.configsubdirectory=loaded ================================================ FILE: examples/demoapp/custom_bazelrun_script.sh ================================================ #!/bin/bash # Copyright (c) 2021-2024, salesforce.com, inc. # All rights reserved. # Licensed under the BSD 3-Clause license. # For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause # set -e # Custom Launcher Script for launching a SpringBoot application with 'bazel run' # this is wired up in the springboot rule (the bazelrun_script attribute) echo "USING A CUSTOM LAUNCHER SCRIPT AS A DEMO (see custom_launcher_script.sh)" # Launcher Script for launching a SpringBoot application with 'bazel run' # The following environment variables will be set by the springboot rule, and can # be reliably used for scripting: # RULE_NAME=helloworld # LABEL_PATH=examples/helloworld/ # SPRINGBOOTJAR_FILENAME=helloworld.jar # JVM_FLAGS="-Dcustomprop=gold -DcustomProp2=silver" # DO_BACKGROUND=true/false (if true, the caller is expecting the launcher not to block and return immediately) # # There are several other env variables set by Bazel. These should be stable between # versions of Bazel because they are documented: # https://docs.bazel.build/versions/master/user-manual.html#run current_dir=$(pwd) # Picking the Java VM to run is a bit of an ordeal. # Precedence order is documented here: # https://github.com/salesforce/rules_spring/blob/main/springboot/bazelrun.md#launcher-jvm if [ -f "${BAZEL_RUN_JAVA}" ]; then # BAZEL_RUN_JAVA points to the actual java executable (file), not the java_home directory echo "Selected the JVM using the BAZEL_RUN_JAVA environment variable." java_cmd=$BAZEL_RUN_JAVA elif [ -f "${JAVABIN}" ]; then # JAVABIN points to the actual java executable (file), not the java_home directory # this is java_binary's convention: https://bazel.build/reference/be/java#java_binary echo "Selected the JVM using the JAVABIN environment variable." java_cmd=$JAVABIN elif [ -f "$JAVA_TOOLCHAIN" ]; then echo "Selected the JVM using the Bazel Java toolchain: $JAVA_TOOLCHAIN_NAME" java_cmd=$JAVA_TOOLCHAIN elif [ -d "${JAVA_HOME}" ]; then echo "Selected the JVM using the JAVA_HOME environment variable." java_cmd="${JAVA_HOME}/bin/java" else echo "Selected the JVM by executing 'which java'" java_cmd="$(which java)" fi if [ -z "${java_cmd}" ]; then echo "ERROR: no java found, either set JAVA_HOME or add the java executable to your PATH" exit 1 fi echo "Using Java at ${java_cmd}" ${java_cmd} -version echo "" # data files, which may include external config files if [ ! -z "${DATAFILES}" ]; then echo "Available datafiles:" configpaths="" for datafile in ${DATAFILES}; do echo " datafile: $current_dir/$datafile" if [[ $datafile == *"application"*".properties" ]]; then path="file:$current_dir/$datafile" if [ ! -z "${configpaths}" ]; then configpaths="$configpaths," fi configpaths="$configpaths$path" fi done if [ ! -z "${configpaths}" ]; then JVM_FLAGS="${JVM_FLAGS} -Dspring.config.additional-location=$configpaths" fi echo "" fi # java args echo "Using JAVA_OPTS from the environment: ${JAVA_OPTS}" echo "Using bazelrun_jvm_flags from the BUILD file: ${JVM_FLAGS}" # main args main_args="$@" # spring boot jar; these are replaced by the springboot starlark code: path=${LABEL_PATH} jar=${SPRINGBOOTJAR_FILENAME} # assemble the command # use exec so that we can pass signals to the underlying process (https://github.com/salesforce/rules_spring/issues/91) cmd="exec ${java_cmd} ${JVM_FLAGS} ${JAVA_OPTS} -jar ${path}${jar} ${main_args}" echo "Running ${cmd}" echo "In directory $current_dir" echo "" echo "You can also run from the root of the repo:" echo "java -jar bazel-bin/${path}${jar}" echo "" # DO_BACKGROUND is set to true if the bazelrun_background attribute on the springboot rule is set to True # BAZELRUN_DO_BACKGROUND=true may be set by the user in the shell env prior to running bazel run # If either is true, we will run the application in the background and return immediately if [ "$DO_BACKGROUND" = true ] || [ "$BAZELRUN_DO_BACKGROUND" = true ]; then logfile=/tmp/${RULE_NAME}.log pidfile=/tmp/${RULE_NAME}.pid ${cmd} > $logfile 2>&1 & pid=$! echo $pid > $pidfile echo "Launched the Spring Boot application in the background..." echo " BUILD rule 'bazelrun_background' attribute = [$DO_BACKGROUND] Environment variable BAZELRUN_DO_BACKGROUND = [$BAZELRUN_DO_BACKGROUND]" echo " Console log is being written to $logfile" echo " Application process id [$pid] has been written to $pidfile" echo "" else echo "Launching the Spring Boot application in the foreground..." echo "" ${cmd} fi ================================================ FILE: examples/demoapp/demoapp_classpath.idx ================================================ - "liblib1.jar" - "liblib2.jar" ================================================ FILE: examples/demoapp/demoapp_dupeclass_allowlist.txt ================================================ # # Copyright (c) 2019-2024, salesforce.com, inc. # All rights reserved. # Licensed under the BSD 3-Clause license. # For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause # liblib1.jar liblib2.jar ================================================ FILE: examples/demoapp/example_data.txt ================================================ x=0 y=0 ================================================ FILE: examples/demoapp/generate-build-info.bzl ================================================ # This macro runs a shell script to implant build variables into a properties file, # which is in turn consumed by Spring's BuildProperties bean. See the script for # usage details. def gen_buildinfo_rule(name, output = "src/main/resources/META-INF/build-info.properties"): native.genrule( name = name, cmd = """$(location //examples/demoapp:generate-build-info.sh) $@""", tools = ["//examples/demoapp:generate-build-info.sh"], outs = [output], ) ================================================ FILE: examples/demoapp/generate-build-info.sh ================================================ #!/bin/bash set -e # This script is invoked by generate-build-info.bzl, which is in turn invoked by # the BUILD file. Consult those files for usage info. # This script implants build data into the Spring Boot app, which is then # accessible by autowiring the org.springframework.boot.info.BuildProperties bean. # See SampleAutoConfiguration.java for an example usage of BuildProperties. buildpropsfile=$1 # These must be set by the bazel command that launches the app. # bazel run --action_env=BUILD_NUMBER=998 --action_env=BUILD_TAG=green examples/demoapp echo "build.number=$BUILD_NUMBER" >> $buildpropsfile echo "build.tag=$BUILD_TAG" >> $buildpropsfile ================================================ FILE: examples/demoapp/info.txt ================================================ This springboot jar was built by Bazel rules_spring. It is copied into the toplevel directory of the springboot jar as an 'addin'. ================================================ FILE: examples/demoapp/libs/lib1/BUILD ================================================ # # Copyright (c) 2020-2021, salesforce.com, inc. # All rights reserved. # Licensed under the BSD 3-Clause license. # For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause # deps = [ "@maven//:org_slf4j_slf4j_api", ] test_deps = [ "@maven//:junit_junit", "@maven//:org_hamcrest_hamcrest_core", ] java_library( name = "lib1", srcs = glob(["src/main/java/**/*.java"]), visibility = ["//visibility:public"], deps = deps, ) java_test( name = "IntentionalDupedClassTest", srcs = ["src/test/java/com/bazel/demo/IntentionalDupedClassTest.java"], deps = [":lib1"] + test_deps, ) ================================================ FILE: examples/demoapp/libs/lib1/src/main/java/com/bazel/demo/IntentionalDupedClass.java ================================================ /* * Copyright (c) 2019-2021, salesforce.com, inc. * All rights reserved. * Licensed under the BSD 3-Clause license. * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause */ package com.bazel.demo; public class IntentionalDupedClass { public String hello() { return "Hello LIB1!"; } } ================================================ FILE: examples/demoapp/libs/lib1/src/test/java/com/bazel/demo/IntentionalDupedClassTest.java ================================================ /* * Copyright (c) 2019-2021, salesforce.com, inc. * All rights reserved. * Licensed under the BSD 3-Clause license. * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause */ package com.bazel.demo; import static org.junit.Assert.assertEquals; import org.junit.Test; public class IntentionalDupedClassTest { @Test public void helloTest() { IntentionalDupedClass testClass = new IntentionalDupedClass(); assertEquals("Hello LIB1!", testClass.hello()); } } ================================================ FILE: examples/demoapp/libs/lib2/BUILD ================================================ # # Copyright (c) 2020-2021, salesforce.com, inc. # All rights reserved. # Licensed under the BSD 3-Clause license. # For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause # deps = [ "@maven//:org_slf4j_slf4j_api", ] test_deps = [ "@maven//:junit_junit", "@maven//:org_hamcrest_hamcrest_core", ] java_library( name = "lib2", srcs = glob(["src/main/java/**/*.java"]), visibility = ["//visibility:public"], deps = deps, ) java_test( name = "IntentionalDupedClassTest", srcs = ["src/test/java/com/bazel/demo/IntentionalDupedClassTest.java"], deps = [":lib2"] + test_deps, ) ================================================ FILE: examples/demoapp/libs/lib2/src/main/java/com/bazel/demo/IntentionalDupedClass.java ================================================ /* * Copyright (c) 2019-2021, salesforce.com, inc. * All rights reserved. * Licensed under the BSD 3-Clause license. * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause */ package com.bazel.demo; public class IntentionalDupedClass { public String hello() { return "Hello LIB2!"; } } ================================================ FILE: examples/demoapp/libs/lib2/src/test/java/com/bazel/demo/IntentionalDupedClassTest.java ================================================ /* * Copyright (c) 2019-2021, salesforce.com, inc. * All rights reserved. * Licensed under the BSD 3-Clause license. * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause */ package com.bazel.demo; import static org.junit.Assert.assertEquals; import org.junit.Test; public class IntentionalDupedClassTest { @Test public void helloTest() { IntentionalDupedClass testClass = new IntentionalDupedClass(); assertEquals("Hello LIB2!", testClass.hello()); } } ================================================ FILE: examples/demoapp/libs/lib3_neverlink/BUILD ================================================ # # Copyright (c) 2020-2024, salesforce.com, inc. # All rights reserved. # Licensed under the BSD 3-Clause license. # For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause # deps = [ "@maven//:org_slf4j_slf4j_api", ] test_deps = [ "@maven//:junit_junit", "@maven//:org_hamcrest_hamcrest_core", ] java_library( name = "lib3_neverlink", srcs = glob(["src/main/java/**/*.java"]), visibility = ["//visibility:public"], deps = deps, # Signals that this is a compile only dep neverlink = 1, ) java_test( name = "NeverLinkTest", srcs = ["src/test/java/com/bazel/demo/NeverLinkTest.java"], deps = [":lib3_neverlink"] + test_deps, ) ================================================ FILE: examples/demoapp/libs/lib3_neverlink/README.md ================================================ ## Neverlink Lib This example *java_library* has *neverlink* set to true. ``` Boolean; default is False Whether this library should only be used for compilation and not at runtime. Useful if the library will be provided by the runtime environment during execution. Examples of such libraries are the IDE APIs for IDE plug-ins or tools.jar for anything running on a standard JDK. Note that neverlink = True does not prevent the compiler from inlining material from this library into compilation targets that depend on it, as permitted by the Java Language Specification (e.g., static final constants of String or of primitive types). The preferred use case is therefore when the runtime library is identical to the compilation library. If the runtime library differs from the compilation library then you must ensure that it differs only in places that the JLS forbids compilers to inline (and that must hold for all future versions of the JLS). ``` ================================================ FILE: examples/demoapp/libs/lib3_neverlink/src/main/java/com/bazel/demo/NeverLinkedClass.java ================================================ /* * Copyright (c) 2019-2021, salesforce.com, inc. * All rights reserved. * Licensed under the BSD 3-Clause license. * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause */ package com.bazel.demo; public class NeverLinkedClass { public String hello() { return "Hello LIB3!"; } } ================================================ FILE: examples/demoapp/libs/lib3_neverlink/src/test/java/com/bazel/demo/NeverLinkTest.java ================================================ /* * Copyright (c) 2019-2024, salesforce.com, inc. * All rights reserved. * Licensed under the BSD 3-Clause license. * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause */ package com.bazel.demo; import static org.junit.Assert.assertEquals; import org.junit.Test; public class NeverLinkTest { // because the library is marked neverlink, it should not be on the runtime classpath // TODO this is not testing the SpringBoot app, just the java_library, need to rewrite as SpringBootTest // manually confirmed with: jar -tvf bazel-bin/examples/demoapp/demoapp.jar | grep lib3 @Test(expected = NoClassDefFoundError.class) public void neverlinkTest() { new NeverLinkedClass(); } } ================================================ FILE: examples/demoapp/remote_debug.sh ================================================ # Remote attach debugging of the demoapp executable jar java -Xdebug -Xrunjdwp:transport=dt_socket,address=8000,server=y,suspend=y -jar ../../bazel-bin/examples/demoapp/demoapp.jar ================================================ FILE: examples/demoapp/src/main/java/com/sample/SampleAutoConfiguration.java ================================================ package com.sample; import jakarta.annotation.PostConstruct; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.beans.factory.annotation.Value; import org.springframework.boot.info.BuildProperties; import org.springframework.boot.loader.tools.SignalUtils; public class SampleAutoConfiguration { @Value("${demoapp.config.internal:not found}") String config_internal; @Value("${demoapp.config.rootdirectory:not found}") String config_external_root; @Value("${demoapp.config.configsubdirectory:not found}") String config_external_configsub; @Value("${prop1:not found}") String config_external_env_prop1; @Value("${prop2:not found}") String config_external_env_prop2; /** * BuildProperties is a Spring facility for implanting build data into the app. * This is not enabled by default for rules_spring. You must wire it up using * the example code in generate-build-info.sh */ @Autowired private BuildProperties buildProperties; @PostConstruct public void logLoadedProperties() { System.out.println("SampleAutoConfiguration loading of application.properties files:"); System.out.println(" internal application.properties: "+config_internal); System.out.println(" external application.properties: "+config_external_root); System.out.println(" external config/application.properties: "+config_external_configsub); System.out.println("SampleAutoConfiguration loading of environment variables:"); System.out.println(" PROP1: "+config_external_env_prop1); System.out.println(" PROP2: "+config_external_env_prop2); System.out.println("SampleAutoConfiguration loading of BuildProperties:"); System.out.println(" (set BUILD_NUMBER and BUILD_TAG action_env variables for Bazel build to use)"); System.out.println(" build.number: "+buildProperties.get("number")); System.out.println(" build.tag: "+buildProperties.get("tag")); } @PostConstruct public void setupSignalHandler() { // SignalUtils is really limited, it only attaches to the INT signal (2) // You could steal the code and attach to other signals. // https://github.com/spring-projects/spring-boot/blob/master/spring-boot-project/spring-boot-tools/spring-boot-loader-tools/src/main/java/org/springframework/boot/loader/tools/SignalUtils.java SignalUtils.attachSignalHandler(new SampleSignalHandler()); } /** * Shows how you can catch an OS signal. This is a good test of the launcher script See * https://github.com/salesforce/rules_spring/issues/91 * The only signal that SignalUtils attaches to is 2 (interrupt). kill -2 [pid] */ private static class SampleSignalHandler implements Runnable { @Override public void run() { System.out.println("Caught an Interrupt signal."); System.exit(0); } } } ================================================ FILE: examples/demoapp/src/main/java/com/sample/SampleMain.java ================================================ /* * Copyright (c) 2019-2021, salesforce.com, inc. * All rights reserved. * Licensed under the BSD 3-Clause license. * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause */ package com.sample; import org.springframework.boot.autoconfigure.SpringBootApplication; import org.springframework.boot.SpringApplication; import com.bazel.demo.IntentionalDupedClass; @SpringBootApplication public class SampleMain { // both //examples/demoapp/libs/lib1 and //examples/demoapp/libs/lib2 have this class // this is only a problem if the springboot rule is configured to fail on dupes. static private IntentionalDupedClass dupedClass = new IntentionalDupedClass(); public static void main(String[] args) throws Exception { System.out.println("SampleMain: Launching the sample SpringBoot demo application..."); StringBuffer sb = new StringBuffer(); for (String arg : args) { sb.append("["); sb.append(arg); sb.append("] "); } System.out.println("SampleMain: Command line args: "+sb.toString()); System.out.println("\nSampleMain: Intentional duped class version: "+dupedClass.hello()); // test that the root class is available Class.forName("com.sample.SampleRootClass"); System.out.println("\nSampleMain: loaded the root class com.sample.SampleRootClass"); SpringApplication.run(SampleMain.class, args); } } ================================================ FILE: examples/demoapp/src/main/java/com/sample/SampleRest.java ================================================ /* * Copyright (c) 2019-2021, salesforce.com, inc. * All rights reserved. * Licensed under the BSD 3-Clause license. * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause */ package com.sample; import org.springframework.web.bind.annotation.RestController; import org.springframework.web.bind.annotation.RequestMapping; @RestController public class SampleRest { @RequestMapping("/") public String hello() { return "Hello!"; } } ================================================ FILE: examples/demoapp/src/main/resources/META-INF/spring/org.springframework.boot.autoconfigure.AutoConfiguration.imports ================================================ com.sample.SampleAutoConfiguration ================================================ FILE: examples/demoapp/src/main/resources/application.properties ================================================ # # Copyright (c) 2017-2021, salesforce.com, inc. # All rights reserved. # Licensed under the BSD 3-Clause license. # For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause # # expose the actuator endpoints # http://localhost:8080/actuator/beans # http://localhost:8080/actuator/info management.endpoints.web.exposure.include=* demoapp.config.internal=loaded ================================================ FILE: examples/demoapp/src/test/java/com/salesforce/rules_spring/PackagingTest.java ================================================ /* * Copyright (c) 2021, salesforce.com, inc. * All rights reserved. * Licensed under the BSD 3-Clause license. * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause */ package com.salesforce.rules_spring; import org.junit.Before; import org.junit.Test; import java.io.File; import java.io.InputStream; import java.nio.charset.StandardCharsets; import java.util.Enumeration; import java.util.Iterator; import java.util.zip.ZipEntry; import java.util.zip.ZipFile; import static org.junit.Assert.*; /** */ public class PackagingTest { File springbootJarFile = null; // file contents String gitPropertiesContents = null; String buildPropertiesContents = null; String applicationPropertiesContents = null; // file existence boolean exists_lib1 = false; boolean exists_lib2 = false; boolean exists_lib3_neverlink = false; @Before public void setup() throws Exception { springbootJarFile = new File("./examples/demoapp/demoapp.jar"); if (!springbootJarFile.exists()) { throw new IllegalStateException("Missing demoapp springboot jar; looked in path: " + springbootJarFile.getAbsolutePath()); } extractFilesFromSpringBootJar(); } @Test public void gitPropertiesFileTest() { assertNotNull(gitPropertiesContents); assertTrue(gitPropertiesContents.contains("git.commit")); } @Test public void buildPropertiesFileTest() { assertNotNull(buildPropertiesContents); assertTrue(buildPropertiesContents.contains("build.number")); } @Test public void applicationPropertiesFileTest() { assertNotNull(applicationPropertiesContents); assertTrue(applicationPropertiesContents.contains("demoapp.config.internal")); } @Test public void internalLibsAreIncludedTest() { assertTrue(this.exists_lib1); assertTrue(this.exists_lib2); } @Test public void neverlinkLibsAreExcludedTest() { assertFalse(this.exists_lib3_neverlink); } private void extractFilesFromSpringBootJar() throws Exception { try (ZipFile sbZip = new ZipFile(springbootJarFile)) { Enumeration entries = sbZip.entries(); for (Iterator it = entries.asIterator(); it.hasNext(); ) { ZipEntry entry = it.next(); String name = entry.getName(); System.out.println(" zipentry: "+name); if (name.equals("BOOT-INF/classes/git.properties")) { InputStream is = sbZip.getInputStream(entry); gitPropertiesContents = new String(is.readAllBytes(), StandardCharsets.UTF_8); } else if (name.equals("BOOT-INF/classes/META-INF/build-info.properties")) { InputStream is = sbZip.getInputStream(entry); buildPropertiesContents = new String(is.readAllBytes(), StandardCharsets.UTF_8); } else if (name.equals("BOOT-INF/classes/application.properties")) { InputStream is = sbZip.getInputStream(entry); applicationPropertiesContents = new String(is.readAllBytes(), StandardCharsets.UTF_8); } else if (name.equals("BOOT-INF/lib/examples/demoapp/libs/lib1/liblib1.jar")) { exists_lib1 = true; } else if (name.equals("BOOT-INF/lib/examples/demoapp/libs/lib2/liblib2.jar")) { exists_lib2 = true; } else if (name.contains("neverlink")) { // we have a lib named lib3_neverlink that has neverlink = True, which means it should NOT be // included in the springboot jar exists_lib3_neverlink = true; } } } } } ================================================ FILE: examples/demoapp/src/test/java/com/sample/SampleRestFuncTest.java ================================================ /* * Copyright (c) 2021, salesforce.com, inc. * All rights reserved. * Licensed under the BSD 3-Clause license. * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause */ package com.sample; import org.junit.runner.RunWith; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.boot.test.context.SpringBootTest; import org.springframework.test.context.TestPropertySource; import org.springframework.test.context.junit4.SpringRunner; import static org.junit.Assert.assertEquals; import org.junit.Test; /** * This test class starts the Spring Boot application. Because the Spring context is * created, you can autowire spring beans into the test. */ @RunWith(SpringRunner.class) @SpringBootTest(classes = SampleMain.class, webEnvironment = SpringBootTest.WebEnvironment.RANDOM_PORT) @TestPropertySource(locations = {"classpath:/test.properties"}) public class SampleRestFuncTest { @Autowired private SampleRest sampleRest; @Test public void apiTest() { assertEquals("Hello!", sampleRest.hello()); } } ================================================ FILE: examples/demoapp/src/test/java/com/sample/SampleRestUnitTest.java ================================================ /* * Copyright (c) 2021, salesforce.com, inc. * All rights reserved. * Licensed under the BSD 3-Clause license. * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause */ package com.sample; import static org.junit.Assert.assertEquals; import org.junit.Test; /** * This test class does NOT start the Spring Boot application. It is a simple unit test. */ public class SampleRestUnitTest { @Test public void apiTest() { SampleRest testClass = new SampleRest(); assertEquals("Hello!", testClass.hello()); } } ================================================ FILE: examples/demoapp/src/test/resources/test.properties ================================================ anyprop=somevalue ================================================ FILE: examples/demoapp/src_root/main/java/com/sample/SampleRootClass.java ================================================ /* * Copyright (c) 2019-2021, salesforce.com, inc. * All rights reserved. * Licensed under the BSD 3-Clause license. * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause */ package com.sample; public class SampleRootClass { public String helloMessage; } ================================================ FILE: examples/helloworld/BUILD ================================================ # # Copyright (c) 2017-2021, salesforce.com, inc. # All rights reserved. # Licensed under the BSD 3-Clause license. # For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause # # NOTE: # This sample is embedded in the same workspace as the springboot rule. Therefore references # to local path "//springboot" work here. But you will need to change them to: # "@rules_spring//springboot" when you consume the official release via http_archive. # load our Spring Boot rule load("//springboot:springboot.bzl", "springboot") # dependencies from other packages in the workspace lib_deps = [ "//examples/helloworld/libs/lib1", "//examples/helloworld/libs/lib2", ] # create our deps list for Spring Boot springboot_deps = [ "//springboot/import_bundles:springboot_required_deps", "@maven//:org_springframework_boot_spring_boot_starter_jetty", "@maven//:org_springframework_boot_spring_boot_starter_web", "@maven//:org_springframework_boot_spring_boot_loader_tools", "@maven//:org_springframework_boot_spring_boot_jarmode_tools", "@maven//:org_springframework_spring_webmvc", "@maven//:javax_annotation_javax_annotation_api", ] # This Java library contains the app code java_library( name = "helloworld_lib", srcs = glob(["src/main/java/**/*.java"]), resources = glob(["src/main/resources/**"]), deps = springboot_deps + lib_deps, ) test_deps = [ "@maven//:junit_junit", "@maven//:org_hamcrest_hamcrest_core", ] java_test( name = "SampleRestUnitTest", srcs = ["src/test/java/com/sample/SampleRestUnitTest.java"], deps = [ ":helloworld_lib" ] + test_deps, ) # Build the app as a Spring Boot executable jar # To launch: bazel run //examples/helloworld springboot( name = "helloworld", boot_app_class = "com.sample.SampleMain", java_library = ":helloworld_lib", # SPRING BOOT 3 # The launcher class changed in between Boot2 and Boot3, so we provide the # Boot3 launcher class here (the Boot2 one is the default) boot_launcher_class = 'org.springframework.boot.loader.launch.JarLauncher', ) springboottest_deps = [ "@maven//:org_springframework_spring_beans", "@maven//:org_springframework_boot_spring_boot_test", "@maven//:org_springframework_spring_test", ] java_test( name = "SampleRestFuncTest", srcs = ["src/test/java/com/sample/SampleRestFuncTest.java"], deps = [ ":helloworld_lib" ] + test_deps + springboottest_deps, resources = glob(["src/test/resources/**"]), ) ================================================ FILE: examples/helloworld/README.md ================================================ ## Hello World Spring Boot Example This example shows a simple Spring Boot application packaged with Bazel. To build: ```bash bazel build //examples/helloworld ``` To run: ```bash bazel run //examples/helloworld ``` For full documentation, see the [//springboot](../../springboot) package documentation. ================================================ FILE: examples/helloworld/libs/lib1/BUILD ================================================ # # Copyright (c) 2020-2021, salesforce.com, inc. # All rights reserved. # Licensed under the BSD 3-Clause license. # For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause # deps = [ "@maven//:org_slf4j_slf4j_api", ] test_deps = [ "@maven//:junit_junit", "@maven//:org_hamcrest_hamcrest_core", ] java_library( name = "lib1", srcs = glob(["src/main/java/**/*.java"]), visibility = ["//visibility:public"], deps = deps, ) java_test( name = "IntentionalDupedClassTest", srcs = ["src/test/java/com/bazel/demo/IntentionalDupedClassTest.java"], deps = [":lib1"] + test_deps, ) ================================================ FILE: examples/helloworld/libs/lib1/src/main/java/com/bazel/demo/IntentionalDupedClass.java ================================================ /* * Copyright (c) 2019-2021, salesforce.com, inc. * All rights reserved. * Licensed under the BSD 3-Clause license. * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause */ package com.bazel.demo; public class IntentionalDupedClass { public String hello() { return "Hello LIB1!"; } } ================================================ FILE: examples/helloworld/libs/lib1/src/test/java/com/bazel/demo/IntentionalDupedClassTest.java ================================================ /* * Copyright (c) 2019-2021, salesforce.com, inc. * All rights reserved. * Licensed under the BSD 3-Clause license. * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause */ package com.bazel.demo; import static org.junit.Assert.assertEquals; import org.junit.Test; public class IntentionalDupedClassTest { @Test public void helloTest() { IntentionalDupedClass testClass = new IntentionalDupedClass(); assertEquals("Hello LIB1!", testClass.hello()); } } ================================================ FILE: examples/helloworld/libs/lib2/BUILD ================================================ # # Copyright (c) 2020-2021, salesforce.com, inc. # All rights reserved. # Licensed under the BSD 3-Clause license. # For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause # deps = [ "@maven//:org_slf4j_slf4j_api", ] test_deps = [ "@maven//:junit_junit", "@maven//:org_hamcrest_hamcrest_core", ] java_library( name = "lib2", srcs = glob(["src/main/java/**/*.java"]), visibility = ["//visibility:public"], deps = deps, ) java_test( name = "IntentionalDupedClassTest", srcs = ["src/test/java/com/bazel/demo/IntentionalDupedClassTest.java"], deps = [":lib2"] + test_deps, ) ================================================ FILE: examples/helloworld/libs/lib2/src/main/java/com/bazel/demo/IntentionalDupedClass.java ================================================ /* * Copyright (c) 2019-2021, salesforce.com, inc. * All rights reserved. * Licensed under the BSD 3-Clause license. * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause */ package com.bazel.demo; public class IntentionalDupedClass { public String hello() { return "Hello LIB2!"; } } ================================================ FILE: examples/helloworld/libs/lib2/src/test/java/com/bazel/demo/IntentionalDupedClassTest.java ================================================ /* * Copyright (c) 2019-2021, salesforce.com, inc. * All rights reserved. * Licensed under the BSD 3-Clause license. * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause */ package com.bazel.demo; import static org.junit.Assert.assertEquals; import org.junit.Test; public class IntentionalDupedClassTest { @Test public void helloTest() { IntentionalDupedClass testClass = new IntentionalDupedClass(); assertEquals("Hello LIB2!", testClass.hello()); } } ================================================ FILE: examples/helloworld/remote_debug.sh ================================================ # Remote attach debugging of the helloworld executable jar java -Xdebug -Xrunjdwp:transport=dt_socket,address=8000,server=y,suspend=y -jar ../../bazel-bin/examples/helloworld/helloworld.jar ================================================ FILE: examples/helloworld/src/main/java/com/sample/SampleAutoConfiguration.java ================================================ package com.sample; import org.springframework.context.annotation.Bean; public class SampleAutoConfiguration { @Bean public String helloMessage() { return "Hello SpringBoot!"; } } ================================================ FILE: examples/helloworld/src/main/java/com/sample/SampleMain.java ================================================ /* * Copyright (c) 2019-2021, salesforce.com, inc. * All rights reserved. * Licensed under the BSD 3-Clause license. * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause */ package com.sample; import org.springframework.boot.SpringApplication; import org.springframework.boot.autoconfigure.SpringBootApplication; @SpringBootApplication public class SampleMain { public static void main(String[] args) { System.out.println("SampleMain: Launching the sample SpringBoot demo application..."); StringBuffer sb = new StringBuffer(); for (String arg : args) { sb.append(arg); sb.append(" "); } System.out.println("SampleMain: Command line args: "+sb.toString()); SpringApplication.run(SampleMain.class, args); } } ================================================ FILE: examples/helloworld/src/main/java/com/sample/SampleRest.java ================================================ /* * Copyright (c) 2019-2021, salesforce.com, inc. * All rights reserved. * Licensed under the BSD 3-Clause license. * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause */ package com.sample; import org.springframework.web.bind.annotation.RequestMapping; import org.springframework.web.bind.annotation.RestController; @RestController public class SampleRest { @RequestMapping("/") public String hello() { return "Hello!"; } } ================================================ FILE: examples/helloworld/src/main/resources/META-INF/spring/org.springframework.boot.autoconfigure.AutoConfiguration.imports ================================================ com.sample.SampleAutoConfiguration ================================================ FILE: examples/helloworld/src/main/resources/application.properties ================================================ # # Copyright (c) 2017-2021, salesforce.com, inc. # All rights reserved. # Licensed under the BSD 3-Clause license. # For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause # # expose the actuator endpoints # http://localhost:8080/actuator/beans # http://localhost:8080/actuator/info management.endpoints.web.exposure.include=* ================================================ FILE: examples/helloworld/src/test/java/com/sample/SampleRestFuncTest.java ================================================ /* * Copyright (c) 2021, salesforce.com, inc. * All rights reserved. * Licensed under the BSD 3-Clause license. * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause */ package com.sample; import static org.junit.Assert.assertEquals; import org.junit.Test; import org.junit.runner.RunWith; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.boot.test.context.SpringBootTest; import org.springframework.test.context.TestPropertySource; import org.springframework.test.context.junit4.SpringRunner; /** * This test class starts the Spring Boot application. Because the Spring context is * created, you can autowire spring beans into the test. */ @RunWith(SpringRunner.class) @SpringBootTest(classes = SampleMain.class, webEnvironment = SpringBootTest.WebEnvironment.RANDOM_PORT) @TestPropertySource(locations = {"classpath:/test.properties"}) public class SampleRestFuncTest { @Autowired private SampleRest sampleRest; @Test public void apiTest() { assertEquals("Hello!", sampleRest.hello()); } } ================================================ FILE: examples/helloworld/src/test/java/com/sample/SampleRestUnitTest.java ================================================ /* * Copyright (c) 2021, salesforce.com, inc. * All rights reserved. * Licensed under the BSD 3-Clause license. * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause */ package com.sample; import static org.junit.Assert.assertEquals; import org.junit.Test; /** * This test class does NOT start the Spring Boot application. It is a simple unit test. */ public class SampleRestUnitTest { @Test public void apiTest() { SampleRest testClass = new SampleRest(); assertEquals("Hello!", testClass.hello()); } } ================================================ FILE: examples/helloworld/src/test/resources/test.properties ================================================ anyprop=somevalue ================================================ FILE: examples/kotlinapp/README.md ================================================ ## Kotlin Example for Bazel Spring Boot To avoid cluttering the WORKSPACE file for everyone, the Kotlin example is published in a dedicated branch of this repository. - [KotlinApp](https://github.com/salesforce/rules_spring/tree/examples_kotlin) shows how to build and run Spring Boot applications written in Kotlin with *rules_spring* ================================================ FILE: makerelease.sh ================================================ # # Copyright (c) 2017-2024, salesforce.com, inc. # All rights reserved. # Licensed under the BSD 3-Clause license. # For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause # release_version=2.4.1 echo "RELEASE: You are about to create a local zip file that contains the release bits." echo "After it is created, there will be instructions on how to upload it to GitHub and create the release metadata." echo "" echo "Please enter the release version (e.g. 2.4.1):" read release_version echo "" echo "You have entered $release_version, are you good with this version? Enter to continue, ctrl-c to abort." read DOTHETHING echo "STEP 1: update MODULE.bazel with version $release_version" echo "You must do this manually, I will wait for you. After it is done, press Enter here." read DOTHETHING echo "" echo "STEP 2: packaging the release zip file." echo "I can do this all by myself...." echo "" # remove/relocate local build artifacts and tools rm -rf bazel-* # move some dev directories out, so they don't get zipped up in the archive tmpdir=/tmp/rules-spring-release mkdir $tmpdir 2>/dev/null mv examples $tmpdir 2>/dev/null rm -rf coverage-reports rm -rf springboot/tests/__pycache__ rm -rf springboot/__pycache__ rm *.zip # jar up the code release_zip=rules-spring-${release_version}.zip jar -cvf $release_zip * # restore the dev directories mv $tmpdir/examples examples 2>/dev/null rm -rf $tmpdir sha256=$(shasum -a 256 $release_zip) echo "" echo "RELEASE artifact built successfully: rules-spring-${release_version}.zip" echo " SHA256 of the release artifact: $sha256" echo "" echo "" echo "STEP 3: release tasks" echo " 0. commit and push the MODULE.bazel update you just did" echo " 1. Create a new release on GitHub and upload the zip file to it. Look at previous releases and use the same doc conventions. Make sure you tag the release." echo " 2. Update the bzlmod/http_archive stanzas in the top level README.md to refer to the latest release." echo " 3. Test new release with the external demoapp repository: https://github.com/plaird/rules_spring_demoapp" echo "" echo "OK, go do those tasks now, please." read DID_RELEASE echo "" echo "" echo "STEP 4: BCR update tasks" echo "OK, now you have to publish the release to the Bazel central registry." echo "1. Activate your python virtual env (e.g. source ~/dev/bin/activate)" echo "2. sync your BCR fork: git pull upstream main" echo "3. run the add module script in your BCR fork: python3 tools/add_module.py" echo " Please enter the module name: rules_spring" echo " Please enter the module version: 2.6.2" echo " Please enter the compatibility level [default is 0]: 2" echo " Please enter the URL of the source archive: https://github.com/salesforce/rules_spring/releases/download/2.6.2/rules-spring-2.6.2.zip" echo " Please enter the strip_prefix value of the archive [default None]:" echo " Do you want to add patch files? [y/N]: n" echo " Do you want to add a BUILD file? [y/N]: n" echo " Do you want to specify a MODULE.bazel file? [y/N]: y" echo " Please enter the MODULE.bazel file path: ../../rules_spring/MODULE.bazel" echo " Do you want to specify an existing presubmit.yml file? y" echo " Please enter the presubmit.yml file path: modules/rules_spring/2.6.0/presubmit.yml" echo "4. git add modules" echo "5. submit a PR to BCR" echo "" ================================================ FILE: maven_install.json ================================================ { "__AUTOGENERATED_FILE_DO_NOT_MODIFY_THIS_FILE_MANUALLY": "THERE_IS_NO_DATA_ONLY_ZUUL", "__INPUT_ARTIFACTS_HASH": 280632942, "__RESOLVED_ARTIFACTS_HASH": 217268227, "conflict_resolution": { "com.google.errorprone:error_prone_annotations:2.5.1": "com.google.errorprone:error_prone_annotations:2.18.0", "org.assertj:assertj-core:3.25.3": "org.assertj:assertj-core:3.26.3", "org.mockito:mockito-core:4.3.1": "org.mockito:mockito-core:5.14.2" }, "artifacts": { "biz.aQute.bnd:biz.aQute.bnd.util": { "shasums": { "jar": "65b5bd4a0fab16812f1800c98ff74a038f37a38bfe899af382efed4efdc1e3e1" }, "version": "6.4.0" }, "biz.aQute.bnd:biz.aQute.bndlib": { "shasums": { "jar": "357145074872f9dbf67e629fcd237e6152707e575d735df4535282f9f588d2d8" }, "version": "6.4.0" }, "ch.qos.logback:logback-classic": { "shasums": { "jar": "3e1533d0321f8815eef46750aee0111b41554f9a4644c3c4d2d404744b09f60f" }, "version": "1.5.18" }, "ch.qos.logback:logback-core": { "shasums": { "jar": "85139e7b57b464f8e5e36326dd81317648bed199ccc4f98cd42585f8d7571027" }, "version": "1.5.18" }, "com.fasterxml.jackson.core:jackson-annotations": { "shasums": { "jar": "8aa5740d80b5a5025508b41bbadbaa1fb3772267c628b2e30681a4f45f8b8931" }, "version": "2.18.3" }, "com.fasterxml.jackson.core:jackson-core": { "shasums": { "jar": "056bc4d3e5e53ce821450fa97b3f9e0f8dde125cf6da6884353bb1f09582e1d9" }, "version": "2.18.3" }, "com.fasterxml.jackson.core:jackson-databind": { "shasums": { "jar": "510bdda75a7a6186c5bf33b851239488a1450906ae5757121f2e1cc48a7e108f" }, "version": "2.18.3" }, "com.fasterxml.jackson.datatype:jackson-datatype-jdk8": { "shasums": { "jar": "1f517af91ace54150525cdb30a012fca19a536194564756f580c21acfc7e04a0" }, "version": "2.18.3" }, "com.fasterxml.jackson.datatype:jackson-datatype-jsr310": { "shasums": { "jar": "2e1df2feb93683d379969ceaf78b76a0ac115c67d04671958fddf4eed6e6401d" }, "version": "2.18.3" }, "com.fasterxml.jackson.module:jackson-module-parameter-names": { "shasums": { "jar": "3797241e299fcde9be2bf5f3a52ac61b66f749e7157478f5b246eb597e962c26" }, "version": "2.18.3" }, "com.google.auto.value:auto-value-annotations": { "shasums": { "jar": "37ec09b47d7ed35a99d13927db5c86fc9071f620f943ead5d757144698310852" }, "version": "1.8.1" }, "com.google.caliper:caliper": { "shasums": { "jar": "d54e1bfdbe9359a79e175c217b8d472555cf20da9c5c0a18bdb1ea7db979ed8e" }, "version": "1.0-beta-3" }, "com.google.caliper:caliper-api": { "shasums": { "jar": "374f0c6c0c1f8784cb69d885e1dcbb7498c34ca20369e0597264568530642928" }, "version": "1.0-beta-3" }, "com.google.caliper:caliper-core": { "shasums": { "jar": "514deac8f8b09dd4262733e0a4406a333208c899dc7ea726b03600b9bb94f192" }, "version": "1.0-beta-3" }, "com.google.caliper:caliper-runner": { "shasums": { "jar": "3ab58890aa01343361adedf859500d280f67813df0cedfcd165b169533b9b1fa" }, "version": "1.0-beta-3" }, "com.google.caliper:caliper-util": { "shasums": { "jar": "6e9af500c7020450dfdb5003d09501d512d395f431c54c7ee8f79e712463fe66" }, "version": "1.0-beta-3" }, "com.google.caliper:caliper-worker": { "shasums": { "jar": "315d8e51df1f60551645a0e3bf2c504d2c79762f688e6f728eb9d1d9cd9a491b" }, "version": "1.0-beta-3" }, "com.google.caliper:caliper-worker-jvm": { "shasums": { "jar": "e14e1ecfdf939c82abdb902105be41ff3f83c18cb968116232015f2662d065a4" }, "version": "1.0-beta-3" }, "com.google.code.findbugs:jsr305": { "shasums": { "jar": "766ad2a0783f2687962c8ad74ceecc38a28b9f72a2d085ee438b7813e928d0c7" }, "version": "3.0.2" }, "com.google.code.gson:gson": { "shasums": { "jar": "d3999291855de495c94c743761b8ab5176cfeabe281a5ab0d8e8d45326fd703e" }, "version": "2.8.9" }, "com.google.code.java-allocation-instrumenter:java-allocation-instrumenter": { "shasums": { "jar": "1ef5535a8bd41cf3072469f381b9ee6ab28275311a7499f53d6e52adf976fef0" }, "version": "3.3.0" }, "com.google.dagger:dagger": { "shasums": { "jar": "329d4340f24c4f5717af016c097e90668bfea2a5376e6aa9964b01cef3fd241a" }, "version": "2.22.1" }, "com.google.dagger:dagger-producers": { "shasums": { "jar": "f834a0082014213a68ff06a0f048d750178d02196c58b0b15beb367d32b97e35" }, "version": "2.22.1" }, "com.google.errorprone:error_prone_annotations": { "shasums": { "jar": "9e6814cb71816988a4fd1b07a993a8f21bb7058d522c162b1de849e19bea54ae" }, "version": "2.18.0" }, "com.google.guava:failureaccess": { "shasums": { "jar": "a171ee4c734dd2da837e4b16be9df4661afab72a41adaf31eb84dfdaf936ca26" }, "version": "1.0.1" }, "com.google.guava:guava": { "shasums": { "jar": "bd7fa227591fb8509677d0d1122cf95158f3b8a9f45653f58281d879f6dc48c5" }, "version": "32.0.1-jre" }, "com.google.guava:guava-testlib": { "shasums": { "jar": "c97511849a5e085280f106df2b059566febd280b118d33d6a9e068d238100b63" }, "version": "32.0.1-jre" }, "com.google.guava:listenablefuture": { "shasums": { "jar": "b372a037d4230aa57fbeffdef30fd6123f9c0c2db85d0aced00c91b974f33f99" }, "version": "9999.0-empty-to-avoid-conflict-with-guava" }, "com.google.j2objc:j2objc-annotations": { "shasums": { "jar": "f02a95fa1a5e95edb3ed859fd0fb7df709d121a35290eff8b74dce2ab7f4d6ed" }, "version": "2.8" }, "com.google.truth:truth": { "shasums": { "jar": "a85e03b8b6ae8780f060cfded9500a3d1b5f52808f99a2ea6da9c683313c7518" }, "version": "1.1.2" }, "com.jayway.jsonpath:json-path": { "shasums": { "jar": "11a9ee6f88bb31f1450108d1cf6441377dec84aca075eb6bb2343be157575bea" }, "version": "2.9.0" }, "com.squareup.okhttp:okhttp": { "shasums": { "jar": "88ac9fd1bb51f82bcc664cc1eb9c225c90dc4389d660231b4cc737bebfe7d0aa" }, "version": "2.7.5" }, "com.squareup.okio:okio": { "shasums": { "jar": "114bdc1f47338a68bcbc95abf2f5cdc72beeec91812f2fcd7b521c1937876266" }, "version": "1.6.0" }, "com.sun.jersey:jersey-client": { "shasums": { "jar": "639c825c5db580f8115bf49ffc893093526d2ed1079fbc929b6a5fbd0b2eda40" }, "version": "1.19.4" }, "com.sun.jersey:jersey-core": { "shasums": { "jar": "64b03198e0264849d0fc341857ebcc9c882b1909a2dc35a0972fe7d901b826e5" }, "version": "1.19.4" }, "com.vaadin.external.google:android-json": { "shasums": { "jar": "dfb7bae2f404cfe0b72b4d23944698cb716b7665171812a0a4d0f5926c0fac79" }, "version": "0.0.20131108.vaadin1" }, "com.zaxxer:HikariCP": { "shasums": { "jar": "a47a6ee62379694ee52c30036f0931b72f9aee2a801d590341ed82bd839e2134" }, "version": "5.1.0" }, "info.picocli:picocli": { "shasums": { "jar": "b0a5159e926de8084ff066025142270443533656bc599b8bb31d14d11fd138a4" }, "version": "4.6.3" }, "io.micrometer:micrometer-commons": { "shasums": { "jar": "e98485ffecb7d8cc9af47cfe627ea8bf3897915dd0f34b3e3a190d6896875b4b" }, "version": "1.14.5" }, "io.micrometer:micrometer-core": { "shasums": { "jar": "7c0c55ef7fe1bef5b89453655e768ee05fd35b381bd67f9d42cfe48362174ca5" }, "version": "1.14.5" }, "io.micrometer:micrometer-jakarta9": { "shasums": { "jar": "08c0e061df58583ae11b4b0ec664f0205e43dbb16ccd41571cf068269823803a" }, "version": "1.14.5" }, "io.micrometer:micrometer-observation": { "shasums": { "jar": "7cfbf714abdf3779c820ff19712199ac9bae03d2f0e809ba8e74c3663c12128a" }, "version": "1.14.5" }, "jakarta.activation:jakarta.activation-api": { "shasums": { "jar": "01b176d718a169263e78290691fc479977186bcc6b333487325084d6586f4627" }, "version": "2.1.3" }, "jakarta.annotation:jakarta.annotation-api": { "shasums": { "jar": "5f65fdaf424eee2b55e1d882ba9bb376be93fb09b37b808be6e22e8851c909fe" }, "version": "2.1.1" }, "jakarta.enterprise:jakarta.enterprise.cdi-api": { "shasums": { "jar": "beaf74c4f2618189309e3f4a09c43effab633dd96aa1f6dc58a6ba7ee0042717" }, "version": "4.0.1" }, "jakarta.enterprise:jakarta.enterprise.lang-model": { "shasums": { "jar": "53acafe65b6ef0195fa1b8a0ef2650e5aa024c32cb4059c4df372d6b32089cd3" }, "version": "4.0.1" }, "jakarta.inject:jakarta.inject-api": { "shasums": { "jar": "f7dc98062fccf14126abb751b64fab12c312566e8cbdc8483598bffcea93af7c" }, "version": "2.0.1" }, "jakarta.interceptor:jakarta.interceptor-api": { "shasums": { "jar": "ef787d3f713fc6ff4f02cd4b0dbed08f93d8af3400c90cbb43fb4b5c0583710b" }, "version": "2.1.0" }, "jakarta.servlet:jakarta.servlet-api": { "shasums": { "jar": "c034eb1afb158987dbb53a5fea0cadf611c8dae8daadd59c44d9d5ab70129cef" }, "version": "6.0.0" }, "jakarta.transaction:jakarta.transaction-api": { "shasums": { "jar": "50c0a7c760c13ae6c042acf182b28f0047413db95b4636fb8879bcffab5ba875" }, "version": "2.0.1" }, "jakarta.websocket:jakarta.websocket-api": { "shasums": { "jar": "beadb92c26d04da653f6d2db2532b549b7a0dbe59c6e22c23e55bd03617f0120" }, "version": "2.1.1" }, "jakarta.websocket:jakarta.websocket-client-api": { "shasums": { "jar": "e8fe8c1dff948385a461dbc85dec5467cbe350f065ec1a0f3bfed53b79e7b102" }, "version": "2.1.1" }, "jakarta.xml.bind:jakarta.xml.bind-api": { "shasums": { "jar": "0d6bcfe47763e85047acf7c398336dc84ff85ebcad0a7cb6f3b9d3e981245406" }, "version": "4.0.2" }, "javax.annotation:javax.annotation-api": { "shasums": { "jar": "e04ba5195bcd555dc95650f7cc614d151e4bcd52d29a10b8aa2197f3ab89ab9b" }, "version": "1.3.2" }, "javax.inject:javax.inject": { "shasums": { "jar": "91c77044a50c481636c32d916fd89c9118a72195390452c81065080f957de7ff" }, "version": "1" }, "javax.ws.rs:jsr311-api": { "shasums": { "jar": "ab1534b73b5fa055808e6598a5e73b599ccda28c3159c3c0908977809422ee4a" }, "version": "1.1.1" }, "joda-time:joda-time": { "shasums": { "jar": "dd8e7c92185a678d1b7b933f31209b6203c8ffa91e9880475a1be0346b9617e3" }, "version": "2.10.10" }, "junit:junit": { "shasums": { "jar": "8e495b634469d64fb8acfa3495a065cbacc8a0fff55ce1e31007be4c16dc57d3" }, "version": "4.13.2" }, "net.bytebuddy:byte-buddy": { "shasums": { "jar": "4a683d83ff219f20d44f35ca302d821e0c6842e3fa8f9f1ee913eb16f49cec6c" }, "version": "1.15.4" }, "net.bytebuddy:byte-buddy-agent": { "shasums": { "jar": "1d76defd159a564b9cb7a968d0dea27367b8b70ebde75a968e7ef1921bc75ee4" }, "version": "1.15.4" }, "net.minidev:accessors-smart": { "shasums": { "jar": "9b8a7bc43861d6156c021166d941fb7dddbe4463e2fa5ee88077e4b01452a836" }, "version": "2.5.2" }, "net.minidev:json-smart": { "shasums": { "jar": "4fbdedb0105cedc7f766b95c297d2e88fb6a560da48f3bbaa0cc538ea8b7bf71" }, "version": "2.5.2" }, "org.apache.commons:commons-compress": { "shasums": { "jar": "d0ec8014ebbb0749f471803122b21796afddf2e98e194e4374622e5fbaf69f49" }, "version": "1.25.0" }, "org.apache.logging.log4j:log4j-api": { "shasums": { "jar": "5b4a0a0cd0e751ded431c162442bdbdd53328d1f8bb2bae5fc1bbeee0f66d80f" }, "version": "2.24.3" }, "org.apache.logging.log4j:log4j-to-slf4j": { "shasums": { "jar": "c7f2b0c612a4eb05b1587d1c880eb4cf5f4f53850676a8ede8da2b8fabb4f73f" }, "version": "2.24.3" }, "org.apache.tomcat.embed:tomcat-embed-core": { "shasums": { "jar": "1a488786e23293aef05c12c14d375b6649e85a312f8d1db23d9274196b7b0eb5" }, "version": "10.1.39" }, "org.apache.tomcat.embed:tomcat-embed-el": { "shasums": { "jar": "de993a5a8af0b6ca6473ba59b95026d7ded93de3a1683d9fb7753b7b76d38ee7" }, "version": "10.1.39" }, "org.apache.tomcat.embed:tomcat-embed-websocket": { "shasums": { "jar": "3b4fb77c4df8c523ec631a817936c4dff152386d4451090f03cb18425bfd8aaf" }, "version": "10.1.39" }, "org.apiguardian:apiguardian-api": { "shasums": { "jar": "b509448ac506d607319f182537f0b35d71007582ec741832a1f111e5b5b70b38" }, "version": "1.1.2" }, "org.aspectj:aspectjweaver": { "shasums": { "jar": "cd2dd01ec2424c05669df4d557f6c6cd7ed87b05257ee3c866b4c5b116b18a78" }, "version": "1.9.22.1" }, "org.assertj:assertj-core": { "shasums": { "jar": "4c2f86418ff47ee6b67fbc6adb194e80219b793281b3bda28799d4425bc9a0bd" }, "version": "3.26.3" }, "org.attoparser:attoparser": { "shasums": { "jar": "75dd1c045492bff8e1963aabb28bfe903c2064e11e27fe2f0f0aff1ad3d84476" }, "version": "2.0.7.RELEASE" }, "org.awaitility:awaitility": { "shasums": { "jar": "e831fee30ed401e2208f1bd5a0ef9add538d9cb1103c0e43216691b647bde9c6" }, "version": "4.2.2" }, "org.checkerframework:checker-compat-qual": { "shasums": { "jar": "d76b9afea61c7c082908023f0cbc1427fab9abd2df915c8b8a3e7a509bccbc6d" }, "version": "2.5.3" }, "org.checkerframework:checker-qual": { "shasums": { "jar": "e316255bbfcd9fe50d165314b85abb2b33cb2a66a93c491db648e498a82c2de1" }, "version": "3.33.0" }, "org.eclipse.jetty.ee10.websocket:jetty-ee10-websocket-jakarta-client": { "shasums": { "jar": "39ae38c9557fe7caaa1f1bc4d17ceb2371c2c22e04142e2b6a0fb885256c7f51" }, "version": "12.0.18" }, "org.eclipse.jetty.ee10.websocket:jetty-ee10-websocket-jakarta-common": { "shasums": { "jar": "20bf9c4bcf43ce40f6f2279a67891a9302c4ee958d89b324a675aa8c2961aa02" }, "version": "12.0.18" }, "org.eclipse.jetty.ee10.websocket:jetty-ee10-websocket-jakarta-server": { "shasums": { "jar": "a295318242248d16b7efbeff99de2ce7b968af2b94032db3b1c56586ac78ecf4" }, "version": "12.0.18" }, "org.eclipse.jetty.ee10.websocket:jetty-ee10-websocket-jetty-server": { "shasums": { "jar": "720ba8972ce908bb6f3346e7635337b73b23f1b1c96bfed6d8bf9f4f2fcd1b02" }, "version": "12.0.18" }, "org.eclipse.jetty.ee10.websocket:jetty-ee10-websocket-servlet": { "shasums": { "jar": "c10bfd34b4042fdea16771520a2ac7a01e3394b483316e83432c8ea6c66c7f45" }, "version": "12.0.18" }, "org.eclipse.jetty.ee10:jetty-ee10-annotations": { "shasums": { "jar": "6ddfe086147eb648560c39cc6ec2daa2aa21a9783a521cc242145a9a5b0dde3b" }, "version": "12.0.18" }, "org.eclipse.jetty.ee10:jetty-ee10-plus": { "shasums": { "jar": "20e74b84e7f584795d1df246007bbf1229b35e6e3231b7678707b5969e9ef550" }, "version": "12.0.18" }, "org.eclipse.jetty.ee10:jetty-ee10-servlet": { "shasums": { "jar": "eaa998fd854d64fe161c822d21f0745986954db5c817ae7b83c3b13e94aa3e06" }, "version": "12.0.18" }, "org.eclipse.jetty.ee10:jetty-ee10-servlets": { "shasums": { "jar": "4adcaedb3a5dd75c55e345b04c457e24da293312563cd08474ef8d5a0b019d0d" }, "version": "12.0.18" }, "org.eclipse.jetty.ee10:jetty-ee10-webapp": { "shasums": { "jar": "c03115edb4a682bdb49ec8245f0acd7ecd25805caf2fbdd50eeac342d56af250" }, "version": "12.0.18" }, "org.eclipse.jetty.websocket:jetty-websocket-core-client": { "shasums": { "jar": "d67d396cdcb673d60742f80e42810b9193dd9f2aeec2692714acdeca7dfbe634" }, "version": "12.0.18" }, "org.eclipse.jetty.websocket:jetty-websocket-core-common": { "shasums": { "jar": "427ec242bc57c02638dd19c2c8d4bf66ebeea52ae58ad6d6a9b4013af88bb201" }, "version": "12.0.18" }, "org.eclipse.jetty.websocket:jetty-websocket-core-server": { "shasums": { "jar": "698163a545e21de0d6a330f0a082f81d4e96988703bea4881825fca4bd21d6f4" }, "version": "12.0.18" }, "org.eclipse.jetty.websocket:jetty-websocket-jetty-api": { "shasums": { "jar": "9ddc0de474bcc065b5cbb4682bb2f3a03f214e77268752c71f082a26683431ca" }, "version": "12.0.18" }, "org.eclipse.jetty.websocket:jetty-websocket-jetty-common": { "shasums": { "jar": "0a0b71ddaed72b8f71c47fe37cceda1ebacfaae69020038d12ec75e2791b15ce" }, "version": "12.0.18" }, "org.eclipse.jetty:jetty-alpn-client": { "shasums": { "jar": "e43c7c5a4cbb605089835b4d73c094768af965eba4bff702f905fe1750bc3846" }, "version": "12.0.18" }, "org.eclipse.jetty:jetty-client": { "shasums": { "jar": "f061ea09047445a79177591f0103deff0e0bdf352027462f094cfe486f0ed30f" }, "version": "12.0.18" }, "org.eclipse.jetty:jetty-ee": { "shasums": { "jar": "c2698b929cd5a2d0122d5c9c6be5daaebbe3fbb8984e925882e277716a14806f" }, "version": "12.0.18" }, "org.eclipse.jetty:jetty-http": { "shasums": { "jar": "640cf950ebad1f88d5a96e46548a34ff8da418b6171e2bc2e30e73f49111b068" }, "version": "12.0.18" }, "org.eclipse.jetty:jetty-io": { "shasums": { "jar": "2528c3240b0615fd735ef67825ee7cd7a2f430e405fd57eed756377d2d0702a7" }, "version": "12.0.18" }, "org.eclipse.jetty:jetty-plus": { "shasums": { "jar": "adedbee25414d4f2b76f641b346c9799494e384b2e14f55df8273f48f90b6be0" }, "version": "12.0.18" }, "org.eclipse.jetty:jetty-security": { "shasums": { "jar": "e98507bf4c273b22ad7bf54910032d0948a9ba838529260f1b91a8d60c76b749" }, "version": "12.0.18" }, "org.eclipse.jetty:jetty-server": { "shasums": { "jar": "118c8f784ffcbf4a69e1018b871fd396cd4ec631fc6f764fe958beb091e50568" }, "version": "12.0.18" }, "org.eclipse.jetty:jetty-session": { "shasums": { "jar": "b69800641f1e9adc15940dbbf226506f4154f543a52a036268e5e298fab85f87" }, "version": "12.0.18" }, "org.eclipse.jetty:jetty-util": { "shasums": { "jar": "c4c9e7435f7f005a74f746d94952e148ec803356e20c99e6d46a52f896e1e413" }, "version": "12.0.18" }, "org.eclipse.jetty:jetty-xml": { "shasums": { "jar": "4c228050d6a0e0fff22844bab9607d2f9093c39f6faea68dec53024448ab441c" }, "version": "12.0.18" }, "org.freemarker:freemarker": { "shasums": { "jar": "9a9fb91cd64199232eb1ca9766148a5d30ef8944be5fac051018f96c70c8f6a3" }, "version": "2.3.34" }, "org.hamcrest:hamcrest": { "shasums": { "jar": "5e62846a89f05cd78cd9c1a553f340d002458380c320455dd1f8fc5497a8a1c1" }, "version": "2.2" }, "org.hamcrest:hamcrest-core": { "shasums": { "jar": "094f5d92b4b7d9c8a2bf53cc69d356243ae89c3499457bcb4b92f7ed3bf95879" }, "version": "2.2" }, "org.hdrhistogram:HdrHistogram": { "shasums": { "jar": "22d1d4316c4ec13a68b559e98c8256d69071593731da96136640f864fa14fad8" }, "version": "2.2.2" }, "org.junit.jupiter:junit-jupiter": { "shasums": { "jar": "aa880e4afba87d447357e4c1fc098c5cb1d200cb9403496c00d3b35a5bd0e8db" }, "version": "5.11.4" }, "org.junit.jupiter:junit-jupiter-api": { "shasums": { "jar": "ab83ef9e51ac4597d59d26b4b58812129550e2f579a404c8af7d09f5ce5b4293" }, "version": "5.11.4" }, "org.junit.jupiter:junit-jupiter-engine": { "shasums": { "jar": "cdf8ac59f3fad774ca738ad03890950eeb91833ef0e8908753177edd26f1581c" }, "version": "5.11.4" }, "org.junit.jupiter:junit-jupiter-params": { "shasums": { "jar": "02a6e015de7ce94ac7f256e7fa05b8091dea861fe79a555a7993313d0f6c7d96" }, "version": "5.11.4" }, "org.junit.platform:junit-platform-commons": { "shasums": { "jar": "9edd969b0d0670c54105bc91ae79bd1c6f503e12115faba82073b84c86bbc334" }, "version": "1.11.4" }, "org.junit.platform:junit-platform-engine": { "shasums": { "jar": "b1dd998f64f9acadc15966d9cd3d08074662677b3e390f0a38fcbf0bb4c72330" }, "version": "1.11.4" }, "org.latencyutils:LatencyUtils": { "shasums": { "jar": "a32a9ffa06b2f4e01c5360f8f9df7bc5d9454a5d373cd8f361347fa5a57165ec" }, "version": "2.0.3" }, "org.mockito:mockito-core": { "shasums": { "jar": "2296141c1e1f2e1ae35c08d36a9ab4563ecd66e03533fe82630a764e7aa49182" }, "version": "5.14.2" }, "org.mockito:mockito-junit-jupiter": { "shasums": { "jar": "9a126e3bf6dd31826a138523c17f49de12b3243f3b5616b9ea977542e4a47a09" }, "version": "5.14.2" }, "org.objenesis:objenesis": { "shasums": { "jar": "02dfd0b0439a5591e35b708ed2f5474eb0948f53abf74637e959b8e4ef69bfeb" }, "version": "3.3" }, "org.opentest4j:opentest4j": { "shasums": { "jar": "48e2df636cab6563ced64dcdff8abb2355627cb236ef0bf37598682ddf742f1b" }, "version": "1.3.0" }, "org.osgi:org.osgi.dto": { "shasums": { "jar": "cb75f3c7e48e5a31a31df22e26873346f5bf659e2dcab2369e031e4850d2ff43" }, "version": "1.0.0" }, "org.osgi:org.osgi.framework": { "shasums": { "jar": "ec194b7871af27681716ff05259319a5c3c9b9727e8000e9e832499b93484b4e" }, "version": "1.8.0" }, "org.osgi:org.osgi.resource": { "shasums": { "jar": "81fc50f1f1d38a4af28e131907d4afe213249aab05060484edca0e60c4af9b4a" }, "version": "1.0.0" }, "org.osgi:org.osgi.service.log": { "shasums": { "jar": "ff6710c4856d32684cf3ebdc45248f41036ff734f2b03bbc08c4609a61fecfa0" }, "version": "1.3.0" }, "org.osgi:org.osgi.service.repository": { "shasums": { "jar": "c5553e95b459529192433486d4c4cc22ff45a2eae4968484f9f717319264a532" }, "version": "1.1.0" }, "org.osgi:org.osgi.util.function": { "shasums": { "jar": "208819c7c71690c15a6bb8b187474e7f9d0147946b680182a62b9f222ae014ec" }, "version": "1.2.0" }, "org.osgi:org.osgi.util.promise": { "shasums": { "jar": "fef86e64f584d012a16a0306160764f6179663b90988a226c4641b920f3a4b36" }, "version": "1.2.0" }, "org.osgi:org.osgi.util.tracker": { "shasums": { "jar": "7d78c2cc9bcb6421c24f17aa097866ce8d9115c219a4f8d6cc753bc4dfb97efa" }, "version": "1.5.4" }, "org.osgi:osgi.annotation": { "shasums": { "jar": "a0e8a4c362bd3600812f37b0ea45fba966c7bc049d01fed56a09ecc74082759e" }, "version": "8.0.1" }, "org.ow2.asm:asm": { "shasums": { "jar": "8cadd43ac5eb6d09de05faecca38b917a040bb9139c7edeb4cc81c740b713281" }, "version": "9.7.1" }, "org.ow2.asm:asm-analysis": { "shasums": { "jar": "be922aae60ff1ff1768e8e6544a38a7f92bd0a6d6b0b9791f94955d1bd453de2" }, "version": "7.2" }, "org.ow2.asm:asm-commons": { "shasums": { "jar": "9a579b54d292ad9be171d4313fd4739c635592c2b5ac3a459bbd1049cddec6a0" }, "version": "9.7.1" }, "org.ow2.asm:asm-tree": { "shasums": { "jar": "9929881f59eb6b840e86d54570c77b59ce721d104e6dfd7a40978991c2d3b41f" }, "version": "9.7.1" }, "org.ow2.asm:asm-util": { "shasums": { "jar": "6e24913b021ffacfe8e7e053d6e0ccc731941148cfa078d4f1ed3d96904530f8" }, "version": "7.2" }, "org.skyscreamer:jsonassert": { "shasums": { "jar": "719095c07d4203961320da593441d8b3b643c18eb1d81aa98ea933bb7eb351ba" }, "version": "1.5.3" }, "org.slf4j:jul-to-slf4j": { "shasums": { "jar": "a7afcd23b9cfd1475e55c94f943b808c5922035e7e2c2a5c65a487a4106bc538" }, "version": "2.0.17" }, "org.slf4j:slf4j-api": { "shasums": { "jar": "7b751d952061954d5abfed7181c1f645d336091b679891591d63329c622eb832" }, "version": "2.0.17" }, "org.springframework.boot:spring-boot": { "shasums": { "jar": "f134d42d19c1f707408e2ce6ace8d5887a9e7c3e50a351a75ada80afbbd6ecaf" }, "version": "3.4.4" }, "org.springframework.boot:spring-boot-actuator": { "shasums": { "jar": "94c1c6c9af96d4d2ca4af55b80c778b9750fcc63a378893f5873122b3b9c0dfc" }, "version": "3.4.4" }, "org.springframework.boot:spring-boot-actuator-autoconfigure": { "shasums": { "jar": "bed2fa189789b95d511ce1838dff9c041a34c93dac6f903c3a86959db033b7ac" }, "version": "3.4.4" }, "org.springframework.boot:spring-boot-autoconfigure": { "shasums": { "jar": "04a3b4f7c4e0ab39fb8b4dd77a2092ed5c036961133d278060af14455dc55d39" }, "version": "3.4.4" }, "org.springframework.boot:spring-boot-configuration-processor": { "shasums": { "jar": "b2db830eb773c97f7afe6b932af9b4cceded82ef44f7ef7da9855f63c1491791" }, "version": "3.4.4" }, "org.springframework.boot:spring-boot-jarmode-tools": { "shasums": { "jar": "c5e02a90aa82ef90a4770b75a6534dabee50702d1b7cefa38188a997f2308bdb" }, "version": "3.4.4" }, "org.springframework.boot:spring-boot-loader": { "shasums": { "jar": "55b6362f3b1c73b59f6b38d8fa6eca2cb576ee004650970c437e7b8f5c39c471" }, "version": "3.4.4" }, "org.springframework.boot:spring-boot-loader-tools": { "shasums": { "jar": "5b0d1f1c1d600f700c6d20b74c04f6e825b3f166ddd21b95d1930c04df9af5f7" }, "version": "3.4.4" }, "org.springframework.boot:spring-boot-starter": { "shasums": { "jar": "2fcdc0037fd1c0acebb4b1ef700818c97d8457fabc6d5bebc3878f584c1c727f" }, "version": "3.4.4" }, "org.springframework.boot:spring-boot-starter-actuator": { "shasums": { "jar": "738e74d67afbeb229ead61d3e233477ee9b45f007789079a5afd7f839ba417cf" }, "version": "3.4.4" }, "org.springframework.boot:spring-boot-starter-freemarker": { "shasums": { "jar": "c7bd38b5acbcaa51d3f1bdd5f994a0aa95271c041ff9d373235b9b192fe60f22" }, "version": "3.4.4" }, "org.springframework.boot:spring-boot-starter-jdbc": { "shasums": { "jar": "170abba02cb4b7d5bbda965872d54d587ec1fa7cd0494337ba6a29440b744e58" }, "version": "3.4.4" }, "org.springframework.boot:spring-boot-starter-jetty": { "shasums": { "jar": "8996a1b5038f95052515fe330e6769c0f4bde4de8b84d4b3a4039772ff134fa2" }, "version": "3.4.4" }, "org.springframework.boot:spring-boot-starter-json": { "shasums": { "jar": "c92ddd6f7d109a517391a59c0d9d4f0256d5c5ba8db5d1af4710e0ca17fdf2c2" }, "version": "3.4.4" }, "org.springframework.boot:spring-boot-starter-logging": { "shasums": { "jar": "1fcd1236a38b5eebc357527c058070669272b7b60c8394f887db882b4b47a240" }, "version": "3.4.4" }, "org.springframework.boot:spring-boot-starter-security": { "shasums": { "jar": "796452c20a9a0b46ed721d6f32fd35daf84074e8e345cec8318ad1217d08e7f1" }, "version": "3.4.4" }, "org.springframework.boot:spring-boot-starter-test": { "shasums": { "jar": "ef3e20f5cc7046ca4e79f5c756ff6a2b3d104acd43facf3e7cfefec7a15e8c08" }, "version": "3.4.4" }, "org.springframework.boot:spring-boot-starter-thymeleaf": { "shasums": { "jar": "cb6cd3fe4392b50bf58ec8ac20b103bbf15a3fcc1fda4891fb298e269ba8c1ee" }, "version": "3.4.4" }, "org.springframework.boot:spring-boot-starter-tomcat": { "shasums": { "jar": "fdae817f961cfc561af6f305895a2d334a3986bd4544d469e26a321814edff54" }, "version": "3.4.4" }, "org.springframework.boot:spring-boot-starter-web": { "shasums": { "jar": "c628b8d0d7c830c7ea3bc125950e11332b7ce3779ebd6d655f183e456ffe4481" }, "version": "3.4.4" }, "org.springframework.boot:spring-boot-test": { "shasums": { "jar": "bc69584886005c5607d89120fba3750bc689396c12586b6b917e21bd5bb92b15" }, "version": "3.4.4" }, "org.springframework.boot:spring-boot-test-autoconfigure": { "shasums": { "jar": "89626caa8edf7d47de5a8b6988c20b89abf4d73a04640d40fba3ad944399113a" }, "version": "3.4.4" }, "org.springframework.security:spring-security-config": { "shasums": { "jar": "f13f2365b4af41b33e40af657014db773de858d84c74f34c9ada471c96f9c169" }, "version": "6.4.4" }, "org.springframework.security:spring-security-core": { "shasums": { "jar": "d9f7ca559ecadc0700555fc16cbd4c8bdfbbedd2474f5fd1f0c429bed946658d" }, "version": "6.4.4" }, "org.springframework.security:spring-security-crypto": { "shasums": { "jar": "62b3424be620e457146a51a3da9aa878ee9874667cd2498d73085a8394d36940" }, "version": "6.4.4" }, "org.springframework.security:spring-security-web": { "shasums": { "jar": "7705eec34c86607d3e2c81965d20584fa46819baf311aa3e9381deebbeceb9a4" }, "version": "6.4.4" }, "org.springframework:spring-aop": { "shasums": { "jar": "dfde58e5b277e12e464d5f0d7d60c49ce10c96da94aa32a196a8711467af7dd8" }, "version": "6.2.5" }, "org.springframework:spring-aspects": { "shasums": { "jar": "4f8ef69ffc4cb3d651596a00f53b29dc813e40e75523ed5213547e20b47d8d8d" }, "version": "6.2.5" }, "org.springframework:spring-beans": { "shasums": { "jar": "63f7ff64a72187d71c402f8c77c5fe6ba9d38e03465e4f9a601c3522265051d4" }, "version": "6.2.5" }, "org.springframework:spring-context": { "shasums": { "jar": "21941e0c9f23310c78403f35a624b27f3a1301f1ccf5de250d7478956e7bab51" }, "version": "6.2.5" }, "org.springframework:spring-context-support": { "shasums": { "jar": "93f2de3b6236dd82ea52f3f184c1c3bd49496162d87f06ddbc426058905fcda7" }, "version": "6.2.5" }, "org.springframework:spring-core": { "shasums": { "jar": "4cee02cf2d0227c1f1bfb97c2edc29d3af83b93c83d08b38e5987c3fa0fe4f1e" }, "version": "6.2.5" }, "org.springframework:spring-expression": { "shasums": { "jar": "ec76c41d4e45779b48ae10020322b32ecb2e2f4f2d930b0d93844a44490d76c5" }, "version": "6.2.5" }, "org.springframework:spring-jcl": { "shasums": { "jar": "4f93915fab10c14df3b90054cfd5d1c01a29def59b6e25c0f33d9eac4ffec079" }, "version": "6.2.5" }, "org.springframework:spring-jdbc": { "shasums": { "jar": "2268b0a2fb0877f47677f6ea67f283d972b9591f4cd28d63719a3dfbabcd0a2d" }, "version": "6.2.5" }, "org.springframework:spring-test": { "shasums": { "jar": "5585586296cf9778d8d027971b529746561e0d9b2953d00956b27a1f5b1f0d7e" }, "version": "6.2.5" }, "org.springframework:spring-tx": { "shasums": { "jar": "a0fc4f275e04cf1b31dde8b5348e10ed03372cd734c6e3d14e0863263794a9e0" }, "version": "6.2.5" }, "org.springframework:spring-web": { "shasums": { "jar": "85f0c1acaf033a5f7abdcaf348f1dd2cebe1f77687ee77f05e8cb66bfbc6fecf" }, "version": "6.2.5" }, "org.springframework:spring-webmvc": { "shasums": { "jar": "b8d281aedf1e9cbf73bb2c6cf72d3eaf811f9298b2dc5017e9c40b3cb9284b46" }, "version": "6.2.5" }, "org.thymeleaf:thymeleaf": { "shasums": { "jar": "165ef16cd71020c4d572e77d73cf7baffd431f3f3e8c1d84b410de23dc79f92c" }, "version": "3.1.3.RELEASE" }, "org.thymeleaf:thymeleaf-spring6": { "shasums": { "jar": "79c7f0897008831e9cf87315c8ca452e5ea95d32cbf04648dc11f9e6bad0a50e" }, "version": "3.1.3.RELEASE" }, "org.unbescape:unbescape": { "shasums": { "jar": "597cf87d5b1a4f385b9d1cec974b7b483abb3ee85fc5b3f8b62af8e4bec95c2c" }, "version": "1.1.6.RELEASE" }, "org.xmlunit:xmlunit-core": { "shasums": { "jar": "3f89b0a629d3d9cca66e15f8dde5e0947852fa44172bc77ea26edf96e3e4fcf8" }, "version": "2.10.0" }, "org.yaml:snakeyaml": { "shasums": { "jar": "63a76fe66b652360bd4c2c107e6f0258daa7d4bb492008ba8c26fcd230ff9146" }, "version": "2.3" } }, "dependencies": { "biz.aQute.bnd:biz.aQute.bndlib": [ "biz.aQute.bnd:biz.aQute.bnd.util", "org.osgi:org.osgi.dto", "org.osgi:org.osgi.framework", "org.osgi:org.osgi.resource", "org.osgi:org.osgi.service.log", "org.osgi:org.osgi.service.repository", "org.osgi:org.osgi.util.function", "org.osgi:org.osgi.util.promise", "org.osgi:org.osgi.util.tracker", "org.slf4j:slf4j-api" ], "ch.qos.logback:logback-classic": [ "ch.qos.logback:logback-core", "org.slf4j:slf4j-api" ], "com.fasterxml.jackson.core:jackson-databind": [ "com.fasterxml.jackson.core:jackson-annotations", "com.fasterxml.jackson.core:jackson-core" ], "com.fasterxml.jackson.datatype:jackson-datatype-jdk8": [ "com.fasterxml.jackson.core:jackson-core", "com.fasterxml.jackson.core:jackson-databind" ], "com.fasterxml.jackson.datatype:jackson-datatype-jsr310": [ "com.fasterxml.jackson.core:jackson-annotations", "com.fasterxml.jackson.core:jackson-core", "com.fasterxml.jackson.core:jackson-databind" ], "com.fasterxml.jackson.module:jackson-module-parameter-names": [ "com.fasterxml.jackson.core:jackson-core", "com.fasterxml.jackson.core:jackson-databind" ], "com.google.caliper:caliper": [ "com.google.caliper:caliper-core", "com.google.caliper:caliper-runner", "com.google.caliper:caliper-worker-jvm", "com.google.code.java-allocation-instrumenter:java-allocation-instrumenter", "com.google.dagger:dagger", "com.google.guava:guava", "com.sun.jersey:jersey-client" ], "com.google.caliper:caliper-api": [ "com.google.guava:guava", "joda-time:joda-time" ], "com.google.caliper:caliper-core": [ "com.google.auto.value:auto-value-annotations", "com.google.caliper:caliper-api", "com.google.caliper:caliper-util", "com.google.dagger:dagger", "com.google.guava:guava", "com.squareup.okhttp:okhttp", "joda-time:joda-time" ], "com.google.caliper:caliper-runner": [ "com.google.caliper:caliper-api", "com.google.caliper:caliper-core", "com.google.caliper:caliper-util", "com.google.dagger:dagger", "com.google.dagger:dagger-producers", "com.google.guava:guava", "com.squareup.okhttp:okhttp", "joda-time:joda-time" ], "com.google.caliper:caliper-util": [ "com.google.code.gson:gson", "com.google.dagger:dagger", "com.google.guava:guava", "joda-time:joda-time" ], "com.google.caliper:caliper-worker": [ "com.google.caliper:caliper-api", "com.google.caliper:caliper-core", "com.google.caliper:caliper-util", "com.google.dagger:dagger", "com.google.guava:guava", "com.squareup.okhttp:okhttp", "joda-time:joda-time" ], "com.google.caliper:caliper-worker-jvm": [ "com.google.caliper:caliper-core", "com.google.caliper:caliper-worker", "com.google.code.java-allocation-instrumenter:java-allocation-instrumenter", "com.google.dagger:dagger", "com.google.guava:guava", "com.sun.jersey:jersey-client" ], "com.google.code.java-allocation-instrumenter:java-allocation-instrumenter": [ "com.google.guava:guava", "javax.annotation:javax.annotation-api", "org.ow2.asm:asm", "org.ow2.asm:asm-analysis", "org.ow2.asm:asm-commons", "org.ow2.asm:asm-tree", "org.ow2.asm:asm-util" ], "com.google.dagger:dagger": [ "javax.inject:javax.inject" ], "com.google.dagger:dagger-producers": [ "com.google.dagger:dagger", "com.google.guava:guava", "javax.inject:javax.inject", "org.checkerframework:checker-compat-qual" ], "com.google.guava:guava": [ "com.google.code.findbugs:jsr305", "com.google.errorprone:error_prone_annotations", "com.google.guava:failureaccess", "com.google.guava:listenablefuture", "com.google.j2objc:j2objc-annotations", "org.checkerframework:checker-qual" ], "com.google.guava:guava-testlib": [ "com.google.code.findbugs:jsr305", "com.google.errorprone:error_prone_annotations", "com.google.guava:guava", "com.google.j2objc:j2objc-annotations", "junit:junit", "org.checkerframework:checker-qual" ], "com.google.truth:truth": [ "com.google.auto.value:auto-value-annotations", "com.google.errorprone:error_prone_annotations", "com.google.guava:guava", "junit:junit", "org.checkerframework:checker-qual", "org.ow2.asm:asm" ], "com.jayway.jsonpath:json-path": [ "net.minidev:json-smart", "org.slf4j:slf4j-api" ], "com.squareup.okhttp:okhttp": [ "com.squareup.okio:okio" ], "com.sun.jersey:jersey-client": [ "com.sun.jersey:jersey-core" ], "com.sun.jersey:jersey-core": [ "javax.ws.rs:jsr311-api" ], "com.zaxxer:HikariCP": [ "org.slf4j:slf4j-api" ], "io.micrometer:micrometer-core": [ "io.micrometer:micrometer-commons", "io.micrometer:micrometer-observation", "org.hdrhistogram:HdrHistogram", "org.latencyutils:LatencyUtils" ], "io.micrometer:micrometer-jakarta9": [ "io.micrometer:micrometer-commons", "io.micrometer:micrometer-core", "io.micrometer:micrometer-observation" ], "io.micrometer:micrometer-observation": [ "io.micrometer:micrometer-commons" ], "jakarta.enterprise:jakarta.enterprise.cdi-api": [ "jakarta.annotation:jakarta.annotation-api", "jakarta.enterprise:jakarta.enterprise.lang-model", "jakarta.inject:jakarta.inject-api", "jakarta.interceptor:jakarta.interceptor-api" ], "jakarta.interceptor:jakarta.interceptor-api": [ "jakarta.annotation:jakarta.annotation-api" ], "jakarta.xml.bind:jakarta.xml.bind-api": [ "jakarta.activation:jakarta.activation-api" ], "junit:junit": [ "org.hamcrest:hamcrest-core" ], "net.minidev:accessors-smart": [ "org.ow2.asm:asm" ], "net.minidev:json-smart": [ "net.minidev:accessors-smart" ], "org.apache.logging.log4j:log4j-to-slf4j": [ "org.apache.logging.log4j:log4j-api", "org.slf4j:slf4j-api" ], "org.apache.tomcat.embed:tomcat-embed-websocket": [ "org.apache.tomcat.embed:tomcat-embed-core" ], "org.assertj:assertj-core": [ "net.bytebuddy:byte-buddy" ], "org.awaitility:awaitility": [ "org.hamcrest:hamcrest" ], "org.eclipse.jetty.ee10.websocket:jetty-ee10-websocket-jakarta-client": [ "jakarta.websocket:jakarta.websocket-api", "jakarta.websocket:jakarta.websocket-client-api", "org.eclipse.jetty.ee10.websocket:jetty-ee10-websocket-jakarta-common", "org.eclipse.jetty.websocket:jetty-websocket-core-client", "org.eclipse.jetty:jetty-client" ], "org.eclipse.jetty.ee10.websocket:jetty-ee10-websocket-jakarta-common": [ "jakarta.websocket:jakarta.websocket-api", "jakarta.websocket:jakarta.websocket-client-api", "org.eclipse.jetty.websocket:jetty-websocket-core-client", "org.slf4j:slf4j-api" ], "org.eclipse.jetty.ee10.websocket:jetty-ee10-websocket-jakarta-server": [ "jakarta.websocket:jakarta.websocket-api", "org.eclipse.jetty.ee10.websocket:jetty-ee10-websocket-jakarta-client", "org.eclipse.jetty.ee10.websocket:jetty-ee10-websocket-servlet", "org.eclipse.jetty.ee10:jetty-ee10-annotations", "org.slf4j:slf4j-api" ], "org.eclipse.jetty.ee10.websocket:jetty-ee10-websocket-jetty-server": [ "jakarta.servlet:jakarta.servlet-api", "org.eclipse.jetty.ee10.websocket:jetty-ee10-websocket-servlet", "org.eclipse.jetty.ee10:jetty-ee10-annotations", "org.eclipse.jetty.ee10:jetty-ee10-servlet", "org.eclipse.jetty.websocket:jetty-websocket-jetty-api", "org.eclipse.jetty.websocket:jetty-websocket-jetty-common", "org.slf4j:slf4j-api" ], "org.eclipse.jetty.ee10.websocket:jetty-ee10-websocket-servlet": [ "org.eclipse.jetty.ee10:jetty-ee10-servlet", "org.eclipse.jetty.websocket:jetty-websocket-core-server", "org.slf4j:slf4j-api" ], "org.eclipse.jetty.ee10:jetty-ee10-annotations": [ "jakarta.annotation:jakarta.annotation-api", "jakarta.servlet:jakarta.servlet-api", "org.eclipse.jetty.ee10:jetty-ee10-plus", "org.eclipse.jetty.ee10:jetty-ee10-webapp", "org.ow2.asm:asm", "org.ow2.asm:asm-commons", "org.slf4j:slf4j-api" ], "org.eclipse.jetty.ee10:jetty-ee10-plus": [ "jakarta.enterprise:jakarta.enterprise.cdi-api", "jakarta.enterprise:jakarta.enterprise.lang-model", "jakarta.interceptor:jakarta.interceptor-api", "jakarta.transaction:jakarta.transaction-api", "org.eclipse.jetty.ee10:jetty-ee10-webapp", "org.eclipse.jetty:jetty-plus", "org.slf4j:slf4j-api" ], "org.eclipse.jetty.ee10:jetty-ee10-servlet": [ "jakarta.servlet:jakarta.servlet-api", "org.eclipse.jetty:jetty-security", "org.eclipse.jetty:jetty-server", "org.eclipse.jetty:jetty-session", "org.slf4j:slf4j-api" ], "org.eclipse.jetty.ee10:jetty-ee10-servlets": [ "org.eclipse.jetty:jetty-http", "org.eclipse.jetty:jetty-io", "org.eclipse.jetty:jetty-util", "org.slf4j:slf4j-api" ], "org.eclipse.jetty.ee10:jetty-ee10-webapp": [ "org.eclipse.jetty.ee10:jetty-ee10-servlet", "org.eclipse.jetty:jetty-ee", "org.eclipse.jetty:jetty-session", "org.eclipse.jetty:jetty-xml", "org.slf4j:slf4j-api" ], "org.eclipse.jetty.websocket:jetty-websocket-core-client": [ "org.eclipse.jetty.websocket:jetty-websocket-core-common", "org.eclipse.jetty:jetty-client" ], "org.eclipse.jetty.websocket:jetty-websocket-core-common": [ "org.eclipse.jetty:jetty-http", "org.eclipse.jetty:jetty-io", "org.slf4j:slf4j-api" ], "org.eclipse.jetty.websocket:jetty-websocket-core-server": [ "org.eclipse.jetty.websocket:jetty-websocket-core-common", "org.eclipse.jetty:jetty-server" ], "org.eclipse.jetty.websocket:jetty-websocket-jetty-common": [ "org.eclipse.jetty.websocket:jetty-websocket-core-common", "org.eclipse.jetty.websocket:jetty-websocket-jetty-api" ], "org.eclipse.jetty:jetty-alpn-client": [ "org.eclipse.jetty:jetty-io", "org.slf4j:slf4j-api" ], "org.eclipse.jetty:jetty-client": [ "org.eclipse.jetty:jetty-alpn-client", "org.eclipse.jetty:jetty-http", "org.eclipse.jetty:jetty-io", "org.slf4j:slf4j-api" ], "org.eclipse.jetty:jetty-ee": [ "org.eclipse.jetty:jetty-server", "org.slf4j:slf4j-api" ], "org.eclipse.jetty:jetty-http": [ "org.eclipse.jetty:jetty-io", "org.eclipse.jetty:jetty-util", "org.slf4j:slf4j-api" ], "org.eclipse.jetty:jetty-io": [ "org.eclipse.jetty:jetty-util", "org.slf4j:slf4j-api" ], "org.eclipse.jetty:jetty-plus": [ "org.eclipse.jetty:jetty-security", "org.eclipse.jetty:jetty-util", "org.slf4j:slf4j-api" ], "org.eclipse.jetty:jetty-security": [ "org.eclipse.jetty:jetty-server", "org.slf4j:slf4j-api" ], "org.eclipse.jetty:jetty-server": [ "org.eclipse.jetty:jetty-http", "org.eclipse.jetty:jetty-io", "org.slf4j:slf4j-api" ], "org.eclipse.jetty:jetty-session": [ "org.eclipse.jetty:jetty-server", "org.slf4j:slf4j-api" ], "org.eclipse.jetty:jetty-util": [ "org.slf4j:slf4j-api" ], "org.eclipse.jetty:jetty-xml": [ "org.eclipse.jetty:jetty-util", "org.slf4j:slf4j-api" ], "org.hamcrest:hamcrest-core": [ "org.hamcrest:hamcrest" ], "org.junit.jupiter:junit-jupiter": [ "org.junit.jupiter:junit-jupiter-api", "org.junit.jupiter:junit-jupiter-engine", "org.junit.jupiter:junit-jupiter-params" ], "org.junit.jupiter:junit-jupiter-api": [ "org.apiguardian:apiguardian-api", "org.junit.platform:junit-platform-commons", "org.opentest4j:opentest4j" ], "org.junit.jupiter:junit-jupiter-engine": [ "org.apiguardian:apiguardian-api", "org.junit.jupiter:junit-jupiter-api", "org.junit.platform:junit-platform-engine" ], "org.junit.jupiter:junit-jupiter-params": [ "org.apiguardian:apiguardian-api", "org.junit.jupiter:junit-jupiter-api" ], "org.junit.platform:junit-platform-commons": [ "org.apiguardian:apiguardian-api" ], "org.junit.platform:junit-platform-engine": [ "org.apiguardian:apiguardian-api", "org.junit.platform:junit-platform-commons", "org.opentest4j:opentest4j" ], "org.mockito:mockito-core": [ "net.bytebuddy:byte-buddy", "net.bytebuddy:byte-buddy-agent", "org.objenesis:objenesis" ], "org.mockito:mockito-junit-jupiter": [ "org.junit.jupiter:junit-jupiter-api", "org.mockito:mockito-core" ], "org.osgi:org.osgi.util.function": [ "org.osgi:osgi.annotation" ], "org.osgi:org.osgi.util.promise": [ "org.osgi:org.osgi.util.function", "org.osgi:osgi.annotation" ], "org.osgi:org.osgi.util.tracker": [ "org.osgi:osgi.annotation" ], "org.ow2.asm:asm-analysis": [ "org.ow2.asm:asm-tree" ], "org.ow2.asm:asm-commons": [ "org.ow2.asm:asm", "org.ow2.asm:asm-tree" ], "org.ow2.asm:asm-tree": [ "org.ow2.asm:asm" ], "org.ow2.asm:asm-util": [ "org.ow2.asm:asm", "org.ow2.asm:asm-analysis", "org.ow2.asm:asm-tree" ], "org.skyscreamer:jsonassert": [ "com.vaadin.external.google:android-json" ], "org.slf4j:jul-to-slf4j": [ "org.slf4j:slf4j-api" ], "org.springframework.boot:spring-boot": [ "org.springframework:spring-context", "org.springframework:spring-core" ], "org.springframework.boot:spring-boot-actuator": [ "org.springframework.boot:spring-boot" ], "org.springframework.boot:spring-boot-actuator-autoconfigure": [ "com.fasterxml.jackson.core:jackson-databind", "com.fasterxml.jackson.datatype:jackson-datatype-jsr310", "org.springframework.boot:spring-boot", "org.springframework.boot:spring-boot-actuator", "org.springframework.boot:spring-boot-autoconfigure" ], "org.springframework.boot:spring-boot-autoconfigure": [ "org.springframework.boot:spring-boot" ], "org.springframework.boot:spring-boot-jarmode-tools": [ "org.springframework.boot:spring-boot-loader", "org.springframework:spring-core" ], "org.springframework.boot:spring-boot-loader-tools": [ "org.apache.commons:commons-compress", "org.springframework:spring-core" ], "org.springframework.boot:spring-boot-starter": [ "jakarta.annotation:jakarta.annotation-api", "org.springframework.boot:spring-boot", "org.springframework.boot:spring-boot-autoconfigure", "org.springframework.boot:spring-boot-starter-logging", "org.springframework:spring-core", "org.yaml:snakeyaml" ], "org.springframework.boot:spring-boot-starter-actuator": [ "io.micrometer:micrometer-jakarta9", "io.micrometer:micrometer-observation", "org.springframework.boot:spring-boot-actuator-autoconfigure", "org.springframework.boot:spring-boot-starter" ], "org.springframework.boot:spring-boot-starter-freemarker": [ "org.freemarker:freemarker", "org.springframework.boot:spring-boot-starter", "org.springframework:spring-context-support" ], "org.springframework.boot:spring-boot-starter-jdbc": [ "com.zaxxer:HikariCP", "org.springframework.boot:spring-boot-starter", "org.springframework:spring-jdbc" ], "org.springframework.boot:spring-boot-starter-jetty": [ "jakarta.servlet:jakarta.servlet-api", "jakarta.websocket:jakarta.websocket-api", "jakarta.websocket:jakarta.websocket-client-api", "org.apache.tomcat.embed:tomcat-embed-el", "org.eclipse.jetty.ee10.websocket:jetty-ee10-websocket-jakarta-server", "org.eclipse.jetty.ee10.websocket:jetty-ee10-websocket-jetty-server", "org.eclipse.jetty.ee10:jetty-ee10-servlets", "org.eclipse.jetty.ee10:jetty-ee10-webapp" ], "org.springframework.boot:spring-boot-starter-json": [ "com.fasterxml.jackson.core:jackson-databind", "com.fasterxml.jackson.datatype:jackson-datatype-jdk8", "com.fasterxml.jackson.datatype:jackson-datatype-jsr310", "com.fasterxml.jackson.module:jackson-module-parameter-names", "org.springframework.boot:spring-boot-starter", "org.springframework:spring-web" ], "org.springframework.boot:spring-boot-starter-logging": [ "ch.qos.logback:logback-classic", "org.apache.logging.log4j:log4j-to-slf4j", "org.slf4j:jul-to-slf4j" ], "org.springframework.boot:spring-boot-starter-security": [ "org.springframework.boot:spring-boot-starter", "org.springframework.security:spring-security-config", "org.springframework.security:spring-security-web", "org.springframework:spring-aop" ], "org.springframework.boot:spring-boot-starter-test": [ "com.jayway.jsonpath:json-path", "jakarta.xml.bind:jakarta.xml.bind-api", "net.minidev:json-smart", "org.assertj:assertj-core", "org.awaitility:awaitility", "org.hamcrest:hamcrest", "org.junit.jupiter:junit-jupiter", "org.mockito:mockito-core", "org.mockito:mockito-junit-jupiter", "org.skyscreamer:jsonassert", "org.springframework.boot:spring-boot-starter", "org.springframework.boot:spring-boot-test", "org.springframework.boot:spring-boot-test-autoconfigure", "org.springframework:spring-core", "org.springframework:spring-test", "org.xmlunit:xmlunit-core" ], "org.springframework.boot:spring-boot-starter-thymeleaf": [ "org.springframework.boot:spring-boot-starter", "org.thymeleaf:thymeleaf-spring6" ], "org.springframework.boot:spring-boot-starter-tomcat": [ "jakarta.annotation:jakarta.annotation-api", "org.apache.tomcat.embed:tomcat-embed-core", "org.apache.tomcat.embed:tomcat-embed-el", "org.apache.tomcat.embed:tomcat-embed-websocket" ], "org.springframework.boot:spring-boot-starter-web": [ "org.springframework.boot:spring-boot-starter", "org.springframework.boot:spring-boot-starter-json", "org.springframework.boot:spring-boot-starter-tomcat", "org.springframework:spring-web", "org.springframework:spring-webmvc" ], "org.springframework.boot:spring-boot-test": [ "org.springframework.boot:spring-boot", "org.springframework:spring-test" ], "org.springframework.boot:spring-boot-test-autoconfigure": [ "org.springframework.boot:spring-boot", "org.springframework.boot:spring-boot-autoconfigure", "org.springframework.boot:spring-boot-test" ], "org.springframework.security:spring-security-config": [ "org.springframework.security:spring-security-core", "org.springframework:spring-aop", "org.springframework:spring-beans", "org.springframework:spring-context", "org.springframework:spring-core" ], "org.springframework.security:spring-security-core": [ "io.micrometer:micrometer-observation", "org.springframework.security:spring-security-crypto", "org.springframework:spring-aop", "org.springframework:spring-beans", "org.springframework:spring-context", "org.springframework:spring-core", "org.springframework:spring-expression" ], "org.springframework.security:spring-security-web": [ "org.springframework.security:spring-security-core", "org.springframework:spring-aop", "org.springframework:spring-beans", "org.springframework:spring-context", "org.springframework:spring-core", "org.springframework:spring-expression", "org.springframework:spring-web" ], "org.springframework:spring-aop": [ "org.springframework:spring-beans", "org.springframework:spring-core" ], "org.springframework:spring-aspects": [ "org.aspectj:aspectjweaver" ], "org.springframework:spring-beans": [ "org.springframework:spring-core" ], "org.springframework:spring-context": [ "io.micrometer:micrometer-observation", "org.springframework:spring-aop", "org.springframework:spring-beans", "org.springframework:spring-core", "org.springframework:spring-expression" ], "org.springframework:spring-context-support": [ "org.springframework:spring-beans", "org.springframework:spring-context", "org.springframework:spring-core" ], "org.springframework:spring-core": [ "org.springframework:spring-jcl" ], "org.springframework:spring-expression": [ "org.springframework:spring-core" ], "org.springframework:spring-jdbc": [ "org.springframework:spring-beans", "org.springframework:spring-core", "org.springframework:spring-tx" ], "org.springframework:spring-test": [ "org.springframework:spring-core" ], "org.springframework:spring-tx": [ "org.springframework:spring-beans", "org.springframework:spring-core" ], "org.springframework:spring-web": [ "io.micrometer:micrometer-observation", "org.springframework:spring-beans", "org.springframework:spring-core" ], "org.springframework:spring-webmvc": [ "org.springframework:spring-aop", "org.springframework:spring-beans", "org.springframework:spring-context", "org.springframework:spring-core", "org.springframework:spring-expression", "org.springframework:spring-web" ], "org.thymeleaf:thymeleaf": [ "org.attoparser:attoparser", "org.slf4j:slf4j-api", "org.unbescape:unbescape" ], "org.thymeleaf:thymeleaf-spring6": [ "org.slf4j:slf4j-api", "org.thymeleaf:thymeleaf" ], "org.xmlunit:xmlunit-core": [ "jakarta.xml.bind:jakarta.xml.bind-api" ] }, "packages": { "biz.aQute.bnd:biz.aQute.bnd.util": [ "aQute.bnd.classfile", "aQute.bnd.classfile.builder", "aQute.bnd.classfile.preview", "aQute.bnd.exceptions", "aQute.bnd.memoize", "aQute.bnd.result", "aQute.bnd.signatures", "aQute.bnd.stream", "aQute.bnd.unmodifiable", "aQute.lib.io", "aQute.lib.stringrover", "aQute.libg.glob" ], "biz.aQute.bnd:biz.aQute.bndlib": [ "aQute.bnd.annotation", "aQute.bnd.annotation.baseline", "aQute.bnd.annotation.component", "aQute.bnd.annotation.headers", "aQute.bnd.annotation.jpms", "aQute.bnd.annotation.licenses", "aQute.bnd.annotation.metatype", "aQute.bnd.annotation.plugin", "aQute.bnd.annotation.service", "aQute.bnd.annotation.spi", "aQute.bnd.annotation.xml", "aQute.bnd.apiguardian.api", "aQute.bnd.aspectj.plugin", "aQute.bnd.build", "aQute.bnd.build.api", "aQute.bnd.build.model", "aQute.bnd.build.model.clauses", "aQute.bnd.build.model.conversions", "aQute.bnd.buildtool", "aQute.bnd.bundle.annotations", "aQute.bnd.cdi", "aQute.bnd.classindex", "aQute.bnd.compatibility", "aQute.bnd.component", "aQute.bnd.component.annotations", "aQute.bnd.component.error", "aQute.bnd.connection.settings", "aQute.bnd.differ", "aQute.bnd.exporter.executable", "aQute.bnd.exporter.runbundles", "aQute.bnd.filerepo", "aQute.bnd.header", "aQute.bnd.help", "aQute.bnd.help.instructions", "aQute.bnd.http", "aQute.bnd.junit", "aQute.bnd.make", "aQute.bnd.make.calltree", "aQute.bnd.make.component", "aQute.bnd.make.coverage", "aQute.bnd.make.metatype", "aQute.bnd.maven", "aQute.bnd.maven.support", "aQute.bnd.metatype", "aQute.bnd.metatype.annotations", "aQute.bnd.obr", "aQute.bnd.osgi", "aQute.bnd.osgi.eclipse", "aQute.bnd.osgi.repository", "aQute.bnd.osgi.resource", "aQute.bnd.plugin.ant", "aQute.bnd.plugin.eclipse", "aQute.bnd.plugin.git", "aQute.bnd.plugin.gradle", "aQute.bnd.plugin.jpms", "aQute.bnd.plugin.maven", "aQute.bnd.plugin.spi", "aQute.bnd.print", "aQute.bnd.properties", "aQute.bnd.remoteworkspace.client", "aQute.bnd.remoteworkspace.server", "aQute.bnd.resource.repository", "aQute.bnd.service", "aQute.bnd.service.action", "aQute.bnd.service.classparser", "aQute.bnd.service.clipboard", "aQute.bnd.service.diff", "aQute.bnd.service.export", "aQute.bnd.service.extension", "aQute.bnd.service.externalplugin", "aQute.bnd.service.generate", "aQute.bnd.service.library", "aQute.bnd.service.lifecycle", "aQute.bnd.service.maven", "aQute.bnd.service.message", "aQute.bnd.service.progress", "aQute.bnd.service.release", "aQute.bnd.service.remotelaunch", "aQute.bnd.service.remoteworkspace", "aQute.bnd.service.reporter", "aQute.bnd.service.repository", "aQute.bnd.service.resolve.hook", "aQute.bnd.service.specifications", "aQute.bnd.service.url", "aQute.bnd.service.verifier", "aQute.bnd.signing", "aQute.bnd.url", "aQute.bnd.util.dto", "aQute.bnd.util.home", "aQute.bnd.util.repository", "aQute.bnd.version", "aQute.bnd.version.maven", "aQute.bnd.xmlattribute", "aQute.lib.aspects", "aQute.lib.base64", "aQute.lib.collections", "aQute.lib.concurrent.serial", "aQute.lib.concurrentinit", "aQute.lib.converter", "aQute.lib.date", "aQute.lib.deployer", "aQute.lib.fileset", "aQute.lib.filter", "aQute.lib.formatter", "aQute.lib.hex", "aQute.lib.hierarchy", "aQute.lib.io", "aQute.lib.json", "aQute.lib.link", "aQute.lib.manifest", "aQute.lib.mavenpasswordobfuscator", "aQute.lib.persistentmap", "aQute.lib.redirect", "aQute.lib.settings", "aQute.lib.specinterface", "aQute.lib.spring", "aQute.lib.stringrover", "aQute.lib.strings", "aQute.lib.tag", "aQute.lib.utf8properties", "aQute.lib.watcher", "aQute.lib.xml", "aQute.lib.xpath", "aQute.lib.zip", "aQute.libg.command", "aQute.libg.cryptography", "aQute.libg.filelock", "aQute.libg.generics", "aQute.libg.glob", "aQute.libg.gzip", "aQute.libg.ints", "aQute.libg.map", "aQute.libg.qtokens", "aQute.libg.reporter", "aQute.libg.reporter.slf4j", "aQute.libg.sed", "aQute.libg.tuple", "aQute.libg.uri", "aQute.service.reporter" ], "ch.qos.logback:logback-classic": [ "ch.qos.logback.classic", "ch.qos.logback.classic.boolex", "ch.qos.logback.classic.encoder", "ch.qos.logback.classic.filter", "ch.qos.logback.classic.helpers", "ch.qos.logback.classic.html", "ch.qos.logback.classic.joran", "ch.qos.logback.classic.joran.action", "ch.qos.logback.classic.joran.sanity", "ch.qos.logback.classic.joran.serializedModel", "ch.qos.logback.classic.jul", "ch.qos.logback.classic.layout", "ch.qos.logback.classic.log4j", "ch.qos.logback.classic.model", "ch.qos.logback.classic.model.processor", "ch.qos.logback.classic.model.util", "ch.qos.logback.classic.net", "ch.qos.logback.classic.net.server", "ch.qos.logback.classic.pattern", "ch.qos.logback.classic.pattern.color", "ch.qos.logback.classic.selector", "ch.qos.logback.classic.selector.servlet", "ch.qos.logback.classic.servlet", "ch.qos.logback.classic.sift", "ch.qos.logback.classic.spi", "ch.qos.logback.classic.turbo", "ch.qos.logback.classic.tyler", "ch.qos.logback.classic.util" ], "ch.qos.logback:logback-core": [ "ch.qos.logback.core", "ch.qos.logback.core.boolex", "ch.qos.logback.core.encoder", "ch.qos.logback.core.filter", "ch.qos.logback.core.helpers", "ch.qos.logback.core.hook", "ch.qos.logback.core.html", "ch.qos.logback.core.joran", "ch.qos.logback.core.joran.action", "ch.qos.logback.core.joran.conditional", "ch.qos.logback.core.joran.event", "ch.qos.logback.core.joran.node", "ch.qos.logback.core.joran.sanity", "ch.qos.logback.core.joran.spi", "ch.qos.logback.core.joran.util", "ch.qos.logback.core.joran.util.beans", "ch.qos.logback.core.layout", "ch.qos.logback.core.model", "ch.qos.logback.core.model.conditional", "ch.qos.logback.core.model.processor", "ch.qos.logback.core.model.processor.conditional", "ch.qos.logback.core.model.util", "ch.qos.logback.core.net", "ch.qos.logback.core.net.server", "ch.qos.logback.core.net.ssl", "ch.qos.logback.core.pattern", "ch.qos.logback.core.pattern.color", "ch.qos.logback.core.pattern.parser", "ch.qos.logback.core.pattern.util", "ch.qos.logback.core.property", "ch.qos.logback.core.read", "ch.qos.logback.core.recovery", "ch.qos.logback.core.rolling", "ch.qos.logback.core.rolling.helper", "ch.qos.logback.core.sift", "ch.qos.logback.core.spi", "ch.qos.logback.core.status", "ch.qos.logback.core.subst", "ch.qos.logback.core.testUtil", "ch.qos.logback.core.util" ], "com.fasterxml.jackson.core:jackson-annotations": [ "com.fasterxml.jackson.annotation" ], "com.fasterxml.jackson.core:jackson-core": [ "com.fasterxml.jackson.core", "com.fasterxml.jackson.core.async", "com.fasterxml.jackson.core.base", "com.fasterxml.jackson.core.exc", "com.fasterxml.jackson.core.filter", "com.fasterxml.jackson.core.format", "com.fasterxml.jackson.core.internal.shaded.fdp.v2_18_3", "com.fasterxml.jackson.core.io", "com.fasterxml.jackson.core.io.schubfach", "com.fasterxml.jackson.core.json", "com.fasterxml.jackson.core.json.async", "com.fasterxml.jackson.core.sym", "com.fasterxml.jackson.core.type", "com.fasterxml.jackson.core.util" ], "com.fasterxml.jackson.core:jackson-databind": [ "com.fasterxml.jackson.databind", "com.fasterxml.jackson.databind.annotation", "com.fasterxml.jackson.databind.cfg", "com.fasterxml.jackson.databind.deser", "com.fasterxml.jackson.databind.deser.impl", "com.fasterxml.jackson.databind.deser.std", "com.fasterxml.jackson.databind.exc", "com.fasterxml.jackson.databind.ext", "com.fasterxml.jackson.databind.introspect", "com.fasterxml.jackson.databind.jdk14", "com.fasterxml.jackson.databind.json", "com.fasterxml.jackson.databind.jsonFormatVisitors", "com.fasterxml.jackson.databind.jsonschema", "com.fasterxml.jackson.databind.jsontype", "com.fasterxml.jackson.databind.jsontype.impl", "com.fasterxml.jackson.databind.module", "com.fasterxml.jackson.databind.node", "com.fasterxml.jackson.databind.ser", "com.fasterxml.jackson.databind.ser.impl", "com.fasterxml.jackson.databind.ser.std", "com.fasterxml.jackson.databind.type", "com.fasterxml.jackson.databind.util", "com.fasterxml.jackson.databind.util.internal" ], "com.fasterxml.jackson.datatype:jackson-datatype-jdk8": [ "com.fasterxml.jackson.datatype.jdk8" ], "com.fasterxml.jackson.datatype:jackson-datatype-jsr310": [ "com.fasterxml.jackson.datatype.jsr310", "com.fasterxml.jackson.datatype.jsr310.deser", "com.fasterxml.jackson.datatype.jsr310.deser.key", "com.fasterxml.jackson.datatype.jsr310.ser", "com.fasterxml.jackson.datatype.jsr310.ser.key", "com.fasterxml.jackson.datatype.jsr310.util" ], "com.fasterxml.jackson.module:jackson-module-parameter-names": [ "com.fasterxml.jackson.module.paramnames" ], "com.google.auto.value:auto-value-annotations": [ "com.google.auto.value", "com.google.auto.value.extension.memoized", "com.google.auto.value.extension.serializable", "com.google.auto.value.extension.toprettystring" ], "com.google.caliper:caliper": [ "com.google.caliper.runner", "com.google.caliper.runner.instrument", "com.google.caliper.runner.resultprocessor" ], "com.google.caliper:caliper-api": [ "com.google.caliper", "com.google.caliper.api", "com.google.caliper.model" ], "com.google.caliper:caliper-core": [ "com.google.caliper.bridge", "com.google.caliper.core", "com.google.caliper.memory" ], "com.google.caliper:caliper-runner": [ "com.google.caliper.runner", "com.google.caliper.runner.config", "com.google.caliper.runner.experiment", "com.google.caliper.runner.instrument", "com.google.caliper.runner.options", "com.google.caliper.runner.resultprocessor", "com.google.caliper.runner.server", "com.google.caliper.runner.target", "com.google.caliper.runner.worker", "com.google.caliper.runner.worker.dryrun", "com.google.caliper.runner.worker.targetinfo", "com.google.caliper.runner.worker.trial" ], "com.google.caliper:caliper-util": [ "com.google.caliper.json", "com.google.caliper.util" ], "com.google.caliper:caliper-worker": [ "com.google.caliper.worker", "com.google.caliper.worker.connection", "com.google.caliper.worker.handler", "com.google.caliper.worker.instrument" ], "com.google.caliper:caliper-worker-jvm": [ "com.google.caliper.worker" ], "com.google.code.findbugs:jsr305": [ "javax.annotation", "javax.annotation.concurrent", "javax.annotation.meta" ], "com.google.code.gson:gson": [ "com.google.gson", "com.google.gson.annotations", "com.google.gson.internal", "com.google.gson.internal.bind", "com.google.gson.internal.bind.util", "com.google.gson.internal.reflect", "com.google.gson.internal.sql", "com.google.gson.reflect", "com.google.gson.stream" ], "com.google.code.java-allocation-instrumenter:java-allocation-instrumenter": [ "com.google.monitoring.runtime.instrumentation", "com.google.monitoring.runtime.instrumentation.asm", "com.google.monitoring.runtime.instrumentation.asm.commons", "com.google.monitoring.runtime.instrumentation.asm.signature", "com.google.monitoring.runtime.instrumentation.asm.tree", "com.google.monitoring.runtime.instrumentation.asm.tree.analysis", "com.google.monitoring.runtime.instrumentation.asm.util", "com.google.monitoring.runtime.instrumentation.checker.nullness.compatqual", "com.google.monitoring.runtime.instrumentation.common.annotations", "com.google.monitoring.runtime.instrumentation.common.base", "com.google.monitoring.runtime.instrumentation.common.base.internal", "com.google.monitoring.runtime.instrumentation.common.cache", "com.google.monitoring.runtime.instrumentation.common.collect", "com.google.monitoring.runtime.instrumentation.common.escape", "com.google.monitoring.runtime.instrumentation.common.eventbus", "com.google.monitoring.runtime.instrumentation.common.graph", "com.google.monitoring.runtime.instrumentation.common.hash", "com.google.monitoring.runtime.instrumentation.common.html", "com.google.monitoring.runtime.instrumentation.common.io", "com.google.monitoring.runtime.instrumentation.common.math", "com.google.monitoring.runtime.instrumentation.common.net", "com.google.monitoring.runtime.instrumentation.common.primitives", "com.google.monitoring.runtime.instrumentation.common.reflect", "com.google.monitoring.runtime.instrumentation.common.util.concurrent", "com.google.monitoring.runtime.instrumentation.common.xml", "com.google.monitoring.runtime.instrumentation.errorprone.annotations", "com.google.monitoring.runtime.instrumentation.errorprone.annotations.concurrent", "com.google.monitoring.runtime.instrumentation.j2objc.annotations", "com.google.thirdparty.publicsuffix" ], "com.google.dagger:dagger": [ "dagger", "dagger.internal", "dagger.multibindings" ], "com.google.dagger:dagger-producers": [ "dagger.producers", "dagger.producers.internal", "dagger.producers.monitoring", "dagger.producers.monitoring.internal" ], "com.google.errorprone:error_prone_annotations": [ "com.google.errorprone.annotations", "com.google.errorprone.annotations.concurrent" ], "com.google.guava:failureaccess": [ "com.google.common.util.concurrent.internal" ], "com.google.guava:guava": [ "com.google.common.annotations", "com.google.common.base", "com.google.common.base.internal", "com.google.common.cache", "com.google.common.collect", "com.google.common.escape", "com.google.common.eventbus", "com.google.common.graph", "com.google.common.hash", "com.google.common.html", "com.google.common.io", "com.google.common.math", "com.google.common.net", "com.google.common.primitives", "com.google.common.reflect", "com.google.common.util.concurrent", "com.google.common.xml", "com.google.thirdparty.publicsuffix" ], "com.google.guava:guava-testlib": [ "com.google.common.collect.testing", "com.google.common.collect.testing.features", "com.google.common.collect.testing.google", "com.google.common.collect.testing.suites", "com.google.common.collect.testing.testers", "com.google.common.escape.testing", "com.google.common.testing", "com.google.common.util.concurrent.testing" ], "com.google.j2objc:j2objc-annotations": [ "com.google.j2objc.annotations" ], "com.google.truth:truth": [ "com.google.common.truth" ], "com.jayway.jsonpath:json-path": [ "com.jayway.jsonpath", "com.jayway.jsonpath.internal", "com.jayway.jsonpath.internal.filter", "com.jayway.jsonpath.internal.function", "com.jayway.jsonpath.internal.function.json", "com.jayway.jsonpath.internal.function.latebinding", "com.jayway.jsonpath.internal.function.numeric", "com.jayway.jsonpath.internal.function.sequence", "com.jayway.jsonpath.internal.function.text", "com.jayway.jsonpath.internal.path", "com.jayway.jsonpath.spi.cache", "com.jayway.jsonpath.spi.json", "com.jayway.jsonpath.spi.mapper" ], "com.squareup.okhttp:okhttp": [ "com.squareup.okhttp", "com.squareup.okhttp.internal", "com.squareup.okhttp.internal.framed", "com.squareup.okhttp.internal.http", "com.squareup.okhttp.internal.io", "com.squareup.okhttp.internal.tls" ], "com.squareup.okio:okio": [ "okio" ], "com.sun.jersey:jersey-client": [ "com.sun.jersey.api.client", "com.sun.jersey.api.client.async", "com.sun.jersey.api.client.config", "com.sun.jersey.api.client.filter", "com.sun.jersey.client.impl", "com.sun.jersey.client.impl.async", "com.sun.jersey.client.proxy", "com.sun.jersey.client.urlconnection", "com.sun.ws.rs.ext" ], "com.sun.jersey:jersey-core": [ "com.sun.jersey.api.provider.jaxb", "com.sun.jersey.api.representation", "com.sun.jersey.api.uri", "com.sun.jersey.core.header", "com.sun.jersey.core.header.reader", "com.sun.jersey.core.impl.provider.entity", "com.sun.jersey.core.impl.provider.header", "com.sun.jersey.core.impl.provider.xml", "com.sun.jersey.core.osgi", "com.sun.jersey.core.provider", "com.sun.jersey.core.provider.jaxb", "com.sun.jersey.core.reflection", "com.sun.jersey.core.spi.component", "com.sun.jersey.core.spi.component.ioc", "com.sun.jersey.core.spi.factory", "com.sun.jersey.core.spi.scanning", "com.sun.jersey.core.spi.scanning.uri", "com.sun.jersey.core.util", "com.sun.jersey.impl", "com.sun.jersey.localization", "com.sun.jersey.spi", "com.sun.jersey.spi.inject", "com.sun.jersey.spi.service" ], "com.vaadin.external.google:android-json": [ "org.json" ], "com.zaxxer:HikariCP": [ "com.zaxxer.hikari", "com.zaxxer.hikari.hibernate", "com.zaxxer.hikari.metrics", "com.zaxxer.hikari.metrics.dropwizard", "com.zaxxer.hikari.metrics.micrometer", "com.zaxxer.hikari.metrics.prometheus", "com.zaxxer.hikari.pool", "com.zaxxer.hikari.util" ], "info.picocli:picocli": [ "picocli" ], "io.micrometer:micrometer-commons": [ "io.micrometer.common", "io.micrometer.common.annotation", "io.micrometer.common.docs", "io.micrometer.common.lang", "io.micrometer.common.util", "io.micrometer.common.util.internal.logging" ], "io.micrometer:micrometer-core": [ "io.micrometer.core.annotation", "io.micrometer.core.aop", "io.micrometer.core.instrument", "io.micrometer.core.instrument.binder", "io.micrometer.core.instrument.binder.cache", "io.micrometer.core.instrument.binder.commonspool2", "io.micrometer.core.instrument.binder.db", "io.micrometer.core.instrument.binder.grpc", "io.micrometer.core.instrument.binder.http", "io.micrometer.core.instrument.binder.httpcomponents", "io.micrometer.core.instrument.binder.httpcomponents.hc5", "io.micrometer.core.instrument.binder.hystrix", "io.micrometer.core.instrument.binder.jdk", "io.micrometer.core.instrument.binder.jersey.server", "io.micrometer.core.instrument.binder.jetty", "io.micrometer.core.instrument.binder.jpa", "io.micrometer.core.instrument.binder.jvm", "io.micrometer.core.instrument.binder.kafka", "io.micrometer.core.instrument.binder.logging", "io.micrometer.core.instrument.binder.mongodb", "io.micrometer.core.instrument.binder.netty4", "io.micrometer.core.instrument.binder.okhttp3", "io.micrometer.core.instrument.binder.system", "io.micrometer.core.instrument.binder.tomcat", "io.micrometer.core.instrument.composite", "io.micrometer.core.instrument.config", "io.micrometer.core.instrument.config.validate", "io.micrometer.core.instrument.cumulative", "io.micrometer.core.instrument.distribution", "io.micrometer.core.instrument.distribution.pause", "io.micrometer.core.instrument.docs", "io.micrometer.core.instrument.dropwizard", "io.micrometer.core.instrument.internal", "io.micrometer.core.instrument.kotlin", "io.micrometer.core.instrument.logging", "io.micrometer.core.instrument.noop", "io.micrometer.core.instrument.observation", "io.micrometer.core.instrument.push", "io.micrometer.core.instrument.search", "io.micrometer.core.instrument.simple", "io.micrometer.core.instrument.step", "io.micrometer.core.instrument.util", "io.micrometer.core.ipc.http", "io.micrometer.core.lang", "io.micrometer.core.util.internal.logging" ], "io.micrometer:micrometer-jakarta9": [ "io.micrometer.jakarta9.instrument.jms" ], "io.micrometer:micrometer-observation": [ "io.micrometer.observation", "io.micrometer.observation.annotation", "io.micrometer.observation.aop", "io.micrometer.observation.contextpropagation", "io.micrometer.observation.docs", "io.micrometer.observation.transport" ], "jakarta.activation:jakarta.activation-api": [ "jakarta.activation", "jakarta.activation.spi" ], "jakarta.annotation:jakarta.annotation-api": [ "jakarta.annotation", "jakarta.annotation.security", "jakarta.annotation.sql" ], "jakarta.enterprise:jakarta.enterprise.cdi-api": [ "jakarta.decorator", "jakarta.enterprise.context", "jakarta.enterprise.context.control", "jakarta.enterprise.context.spi", "jakarta.enterprise.event", "jakarta.enterprise.inject", "jakarta.enterprise.inject.build.compatible.spi", "jakarta.enterprise.inject.literal", "jakarta.enterprise.inject.se", "jakarta.enterprise.inject.spi", "jakarta.enterprise.inject.spi.configurator", "jakarta.enterprise.util" ], "jakarta.enterprise:jakarta.enterprise.lang-model": [ "jakarta.enterprise.lang.model", "jakarta.enterprise.lang.model.declarations", "jakarta.enterprise.lang.model.types" ], "jakarta.inject:jakarta.inject-api": [ "jakarta.inject" ], "jakarta.interceptor:jakarta.interceptor-api": [ "jakarta.interceptor" ], "jakarta.servlet:jakarta.servlet-api": [ "jakarta.servlet", "jakarta.servlet.annotation", "jakarta.servlet.descriptor", "jakarta.servlet.http" ], "jakarta.transaction:jakarta.transaction-api": [ "jakarta.transaction" ], "jakarta.websocket:jakarta.websocket-api": [ "jakarta.websocket.server" ], "jakarta.websocket:jakarta.websocket-client-api": [ "jakarta.websocket" ], "jakarta.xml.bind:jakarta.xml.bind-api": [ "jakarta.xml.bind", "jakarta.xml.bind.annotation", "jakarta.xml.bind.annotation.adapters", "jakarta.xml.bind.attachment", "jakarta.xml.bind.helpers", "jakarta.xml.bind.util" ], "javax.annotation:javax.annotation-api": [ "javax.annotation", "javax.annotation.security", "javax.annotation.sql" ], "javax.inject:javax.inject": [ "javax.inject" ], "javax.ws.rs:jsr311-api": [ "javax.ws.rs", "javax.ws.rs.core", "javax.ws.rs.ext" ], "joda-time:joda-time": [ "org.joda.time", "org.joda.time.base", "org.joda.time.chrono", "org.joda.time.convert", "org.joda.time.field", "org.joda.time.format", "org.joda.time.tz" ], "junit:junit": [ "junit.extensions", "junit.framework", "junit.runner", "junit.textui", "org.junit", "org.junit.experimental", "org.junit.experimental.categories", "org.junit.experimental.max", "org.junit.experimental.results", "org.junit.experimental.runners", "org.junit.experimental.theories", "org.junit.experimental.theories.internal", "org.junit.experimental.theories.suppliers", "org.junit.function", "org.junit.internal", "org.junit.internal.builders", "org.junit.internal.management", "org.junit.internal.matchers", "org.junit.internal.requests", "org.junit.internal.runners", "org.junit.internal.runners.model", "org.junit.internal.runners.rules", "org.junit.internal.runners.statements", "org.junit.matchers", "org.junit.rules", "org.junit.runner", "org.junit.runner.manipulation", "org.junit.runner.notification", "org.junit.runners", "org.junit.runners.model", "org.junit.runners.parameterized", "org.junit.validator" ], "net.bytebuddy:byte-buddy": [ "net.bytebuddy", "net.bytebuddy.agent.builder", "net.bytebuddy.asm", "net.bytebuddy.build", "net.bytebuddy.description", "net.bytebuddy.description.annotation", "net.bytebuddy.description.enumeration", "net.bytebuddy.description.field", "net.bytebuddy.description.method", "net.bytebuddy.description.modifier", "net.bytebuddy.description.type", "net.bytebuddy.dynamic", "net.bytebuddy.dynamic.loading", "net.bytebuddy.dynamic.scaffold", "net.bytebuddy.dynamic.scaffold.inline", "net.bytebuddy.dynamic.scaffold.subclass", "net.bytebuddy.implementation", "net.bytebuddy.implementation.attribute", "net.bytebuddy.implementation.auxiliary", "net.bytebuddy.implementation.bind", "net.bytebuddy.implementation.bind.annotation", "net.bytebuddy.implementation.bytecode", "net.bytebuddy.implementation.bytecode.assign", "net.bytebuddy.implementation.bytecode.assign.primitive", "net.bytebuddy.implementation.bytecode.assign.reference", "net.bytebuddy.implementation.bytecode.collection", "net.bytebuddy.implementation.bytecode.constant", "net.bytebuddy.implementation.bytecode.member", "net.bytebuddy.jar.asm", "net.bytebuddy.jar.asm.commons", "net.bytebuddy.jar.asm.signature", "net.bytebuddy.matcher", "net.bytebuddy.pool", "net.bytebuddy.utility", "net.bytebuddy.utility.dispatcher", "net.bytebuddy.utility.nullability", "net.bytebuddy.utility.privilege", "net.bytebuddy.utility.visitor" ], "net.bytebuddy:byte-buddy-agent": [ "net.bytebuddy.agent", "net.bytebuddy.agent.utility.nullability" ], "net.minidev:accessors-smart": [ "net.minidev.asm", "net.minidev.asm.ex" ], "net.minidev:json-smart": [ "net.minidev.json", "net.minidev.json.annotate", "net.minidev.json.parser", "net.minidev.json.reader", "net.minidev.json.writer" ], "org.apache.commons:commons-compress": [ "org.apache.commons.compress", "org.apache.commons.compress.archivers", "org.apache.commons.compress.archivers.ar", "org.apache.commons.compress.archivers.arj", "org.apache.commons.compress.archivers.cpio", "org.apache.commons.compress.archivers.dump", "org.apache.commons.compress.archivers.examples", "org.apache.commons.compress.archivers.jar", "org.apache.commons.compress.archivers.sevenz", "org.apache.commons.compress.archivers.tar", "org.apache.commons.compress.archivers.zip", "org.apache.commons.compress.changes", "org.apache.commons.compress.compressors", "org.apache.commons.compress.compressors.brotli", "org.apache.commons.compress.compressors.bzip2", "org.apache.commons.compress.compressors.deflate", "org.apache.commons.compress.compressors.deflate64", "org.apache.commons.compress.compressors.gzip", "org.apache.commons.compress.compressors.lz4", "org.apache.commons.compress.compressors.lz77support", "org.apache.commons.compress.compressors.lzma", "org.apache.commons.compress.compressors.lzw", "org.apache.commons.compress.compressors.pack200", "org.apache.commons.compress.compressors.snappy", "org.apache.commons.compress.compressors.xz", "org.apache.commons.compress.compressors.z", "org.apache.commons.compress.compressors.zstandard", "org.apache.commons.compress.harmony", "org.apache.commons.compress.harmony.archive.internal.nls", "org.apache.commons.compress.harmony.pack200", "org.apache.commons.compress.harmony.unpack200", "org.apache.commons.compress.harmony.unpack200.bytecode", "org.apache.commons.compress.harmony.unpack200.bytecode.forms", "org.apache.commons.compress.java.util.jar", "org.apache.commons.compress.parallel", "org.apache.commons.compress.utils" ], "org.apache.logging.log4j:log4j-api": [ "org.apache.logging.log4j", "org.apache.logging.log4j.internal", "org.apache.logging.log4j.internal.map", "org.apache.logging.log4j.message", "org.apache.logging.log4j.simple", "org.apache.logging.log4j.simple.internal", "org.apache.logging.log4j.spi", "org.apache.logging.log4j.status", "org.apache.logging.log4j.util", "org.apache.logging.log4j.util.internal" ], "org.apache.logging.log4j:log4j-to-slf4j": [ "org.apache.logging.slf4j" ], "org.apache.tomcat.embed:tomcat-embed-core": [ "jakarta.security.auth.message", "jakarta.security.auth.message.callback", "jakarta.security.auth.message.config", "jakarta.security.auth.message.module", "jakarta.servlet", "jakarta.servlet.annotation", "jakarta.servlet.descriptor", "jakarta.servlet.http", "org.apache.catalina", "org.apache.catalina.authenticator", "org.apache.catalina.authenticator.jaspic", "org.apache.catalina.connector", "org.apache.catalina.core", "org.apache.catalina.deploy", "org.apache.catalina.filters", "org.apache.catalina.loader", "org.apache.catalina.manager", "org.apache.catalina.manager.host", "org.apache.catalina.manager.util", "org.apache.catalina.mapper", "org.apache.catalina.mbeans", "org.apache.catalina.realm", "org.apache.catalina.security", "org.apache.catalina.servlets", "org.apache.catalina.session", "org.apache.catalina.startup", "org.apache.catalina.users", "org.apache.catalina.util", "org.apache.catalina.valves", "org.apache.catalina.valves.rewrite", "org.apache.catalina.webresources", "org.apache.catalina.webresources.war", "org.apache.coyote", "org.apache.coyote.ajp", "org.apache.coyote.http11", "org.apache.coyote.http11.filters", "org.apache.coyote.http11.upgrade", "org.apache.coyote.http2", "org.apache.juli", "org.apache.juli.logging", "org.apache.naming", "org.apache.naming.factory", "org.apache.naming.factory.webservices", "org.apache.naming.java", "org.apache.tomcat", "org.apache.tomcat.jni", "org.apache.tomcat.util", "org.apache.tomcat.util.bcel", "org.apache.tomcat.util.bcel.classfile", "org.apache.tomcat.util.buf", "org.apache.tomcat.util.codec.binary", "org.apache.tomcat.util.collections", "org.apache.tomcat.util.compat", "org.apache.tomcat.util.descriptor", "org.apache.tomcat.util.descriptor.tagplugin", "org.apache.tomcat.util.descriptor.web", "org.apache.tomcat.util.digester", "org.apache.tomcat.util.file", "org.apache.tomcat.util.http", "org.apache.tomcat.util.http.fileupload", "org.apache.tomcat.util.http.fileupload.disk", "org.apache.tomcat.util.http.fileupload.impl", "org.apache.tomcat.util.http.fileupload.servlet", "org.apache.tomcat.util.http.fileupload.util", "org.apache.tomcat.util.http.fileupload.util.mime", "org.apache.tomcat.util.http.parser", "org.apache.tomcat.util.json", "org.apache.tomcat.util.log", "org.apache.tomcat.util.modeler", "org.apache.tomcat.util.modeler.modules", "org.apache.tomcat.util.net", "org.apache.tomcat.util.net.jsse", "org.apache.tomcat.util.net.openssl", "org.apache.tomcat.util.net.openssl.ciphers", "org.apache.tomcat.util.res", "org.apache.tomcat.util.scan", "org.apache.tomcat.util.security", "org.apache.tomcat.util.threads" ], "org.apache.tomcat.embed:tomcat-embed-el": [ "jakarta.el", "org.apache.el", "org.apache.el.lang", "org.apache.el.parser", "org.apache.el.stream", "org.apache.el.util" ], "org.apache.tomcat.embed:tomcat-embed-websocket": [ "jakarta.websocket", "jakarta.websocket.server", "org.apache.tomcat.websocket", "org.apache.tomcat.websocket.pojo", "org.apache.tomcat.websocket.server" ], "org.apiguardian:apiguardian-api": [ "org.apiguardian.api" ], "org.aspectj:aspectjweaver": [ "aj.org.objectweb.asm", "aj.org.objectweb.asm.commons", "aj.org.objectweb.asm.signature", "org.aspectj.apache.bcel", "org.aspectj.apache.bcel.classfile", "org.aspectj.apache.bcel.classfile.annotation", "org.aspectj.apache.bcel.generic", "org.aspectj.apache.bcel.util", "org.aspectj.asm", "org.aspectj.asm.internal", "org.aspectj.bridge", "org.aspectj.bridge.context", "org.aspectj.internal.lang.annotation", "org.aspectj.internal.lang.reflect", "org.aspectj.lang", "org.aspectj.lang.annotation", "org.aspectj.lang.annotation.control", "org.aspectj.lang.internal.lang", "org.aspectj.lang.reflect", "org.aspectj.runtime", "org.aspectj.runtime.internal", "org.aspectj.runtime.internal.cflowstack", "org.aspectj.runtime.reflect", "org.aspectj.util", "org.aspectj.weaver", "org.aspectj.weaver.ast", "org.aspectj.weaver.bcel", "org.aspectj.weaver.bcel.asm", "org.aspectj.weaver.internal.tools", "org.aspectj.weaver.loadtime", "org.aspectj.weaver.loadtime.definition", "org.aspectj.weaver.ltw", "org.aspectj.weaver.model", "org.aspectj.weaver.patterns", "org.aspectj.weaver.reflect", "org.aspectj.weaver.tools", "org.aspectj.weaver.tools.cache" ], "org.assertj:assertj-core": [ "org.assertj.core.annotations", "org.assertj.core.api", "org.assertj.core.api.exception", "org.assertj.core.api.filter", "org.assertj.core.api.iterable", "org.assertj.core.api.junit.jupiter", "org.assertj.core.api.recursive", "org.assertj.core.api.recursive.assertion", "org.assertj.core.api.recursive.comparison", "org.assertj.core.condition", "org.assertj.core.configuration", "org.assertj.core.data", "org.assertj.core.description", "org.assertj.core.error", "org.assertj.core.error.array2d", "org.assertj.core.error.future", "org.assertj.core.error.uri", "org.assertj.core.extractor", "org.assertj.core.groups", "org.assertj.core.internal", "org.assertj.core.matcher", "org.assertj.core.presentation", "org.assertj.core.util", "org.assertj.core.util.diff", "org.assertj.core.util.diff.myers", "org.assertj.core.util.introspection", "org.assertj.core.util.xml" ], "org.attoparser:attoparser": [ "org.attoparser", "org.attoparser.config", "org.attoparser.discard", "org.attoparser.dom", "org.attoparser.duplicate", "org.attoparser.minimize", "org.attoparser.output", "org.attoparser.prettyhtml", "org.attoparser.select", "org.attoparser.simple", "org.attoparser.trace", "org.attoparser.util" ], "org.awaitility:awaitility": [ "org.awaitility", "org.awaitility.classpath", "org.awaitility.constraint", "org.awaitility.core", "org.awaitility.pollinterval", "org.awaitility.reflect", "org.awaitility.reflect.exception", "org.awaitility.spi" ], "org.checkerframework:checker-compat-qual": [ "org.checkerframework.checker.nullness.compatqual" ], "org.checkerframework:checker-qual": [ "org.checkerframework.checker.builder.qual", "org.checkerframework.checker.calledmethods.qual", "org.checkerframework.checker.compilermsgs.qual", "org.checkerframework.checker.fenum.qual", "org.checkerframework.checker.formatter.qual", "org.checkerframework.checker.guieffect.qual", "org.checkerframework.checker.i18n.qual", "org.checkerframework.checker.i18nformatter.qual", "org.checkerframework.checker.index.qual", "org.checkerframework.checker.initialization.qual", "org.checkerframework.checker.interning.qual", "org.checkerframework.checker.lock.qual", "org.checkerframework.checker.mustcall.qual", "org.checkerframework.checker.nullness.qual", "org.checkerframework.checker.optional.qual", "org.checkerframework.checker.propkey.qual", "org.checkerframework.checker.regex.qual", "org.checkerframework.checker.signature.qual", "org.checkerframework.checker.signedness.qual", "org.checkerframework.checker.tainting.qual", "org.checkerframework.checker.units.qual", "org.checkerframework.common.aliasing.qual", "org.checkerframework.common.initializedfields.qual", "org.checkerframework.common.reflection.qual", "org.checkerframework.common.returnsreceiver.qual", "org.checkerframework.common.subtyping.qual", "org.checkerframework.common.util.report.qual", "org.checkerframework.common.value.qual", "org.checkerframework.dataflow.qual", "org.checkerframework.framework.qual" ], "org.eclipse.jetty.ee10.websocket:jetty-ee10-websocket-jakarta-client": [ "org.eclipse.jetty.ee10.websocket.jakarta.client", "org.eclipse.jetty.ee10.websocket.jakarta.client.internal" ], "org.eclipse.jetty.ee10.websocket:jetty-ee10-websocket-jakarta-common": [ "org.eclipse.jetty.ee10.websocket.jakarta.common", "org.eclipse.jetty.ee10.websocket.jakarta.common.decoders", "org.eclipse.jetty.ee10.websocket.jakarta.common.encoders", "org.eclipse.jetty.ee10.websocket.jakarta.common.messages" ], "org.eclipse.jetty.ee10.websocket:jetty-ee10-websocket-jakarta-server": [ "org.eclipse.jetty.ee10.websocket.jakarta.server", "org.eclipse.jetty.ee10.websocket.jakarta.server.config", "org.eclipse.jetty.ee10.websocket.jakarta.server.internal" ], "org.eclipse.jetty.ee10.websocket:jetty-ee10-websocket-jetty-server": [ "org.eclipse.jetty.ee10.websocket.server", "org.eclipse.jetty.ee10.websocket.server.config", "org.eclipse.jetty.ee10.websocket.server.internal" ], "org.eclipse.jetty.ee10.websocket:jetty-ee10-websocket-servlet": [ "org.eclipse.jetty.ee10.websocket.servlet" ], "org.eclipse.jetty.ee10:jetty-ee10-annotations": [ "org.eclipse.jetty.ee10.annotations" ], "org.eclipse.jetty.ee10:jetty-ee10-plus": [ "org.eclipse.jetty.ee10.plus.jndi", "org.eclipse.jetty.ee10.plus.webapp" ], "org.eclipse.jetty.ee10:jetty-ee10-servlet": [ "org.eclipse.jetty.ee10.servlet", "org.eclipse.jetty.ee10.servlet.jmx", "org.eclipse.jetty.ee10.servlet.listener", "org.eclipse.jetty.ee10.servlet.security", "org.eclipse.jetty.ee10.servlet.security.authentication", "org.eclipse.jetty.ee10.servlet.util" ], "org.eclipse.jetty.ee10:jetty-ee10-servlets": [ "org.eclipse.jetty.ee10.servlets" ], "org.eclipse.jetty.ee10:jetty-ee10-webapp": [ "org.eclipse.jetty.ee10.webapp" ], "org.eclipse.jetty.websocket:jetty-websocket-core-client": [ "org.eclipse.jetty.websocket.core.client", "org.eclipse.jetty.websocket.core.client.internal" ], "org.eclipse.jetty.websocket:jetty-websocket-core-common": [ "org.eclipse.jetty.websocket.core", "org.eclipse.jetty.websocket.core.exception", "org.eclipse.jetty.websocket.core.internal", "org.eclipse.jetty.websocket.core.messages", "org.eclipse.jetty.websocket.core.util" ], "org.eclipse.jetty.websocket:jetty-websocket-core-server": [ "org.eclipse.jetty.websocket.core.server", "org.eclipse.jetty.websocket.core.server.internal" ], "org.eclipse.jetty.websocket:jetty-websocket-jetty-api": [ "org.eclipse.jetty.websocket.api", "org.eclipse.jetty.websocket.api.annotations", "org.eclipse.jetty.websocket.api.exceptions", "org.eclipse.jetty.websocket.api.util" ], "org.eclipse.jetty.websocket:jetty-websocket-jetty-common": [ "org.eclipse.jetty.websocket.common", "org.eclipse.jetty.websocket.common.internal" ], "org.eclipse.jetty:jetty-alpn-client": [ "org.eclipse.jetty.alpn.client" ], "org.eclipse.jetty:jetty-client": [ "org.eclipse.jetty.client", "org.eclipse.jetty.client.internal", "org.eclipse.jetty.client.jmx", "org.eclipse.jetty.client.transport", "org.eclipse.jetty.client.transport.internal" ], "org.eclipse.jetty:jetty-ee": [ "org.eclipse.jetty.ee" ], "org.eclipse.jetty:jetty-http": [ "org.eclipse.jetty.http", "org.eclipse.jetty.http.compression", "org.eclipse.jetty.http.content", "org.eclipse.jetty.http.pathmap" ], "org.eclipse.jetty:jetty-io": [ "org.eclipse.jetty.io", "org.eclipse.jetty.io.content", "org.eclipse.jetty.io.internal", "org.eclipse.jetty.io.jmx", "org.eclipse.jetty.io.ssl" ], "org.eclipse.jetty:jetty-plus": [ "org.eclipse.jetty.plus.annotation", "org.eclipse.jetty.plus.jndi", "org.eclipse.jetty.plus.security" ], "org.eclipse.jetty:jetty-security": [ "org.eclipse.jetty.security", "org.eclipse.jetty.security.authentication", "org.eclipse.jetty.security.internal", "org.eclipse.jetty.security.jaas", "org.eclipse.jetty.security.jaas.callback", "org.eclipse.jetty.security.jaas.spi" ], "org.eclipse.jetty:jetty-server": [ "org.eclipse.jetty.server", "org.eclipse.jetty.server.handler", "org.eclipse.jetty.server.handler.gzip", "org.eclipse.jetty.server.handler.jmx", "org.eclipse.jetty.server.internal", "org.eclipse.jetty.server.jmx" ], "org.eclipse.jetty:jetty-session": [ "org.eclipse.jetty.session" ], "org.eclipse.jetty:jetty-util": [ "org.eclipse.jetty.util", "org.eclipse.jetty.util.annotation", "org.eclipse.jetty.util.component", "org.eclipse.jetty.util.compression", "org.eclipse.jetty.util.jndi", "org.eclipse.jetty.util.preventers", "org.eclipse.jetty.util.resource", "org.eclipse.jetty.util.security", "org.eclipse.jetty.util.ssl", "org.eclipse.jetty.util.statistic", "org.eclipse.jetty.util.thread", "org.eclipse.jetty.util.thread.strategy" ], "org.eclipse.jetty:jetty-xml": [ "org.eclipse.jetty.xml" ], "org.freemarker:freemarker": [ "freemarker.cache", "freemarker.core", "freemarker.debug", "freemarker.debug.impl", "freemarker.ext.ant", "freemarker.ext.beans", "freemarker.ext.dom", "freemarker.ext.jakarta.jsp", "freemarker.ext.jakarta.servlet", "freemarker.ext.jdom", "freemarker.ext.jsp", "freemarker.ext.jython", "freemarker.ext.rhino", "freemarker.ext.servlet", "freemarker.ext.util", "freemarker.ext.xml", "freemarker.log", "freemarker.template", "freemarker.template.utility" ], "org.hamcrest:hamcrest": [ "org.hamcrest", "org.hamcrest.beans", "org.hamcrest.collection", "org.hamcrest.comparator", "org.hamcrest.core", "org.hamcrest.internal", "org.hamcrest.io", "org.hamcrest.number", "org.hamcrest.object", "org.hamcrest.text", "org.hamcrest.xml" ], "org.hamcrest:hamcrest-core": [ "org.hamcrest.core.deprecated" ], "org.hdrhistogram:HdrHistogram": [ "org.HdrHistogram", "org.HdrHistogram.packedarray" ], "org.junit.jupiter:junit-jupiter-api": [ "org.junit.jupiter.api", "org.junit.jupiter.api.condition", "org.junit.jupiter.api.extension", "org.junit.jupiter.api.extension.support", "org.junit.jupiter.api.function", "org.junit.jupiter.api.io", "org.junit.jupiter.api.parallel" ], "org.junit.jupiter:junit-jupiter-engine": [ "org.junit.jupiter.engine", "org.junit.jupiter.engine.config", "org.junit.jupiter.engine.descriptor", "org.junit.jupiter.engine.discovery", "org.junit.jupiter.engine.discovery.predicates", "org.junit.jupiter.engine.execution", "org.junit.jupiter.engine.extension", "org.junit.jupiter.engine.support" ], "org.junit.jupiter:junit-jupiter-params": [ "org.junit.jupiter.params", "org.junit.jupiter.params.aggregator", "org.junit.jupiter.params.converter", "org.junit.jupiter.params.provider", "org.junit.jupiter.params.shadow.com.univocity.parsers.annotations", "org.junit.jupiter.params.shadow.com.univocity.parsers.annotations.helpers", "org.junit.jupiter.params.shadow.com.univocity.parsers.common", "org.junit.jupiter.params.shadow.com.univocity.parsers.common.beans", "org.junit.jupiter.params.shadow.com.univocity.parsers.common.fields", "org.junit.jupiter.params.shadow.com.univocity.parsers.common.input", "org.junit.jupiter.params.shadow.com.univocity.parsers.common.input.concurrent", "org.junit.jupiter.params.shadow.com.univocity.parsers.common.iterators", "org.junit.jupiter.params.shadow.com.univocity.parsers.common.processor", "org.junit.jupiter.params.shadow.com.univocity.parsers.common.processor.core", "org.junit.jupiter.params.shadow.com.univocity.parsers.common.record", "org.junit.jupiter.params.shadow.com.univocity.parsers.common.routine", "org.junit.jupiter.params.shadow.com.univocity.parsers.conversions", "org.junit.jupiter.params.shadow.com.univocity.parsers.csv", "org.junit.jupiter.params.shadow.com.univocity.parsers.fixed", "org.junit.jupiter.params.shadow.com.univocity.parsers.tsv", "org.junit.jupiter.params.support" ], "org.junit.platform:junit-platform-commons": [ "org.junit.platform.commons", "org.junit.platform.commons.annotation", "org.junit.platform.commons.function", "org.junit.platform.commons.logging", "org.junit.platform.commons.support", "org.junit.platform.commons.support.conversion", "org.junit.platform.commons.util" ], "org.junit.platform:junit-platform-engine": [ "org.junit.platform.engine", "org.junit.platform.engine.discovery", "org.junit.platform.engine.reporting", "org.junit.platform.engine.support.config", "org.junit.platform.engine.support.descriptor", "org.junit.platform.engine.support.discovery", "org.junit.platform.engine.support.filter", "org.junit.platform.engine.support.hierarchical", "org.junit.platform.engine.support.store" ], "org.latencyutils:LatencyUtils": [ "org.LatencyUtils" ], "org.mockito:mockito-core": [ "org.mockito", "org.mockito.codegen", "org.mockito.configuration", "org.mockito.creation.instance", "org.mockito.exceptions.base", "org.mockito.exceptions.misusing", "org.mockito.exceptions.stacktrace", "org.mockito.exceptions.verification", "org.mockito.exceptions.verification.junit", "org.mockito.exceptions.verification.opentest4j", "org.mockito.hamcrest", "org.mockito.internal", "org.mockito.internal.configuration", "org.mockito.internal.configuration.injection", "org.mockito.internal.configuration.injection.filter", "org.mockito.internal.configuration.injection.scanner", "org.mockito.internal.configuration.plugins", "org.mockito.internal.creation", "org.mockito.internal.creation.bytebuddy", "org.mockito.internal.creation.instance", "org.mockito.internal.creation.proxy", "org.mockito.internal.creation.settings", "org.mockito.internal.creation.util", "org.mockito.internal.debugging", "org.mockito.internal.exceptions", "org.mockito.internal.exceptions.stacktrace", "org.mockito.internal.exceptions.util", "org.mockito.internal.framework", "org.mockito.internal.hamcrest", "org.mockito.internal.handler", "org.mockito.internal.invocation", "org.mockito.internal.invocation.finder", "org.mockito.internal.invocation.mockref", "org.mockito.internal.junit", "org.mockito.internal.listeners", "org.mockito.internal.matchers", "org.mockito.internal.matchers.apachecommons", "org.mockito.internal.matchers.text", "org.mockito.internal.progress", "org.mockito.internal.reporting", "org.mockito.internal.runners", "org.mockito.internal.runners.util", "org.mockito.internal.session", "org.mockito.internal.stubbing", "org.mockito.internal.stubbing.answers", "org.mockito.internal.stubbing.defaultanswers", "org.mockito.internal.util", "org.mockito.internal.util.collections", "org.mockito.internal.util.concurrent", "org.mockito.internal.util.io", "org.mockito.internal.util.reflection", "org.mockito.internal.verification", "org.mockito.internal.verification.api", "org.mockito.internal.verification.argumentmatching", "org.mockito.internal.verification.checkers", "org.mockito.invocation", "org.mockito.junit", "org.mockito.listeners", "org.mockito.mock", "org.mockito.plugins", "org.mockito.quality", "org.mockito.session", "org.mockito.stubbing", "org.mockito.verification" ], "org.mockito:mockito-junit-jupiter": [ "org.mockito.junit.jupiter", "org.mockito.junit.jupiter.resolver" ], "org.objenesis:objenesis": [ "org.objenesis", "org.objenesis.instantiator", "org.objenesis.instantiator.android", "org.objenesis.instantiator.annotations", "org.objenesis.instantiator.basic", "org.objenesis.instantiator.gcj", "org.objenesis.instantiator.perc", "org.objenesis.instantiator.sun", "org.objenesis.instantiator.util", "org.objenesis.strategy" ], "org.opentest4j:opentest4j": [ "org.opentest4j" ], "org.osgi:org.osgi.dto": [ "org.osgi.dto" ], "org.osgi:org.osgi.framework": [ "org.osgi.framework", "org.osgi.framework.dto", "org.osgi.framework.hooks.bundle", "org.osgi.framework.hooks.resolver", "org.osgi.framework.hooks.service", "org.osgi.framework.hooks.weaving", "org.osgi.framework.launch", "org.osgi.framework.namespace", "org.osgi.framework.startlevel", "org.osgi.framework.startlevel.dto", "org.osgi.framework.wiring", "org.osgi.framework.wiring.dto" ], "org.osgi:org.osgi.resource": [ "org.osgi.resource", "org.osgi.resource.dto" ], "org.osgi:org.osgi.service.log": [ "org.osgi.service.log" ], "org.osgi:org.osgi.service.repository": [ "org.osgi.service.repository" ], "org.osgi:org.osgi.util.function": [ "org.osgi.util.function" ], "org.osgi:org.osgi.util.promise": [ "org.osgi.util.promise" ], "org.osgi:org.osgi.util.tracker": [ "org.osgi.util.tracker" ], "org.osgi:osgi.annotation": [ "org.osgi.annotation.bundle", "org.osgi.annotation.versioning" ], "org.ow2.asm:asm": [ "org.objectweb.asm", "org.objectweb.asm.signature" ], "org.ow2.asm:asm-analysis": [ "org.objectweb.asm.tree.analysis" ], "org.ow2.asm:asm-commons": [ "org.objectweb.asm.commons" ], "org.ow2.asm:asm-tree": [ "org.objectweb.asm.tree" ], "org.ow2.asm:asm-util": [ "org.objectweb.asm.util" ], "org.skyscreamer:jsonassert": [ "org.json", "org.skyscreamer.jsonassert", "org.skyscreamer.jsonassert.comparator" ], "org.slf4j:jul-to-slf4j": [ "org.slf4j.bridge" ], "org.slf4j:slf4j-api": [ "org.slf4j", "org.slf4j.event", "org.slf4j.helpers", "org.slf4j.spi" ], "org.springframework.boot:spring-boot": [ "org.springframework.boot", "org.springframework.boot.admin", "org.springframework.boot.ansi", "org.springframework.boot.availability", "org.springframework.boot.builder", "org.springframework.boot.cloud", "org.springframework.boot.context", "org.springframework.boot.context.annotation", "org.springframework.boot.context.config", "org.springframework.boot.context.event", "org.springframework.boot.context.logging", "org.springframework.boot.context.metrics.buffering", "org.springframework.boot.context.properties", "org.springframework.boot.context.properties.bind", "org.springframework.boot.context.properties.bind.handler", "org.springframework.boot.context.properties.bind.validation", "org.springframework.boot.context.properties.source", "org.springframework.boot.convert", "org.springframework.boot.diagnostics", "org.springframework.boot.diagnostics.analyzer", "org.springframework.boot.env", "org.springframework.boot.flyway", "org.springframework.boot.http.client", "org.springframework.boot.info", "org.springframework.boot.io", "org.springframework.boot.jackson", "org.springframework.boot.jdbc", "org.springframework.boot.jdbc.init", "org.springframework.boot.jdbc.metadata", "org.springframework.boot.jms", "org.springframework.boot.jooq", "org.springframework.boot.json", "org.springframework.boot.liquibase", "org.springframework.boot.logging", "org.springframework.boot.logging.java", "org.springframework.boot.logging.log4j2", "org.springframework.boot.logging.logback", "org.springframework.boot.logging.structured", "org.springframework.boot.origin", "org.springframework.boot.orm.jpa", "org.springframework.boot.orm.jpa.hibernate", "org.springframework.boot.r2dbc", "org.springframework.boot.r2dbc.init", "org.springframework.boot.reactor", "org.springframework.boot.rsocket.context", "org.springframework.boot.rsocket.messaging", "org.springframework.boot.rsocket.netty", "org.springframework.boot.rsocket.server", "org.springframework.boot.security.reactive", "org.springframework.boot.security.servlet", "org.springframework.boot.sql.init", "org.springframework.boot.sql.init.dependency", "org.springframework.boot.ssl", "org.springframework.boot.ssl.jks", "org.springframework.boot.ssl.pem", "org.springframework.boot.system", "org.springframework.boot.task", "org.springframework.boot.type.classreading", "org.springframework.boot.util", "org.springframework.boot.validation", "org.springframework.boot.validation.beanvalidation", "org.springframework.boot.web.client", "org.springframework.boot.web.codec", "org.springframework.boot.web.context", "org.springframework.boot.web.embedded.jetty", "org.springframework.boot.web.embedded.netty", "org.springframework.boot.web.embedded.tomcat", "org.springframework.boot.web.embedded.undertow", "org.springframework.boot.web.error", "org.springframework.boot.web.reactive.context", "org.springframework.boot.web.reactive.error", "org.springframework.boot.web.reactive.filter", "org.springframework.boot.web.reactive.function.client", "org.springframework.boot.web.reactive.result.view", "org.springframework.boot.web.reactive.server", "org.springframework.boot.web.server", "org.springframework.boot.web.servlet", "org.springframework.boot.web.servlet.context", "org.springframework.boot.web.servlet.error", "org.springframework.boot.web.servlet.filter", "org.springframework.boot.web.servlet.server", "org.springframework.boot.web.servlet.support", "org.springframework.boot.web.servlet.view", "org.springframework.boot.webservices.client" ], "org.springframework.boot:spring-boot-actuator": [ "org.springframework.boot.actuate.amqp", "org.springframework.boot.actuate.audit", "org.springframework.boot.actuate.audit.listener", "org.springframework.boot.actuate.availability", "org.springframework.boot.actuate.beans", "org.springframework.boot.actuate.cache", "org.springframework.boot.actuate.cassandra", "org.springframework.boot.actuate.context", "org.springframework.boot.actuate.context.properties", "org.springframework.boot.actuate.couchbase", "org.springframework.boot.actuate.data.elasticsearch", "org.springframework.boot.actuate.data.mongo", "org.springframework.boot.actuate.data.redis", "org.springframework.boot.actuate.elasticsearch", "org.springframework.boot.actuate.endpoint", "org.springframework.boot.actuate.endpoint.annotation", "org.springframework.boot.actuate.endpoint.invoke", "org.springframework.boot.actuate.endpoint.invoke.convert", "org.springframework.boot.actuate.endpoint.invoke.reflect", "org.springframework.boot.actuate.endpoint.invoker.cache", "org.springframework.boot.actuate.endpoint.jackson", "org.springframework.boot.actuate.endpoint.jmx", "org.springframework.boot.actuate.endpoint.jmx.annotation", "org.springframework.boot.actuate.endpoint.web", "org.springframework.boot.actuate.endpoint.web.annotation", "org.springframework.boot.actuate.endpoint.web.jersey", "org.springframework.boot.actuate.endpoint.web.reactive", "org.springframework.boot.actuate.endpoint.web.servlet", "org.springframework.boot.actuate.env", "org.springframework.boot.actuate.flyway", "org.springframework.boot.actuate.hazelcast", "org.springframework.boot.actuate.health", "org.springframework.boot.actuate.info", "org.springframework.boot.actuate.integration", "org.springframework.boot.actuate.jdbc", "org.springframework.boot.actuate.jms", "org.springframework.boot.actuate.ldap", "org.springframework.boot.actuate.liquibase", "org.springframework.boot.actuate.logging", "org.springframework.boot.actuate.mail", "org.springframework.boot.actuate.management", "org.springframework.boot.actuate.metrics", "org.springframework.boot.actuate.metrics.amqp", "org.springframework.boot.actuate.metrics.annotation", "org.springframework.boot.actuate.metrics.cache", "org.springframework.boot.actuate.metrics.data", "org.springframework.boot.actuate.metrics.export.prometheus", "org.springframework.boot.actuate.metrics.http", "org.springframework.boot.actuate.metrics.jdbc", "org.springframework.boot.actuate.metrics.r2dbc", "org.springframework.boot.actuate.metrics.startup", "org.springframework.boot.actuate.metrics.system", "org.springframework.boot.actuate.metrics.web.client", "org.springframework.boot.actuate.metrics.web.jetty", "org.springframework.boot.actuate.metrics.web.reactive.client", "org.springframework.boot.actuate.metrics.web.tomcat", "org.springframework.boot.actuate.neo4j", "org.springframework.boot.actuate.quartz", "org.springframework.boot.actuate.r2dbc", "org.springframework.boot.actuate.sbom", "org.springframework.boot.actuate.scheduling", "org.springframework.boot.actuate.security", "org.springframework.boot.actuate.session", "org.springframework.boot.actuate.ssl", "org.springframework.boot.actuate.startup", "org.springframework.boot.actuate.system", "org.springframework.boot.actuate.web.exchanges", "org.springframework.boot.actuate.web.exchanges.reactive", "org.springframework.boot.actuate.web.exchanges.servlet", "org.springframework.boot.actuate.web.mappings", "org.springframework.boot.actuate.web.mappings.reactive", "org.springframework.boot.actuate.web.mappings.servlet" ], "org.springframework.boot:spring-boot-actuator-autoconfigure": [ "org.springframework.boot.actuate.autoconfigure", "org.springframework.boot.actuate.autoconfigure.amqp", "org.springframework.boot.actuate.autoconfigure.audit", "org.springframework.boot.actuate.autoconfigure.availability", "org.springframework.boot.actuate.autoconfigure.beans", "org.springframework.boot.actuate.autoconfigure.cache", "org.springframework.boot.actuate.autoconfigure.cassandra", "org.springframework.boot.actuate.autoconfigure.cloudfoundry", "org.springframework.boot.actuate.autoconfigure.cloudfoundry.reactive", "org.springframework.boot.actuate.autoconfigure.cloudfoundry.servlet", "org.springframework.boot.actuate.autoconfigure.condition", "org.springframework.boot.actuate.autoconfigure.context", "org.springframework.boot.actuate.autoconfigure.context.properties", "org.springframework.boot.actuate.autoconfigure.couchbase", "org.springframework.boot.actuate.autoconfigure.data.elasticsearch", "org.springframework.boot.actuate.autoconfigure.data.mongo", "org.springframework.boot.actuate.autoconfigure.data.redis", "org.springframework.boot.actuate.autoconfigure.elasticsearch", "org.springframework.boot.actuate.autoconfigure.endpoint", "org.springframework.boot.actuate.autoconfigure.endpoint.condition", "org.springframework.boot.actuate.autoconfigure.endpoint.expose", "org.springframework.boot.actuate.autoconfigure.endpoint.jackson", "org.springframework.boot.actuate.autoconfigure.endpoint.jmx", "org.springframework.boot.actuate.autoconfigure.endpoint.web", "org.springframework.boot.actuate.autoconfigure.endpoint.web.jersey", "org.springframework.boot.actuate.autoconfigure.endpoint.web.reactive", "org.springframework.boot.actuate.autoconfigure.endpoint.web.servlet", "org.springframework.boot.actuate.autoconfigure.env", "org.springframework.boot.actuate.autoconfigure.flyway", "org.springframework.boot.actuate.autoconfigure.hazelcast", "org.springframework.boot.actuate.autoconfigure.health", "org.springframework.boot.actuate.autoconfigure.info", "org.springframework.boot.actuate.autoconfigure.integration", "org.springframework.boot.actuate.autoconfigure.jdbc", "org.springframework.boot.actuate.autoconfigure.jms", "org.springframework.boot.actuate.autoconfigure.ldap", "org.springframework.boot.actuate.autoconfigure.liquibase", "org.springframework.boot.actuate.autoconfigure.logging", "org.springframework.boot.actuate.autoconfigure.logging.otlp", "org.springframework.boot.actuate.autoconfigure.mail", "org.springframework.boot.actuate.autoconfigure.management", "org.springframework.boot.actuate.autoconfigure.metrics", "org.springframework.boot.actuate.autoconfigure.metrics.amqp", "org.springframework.boot.actuate.autoconfigure.metrics.cache", "org.springframework.boot.actuate.autoconfigure.metrics.data", "org.springframework.boot.actuate.autoconfigure.metrics.export", "org.springframework.boot.actuate.autoconfigure.metrics.export.appoptics", "org.springframework.boot.actuate.autoconfigure.metrics.export.atlas", "org.springframework.boot.actuate.autoconfigure.metrics.export.datadog", "org.springframework.boot.actuate.autoconfigure.metrics.export.dynatrace", "org.springframework.boot.actuate.autoconfigure.metrics.export.elastic", "org.springframework.boot.actuate.autoconfigure.metrics.export.ganglia", "org.springframework.boot.actuate.autoconfigure.metrics.export.graphite", "org.springframework.boot.actuate.autoconfigure.metrics.export.humio", "org.springframework.boot.actuate.autoconfigure.metrics.export.influx", "org.springframework.boot.actuate.autoconfigure.metrics.export.jmx", "org.springframework.boot.actuate.autoconfigure.metrics.export.kairos", "org.springframework.boot.actuate.autoconfigure.metrics.export.newrelic", "org.springframework.boot.actuate.autoconfigure.metrics.export.otlp", "org.springframework.boot.actuate.autoconfigure.metrics.export.prometheus", "org.springframework.boot.actuate.autoconfigure.metrics.export.properties", "org.springframework.boot.actuate.autoconfigure.metrics.export.signalfx", "org.springframework.boot.actuate.autoconfigure.metrics.export.simple", "org.springframework.boot.actuate.autoconfigure.metrics.export.stackdriver", "org.springframework.boot.actuate.autoconfigure.metrics.export.statsd", "org.springframework.boot.actuate.autoconfigure.metrics.export.wavefront", "org.springframework.boot.actuate.autoconfigure.metrics.integration", "org.springframework.boot.actuate.autoconfigure.metrics.jdbc", "org.springframework.boot.actuate.autoconfigure.metrics.jersey", "org.springframework.boot.actuate.autoconfigure.metrics.mongo", "org.springframework.boot.actuate.autoconfigure.metrics.orm.jpa", "org.springframework.boot.actuate.autoconfigure.metrics.r2dbc", "org.springframework.boot.actuate.autoconfigure.metrics.redis", "org.springframework.boot.actuate.autoconfigure.metrics.startup", "org.springframework.boot.actuate.autoconfigure.metrics.task", "org.springframework.boot.actuate.autoconfigure.metrics.web.jetty", "org.springframework.boot.actuate.autoconfigure.metrics.web.tomcat", "org.springframework.boot.actuate.autoconfigure.neo4j", "org.springframework.boot.actuate.autoconfigure.observation", "org.springframework.boot.actuate.autoconfigure.observation.batch", "org.springframework.boot.actuate.autoconfigure.observation.graphql", "org.springframework.boot.actuate.autoconfigure.observation.web.client", "org.springframework.boot.actuate.autoconfigure.observation.web.reactive", "org.springframework.boot.actuate.autoconfigure.observation.web.servlet", "org.springframework.boot.actuate.autoconfigure.opentelemetry", "org.springframework.boot.actuate.autoconfigure.quartz", "org.springframework.boot.actuate.autoconfigure.r2dbc", "org.springframework.boot.actuate.autoconfigure.sbom", "org.springframework.boot.actuate.autoconfigure.scheduling", "org.springframework.boot.actuate.autoconfigure.security.reactive", "org.springframework.boot.actuate.autoconfigure.security.servlet", "org.springframework.boot.actuate.autoconfigure.session", "org.springframework.boot.actuate.autoconfigure.ssl", "org.springframework.boot.actuate.autoconfigure.startup", "org.springframework.boot.actuate.autoconfigure.system", "org.springframework.boot.actuate.autoconfigure.tracing", "org.springframework.boot.actuate.autoconfigure.tracing.otlp", "org.springframework.boot.actuate.autoconfigure.tracing.prometheus", "org.springframework.boot.actuate.autoconfigure.tracing.wavefront", "org.springframework.boot.actuate.autoconfigure.tracing.zipkin", "org.springframework.boot.actuate.autoconfigure.wavefront", "org.springframework.boot.actuate.autoconfigure.web", "org.springframework.boot.actuate.autoconfigure.web.exchanges", "org.springframework.boot.actuate.autoconfigure.web.jersey", "org.springframework.boot.actuate.autoconfigure.web.mappings", "org.springframework.boot.actuate.autoconfigure.web.reactive", "org.springframework.boot.actuate.autoconfigure.web.server", "org.springframework.boot.actuate.autoconfigure.web.servlet" ], "org.springframework.boot:spring-boot-autoconfigure": [ "org.springframework.boot.autoconfigure", "org.springframework.boot.autoconfigure.admin", "org.springframework.boot.autoconfigure.amqp", "org.springframework.boot.autoconfigure.aop", "org.springframework.boot.autoconfigure.availability", "org.springframework.boot.autoconfigure.batch", "org.springframework.boot.autoconfigure.cache", "org.springframework.boot.autoconfigure.cassandra", "org.springframework.boot.autoconfigure.codec", "org.springframework.boot.autoconfigure.condition", "org.springframework.boot.autoconfigure.container", "org.springframework.boot.autoconfigure.context", "org.springframework.boot.autoconfigure.couchbase", "org.springframework.boot.autoconfigure.dao", "org.springframework.boot.autoconfigure.data", "org.springframework.boot.autoconfigure.data.cassandra", "org.springframework.boot.autoconfigure.data.couchbase", "org.springframework.boot.autoconfigure.data.elasticsearch", "org.springframework.boot.autoconfigure.data.jdbc", "org.springframework.boot.autoconfigure.data.jpa", "org.springframework.boot.autoconfigure.data.ldap", "org.springframework.boot.autoconfigure.data.mongo", "org.springframework.boot.autoconfigure.data.neo4j", "org.springframework.boot.autoconfigure.data.r2dbc", "org.springframework.boot.autoconfigure.data.redis", "org.springframework.boot.autoconfigure.data.rest", "org.springframework.boot.autoconfigure.data.web", "org.springframework.boot.autoconfigure.diagnostics.analyzer", "org.springframework.boot.autoconfigure.domain", "org.springframework.boot.autoconfigure.elasticsearch", "org.springframework.boot.autoconfigure.flyway", "org.springframework.boot.autoconfigure.freemarker", "org.springframework.boot.autoconfigure.graphql", "org.springframework.boot.autoconfigure.graphql.data", "org.springframework.boot.autoconfigure.graphql.reactive", "org.springframework.boot.autoconfigure.graphql.rsocket", "org.springframework.boot.autoconfigure.graphql.security", "org.springframework.boot.autoconfigure.graphql.servlet", "org.springframework.boot.autoconfigure.groovy.template", "org.springframework.boot.autoconfigure.gson", "org.springframework.boot.autoconfigure.h2", "org.springframework.boot.autoconfigure.hateoas", "org.springframework.boot.autoconfigure.hazelcast", "org.springframework.boot.autoconfigure.http", "org.springframework.boot.autoconfigure.http.client", "org.springframework.boot.autoconfigure.http.codec", "org.springframework.boot.autoconfigure.info", "org.springframework.boot.autoconfigure.integration", "org.springframework.boot.autoconfigure.jackson", "org.springframework.boot.autoconfigure.jdbc", "org.springframework.boot.autoconfigure.jdbc.metadata", "org.springframework.boot.autoconfigure.jersey", "org.springframework.boot.autoconfigure.jms", "org.springframework.boot.autoconfigure.jms.activemq", "org.springframework.boot.autoconfigure.jms.artemis", "org.springframework.boot.autoconfigure.jmx", "org.springframework.boot.autoconfigure.jooq", "org.springframework.boot.autoconfigure.jsonb", "org.springframework.boot.autoconfigure.kafka", "org.springframework.boot.autoconfigure.ldap", "org.springframework.boot.autoconfigure.ldap.embedded", "org.springframework.boot.autoconfigure.liquibase", "org.springframework.boot.autoconfigure.logging", "org.springframework.boot.autoconfigure.mail", "org.springframework.boot.autoconfigure.mongo", "org.springframework.boot.autoconfigure.mustache", "org.springframework.boot.autoconfigure.neo4j", "org.springframework.boot.autoconfigure.netty", "org.springframework.boot.autoconfigure.orm.jpa", "org.springframework.boot.autoconfigure.pulsar", "org.springframework.boot.autoconfigure.quartz", "org.springframework.boot.autoconfigure.r2dbc", "org.springframework.boot.autoconfigure.reactor", "org.springframework.boot.autoconfigure.reactor.netty", "org.springframework.boot.autoconfigure.rsocket", "org.springframework.boot.autoconfigure.security", "org.springframework.boot.autoconfigure.security.oauth2.client", "org.springframework.boot.autoconfigure.security.oauth2.client.reactive", "org.springframework.boot.autoconfigure.security.oauth2.client.servlet", "org.springframework.boot.autoconfigure.security.oauth2.resource", "org.springframework.boot.autoconfigure.security.oauth2.resource.reactive", "org.springframework.boot.autoconfigure.security.oauth2.resource.servlet", "org.springframework.boot.autoconfigure.security.oauth2.server.servlet", "org.springframework.boot.autoconfigure.security.reactive", "org.springframework.boot.autoconfigure.security.rsocket", "org.springframework.boot.autoconfigure.security.saml2", "org.springframework.boot.autoconfigure.security.servlet", "org.springframework.boot.autoconfigure.sendgrid", "org.springframework.boot.autoconfigure.service.connection", "org.springframework.boot.autoconfigure.session", "org.springframework.boot.autoconfigure.sql.init", "org.springframework.boot.autoconfigure.ssl", "org.springframework.boot.autoconfigure.task", "org.springframework.boot.autoconfigure.template", "org.springframework.boot.autoconfigure.thread", "org.springframework.boot.autoconfigure.thymeleaf", "org.springframework.boot.autoconfigure.transaction", "org.springframework.boot.autoconfigure.transaction.jta", "org.springframework.boot.autoconfigure.validation", "org.springframework.boot.autoconfigure.web", "org.springframework.boot.autoconfigure.web.client", "org.springframework.boot.autoconfigure.web.embedded", "org.springframework.boot.autoconfigure.web.format", "org.springframework.boot.autoconfigure.web.reactive", "org.springframework.boot.autoconfigure.web.reactive.error", "org.springframework.boot.autoconfigure.web.reactive.function.client", "org.springframework.boot.autoconfigure.web.servlet", "org.springframework.boot.autoconfigure.web.servlet.error", "org.springframework.boot.autoconfigure.webservices", "org.springframework.boot.autoconfigure.webservices.client", "org.springframework.boot.autoconfigure.websocket.reactive", "org.springframework.boot.autoconfigure.websocket.servlet" ], "org.springframework.boot:spring-boot-configuration-processor": [ "org.springframework.boot.configurationprocessor", "org.springframework.boot.configurationprocessor.fieldvalues", "org.springframework.boot.configurationprocessor.fieldvalues.javac", "org.springframework.boot.configurationprocessor.json", "org.springframework.boot.configurationprocessor.metadata", "org.springframework.boot.configurationprocessor.support" ], "org.springframework.boot:spring-boot-jarmode-tools": [ "org.springframework.boot.jarmode.tools" ], "org.springframework.boot:spring-boot-loader": [ "org.springframework.boot.loader.jar", "org.springframework.boot.loader.jarmode", "org.springframework.boot.loader.launch", "org.springframework.boot.loader.log", "org.springframework.boot.loader.net.protocol", "org.springframework.boot.loader.net.protocol.jar", "org.springframework.boot.loader.net.protocol.nested", "org.springframework.boot.loader.net.util", "org.springframework.boot.loader.nio.file", "org.springframework.boot.loader.ref", "org.springframework.boot.loader.zip" ], "org.springframework.boot:spring-boot-loader-tools": [ "org.springframework.boot.loader.tools", "org.springframework.boot.loader.tools.layer" ], "org.springframework.boot:spring-boot-test": [ "org.springframework.boot.test.context", "org.springframework.boot.test.context.assertj", "org.springframework.boot.test.context.filter", "org.springframework.boot.test.context.runner", "org.springframework.boot.test.graphql.tester", "org.springframework.boot.test.json", "org.springframework.boot.test.mock.mockito", "org.springframework.boot.test.mock.web", "org.springframework.boot.test.rsocket.server", "org.springframework.boot.test.system", "org.springframework.boot.test.util", "org.springframework.boot.test.web", "org.springframework.boot.test.web.client", "org.springframework.boot.test.web.htmlunit", "org.springframework.boot.test.web.htmlunit.webdriver", "org.springframework.boot.test.web.reactive.server", "org.springframework.boot.test.web.reactor.netty", "org.springframework.boot.test.web.server" ], "org.springframework.boot:spring-boot-test-autoconfigure": [ "org.springframework.boot.test.autoconfigure", "org.springframework.boot.test.autoconfigure.actuate.observability", "org.springframework.boot.test.autoconfigure.core", "org.springframework.boot.test.autoconfigure.data.cassandra", "org.springframework.boot.test.autoconfigure.data.couchbase", "org.springframework.boot.test.autoconfigure.data.elasticsearch", "org.springframework.boot.test.autoconfigure.data.jdbc", "org.springframework.boot.test.autoconfigure.data.ldap", "org.springframework.boot.test.autoconfigure.data.mongo", "org.springframework.boot.test.autoconfigure.data.neo4j", "org.springframework.boot.test.autoconfigure.data.r2dbc", "org.springframework.boot.test.autoconfigure.data.redis", "org.springframework.boot.test.autoconfigure.filter", "org.springframework.boot.test.autoconfigure.graphql", "org.springframework.boot.test.autoconfigure.graphql.tester", "org.springframework.boot.test.autoconfigure.jdbc", "org.springframework.boot.test.autoconfigure.jooq", "org.springframework.boot.test.autoconfigure.json", "org.springframework.boot.test.autoconfigure.orm.jpa", "org.springframework.boot.test.autoconfigure.properties", "org.springframework.boot.test.autoconfigure.restdocs", "org.springframework.boot.test.autoconfigure.web.client", "org.springframework.boot.test.autoconfigure.web.reactive", "org.springframework.boot.test.autoconfigure.web.servlet", "org.springframework.boot.test.autoconfigure.webservices.client", "org.springframework.boot.test.autoconfigure.webservices.server" ], "org.springframework.security:spring-security-config": [ "org.springframework.security.config", "org.springframework.security.config.annotation", "org.springframework.security.config.annotation.authentication", "org.springframework.security.config.annotation.authentication.builders", "org.springframework.security.config.annotation.authentication.configuration", "org.springframework.security.config.annotation.authentication.configurers.ldap", "org.springframework.security.config.annotation.authentication.configurers.provisioning", "org.springframework.security.config.annotation.authentication.configurers.userdetails", "org.springframework.security.config.annotation.configuration", "org.springframework.security.config.annotation.method.configuration", "org.springframework.security.config.annotation.rsocket", "org.springframework.security.config.annotation.web", "org.springframework.security.config.annotation.web.builders", "org.springframework.security.config.annotation.web.configuration", "org.springframework.security.config.annotation.web.configurers", "org.springframework.security.config.annotation.web.configurers.oauth2.client", "org.springframework.security.config.annotation.web.configurers.oauth2.server.resource", "org.springframework.security.config.annotation.web.configurers.ott", "org.springframework.security.config.annotation.web.configurers.saml2", "org.springframework.security.config.annotation.web.headers", "org.springframework.security.config.annotation.web.messaging", "org.springframework.security.config.annotation.web.oauth2.client", "org.springframework.security.config.annotation.web.oauth2.login", "org.springframework.security.config.annotation.web.oauth2.resourceserver", "org.springframework.security.config.annotation.web.reactive", "org.springframework.security.config.annotation.web.saml2", "org.springframework.security.config.annotation.web.servlet.configuration", "org.springframework.security.config.annotation.web.session", "org.springframework.security.config.annotation.web.socket", "org.springframework.security.config.aot.hint", "org.springframework.security.config.authentication", "org.springframework.security.config.core", "org.springframework.security.config.core.userdetails", "org.springframework.security.config.crypto", "org.springframework.security.config.debug", "org.springframework.security.config.http", "org.springframework.security.config.ldap", "org.springframework.security.config.method", "org.springframework.security.config.oauth2.client", "org.springframework.security.config.observation", "org.springframework.security.config.provisioning", "org.springframework.security.config.saml2", "org.springframework.security.config.web.server", "org.springframework.security.config.websocket" ], "org.springframework.security:spring-security-core": [ "org.springframework.security.access", "org.springframework.security.access.annotation", "org.springframework.security.access.event", "org.springframework.security.access.expression", "org.springframework.security.access.expression.method", "org.springframework.security.access.hierarchicalroles", "org.springframework.security.access.intercept", "org.springframework.security.access.intercept.aopalliance", "org.springframework.security.access.intercept.aspectj", "org.springframework.security.access.method", "org.springframework.security.access.prepost", "org.springframework.security.access.vote", "org.springframework.security.aot.hint", "org.springframework.security.authentication", "org.springframework.security.authentication.dao", "org.springframework.security.authentication.event", "org.springframework.security.authentication.jaas", "org.springframework.security.authentication.jaas.event", "org.springframework.security.authentication.jaas.memory", "org.springframework.security.authentication.ott", "org.springframework.security.authentication.ott.reactive", "org.springframework.security.authentication.password", "org.springframework.security.authorization", "org.springframework.security.authorization.event", "org.springframework.security.authorization.method", "org.springframework.security.concurrent", "org.springframework.security.context", "org.springframework.security.converter", "org.springframework.security.core", "org.springframework.security.core.annotation", "org.springframework.security.core.authority", "org.springframework.security.core.authority.mapping", "org.springframework.security.core.context", "org.springframework.security.core.parameters", "org.springframework.security.core.session", "org.springframework.security.core.token", "org.springframework.security.core.userdetails", "org.springframework.security.core.userdetails.cache", "org.springframework.security.core.userdetails.jdbc", "org.springframework.security.core.userdetails.memory", "org.springframework.security.jackson2", "org.springframework.security.provisioning", "org.springframework.security.scheduling", "org.springframework.security.task", "org.springframework.security.util" ], "org.springframework.security:spring-security-crypto": [ "org.springframework.security.crypto.argon2", "org.springframework.security.crypto.bcrypt", "org.springframework.security.crypto.codec", "org.springframework.security.crypto.encrypt", "org.springframework.security.crypto.factory", "org.springframework.security.crypto.keygen", "org.springframework.security.crypto.password", "org.springframework.security.crypto.scrypt", "org.springframework.security.crypto.util" ], "org.springframework.security:spring-security-web": [ "org.springframework.security.web", "org.springframework.security.web.access", "org.springframework.security.web.access.channel", "org.springframework.security.web.access.expression", "org.springframework.security.web.access.intercept", "org.springframework.security.web.aot.hint", "org.springframework.security.web.authentication", "org.springframework.security.web.authentication.logout", "org.springframework.security.web.authentication.ott", "org.springframework.security.web.authentication.password", "org.springframework.security.web.authentication.preauth", "org.springframework.security.web.authentication.preauth.j2ee", "org.springframework.security.web.authentication.preauth.websphere", "org.springframework.security.web.authentication.preauth.x509", "org.springframework.security.web.authentication.rememberme", "org.springframework.security.web.authentication.session", "org.springframework.security.web.authentication.switchuser", "org.springframework.security.web.authentication.ui", "org.springframework.security.web.authentication.www", "org.springframework.security.web.bind.annotation", "org.springframework.security.web.bind.support", "org.springframework.security.web.context", "org.springframework.security.web.context.request.async", "org.springframework.security.web.context.support", "org.springframework.security.web.csrf", "org.springframework.security.web.debug", "org.springframework.security.web.firewall", "org.springframework.security.web.header", "org.springframework.security.web.header.writers", "org.springframework.security.web.header.writers.frameoptions", "org.springframework.security.web.http", "org.springframework.security.web.jaasapi", "org.springframework.security.web.jackson2", "org.springframework.security.web.method.annotation", "org.springframework.security.web.reactive.result.method.annotation", "org.springframework.security.web.reactive.result.view", "org.springframework.security.web.savedrequest", "org.springframework.security.web.server", "org.springframework.security.web.server.authentication", "org.springframework.security.web.server.authentication.logout", "org.springframework.security.web.server.authentication.ott", "org.springframework.security.web.server.authorization", "org.springframework.security.web.server.context", "org.springframework.security.web.server.csrf", "org.springframework.security.web.server.firewall", "org.springframework.security.web.server.header", "org.springframework.security.web.server.jackson2", "org.springframework.security.web.server.savedrequest", "org.springframework.security.web.server.transport", "org.springframework.security.web.server.ui", "org.springframework.security.web.server.util.matcher", "org.springframework.security.web.servlet.support.csrf", "org.springframework.security.web.servlet.util.matcher", "org.springframework.security.web.servletapi", "org.springframework.security.web.session", "org.springframework.security.web.util", "org.springframework.security.web.util.matcher", "org.springframework.security.web.webauthn.api", "org.springframework.security.web.webauthn.authentication", "org.springframework.security.web.webauthn.jackson", "org.springframework.security.web.webauthn.management", "org.springframework.security.web.webauthn.registration" ], "org.springframework:spring-aop": [ "org.aopalliance.aop", "org.aopalliance.intercept", "org.springframework.aop", "org.springframework.aop.aspectj", "org.springframework.aop.aspectj.annotation", "org.springframework.aop.aspectj.autoproxy", "org.springframework.aop.config", "org.springframework.aop.framework", "org.springframework.aop.framework.adapter", "org.springframework.aop.framework.autoproxy", "org.springframework.aop.framework.autoproxy.target", "org.springframework.aop.interceptor", "org.springframework.aop.scope", "org.springframework.aop.support", "org.springframework.aop.support.annotation", "org.springframework.aop.target", "org.springframework.aop.target.dynamic" ], "org.springframework:spring-aspects": [ "org.springframework.beans.factory.aspectj", "org.springframework.cache.aspectj", "org.springframework.context.annotation.aspectj", "org.springframework.scheduling.aspectj", "org.springframework.transaction.aspectj" ], "org.springframework:spring-beans": [ "org.springframework.beans", "org.springframework.beans.factory", "org.springframework.beans.factory.annotation", "org.springframework.beans.factory.aot", "org.springframework.beans.factory.config", "org.springframework.beans.factory.groovy", "org.springframework.beans.factory.parsing", "org.springframework.beans.factory.serviceloader", "org.springframework.beans.factory.support", "org.springframework.beans.factory.wiring", "org.springframework.beans.factory.xml", "org.springframework.beans.propertyeditors", "org.springframework.beans.support" ], "org.springframework:spring-context": [ "org.springframework.cache", "org.springframework.cache.annotation", "org.springframework.cache.concurrent", "org.springframework.cache.config", "org.springframework.cache.interceptor", "org.springframework.cache.support", "org.springframework.context", "org.springframework.context.annotation", "org.springframework.context.aot", "org.springframework.context.config", "org.springframework.context.event", "org.springframework.context.expression", "org.springframework.context.i18n", "org.springframework.context.index", "org.springframework.context.support", "org.springframework.context.weaving", "org.springframework.ejb.config", "org.springframework.format", "org.springframework.format.annotation", "org.springframework.format.datetime", "org.springframework.format.datetime.standard", "org.springframework.format.number", "org.springframework.format.number.money", "org.springframework.format.support", "org.springframework.instrument.classloading", "org.springframework.instrument.classloading.glassfish", "org.springframework.instrument.classloading.jboss", "org.springframework.instrument.classloading.tomcat", "org.springframework.jmx", "org.springframework.jmx.access", "org.springframework.jmx.export", "org.springframework.jmx.export.annotation", "org.springframework.jmx.export.assembler", "org.springframework.jmx.export.metadata", "org.springframework.jmx.export.naming", "org.springframework.jmx.export.notification", "org.springframework.jmx.support", "org.springframework.jndi", "org.springframework.jndi.support", "org.springframework.scheduling", "org.springframework.scheduling.annotation", "org.springframework.scheduling.concurrent", "org.springframework.scheduling.config", "org.springframework.scheduling.support", "org.springframework.scripting", "org.springframework.scripting.bsh", "org.springframework.scripting.config", "org.springframework.scripting.groovy", "org.springframework.scripting.support", "org.springframework.stereotype", "org.springframework.ui", "org.springframework.ui.context", "org.springframework.ui.context.support", "org.springframework.validation", "org.springframework.validation.annotation", "org.springframework.validation.beanvalidation", "org.springframework.validation.method", "org.springframework.validation.support" ], "org.springframework:spring-context-support": [ "org.springframework.cache.caffeine", "org.springframework.cache.jcache", "org.springframework.cache.jcache.config", "org.springframework.cache.jcache.interceptor", "org.springframework.cache.transaction", "org.springframework.mail", "org.springframework.mail.javamail", "org.springframework.scheduling.quartz", "org.springframework.ui.freemarker" ], "org.springframework:spring-core": [ "org.springframework.aot", "org.springframework.aot.generate", "org.springframework.aot.hint", "org.springframework.aot.hint.annotation", "org.springframework.aot.hint.predicate", "org.springframework.aot.hint.support", "org.springframework.aot.nativex", "org.springframework.aot.nativex.feature", "org.springframework.aot.nativex.substitution", "org.springframework.asm", "org.springframework.cglib", "org.springframework.cglib.beans", "org.springframework.cglib.core", "org.springframework.cglib.core.internal", "org.springframework.cglib.proxy", "org.springframework.cglib.reflect", "org.springframework.cglib.transform", "org.springframework.cglib.transform.impl", "org.springframework.cglib.util", "org.springframework.core", "org.springframework.core.annotation", "org.springframework.core.codec", "org.springframework.core.convert", "org.springframework.core.convert.converter", "org.springframework.core.convert.support", "org.springframework.core.env", "org.springframework.core.io", "org.springframework.core.io.buffer", "org.springframework.core.io.support", "org.springframework.core.log", "org.springframework.core.metrics", "org.springframework.core.metrics.jfr", "org.springframework.core.serializer", "org.springframework.core.serializer.support", "org.springframework.core.style", "org.springframework.core.task", "org.springframework.core.task.support", "org.springframework.core.type", "org.springframework.core.type.classreading", "org.springframework.core.type.filter", "org.springframework.javapoet", "org.springframework.lang", "org.springframework.objenesis", "org.springframework.objenesis.instantiator", "org.springframework.objenesis.instantiator.android", "org.springframework.objenesis.instantiator.annotations", "org.springframework.objenesis.instantiator.basic", "org.springframework.objenesis.instantiator.gcj", "org.springframework.objenesis.instantiator.perc", "org.springframework.objenesis.instantiator.sun", "org.springframework.objenesis.instantiator.util", "org.springframework.objenesis.strategy", "org.springframework.util", "org.springframework.util.backoff", "org.springframework.util.comparator", "org.springframework.util.concurrent", "org.springframework.util.function", "org.springframework.util.unit", "org.springframework.util.xml" ], "org.springframework:spring-expression": [ "org.springframework.expression", "org.springframework.expression.common", "org.springframework.expression.spel", "org.springframework.expression.spel.ast", "org.springframework.expression.spel.standard", "org.springframework.expression.spel.support" ], "org.springframework:spring-jcl": [ "org.apache.commons.logging", "org.apache.commons.logging.impl" ], "org.springframework:spring-jdbc": [ "org.springframework.jdbc", "org.springframework.jdbc.config", "org.springframework.jdbc.core", "org.springframework.jdbc.core.metadata", "org.springframework.jdbc.core.namedparam", "org.springframework.jdbc.core.simple", "org.springframework.jdbc.core.support", "org.springframework.jdbc.datasource", "org.springframework.jdbc.datasource.embedded", "org.springframework.jdbc.datasource.init", "org.springframework.jdbc.datasource.lookup", "org.springframework.jdbc.object", "org.springframework.jdbc.support", "org.springframework.jdbc.support.incrementer", "org.springframework.jdbc.support.lob", "org.springframework.jdbc.support.rowset", "org.springframework.jdbc.support.xml" ], "org.springframework:spring-test": [ "org.springframework.mock.env", "org.springframework.mock.http", "org.springframework.mock.http.client", "org.springframework.mock.http.client.reactive", "org.springframework.mock.http.server.reactive", "org.springframework.mock.web", "org.springframework.mock.web.reactive.function.server", "org.springframework.mock.web.server", "org.springframework.test.annotation", "org.springframework.test.context", "org.springframework.test.context.aot", "org.springframework.test.context.bean.override", "org.springframework.test.context.bean.override.convention", "org.springframework.test.context.bean.override.mockito", "org.springframework.test.context.cache", "org.springframework.test.context.event", "org.springframework.test.context.event.annotation", "org.springframework.test.context.hint", "org.springframework.test.context.jdbc", "org.springframework.test.context.junit.jupiter", "org.springframework.test.context.junit.jupiter.web", "org.springframework.test.context.junit4", "org.springframework.test.context.junit4.rules", "org.springframework.test.context.junit4.statements", "org.springframework.test.context.observation", "org.springframework.test.context.support", "org.springframework.test.context.testng", "org.springframework.test.context.transaction", "org.springframework.test.context.util", "org.springframework.test.context.web", "org.springframework.test.context.web.socket", "org.springframework.test.http", "org.springframework.test.jdbc", "org.springframework.test.json", "org.springframework.test.util", "org.springframework.test.validation", "org.springframework.test.web", "org.springframework.test.web.client", "org.springframework.test.web.client.match", "org.springframework.test.web.client.response", "org.springframework.test.web.reactive.server", "org.springframework.test.web.servlet", "org.springframework.test.web.servlet.assertj", "org.springframework.test.web.servlet.client", "org.springframework.test.web.servlet.htmlunit", "org.springframework.test.web.servlet.htmlunit.webdriver", "org.springframework.test.web.servlet.request", "org.springframework.test.web.servlet.result", "org.springframework.test.web.servlet.setup" ], "org.springframework:spring-tx": [ "org.springframework.dao", "org.springframework.dao.annotation", "org.springframework.dao.support", "org.springframework.jca.endpoint", "org.springframework.jca.support", "org.springframework.transaction", "org.springframework.transaction.annotation", "org.springframework.transaction.config", "org.springframework.transaction.event", "org.springframework.transaction.interceptor", "org.springframework.transaction.jta", "org.springframework.transaction.reactive", "org.springframework.transaction.support" ], "org.springframework:spring-web": [ "org.springframework.http", "org.springframework.http.client", "org.springframework.http.client.observation", "org.springframework.http.client.reactive", "org.springframework.http.client.support", "org.springframework.http.codec", "org.springframework.http.codec.cbor", "org.springframework.http.codec.json", "org.springframework.http.codec.multipart", "org.springframework.http.codec.protobuf", "org.springframework.http.codec.support", "org.springframework.http.codec.xml", "org.springframework.http.converter", "org.springframework.http.converter.cbor", "org.springframework.http.converter.feed", "org.springframework.http.converter.json", "org.springframework.http.converter.protobuf", "org.springframework.http.converter.smile", "org.springframework.http.converter.support", "org.springframework.http.converter.xml", "org.springframework.http.converter.yaml", "org.springframework.http.server", "org.springframework.http.server.observation", "org.springframework.http.server.reactive", "org.springframework.http.server.reactive.observation", "org.springframework.http.support", "org.springframework.web", "org.springframework.web.accept", "org.springframework.web.bind", "org.springframework.web.bind.annotation", "org.springframework.web.bind.support", "org.springframework.web.client", "org.springframework.web.client.support", "org.springframework.web.context", "org.springframework.web.context.annotation", "org.springframework.web.context.request", "org.springframework.web.context.request.async", "org.springframework.web.context.support", "org.springframework.web.cors", "org.springframework.web.cors.reactive", "org.springframework.web.filter", "org.springframework.web.filter.reactive", "org.springframework.web.jsf", "org.springframework.web.jsf.el", "org.springframework.web.method", "org.springframework.web.method.annotation", "org.springframework.web.method.support", "org.springframework.web.multipart", "org.springframework.web.multipart.support", "org.springframework.web.server", "org.springframework.web.server.adapter", "org.springframework.web.server.handler", "org.springframework.web.server.i18n", "org.springframework.web.server.session", "org.springframework.web.service", "org.springframework.web.service.annotation", "org.springframework.web.service.invoker", "org.springframework.web.util", "org.springframework.web.util.pattern" ], "org.springframework:spring-webmvc": [ "org.springframework.web.servlet", "org.springframework.web.servlet.config", "org.springframework.web.servlet.config.annotation", "org.springframework.web.servlet.function", "org.springframework.web.servlet.function.support", "org.springframework.web.servlet.handler", "org.springframework.web.servlet.i18n", "org.springframework.web.servlet.mvc", "org.springframework.web.servlet.mvc.annotation", "org.springframework.web.servlet.mvc.condition", "org.springframework.web.servlet.mvc.method", "org.springframework.web.servlet.mvc.method.annotation", "org.springframework.web.servlet.mvc.support", "org.springframework.web.servlet.resource", "org.springframework.web.servlet.support", "org.springframework.web.servlet.tags", "org.springframework.web.servlet.tags.form", "org.springframework.web.servlet.theme", "org.springframework.web.servlet.view", "org.springframework.web.servlet.view.document", "org.springframework.web.servlet.view.feed", "org.springframework.web.servlet.view.freemarker", "org.springframework.web.servlet.view.groovy", "org.springframework.web.servlet.view.json", "org.springframework.web.servlet.view.script", "org.springframework.web.servlet.view.xml", "org.springframework.web.servlet.view.xslt" ], "org.thymeleaf:thymeleaf": [ "org.thymeleaf", "org.thymeleaf.cache", "org.thymeleaf.context", "org.thymeleaf.dialect", "org.thymeleaf.engine", "org.thymeleaf.exceptions", "org.thymeleaf.expression", "org.thymeleaf.inline", "org.thymeleaf.linkbuilder", "org.thymeleaf.messageresolver", "org.thymeleaf.model", "org.thymeleaf.postprocessor", "org.thymeleaf.preprocessor", "org.thymeleaf.processor", "org.thymeleaf.processor.cdatasection", "org.thymeleaf.processor.comment", "org.thymeleaf.processor.doctype", "org.thymeleaf.processor.element", "org.thymeleaf.processor.processinginstruction", "org.thymeleaf.processor.templateboundaries", "org.thymeleaf.processor.text", "org.thymeleaf.processor.xmldeclaration", "org.thymeleaf.standard", "org.thymeleaf.standard.expression", "org.thymeleaf.standard.inline", "org.thymeleaf.standard.processor", "org.thymeleaf.standard.serializer", "org.thymeleaf.standard.util", "org.thymeleaf.templatemode", "org.thymeleaf.templateparser", "org.thymeleaf.templateparser.markup", "org.thymeleaf.templateparser.markup.decoupled", "org.thymeleaf.templateparser.raw", "org.thymeleaf.templateparser.reader", "org.thymeleaf.templateparser.text", "org.thymeleaf.templateresolver", "org.thymeleaf.templateresource", "org.thymeleaf.util", "org.thymeleaf.util.temporal", "org.thymeleaf.web", "org.thymeleaf.web.servlet" ], "org.thymeleaf:thymeleaf-spring6": [ "org.thymeleaf.spring6", "org.thymeleaf.spring6.context", "org.thymeleaf.spring6.context.webflux", "org.thymeleaf.spring6.context.webmvc", "org.thymeleaf.spring6.dialect", "org.thymeleaf.spring6.expression", "org.thymeleaf.spring6.messageresolver", "org.thymeleaf.spring6.naming", "org.thymeleaf.spring6.processor", "org.thymeleaf.spring6.requestdata", "org.thymeleaf.spring6.templateresolver", "org.thymeleaf.spring6.templateresource", "org.thymeleaf.spring6.util", "org.thymeleaf.spring6.view", "org.thymeleaf.spring6.view.reactive", "org.thymeleaf.spring6.web.webflux", "org.thymeleaf.spring6.webflow.view" ], "org.unbescape:unbescape": [ "org.unbescape", "org.unbescape.css", "org.unbescape.csv", "org.unbescape.html", "org.unbescape.java", "org.unbescape.javascript", "org.unbescape.json", "org.unbescape.properties", "org.unbescape.uri", "org.unbescape.xml" ], "org.xmlunit:xmlunit-core": [ "org.xmlunit", "org.xmlunit.builder", "org.xmlunit.builder.javax_jaxb", "org.xmlunit.diff", "org.xmlunit.input", "org.xmlunit.transform", "org.xmlunit.util", "org.xmlunit.validation", "org.xmlunit.xpath" ], "org.yaml:snakeyaml": [ "org.yaml.snakeyaml", "org.yaml.snakeyaml.comments", "org.yaml.snakeyaml.composer", "org.yaml.snakeyaml.constructor", "org.yaml.snakeyaml.emitter", "org.yaml.snakeyaml.env", "org.yaml.snakeyaml.error", "org.yaml.snakeyaml.events", "org.yaml.snakeyaml.extensions.compactnotation", "org.yaml.snakeyaml.external.biz.base64Coder", "org.yaml.snakeyaml.external.com.google.gdata.util.common.base", "org.yaml.snakeyaml.inspector", "org.yaml.snakeyaml.internal", "org.yaml.snakeyaml.introspector", "org.yaml.snakeyaml.nodes", "org.yaml.snakeyaml.parser", "org.yaml.snakeyaml.reader", "org.yaml.snakeyaml.representer", "org.yaml.snakeyaml.resolver", "org.yaml.snakeyaml.scanner", "org.yaml.snakeyaml.serializer", "org.yaml.snakeyaml.tokens", "org.yaml.snakeyaml.util" ] }, "repositories": { "https://repo1.maven.org/maven2/": [ "biz.aQute.bnd:biz.aQute.bnd.util", "biz.aQute.bnd:biz.aQute.bndlib", "ch.qos.logback:logback-classic", "ch.qos.logback:logback-core", "com.fasterxml.jackson.core:jackson-annotations", "com.fasterxml.jackson.core:jackson-core", "com.fasterxml.jackson.core:jackson-databind", "com.fasterxml.jackson.datatype:jackson-datatype-jdk8", "com.fasterxml.jackson.datatype:jackson-datatype-jsr310", "com.fasterxml.jackson.module:jackson-module-parameter-names", "com.google.auto.value:auto-value-annotations", "com.google.caliper:caliper", "com.google.caliper:caliper-api", "com.google.caliper:caliper-core", "com.google.caliper:caliper-runner", "com.google.caliper:caliper-util", "com.google.caliper:caliper-worker", "com.google.caliper:caliper-worker-jvm", "com.google.code.findbugs:jsr305", "com.google.code.gson:gson", "com.google.code.java-allocation-instrumenter:java-allocation-instrumenter", "com.google.dagger:dagger", "com.google.dagger:dagger-producers", "com.google.errorprone:error_prone_annotations", "com.google.guava:failureaccess", "com.google.guava:guava", "com.google.guava:guava-testlib", "com.google.guava:listenablefuture", "com.google.j2objc:j2objc-annotations", "com.google.truth:truth", "com.jayway.jsonpath:json-path", "com.squareup.okhttp:okhttp", "com.squareup.okio:okio", "com.sun.jersey:jersey-client", "com.sun.jersey:jersey-core", "com.vaadin.external.google:android-json", "com.zaxxer:HikariCP", "info.picocli:picocli", "io.micrometer:micrometer-commons", "io.micrometer:micrometer-core", "io.micrometer:micrometer-jakarta9", "io.micrometer:micrometer-observation", "jakarta.activation:jakarta.activation-api", "jakarta.annotation:jakarta.annotation-api", "jakarta.enterprise:jakarta.enterprise.cdi-api", "jakarta.enterprise:jakarta.enterprise.lang-model", "jakarta.inject:jakarta.inject-api", "jakarta.interceptor:jakarta.interceptor-api", "jakarta.servlet:jakarta.servlet-api", "jakarta.transaction:jakarta.transaction-api", "jakarta.websocket:jakarta.websocket-api", "jakarta.websocket:jakarta.websocket-client-api", "jakarta.xml.bind:jakarta.xml.bind-api", "javax.annotation:javax.annotation-api", "javax.inject:javax.inject", "javax.ws.rs:jsr311-api", "joda-time:joda-time", "junit:junit", "net.bytebuddy:byte-buddy", "net.bytebuddy:byte-buddy-agent", "net.minidev:accessors-smart", "net.minidev:json-smart", "org.apache.commons:commons-compress", "org.apache.logging.log4j:log4j-api", "org.apache.logging.log4j:log4j-to-slf4j", "org.apache.tomcat.embed:tomcat-embed-core", "org.apache.tomcat.embed:tomcat-embed-el", "org.apache.tomcat.embed:tomcat-embed-websocket", "org.apiguardian:apiguardian-api", "org.aspectj:aspectjweaver", "org.assertj:assertj-core", "org.attoparser:attoparser", "org.awaitility:awaitility", "org.checkerframework:checker-compat-qual", "org.checkerframework:checker-qual", "org.eclipse.jetty.ee10.websocket:jetty-ee10-websocket-jakarta-client", "org.eclipse.jetty.ee10.websocket:jetty-ee10-websocket-jakarta-common", "org.eclipse.jetty.ee10.websocket:jetty-ee10-websocket-jakarta-server", "org.eclipse.jetty.ee10.websocket:jetty-ee10-websocket-jetty-server", "org.eclipse.jetty.ee10.websocket:jetty-ee10-websocket-servlet", "org.eclipse.jetty.ee10:jetty-ee10-annotations", "org.eclipse.jetty.ee10:jetty-ee10-plus", "org.eclipse.jetty.ee10:jetty-ee10-servlet", "org.eclipse.jetty.ee10:jetty-ee10-servlets", "org.eclipse.jetty.ee10:jetty-ee10-webapp", "org.eclipse.jetty.websocket:jetty-websocket-core-client", "org.eclipse.jetty.websocket:jetty-websocket-core-common", "org.eclipse.jetty.websocket:jetty-websocket-core-server", "org.eclipse.jetty.websocket:jetty-websocket-jetty-api", "org.eclipse.jetty.websocket:jetty-websocket-jetty-common", "org.eclipse.jetty:jetty-alpn-client", "org.eclipse.jetty:jetty-client", "org.eclipse.jetty:jetty-ee", "org.eclipse.jetty:jetty-http", "org.eclipse.jetty:jetty-io", "org.eclipse.jetty:jetty-plus", "org.eclipse.jetty:jetty-security", "org.eclipse.jetty:jetty-server", "org.eclipse.jetty:jetty-session", "org.eclipse.jetty:jetty-util", "org.eclipse.jetty:jetty-xml", "org.freemarker:freemarker", "org.hamcrest:hamcrest", "org.hamcrest:hamcrest-core", "org.hdrhistogram:HdrHistogram", "org.junit.jupiter:junit-jupiter", "org.junit.jupiter:junit-jupiter-api", "org.junit.jupiter:junit-jupiter-engine", "org.junit.jupiter:junit-jupiter-params", "org.junit.platform:junit-platform-commons", "org.junit.platform:junit-platform-engine", "org.latencyutils:LatencyUtils", "org.mockito:mockito-core", "org.mockito:mockito-junit-jupiter", "org.objenesis:objenesis", "org.opentest4j:opentest4j", "org.osgi:org.osgi.dto", "org.osgi:org.osgi.framework", "org.osgi:org.osgi.resource", "org.osgi:org.osgi.service.log", "org.osgi:org.osgi.service.repository", "org.osgi:org.osgi.util.function", "org.osgi:org.osgi.util.promise", "org.osgi:org.osgi.util.tracker", "org.osgi:osgi.annotation", "org.ow2.asm:asm", "org.ow2.asm:asm-analysis", "org.ow2.asm:asm-commons", "org.ow2.asm:asm-tree", "org.ow2.asm:asm-util", "org.skyscreamer:jsonassert", "org.slf4j:jul-to-slf4j", "org.slf4j:slf4j-api", "org.springframework.boot:spring-boot", "org.springframework.boot:spring-boot-actuator", "org.springframework.boot:spring-boot-actuator-autoconfigure", "org.springframework.boot:spring-boot-autoconfigure", "org.springframework.boot:spring-boot-configuration-processor", "org.springframework.boot:spring-boot-jarmode-tools", "org.springframework.boot:spring-boot-loader", "org.springframework.boot:spring-boot-loader-tools", "org.springframework.boot:spring-boot-starter", "org.springframework.boot:spring-boot-starter-actuator", "org.springframework.boot:spring-boot-starter-freemarker", "org.springframework.boot:spring-boot-starter-jdbc", "org.springframework.boot:spring-boot-starter-jetty", "org.springframework.boot:spring-boot-starter-json", "org.springframework.boot:spring-boot-starter-logging", "org.springframework.boot:spring-boot-starter-security", "org.springframework.boot:spring-boot-starter-test", "org.springframework.boot:spring-boot-starter-thymeleaf", "org.springframework.boot:spring-boot-starter-tomcat", "org.springframework.boot:spring-boot-starter-web", "org.springframework.boot:spring-boot-test", "org.springframework.boot:spring-boot-test-autoconfigure", "org.springframework.security:spring-security-config", "org.springframework.security:spring-security-core", "org.springframework.security:spring-security-crypto", "org.springframework.security:spring-security-web", "org.springframework:spring-aop", "org.springframework:spring-aspects", "org.springframework:spring-beans", "org.springframework:spring-context", "org.springframework:spring-context-support", "org.springframework:spring-core", "org.springframework:spring-expression", "org.springframework:spring-jcl", "org.springframework:spring-jdbc", "org.springframework:spring-test", "org.springframework:spring-tx", "org.springframework:spring-web", "org.springframework:spring-webmvc", "org.thymeleaf:thymeleaf", "org.thymeleaf:thymeleaf-spring6", "org.unbescape:unbescape", "org.xmlunit:xmlunit-core", "org.yaml:snakeyaml" ] }, "services": { "ch.qos.logback:logback-classic": { "jakarta.servlet.ServletContainerInitializer": [ "ch.qos.logback.classic.servlet.LogbackServletContainerInitializer" ], "org.slf4j.spi.SLF4JServiceProvider": [ "ch.qos.logback.classic.spi.LogbackServiceProvider" ] }, "com.fasterxml.jackson.core:jackson-core": { "com.fasterxml.jackson.core.JsonFactory": [ "com.fasterxml.jackson.core.JsonFactory" ] }, "com.fasterxml.jackson.core:jackson-databind": { "com.fasterxml.jackson.core.ObjectCodec": [ "com.fasterxml.jackson.databind.ObjectMapper" ] }, "com.fasterxml.jackson.datatype:jackson-datatype-jdk8": { "com.fasterxml.jackson.databind.Module": [ "com.fasterxml.jackson.datatype.jdk8.Jdk8Module" ] }, "com.fasterxml.jackson.datatype:jackson-datatype-jsr310": { "com.fasterxml.jackson.databind.Module": [ "com.fasterxml.jackson.datatype.jsr310.JavaTimeModule" ] }, "com.fasterxml.jackson.module:jackson-module-parameter-names": { "com.fasterxml.jackson.databind.Module": [ "com.fasterxml.jackson.module.paramnames.ParameterNamesModule" ] }, "com.sun.jersey:jersey-core": { "com.sun.jersey.spi.HeaderDelegateProvider": [ "com.sun.jersey.core.impl.provider.header.CacheControlProvider", "com.sun.jersey.core.impl.provider.header.CookieProvider", "com.sun.jersey.core.impl.provider.header.DateProvider", "com.sun.jersey.core.impl.provider.header.EntityTagProvider", "com.sun.jersey.core.impl.provider.header.LocaleProvider", "com.sun.jersey.core.impl.provider.header.MediaTypeProvider", "com.sun.jersey.core.impl.provider.header.NewCookieProvider", "com.sun.jersey.core.impl.provider.header.StringProvider", "com.sun.jersey.core.impl.provider.header.URIProvider" ], "com.sun.jersey.spi.inject.InjectableProvider": [ "com.sun.jersey.core.impl.provider.xml.DocumentBuilderFactoryProvider", "com.sun.jersey.core.impl.provider.xml.SAXParserContextProvider", "com.sun.jersey.core.impl.provider.xml.TransformerFactoryProvider", "com.sun.jersey.core.impl.provider.xml.XMLStreamReaderContextProvider" ], "javax.ws.rs.ext.MessageBodyReader": [ "com.sun.jersey.core.impl.provider.entity.ByteArrayProvider", "com.sun.jersey.core.impl.provider.entity.DataSourceProvider", "com.sun.jersey.core.impl.provider.entity.DocumentProvider", "com.sun.jersey.core.impl.provider.entity.EntityHolderReader", "com.sun.jersey.core.impl.provider.entity.FileProvider", "com.sun.jersey.core.impl.provider.entity.FormMultivaluedMapProvider", "com.sun.jersey.core.impl.provider.entity.FormProvider", "com.sun.jersey.core.impl.provider.entity.InputStreamProvider", "com.sun.jersey.core.impl.provider.entity.MimeMultipartProvider", "com.sun.jersey.core.impl.provider.entity.ReaderProvider", "com.sun.jersey.core.impl.provider.entity.RenderedImageProvider", "com.sun.jersey.core.impl.provider.entity.SourceProvider$DOMSourceReader", "com.sun.jersey.core.impl.provider.entity.SourceProvider$SAXSourceReader", "com.sun.jersey.core.impl.provider.entity.SourceProvider$StreamSourceReader", "com.sun.jersey.core.impl.provider.entity.StringProvider", "com.sun.jersey.core.impl.provider.entity.XMLJAXBElementProvider$App", "com.sun.jersey.core.impl.provider.entity.XMLJAXBElementProvider$General", "com.sun.jersey.core.impl.provider.entity.XMLJAXBElementProvider$Text", "com.sun.jersey.core.impl.provider.entity.XMLListElementProvider$App", "com.sun.jersey.core.impl.provider.entity.XMLListElementProvider$General", "com.sun.jersey.core.impl.provider.entity.XMLListElementProvider$Text", "com.sun.jersey.core.impl.provider.entity.XMLRootElementProvider$App", "com.sun.jersey.core.impl.provider.entity.XMLRootElementProvider$General", "com.sun.jersey.core.impl.provider.entity.XMLRootElementProvider$Text", "com.sun.jersey.core.impl.provider.entity.XMLRootObjectProvider$App", "com.sun.jersey.core.impl.provider.entity.XMLRootObjectProvider$General", "com.sun.jersey.core.impl.provider.entity.XMLRootObjectProvider$Text" ], "javax.ws.rs.ext.MessageBodyWriter": [ "com.sun.jersey.core.impl.provider.entity.ByteArrayProvider", "com.sun.jersey.core.impl.provider.entity.DataSourceProvider", "com.sun.jersey.core.impl.provider.entity.DocumentProvider", "com.sun.jersey.core.impl.provider.entity.FileProvider", "com.sun.jersey.core.impl.provider.entity.FormMultivaluedMapProvider", "com.sun.jersey.core.impl.provider.entity.FormProvider", "com.sun.jersey.core.impl.provider.entity.InputStreamProvider", "com.sun.jersey.core.impl.provider.entity.MimeMultipartProvider", "com.sun.jersey.core.impl.provider.entity.ReaderProvider", "com.sun.jersey.core.impl.provider.entity.RenderedImageProvider", "com.sun.jersey.core.impl.provider.entity.SourceProvider$SourceWriter", "com.sun.jersey.core.impl.provider.entity.StreamingOutputProvider", "com.sun.jersey.core.impl.provider.entity.StringProvider", "com.sun.jersey.core.impl.provider.entity.XMLJAXBElementProvider$App", "com.sun.jersey.core.impl.provider.entity.XMLJAXBElementProvider$General", "com.sun.jersey.core.impl.provider.entity.XMLJAXBElementProvider$Text", "com.sun.jersey.core.impl.provider.entity.XMLListElementProvider$App", "com.sun.jersey.core.impl.provider.entity.XMLListElementProvider$General", "com.sun.jersey.core.impl.provider.entity.XMLListElementProvider$Text", "com.sun.jersey.core.impl.provider.entity.XMLRootElementProvider$App", "com.sun.jersey.core.impl.provider.entity.XMLRootElementProvider$General", "com.sun.jersey.core.impl.provider.entity.XMLRootElementProvider$Text" ] }, "io.micrometer:micrometer-observation": { "io.micrometer.context.ThreadLocalAccessor": [ "io.micrometer.observation.contextpropagation.ObservationThreadLocalAccessor" ] }, "org.apache.logging.log4j:log4j-api": { "org.apache.logging.log4j.util.PropertySource": [ "org.apache.logging.log4j.util.EnvironmentPropertySource", "org.apache.logging.log4j.util.SystemPropertiesPropertySource" ] }, "org.apache.logging.log4j:log4j-to-slf4j": { "org.apache.logging.log4j.spi.Provider": [ "org.apache.logging.slf4j.SLF4JProvider" ] }, "org.apache.tomcat.embed:tomcat-embed-el": { "jakarta.el.ExpressionFactory": [ "org.apache.el.ExpressionFactoryImpl" ] }, "org.apache.tomcat.embed:tomcat-embed-websocket": { "jakarta.servlet.ServletContainerInitializer": [ "org.apache.tomcat.websocket.server.WsSci" ], "jakarta.websocket.ContainerProvider": [ "org.apache.tomcat.websocket.WsContainerProvider" ], "jakarta.websocket.server.ServerEndpointConfig$Configurator": [ "org.apache.tomcat.websocket.server.DefaultServerEndpointConfigurator" ] }, "org.eclipse.jetty.ee10.websocket:jetty-ee10-websocket-jakarta-client": { "jakarta.websocket.ContainerProvider": [ "org.eclipse.jetty.ee10.websocket.jakarta.client.JakartaWebSocketClientContainerProvider" ] }, "org.eclipse.jetty.ee10.websocket:jetty-ee10-websocket-jakarta-server": { "jakarta.servlet.ServletContainerInitializer": [ "org.eclipse.jetty.ee10.websocket.jakarta.server.config.JakartaWebSocketServletContainerInitializer" ], "jakarta.websocket.server.ServerEndpointConfig$Configurator": [ "org.eclipse.jetty.ee10.websocket.jakarta.server.config.ContainerDefaultConfigurator" ], "org.eclipse.jetty.ee10.webapp.Configuration": [ "org.eclipse.jetty.ee10.websocket.jakarta.server.config.JakartaWebSocketConfiguration" ] }, "org.eclipse.jetty.ee10.websocket:jetty-ee10-websocket-jetty-server": { "jakarta.servlet.ServletContainerInitializer": [ "org.eclipse.jetty.ee10.websocket.server.config.JettyWebSocketServletContainerInitializer" ], "org.eclipse.jetty.ee10.webapp.Configuration": [ "org.eclipse.jetty.ee10.websocket.server.config.JettyWebSocketConfiguration" ] }, "org.eclipse.jetty.ee10:jetty-ee10-annotations": { "org.eclipse.jetty.ee10.webapp.Configuration": [ "org.eclipse.jetty.ee10.annotations.AnnotationConfiguration" ] }, "org.eclipse.jetty.ee10:jetty-ee10-plus": { "org.eclipse.jetty.ee10.webapp.Configuration": [ "org.eclipse.jetty.ee10.plus.webapp.EnvConfiguration", "org.eclipse.jetty.ee10.plus.webapp.PlusConfiguration" ] }, "org.eclipse.jetty.ee10:jetty-ee10-webapp": { "org.eclipse.jetty.ee10.webapp.Configuration": [ "org.eclipse.jetty.ee10.webapp.FragmentConfiguration", "org.eclipse.jetty.ee10.webapp.JaasConfiguration", "org.eclipse.jetty.ee10.webapp.JaspiConfiguration", "org.eclipse.jetty.ee10.webapp.JettyWebXmlConfiguration", "org.eclipse.jetty.ee10.webapp.JmxConfiguration", "org.eclipse.jetty.ee10.webapp.JndiConfiguration", "org.eclipse.jetty.ee10.webapp.JspConfiguration", "org.eclipse.jetty.ee10.webapp.MetaInfConfiguration", "org.eclipse.jetty.ee10.webapp.ServletsConfiguration", "org.eclipse.jetty.ee10.webapp.WebAppConfiguration", "org.eclipse.jetty.ee10.webapp.WebInfConfiguration", "org.eclipse.jetty.ee10.webapp.WebXmlConfiguration" ] }, "org.eclipse.jetty.websocket:jetty-websocket-core-common": { "org.eclipse.jetty.websocket.core.Extension": [ "org.eclipse.jetty.websocket.core.internal.FragmentExtension", "org.eclipse.jetty.websocket.core.internal.FrameCaptureExtension", "org.eclipse.jetty.websocket.core.internal.IdentityExtension", "org.eclipse.jetty.websocket.core.internal.PerMessageDeflateExtension", "org.eclipse.jetty.websocket.core.internal.ValidationExtension" ] }, "org.eclipse.jetty.websocket:jetty-websocket-jetty-common": { "org.eclipse.jetty.websocket.api.ExtensionConfig$Parser": [ "org.eclipse.jetty.websocket.common.ExtensionConfigParser" ] }, "org.eclipse.jetty:jetty-http": { "org.eclipse.jetty.http.HttpFieldPreEncoder": [ "org.eclipse.jetty.http.Http10FieldPreEncoder", "org.eclipse.jetty.http.Http11FieldPreEncoder" ] }, "org.junit.jupiter:junit-jupiter-engine": { "org.junit.platform.engine.TestEngine": [ "org.junit.jupiter.engine.JupiterTestEngine" ] }, "org.junit.platform:junit-platform-engine": { "org.junit.platform.engine.discovery.DiscoverySelectorIdentifierParser": [ "org.junit.platform.engine.discovery.ClassSelector$IdentifierParser", "org.junit.platform.engine.discovery.ClasspathResourceSelector$IdentifierParser", "org.junit.platform.engine.discovery.ClasspathRootSelector$IdentifierParser", "org.junit.platform.engine.discovery.DirectorySelector$IdentifierParser", "org.junit.platform.engine.discovery.FileSelector$IdentifierParser", "org.junit.platform.engine.discovery.IterationSelector$IdentifierParser", "org.junit.platform.engine.discovery.MethodSelector$IdentifierParser", "org.junit.platform.engine.discovery.ModuleSelector$IdentifierParser", "org.junit.platform.engine.discovery.NestedClassSelector$IdentifierParser", "org.junit.platform.engine.discovery.NestedMethodSelector$IdentifierParser", "org.junit.platform.engine.discovery.PackageSelector$IdentifierParser", "org.junit.platform.engine.discovery.UniqueIdSelector$IdentifierParser", "org.junit.platform.engine.discovery.UriSelector$IdentifierParser" ] }, "org.springframework.boot:spring-boot": { "ch.qos.logback.classic.spi.Configurator": [ "org.springframework.boot.logging.logback.RootLogLevelConfigurator" ], "org.apache.logging.log4j.util.PropertySource": [ "org.springframework.boot.logging.log4j2.SpringBootPropertySource" ] }, "org.springframework.boot:spring-boot-actuator-autoconfigure": { "org.junit.platform.launcher.TestExecutionListener": [ "org.springframework.boot.actuate.autoconfigure.tracing.OpenTelemetryEventPublisherBeansTestExecutionListener" ] }, "org.springframework.boot:spring-boot-configuration-processor": { "javax.annotation.processing.Processor": [ "org.springframework.boot.configurationprocessor.ConfigurationMetadataAnnotationProcessor" ] }, "org.springframework.boot:spring-boot-loader": { "java.nio.file.spi.FileSystemProvider": [ "org.springframework.boot.loader.nio.file.NestedFileSystemProvider" ] }, "org.springframework:spring-core": { "reactor.blockhound.integration.BlockHoundIntegration": [ "org.springframework.core.ReactiveAdapterRegistry$SpringCoreBlockHoundIntegration" ] }, "org.springframework:spring-jcl": { "org.apache.commons.logging.LogFactory": [ "org.apache.commons.logging.LogFactoryService" ] }, "org.springframework:spring-web": { "jakarta.servlet.ServletContainerInitializer": [ "org.springframework.web.SpringServletContainerInitializer" ], "reactor.blockhound.integration.BlockHoundIntegration": [ "org.springframework.web.server.adapter.WebHttpHandlerBuilder$SpringWebBlockHoundIntegration" ] } }, "version": "2" } ================================================ FILE: springboot/BUILD ================================================ # # Copyright (c) 2017-2021, salesforce.com, inc. # All rights reserved. # Licensed under the BSD 3-Clause license. # For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause # # Spring Boot Packager # (implemented by Salesforce) # See the README.md file for detailed usage instructions. load("@rules_python//python:defs.bzl", "py_binary", "py_test") 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"], ) exports_files([ "springboot.bzl", "springboot_pkg.sh", "check_dupe_classes.py", "detect_javax_classes.py", "write_gitinfo_properties.sh", "write_manifest.sh", "write_bazelrun_env.sh", "default_bazelrun_script.sh", "dupe_class_jar_allowlist.txt", "empty.txt", "addin_end.txt", ]) license( name = "license", copyright_notice = "Copyright (c) 2017-2024, Salesforce", license_kinds = [ "@rules_license//licenses/spdx:Apache-2.0", ], license_text = "//:LICENSE.txt", package_name = "@rules_spring//springboot", package_url = "https://github.com/salesforce/rules_spring", package_version = "2.4.2", visibility = ["//visibility:public"], ) py_binary( name = "detect_javax_classes", srcs = [ "detect_javax_classes.py", ], visibility = ["//visibility:public"], ) py_binary( name = "check_dupe_classes", srcs = [ "check_dupe_classes.py", ], visibility = ["//visibility:public"], ) py_test( name = "check_dupe_classes_test", size = "small", srcs = [ "check_dupe_classes.py", "tests/check_dupe_classes_test.py", ], imports = ["."], tags = ["manual"], ) java_library( name = "springboot_lib", srcs = glob(["src/main/java/**/*.java"]), deps = [], ) java_binary( name = "springboot_cli", runtime_deps = [":springboot_lib"], main_class = "com.salesforce.rulesspring.cli.SpringBootInspector", ) ================================================ FILE: springboot/README.md ================================================ ## SpringBoot Rule This implements a Bazel rule for packaging a Spring Boot application as an executable jar file from a Bazel build. The output of this rule is a jar file that can be copied to production environments and run as an executable jar. See the [top-level README](../README.md) for the stanza to add to your *MODULE.bazel* file to load the rule. The *springboot* rule runs on modern versions of Bazel. See the [.bazelversion](../.bazelversion) file to see which one is used for testing. ### Spring Boot 3 Upgrade? :eyes: are you an existing rules_spring user upgrading to Spring Boot 3? We [have some docs for that](https://github.com/salesforce/rules_spring/issues/230). ### Use the rule in your BUILD file This is a *BUILD* file code snippet of how to invoke the rule: ```starlark # load our Spring Boot rule load("@rules_spring//springboot:springboot.bzl", "springboot",) # create our deps list for Spring Boot springboot_deps = [ # the import bundle has some common defaults "@rules_spring//springboot/import_bundles:springboot_required_deps", # and add some others "@maven//:org_springframework_boot_spring_boot_starter_jetty", "@maven//:org_springframework_boot_spring_boot_starter_web", "@maven//:org_springframework_spring_webmvc", ] # this Java library contains your service code java_library( name = 'helloworld_lib', srcs = glob(["src/main/java/**/*.java"]), resources = glob(["src/main/resources/**"]), deps = springboot_deps + [ "@maven//:green_lib", # red/green libs are fake, put each dep you need here "@maven//:red_lib", ], ) # use the springboot rule to build the app as a Spring Boot executable jar springboot( name = "helloworld", boot_app_class = "com.sample.SampleMain", java_library = ":helloworld_lib", ) ``` The required *springboot* rule attributes are as follows: - *name*: name of your application; the convention is to use the same name as the enclosing folder (i.e. the Bazel package name) - *boot_app_class*: the classname (java package+type) of the @SpringBootApplication class in your app - *java_library*: the library containing your service code There are many more attributes described below and in the [Springboot() Attribute doc](attributes.md). ## Build and Run After installing the rule into your workspace, you are ready to build. Add the rule invocation to your Spring Boot application *BUILD* file as shown above. ```bash # Build bazel build //examples/helloworld # Run bazel run //examples/helloworld # Run with arguments bazel run //examples/helloworld red green blue ``` In production environments, you will likely not have Bazel installed nor the Bazel workspace files. This is the primary use case for the executable jar file. The build will create the executable jar file in the *bazel-bin* directory. Run the jar file locally using *java* like so: ```bash java -jar bazel-bin/examples/helloworld/helloworld.jar ``` The executable jar file is ready to be copied to your production environment or embedded into [a Docker image in your build](https://github.com/salesforce/rules_spring/issues/94). ## In Depth The documentation below explains how to use (or links to subdocuments) all of the features supported by the _springboot_ rule. ### Rule Attributes Reference For reference, the full list available attributes that support these features are documented on the [attributes reference doc.](attributes.md). ### Manage External Dependencies in your MODULE.bazel This repository has an example [MODULE.bazel](../../MODULE.bazel) file that lists necessary and some optional Spring Boot dependencies. These will come from a Nexus/Artifactory repository, or Maven Central. Because the version of each dependency needs to be explicitly managed, it is left for you to review and add to your *MODULE.bazel* file. ### Detecting, Excluding and Suppressing Unwanted Classes The Spring Boot rule will copy the transitive closure of all Java jar deps into the Spring Boot executable jar. This is normally what you want. But sometimes you have a transitive dependency that causes problems when included in your Spring Boot jar, but you don't have the control to remove it from your dependency graph. This can cause problems such as: - multiple jars have the same class, but at different versions - an unwanted class carries a Spring annotation such that the class gets instantiated at startup The Spring Boot rule has a set of strategies and features for dealing with this situation, which unfortunately is somewhat common: - [Detecting, Excluding and Suppressing Unwanted Classes](unwanted_classes.md) - dupe checking, excludes, classpath order, classpath index ### Build Stamping of the Spring Boot jar Spring Boot has a nice feature that can display Git coordinates for your built service in the [/actuator/info](https://docs.spring.io/spring-boot/docs/current/reference/html/production-ready-features.html#production-ready-endpoints) webadmin endpoint. If you are interested in this feature, it is supported by this *springboot* rule. However, to avoid breaking Bazel remote caching, we generally have this feature disabled for most builds. See the [//tools/buildstamp](../buildstamp) package for more details on how to enable and disable it. ### Customizing Bazel Run As shown above, the *springboot* rule has support for launching the application using *bazel run*. There are many ways to customize the way the application is launched. See the dedicated *bazel run* documentation for details: - [Customizing Bazel Run](bazelrun.md) ### Debugging the Rule Execution If the environment variable `DEBUG_SPRINGBOOT_RULE` is set, the rule writes debug output to `$TMPDIR/bazel/debug/springboot`. If `$TMPDIR` is not defined, it defaults to `/tmp`. In order to pass this environment variable to Bazel, use the `--action_env` argument: ```bash bazel build //... --action_env=DEBUG_SPRINGBOOT_RULE=1 ``` ### Writing Tests for your Spring Boot Application This topic is covered in our dedicated [testing guide](testing_springboot.md). ### Customizing the Spring Boot rule To understand how this rule works, start by reading the [springboot.bzl file](springboot.bzl). ### Springboot CLI This package also contains a CLI for inspecting Spring Boot jars after they have been built. This can be useful when troubleshooting behavior differences over time due to changing dependencies. See [the CLI user guide](cli.md) for details. ================================================ FILE: springboot/addin_end.txt ================================================ Marker file that indicates the end of the addin list. ================================================ FILE: springboot/attributes.md ================================================ ## Springboot() Attributes This doc explains conventions and reference for the rule attributes. ### Standard Spring Boot Dependencies The [@rules_spring//springboot/import_bundles](import_bundles) package contains an example list of core set of Spring Boot dependencies. We recommend starting with this list, and then creating your own lists that fit your needs. ### Pattern of Repo-Wide Defaults Do you want to provide a default value for an attribute, across all _springboot()_ invocations in your repo? There is a pattern for that. This is just standard Bazel, nothing specific to *rules_spring*. First, create a Bazel file somewhere in your repo, with a function like this: ``` def mycompany_springboot(**kwargs): # OVERRIDE: The rules_spring default list is [], which is too strict for mycompany, # open up some modules if the caller does not override it. if kwargs.get("bazelrun_addopens") == None: kwargs["bazelrun_addopens"] = [ "java.base/java.base=ALL-UNNAMED", "java.base/java.io=ALL-UNNAMED", "java.base/java.math=ALL-UNNAMED", ] # And then delegate to the default impl springboot(**kwargs) ``` And then use your function in your BUILD file like: ``` load("//tools/mycompany:myutils.bzl", "mycompany_springboot", mycompany_springboot( name = "myapp", java_library = ":base_lib", boot_app_class = "com.mycompany.MyApp", ) ``` ### Attribute Reference | Name | Description | Default Value | Doc Link | | :-------------: | :-------------: | :-------------: | :-------------: | | name | **Required**. The name of the Spring Boot application. Typically this is set the same as the package name. Ex: *helloworld*. | none | | | java_library | **Required**. The built jar, identified by the name of the java_library rule, that contains the Spring Boot application. | none | | | boot_app_class | **Required**. The fully qualified name of the class annotated with @SpringBootApplication. Ex: *com.sample.SampleMain* | none | | | boot_launcher_class | Optional. Allows you to switch to the new *org.springframework.boot.loader.launch.JarLauncher* introduced in Boot 3.2.0. Defaults to the old launcher. | *org.springframework.boot.loader.JarLauncher* | [details](../README.md#upgrading-to-spring-boot-3) | | include_git_properties_file | If *True*, will include a git.properties file with build details in the resulting jar. | True | [details](README.md#build-stamping-of-the-spring-boot-jar) | | addins | Uncommon option to add additional files to the root of the springboot jar. For example, a license file. Pass an array of files from the package. | [] | | | jartools_toolchains | Optional. Toolchain for running build tools like singlejar | ["@bazel_tools//tools/jdk:current_host_java_runtime"] | see [Issue 250](https://github.com/salesforce/rules_spring/issues/250) | | **Dependencies** | | | | | deps | Optional. An additional set of Java dependencies to add to the executable. Normally all dependencies are set on the *java_library*. | None | | | deps_exclude_labels | Optional. A list of jar labels that will be omitted from the final packaging step. This is a manual option for eliminating a problematic dependency that cannot be eliminated upstream. Ex: *["@maven//:commons_cli_commons_cli"]*. | None | [details](unwanted_classes.md) | | deps_exclude | Deprecated. Use deps_exclude_labels instead. Functions the same as deps_exclude_labels but retained for backward compatibility. | None | | None | | | deps_exclude_paths | Optional. This attribute provides a list of partial paths that will be omitted from the final packaging step if the string is contained within the dep filename. This is a more raw method than deps_exclude_labels for eliminating a problematic dependency/file that cannot be eliminated upstream. Ex: [*jackson-databind-*]. | None | [details](unwanted_classes.md) | | deps_banned| Optional. A list of strings to match against the jar filenames in the transitive graph of dependencies for this springboot app. If any of these strings is found within any jar name, the rule will fail. This is useful for detecting jars that should never go to production. The list of dependencies is obtained after the deps_exclude_labels and deps_exclude_paths processing has run. | [ "junit", "mockito" ] | [details](unwanted_classes.md) | | dupeclassescheck_enable | If *True*, will analyze the list of dependencies looking for any class that appears more than once, but with a different hash. This indicates that your dependency tree has conflicting libraries. | False | [details](unwanted_classes.md) | | dupeclassescheck_ignorelist | Optional. When using the duplicate class check, this attribute provides a file that contains a list of libraries excluded from the analysis. Ex: *dupeclass_libs.txt* | None | [details](unwanted_classes.md) | | deps_index_file | Optional. Uses Spring Boot's index to define classpath order. This feature is not commonly used, as the application must be extracted from the jar file for it to work. Ex: *my_classpath_index.idx* | None | [classpath index feature](https://docs.spring.io/spring-boot/docs/current/reference/html/appendix-executable-jar-format.html#executable-jar-war-index-files-classpath) | | deps_use_starlark_order | When running the Spring Boot application from the executable jar file, setting this attribute to *True* will use the classpath order as expressed by the order of deps in the BUILD file. Otherwise it is random order. | True | | | **Bazel Run** | | | | | bazelrun_java_toolchain | Optional. When launching the application using 'bazel run', this attribute can identify the label of the Java toolchain used to launch the JVM. Ex: *//tools/jdk:my_default_toolchain*. See *default_java_toolchain* in the Bazel documentation. | None | [details](bazelrun.md) | | bazelrun_script | Optional. When launching the application using 'bazel run', a default launcher script is used. This attribute can be used to provide a customized launcher script. Ex: *my_custom_script.sh* | None | [details](bazelrun.md) | | bazelrun_jvm_flag_list | Optional. An optional set of JVM flags to pass to the JVM at startup. Ex: *["-Dcustomprop=gold", "-DcustomProp2=silver*"] | None | [details](bazelrun.md) | | bazelrun_env_flag_list | Optional. An optional set of OS environment variables to set before startup. Ex: *["PROP1", "PROP2=copper"] | None | [details](bazelrun.md) | | bazelrun_data | Optional. Adds data files to target's runfiles. Behaves like the *data* attribute defined for *java_binary*. See *bazel run* docs for special behavior when application.properties files are listed here. | None | [details](bazelrun.md) | | bazelrun_background | Optional. If True, the *bazel run* launcher will not block. The run command will return and process will remain running. | False | [details](bazelrun.md) | | **Standard Attributes** | | | | | tags | Optional. Bazel standard attribute. | [] | | | testonly | Optional. Bazel standard attribute. Defaults to False. | False | | | visibility | Optional. Bazel standard attribute. | None | | | **Javax -> Jakarta** | | | | | javaxdetect_enable | If *True*, will analyze the list of dependencies looking for any class from javax.* package and fail the build if found. The lib is a candidate for migration to jakarta. | False | [details](javax.md) | | javaxdetect_ignorelist | Optional. When using the javax detect check, this attribute provides a file that contains a list of libraries excluded from the analysis. Ex: *javaxdetect_ignorelist.txt* | None | [details](javax.md) | The following attributes are deprecated and will be removed in a future release. | Name | Description | | :-------------: | :-------------: | | exclude | Deprecated synonym of *deps_exclude_labels* and *deps_exclude* | | classpath_index | Deprecated synonym of *deps_index_file* | | use_build_dependency_order | Deprecated synonym of *deps_use_starlark_order* | | fail_on_duplicate_classes | Deprecated synonym of *dupeclassescheck_enable* | | duplicate_class_allowlist | Deprecated synonym of *dupeclassescheck_ignorelist* | | jvm_flags | Deprecated form of *bazelrun_jvm_flag_list* | | bazelrun_jvm_flags | Deprecated form of *bazelrun_jvm_flag_list* | | data | Deprecated synonym of *bazelrun_data* | ================================================ FILE: springboot/bazelrun.md ================================================ ## Customizing Bazel Run As shown in the [README](README.md), you can launch the Spring Boot application directly from Bazel using the *bazel run* idiom: ```bash bazel run //examples/helloworld ``` But you may wish to customize the launch. The *springboot* rule supports several features for customization. Note that these features do **not** apply when running the application directly using ```java -jar [file]```. ### Launcher JVM :warning: It is best to use the docs from the Git tag of the release of *rules_spring* you are using. This section in particular has changed often, so please make sure you are looking at the correct version (tag) of this doc for your chosen release. By default, the service will be started using the JVM from the current Java toolchain in your Bazel workspace - `@bazel_tools//tools/jdk:current_java_toolchain` See the [Bazel Java docs](https://bazel.build/docs/bazel-and-java) on how toolchains are defined. However, there are multiple ways to override this. First, you can set the `BAZEL_RUN_JAVA` environment variable to the Java executable of your choice. For example, this works well for local override when you want to quickly test your service on an alternate JVM. This variable, when set, takes priority over the toolchain configurations. ``` # note this is different than setting JAVA_HOME, it needs the path to the actual java executable export BAZEL_RUN_JAVA=/opt/my_jdk/bin/java ``` Second, you can set the `JAVABIN` environment variable, set with the same convention as `BAZEL_RUN_JAVA`. `JAVABIN` is also used by [Bazel's java_binary()](https://bazel.build/reference/be/java#java_binary), so may be more convenient to use. ``` # note this is different than setting JAVA_HOME, it needs the path to the actual java executable export JAVABIN=/opt/my_jdk/bin/java ``` Third, you can use the `bazelrun_java_toolchain` attribute on the `springboot` rule to pass the label of a specific Java toolchain defined in your Bazel workspace. This is useful when your workspace has multiple Java toolchains, and you want the service to use an alternate one when launching with `bazel run`. When set, the launcher will use the JVM from the toolchain. ``` springboot( ... bazelrun_java_toolchain = "//tools/jdk:my_other_toolchain", ) ``` Fourth, the default Java toolchain `@bazel_tools//tools/jdk:current_java_toolchain` will be used. Summary of the precedence order: 1. environmental variable BAZEL_RUN_JAVA 1. environmental variable JAVABIN 1. java executable from the custom java toolchain passed into the rule 1. java executable from the default java toolchain (default) 1. environmental variable JAVA_HOME (fallback, we only get here if there is a bug in the above logic) 1. as a last resort, use 'which java' Additional usages of Bazel Java configuraiton, such as *runtime_java_version*, is perhaps desirable. But due to variations of implementation across Bazel versions, and other complexities, it has not been implemented. The [Java configured for Bazel Run Issue](https://github.com/salesforce/rules_spring/issues/16) tracks thoughts and experiments with this feature. Alternatively, you can provide a custom launcher script (see below) that can tailor JVM selection as needed. This is the most flexible option, but it may cause compatibility issues with newer versions of rules_spring. ### Java Startup Options You may wish to customize the bazel run launcher with JVM options. There are two mechanisms that are supported for this - *bazelrun_jvm_flags* and *JAVA_OPTS*. The *springboot* rule attribute *bazelrun_jvm_flags* is for cases in which you always want the options to apply when the application is launched from Bazel. It is specified as an attribute on the *springboot* rule invocation: ```starlark springboot( name = "helloworld", boot_app_class = "com.sample.SampleMain", java_library = ":helloworld_lib", bazelrun_jvm_flag_list = ["-Dcustomprop=gold", "-Dcustomprop2=silver"], ) ``` The environment variable *JAVA_OPTS* is useful when a developer wants to make a local override. It is set in your shell before launching the application: ```bash export JAVA_OPTS='-Dcustomprop3=bronze' bazel run //examples/helloworld ``` Inside the bazel run launcher, these two options are injected into the command line launcher as if you had invoked the jar like this: ```bash # internally, this is how bazelrun_jvm_flags and JAVA_OPTS are passed to java java [bazelrun_jvm_flag_list] [JAVA_OPTS] -jar [springboot jar] ``` ### Application Arguments You may wish to pass arguments to your Spring Boot application. These arguments are interpreted by your application as you like (see SampleMain.java for an example). For most cases, you can just add them after the Bazel target, like this: ```bash bazel run //examples/helloworld one two three=four ``` which would arrive in your main class as args \[one\] \[two\] \[three=four\]. But if you need to pass an argument that starts with '--' to Spring Boot or your application, you will need to follow this pattern (notice the extra -- in the command line): ```bash bazel run //examples/helloworld -- --spring.config.location=/tmp/myconfig/ ``` otherwise Bazel will try to consume the '--' argument for itself. ### External Configuration with application.properties Spring Boot will load internal application.properties files, typically put in *src/main/resources* and add to your *java_library* resources attribute. But when launching with *bazel run*, you may also provide external application.properties files. This is done via Bazel's [data dependencies](https://bazel.build/concepts/dependencies#data-dependencies) capability, surfaced in the *springboot* rule via the *bazelrun_data* attribute. ``` filegroup( name = "bazelrun_data_files", srcs = [ "application.properties", "application-dev.properties", "config/application.properties", ], ) springboot( ... bazelrun_data = [":bazelrun_data_files"], ) ``` The default launcher script will detect filenames with pattern _application*.properties_ as being external configuration files, and configure them as additional configuration files for Spring Boot. ### External Configuration with Environment Variables Spring Boot will read in [shell environment variables](https://docs.spring.io/spring-boot/reference/features/external-config.html) as external configuration. This technique can be used to set individual configuration properties. This is surfaced in the *springboot* rule using the *bazelrun_env_flag_list* attribute, which is set as an array of environment variables. ``` springboot( ... bazelrun_env_flag_list = ["PROP1=blue", "PROP2=green"], ) ``` which could then be used in @Value annotations using lowercased names: ``` @Value("${prop1:not found}") String prop1; ``` ### Custom Launcher Script If you need more customization, you may completely replace the *bazel run* launcher script for advanced use cases. Make a copy of the [default_bazelrun_script.sh](default_bazelrun_script.sh) into your package, and make changes as necessary. Then pass it via the *bazelrun_script* attribute, like this: ```starlark springboot( name = "helloworld", boot_app_class = "com.sample.SampleMain", java_library = ":helloworld_lib", bazelrun_script = "my_custom_bazelrun_script.sh", ) ``` ### Background the Application on Launch By default, the *bazel run* command will block on the application. Control will not return until the Spring Boot application has terminated. For some use cases, this is not desirable. You may want the *bazel run* command to return immediately, and leave the Spring Boot application running in the background. This is common for integration testing, where you want to have a scripted flow such as: - start the application - run the integration tests - stop the application This is supported. There are two mechanisms for signaling that the application should be started in the background: - the *springboot* rule supports the optional *bazelrun_background* attribute, which can be set to *True* - the user may set the environment variable *BAZELRUN_DO_BACKGROUND=true* in the shell prior to invoking *bazel run* If either the attribute or environment variable are set to true, the application will be launched in the background and: - the process id will be persisted to a file (/tmp/${rulename}.pid) - stdout and stderr will be piped to a file (/tmp/${rulename}.log) ### Bazel Run Internals If you need to modify your service launch via *bazel run* using the above options, it is sometimes helpful to understand how it all works. There are three main components to it. The biggest reveal is that *bazel run* is nothing more than a shell script invocation of a "wrapper script". The springboot() rule writes that wrapper script, plus two other scripts to support launch. In fact, you can invoke the wrapper script directly, which is useful when troubleshooting. ``` # Direct invocation # Format: bazel-bin/relative-path/packagename/targetname # The last element of the path is a file, named the same as your target name. # It is without a .sh suffix, even though it is a shell script file. ./bazel-bin/examples/demoapp/demoapp ``` The best way to learn is to inspect the script files. The paths below are listed for the //examples/demoapp service. - **wrapper script** (*bazel-bin/examples/demoapp/demoapp*): is mostly boiler plate; the contents are embedded directly into the [springboot.bzl](springboot.bzl) code - look for the *_bazelrun_script_template* variable. It coordinates the launch of the other two scripts. - **env script** (*bazel-bin/examples/demoapp/demoapp_bazelrun_env.sh*): is written by the [write_bazelrun_env.sh](write_bazelrun_env.sh) script that is run by the springboot macro. Certain springboot() attributes allow you to add more variables to this file (e.g. *bazelrun_data* and *bazelrun_env_flag_list*). - **launcher script** (*bazel-bin/examples/demoapp/demoapp.runfiles/_main/springboot/default_bazelrun_script.sh*): actually launches the springboot jar. The default launcher script is [default_bazelrun_script.sh](default_bazelrun_script.sh). This script can be completely replaced by using the *bazelrun_script* attribute to fully customize your service launch. ================================================ FILE: springboot/check_dupe_classes.py ================================================ # # Copyright (c) 2019-2021, salesforce.com, inc. # All rights reserved. # Licensed under the BSD 3-Clause license. # For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause # from collections import defaultdict import hashlib import os import sys import zipfile import tempfile def _check_for_duplicate_classes(springbootzip_filepath, ignorelisted_jars, output_filepath): """ Prints error message and returns True if duplicate classes were found, false otherwise. Jars in the ignorelisted_jars list are excluded from the check. """ # this will be set to True if any duplicate classes are found, that are not # contained by any jar in the ignorelist found_illegal_duplicates = False # this set will contain the jars that contain the violaters dupe_containing_jars = set() # list of paths of classes that are duped and have different hashes # use each string entry as a key into the class_catalog dict dupe_classes = [] dupe_message_lines = "" # dict that maps the path to a class to all jars (as list) it was found in, # and the hash for each appearance # for example: # com/acme/common/HostUtil.class -> # [ # { bazel-out/.../foolib.jar, 5807cc49dfbda8dd937de3b33a885409 }, # { bazel-out/.../blahlib.jar, 5807cc49dfbda8dd937de3b33a885409 } # ] class_catalog = defaultdict(list) # Starting the search.... # iterate through the springboot jar file, and find inner jars, # open each inner jar and catalog each .class file found try: springbootzip = zipfile.ZipFile(springbootzip_filepath) except zipfile.BadZipFile: # this error happened to me when my computer ran out of disk space during a build result = "Spring Boot dupe detection has failed for %s because the generated jar file is corrupt, please delete this file.\n" % springbootzip_filepath print(result) _write_result_to_output_file(output_filepath, result) return True sprintbootzipentries = springbootzip.infolist() for springbootzipentry in sprintbootzipentries: if springbootzipentry.filename.endswith(".jar"): jar_path = springbootzipentry.filename innerjar = springbootzip.open(springbootzipentry.filename) # create a temporary copy of the inner jar as a file on disk innerjar_binarycontent = innerjar.read() innerjar_tmp_fileondisk = tempfile.TemporaryFile() innerjar_tmp_fileondisk.write(innerjar_binarycontent) # initialize a ZipFile object using the temporary copy innerjar_zip = zipfile.ZipFile(innerjar_tmp_fileondisk) innerjar_zipentries = innerjar_zip.infolist() for innerjar_zipentry in innerjar_zipentries: innerjar_zipentry_path = innerjar_zipentry.filename if innerjar_zipentry_path.endswith(".class"): if innerjar_zipentry_path.endswith("module-info.class"): continue class_bytes = innerjar_zip.read(innerjar_zipentry_path) digest = hashlib.md5(class_bytes).hexdigest() # now check if we have seen this class before other_locations = class_catalog[innerjar_zipentry_path] for other_location in other_locations: other_digest = other_location[1] if other_digest != digest: jar_base = os.path.basename(jar_path) other_jar_base = os.path.basename(other_location[0]) this_is_a_dupe = False # we fail as a dupe if both jars are not in the ignorelist # we could be nicer and only fail if one of the jars is not in the ignorelist? if jar_base not in ignorelisted_jars: dupe_containing_jars.add(jar_base) found_illegal_duplicates = True this_is_a_dupe = True if other_jar_base not in ignorelisted_jars: dupe_containing_jars.add(other_jar_base) found_illegal_duplicates = True this_is_a_dupe = True if this_is_a_dupe: dupe_message_lines += " class %s\n" % (innerjar_zipentry_path) dupe_message_lines += " jar %s hash %s\n" % (jar_base, digest) dupe_message_lines += " jar %s hash %s\n" % (other_jar_base, other_digest) class_catalog_entry = (jar_path, digest) class_catalog[innerjar_zipentry_path].append(class_catalog_entry) # end innerzipentries for loop innerjar_tmp_fileondisk.close() if found_illegal_duplicates: result = "Spring Boot packaging has failed for %s because multiple copies of the same class, but with different hashes, were found:\n" % springbootzip_filepath result += dupe_message_lines result += "You should eliminate the conflicting dependencies, or if that is not possible you can add these jars to the dupeclassescheck_ignorelist file:\n" for ignorelist_candidate in dupe_containing_jars: result += " %s\n" % ignorelist_candidate print(result) _write_result_to_output_file(output_filepath, result) return found_illegal_duplicates def _parse_ignorelisted_jars_file(ignorelist_file): """ Reads the ignorelist.txt file and returns the jars as a set. File format: each line in the file is the name of a jar, like: foo.jar bar.jar """ ignorelisted_jars = set() if ignorelist_file != None: with open(ignorelist_file, "r") as lines: for line in lines: line = line.strip() if len(line) == 0 or line.startswith("#"): continue # cannot use the whole jar path as it is different for generated jars on linux and mac # this logic might need to change if two jars with the same name are part of the ignorelist jar = os.path.basename(line) ignorelisted_jars.add(jar) #if len(ignorelisted_jars) > 0: # print("Springboot duplicate class checker ignorelisted jars:") # for ignorelisted_jar in ignorelisted_jars: # print(" %s" % ignorelisted_jar) return ignorelisted_jars def _write_result_to_output_file(output_filepath, result): if output_filepath != None: f = open(output_filepath, "a") f.write(result) f.close() def run_with_ignorelist(springbootzip_filepath, ignorelisted_jars, output_filepath): found_illegal_duplicates = _check_for_duplicate_classes(springbootzip_filepath, ignorelisted_jars, output_filepath) if found_illegal_duplicates: raise Exception("Found duplicate classes in the packaged springboot jar") else: _write_result_to_output_file(output_filepath, "SUCCESS") return found_illegal_duplicates def run(springbootzip_filepath, ignorelist_file, output_filepath): """ Iterates through a Spring Boot jar and looks for classes in inner jars. If the same class (package name + class name) appears more than once, verify that the .class files have the same hash code. If there is a conflict, this invocation will fail with an error. If both jars are listed in the ignorelist, the conflict will be ignored. """ ignorelisted_jars = _parse_ignorelisted_jars_file(ignorelist_file) run_with_ignorelist(springbootzip_filepath, ignorelisted_jars, output_filepath) if __name__ == "__main__": # arg1 path to the spring boot jar file (required) # arg2 path to the text file containing the jars to ignore as sources of dupes (optional) # arg3 outputfile (optional, will contain "SUCCESS" if the check passed, or the list of errors) ignorelist_file = None if len(sys.argv) > 2: ignorelist_file = sys.argv[2] if ignorelist_file == "no_ignorelist": ignorelist_file = None output_file = None if len(sys.argv) > 3: output_file = sys.argv[3] run(sys.argv[1], ignorelist_file, output_file) ================================================ FILE: springboot/cli.md ================================================ ## SpringBoot Jar CLI In addition to the Bazel rule, this package also contains a CLI for inspecting Spring Boot jars after they have been built. This can be useful when troubleshooting behavior differences over time due to changing dependencies. The CLI works on any executable Spring Boot jar, regardless of whether it was built with Bazel, Maven, or Gradle. ### Running the CLI If you are importing rules_spring into your Bazel workspace, you can access the tool by a pattern like this: ``` bazel run @rules_spring//springboot:springboot_cli [args] ``` Otherwise, if you have Bazel, you can run it from this repository: ``` bazel run //springboot:springboot_cli [args] ``` For non-Bazel users, a built jar will periodically be added to this directory as _springboot-cli.jar_. ``` jar -jar springboot-cli.jar [args] ``` ### Inspector Inspector is used for any operation involving a single Spring Boot jar. #### Inspector Index The _index_ operation iterates through the Spring Boot jar and creates an index of the contained files. The index is written to file, and the output can be customized to meet the requirements of your analysis work. This operation can be useful when trying to investigate issues with dependencies in the application. If you are building your Spring Boot application with Bazel, this operation is similar in some ways to what can be obtained from Bazel Query. Bazel Query will output the set of libraries that are dependencies. The _index_ is more detailed though in that it can output exact file sizes and is run on the final Spring Boot jar. If you are using *rules_spring* features like *deps_exclude_labels* and *deps_exclude_paths*, the Bazel Query output will be incorrect. Usage examples: ``` # do the default index operation bazel run @rules_spring//springboot:springboot_cli inspector index /opt/bazelws/bazel-bin/services/ordering/ordering.jar /tmp/output.txt # customize the report output; this only writes out the jar files found (L) and will also write the file size of each jar file (Z) bazel run @rules_spring//springboot:springboot_cli inspector index /opt/bazelws/bazel-bin/services/ordering/ordering.jar /tmp/output.txt --report LZ ``` The customizable report output options are implemented in *SpringBootIndexReporter* which is the best place to look for documentation. This class is pretty simple, so the code serves as the documentation. ================================================ FILE: springboot/default_bazelrun_script.sh ================================================ #!/bin/bash # Copyright (c) 2021-2024, salesforce.com, inc. # All rights reserved. # Licensed under the BSD 3-Clause license. # For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause # set -e # Launcher Script for launching a SpringBoot application with 'bazel run' # The following environment variables will be set by the springboot rule, and can # be reliably used for scripting (with example values): # RULE_NAME=helloworld # LABEL_PATH=examples/helloworld/ # SPRINGBOOTJAR_FILENAME=helloworld.jar # DATAFILES=application.properties # JVM_FLAGS="-Dcustomprop=gold -DcustomProp2=silver" # DO_BACKGROUND=true/false (if true, the caller is expecting the launcher not to block and return immediately) # # There are several other env variables set by Bazel. These should be stable between # versions of Bazel because they are documented: # https://docs.bazel.build/versions/master/user-manual.html#run current_dir=$(pwd) # Picking the Java VM to run is a bit of an ordeal. # Precedence order is documented here: # https://github.com/salesforce/rules_spring/blob/main/springboot/bazelrun.md#launcher-jvm if [ -f "${BAZEL_RUN_JAVA}" ]; then # BAZEL_RUN_JAVA points to the actual java executable (file), not the java_home directory echo "Selected the JVM using the BAZEL_RUN_JAVA environment variable." java_cmd=$BAZEL_RUN_JAVA elif [ -f "${JAVABIN}" ]; then # JAVABIN points to the actual java executable (file), not the java_home directory # this is java_binary's convention: https://bazel.build/reference/be/java#java_binary echo "Selected the JVM using the JAVABIN environment variable." java_cmd=$JAVABIN elif [ -f "$JAVA_TOOLCHAIN" ]; then echo "Selected the JVM using the Bazel Java toolchain: $JAVA_TOOLCHAIN_NAME" java_cmd=$JAVA_TOOLCHAIN elif [ -d "${JAVA_HOME}" ]; then echo "Selected the JVM using the JAVA_HOME environment variable." java_cmd="${JAVA_HOME}/bin/java" else echo "Selected the JVM by executing 'which java'" java_cmd="$(which java)" fi if [ -z "${java_cmd}" ]; then echo "ERROR: no java found. See the Bazel Run docs in rules_spring for details." exit 1 fi echo "Using Java at ${java_cmd}" ${java_cmd} -version echo "" # data files, which may include external config files if [ ! -z "${DATAFILES}" ]; then configpaths="" echo "Available datafiles:" for datafile in ${DATAFILES}; do echo " datafile: $current_dir/$datafile" if [[ $datafile == *"application"*".properties" ]]; then path="file:$current_dir/$datafile" if [ ! -z "${configpaths}" ]; then configpaths="$configpaths," fi configpaths="$configpaths$path" fi done if [ ! -z "${configpaths}" ]; then JVM_FLAGS="${JVM_FLAGS} -Dspring.config.additional-location=$configpaths" fi echo "" fi # java args echo "Using JAVA_OPTS from the environment: ${JAVA_OPTS}" echo "Using bazelrun_jvm_flags from the BUILD file: ${JVM_FLAGS}" # main args main_args="$@" # spring boot jar; these are replaced by the springboot starlark code: path=${LABEL_PATH} jar=${SPRINGBOOTJAR_FILENAME} jar_path=${path}${jar} if [ ! -f $jar_path ]; then # some folks like to hit the bazel run wrapper script directly, which requires us to dig for the jar in bazel-bin # ./bazel-bin/examples/helloworld/helloworld <= invocation command jar_path="bazel-bin/${path}${jar}" fi # assemble the command # use exec so that we can pass signals to the underlying process (https://github.com/salesforce/rules_spring/issues/91) cmd="exec ${java_cmd} ${JVM_FLAGS} ${JAVA_OPTS} -jar ${jar_path} ${main_args}" echo "Running ${cmd}" echo "In directory $current_dir" echo "" echo "You can also run from the root of the repo:" echo "java -jar bazel-bin/${jar_path}" echo "" # DO_BACKGROUND is set to true if the bazelrun_background attribute on the springboot rule is set to True # BAZELRUN_DO_BACKGROUND=true may be set by the user in the shell env prior to running bazel run # If either is true, we will run the application in the background and return immediately if [ "$DO_BACKGROUND" = true ] || [ "$BAZELRUN_DO_BACKGROUND" = true ]; then logfile=/tmp/${RULE_NAME}.log pidfile=/tmp/${RULE_NAME}.pid ${cmd} > $logfile 2>&1 & pid=$! echo $pid > $pidfile echo "Launched the Spring Boot application in the background..." echo " BUILD rule 'bazelrun_background' attribute = [$DO_BACKGROUND] Environment variable BAZELRUN_DO_BACKGROUND = [$BAZELRUN_DO_BACKGROUND]" echo " Console log is being written to $logfile" echo " Application process id [$pid] has been written to $pidfile" echo "" else echo "Launching the Spring Boot application in the foreground..." echo "" ${cmd} fi ================================================ FILE: springboot/deps_filter_rules/BUILD ================================================ ================================================ FILE: springboot/deps_filter_rules/README.md ================================================ # Dependencies Filter A Bazel rule that filters compile-time and runtime dependencies in Java projects, ensuring only the necessary ones are included in the build. This rule can be referenced by other Java targets, such as `java_library`, and helps to remove problematic or unwanted dependencies, offering better control over dependency graphs. ## Overview The `deps_filter` rule removes Java dependencies from your dependency graph when you have knowledge that Bazel does not, specifically that your application does not need a dependency at runtime. It provides two main exclusion mechanisms: - **Label-based exclusions**: Exclude specific dependencies by their Bazel label - **Path-based exclusions**: Exclude dependencies matching path patterns in their filenames This is useful in cases where: - You want to exclude a dependency for a specific reason (it has a vulnerability) - There are multiple versions of a dependency on the classpath (dupe classes) and you want to exclude the unfavored one > **For large monorepos**: Consider using the [`dependencyset` macro](DEPENDENCYSET.md) which wraps `deps_filter` to enable centralized exclusion management and policy-as-code enforcement across hundreds of services. ## Usage ```python load("//springboot/deps_filter_rules:deps_filter.bzl", "deps_filter") deps_filter( name = "filtered_deps", deps = [":lib_a", ":lib_b"], runtime_deps = [":lib_c", ":lib_d"], deps_exclude_labels = [":lib_e"], # Exclude by label deps_exclude_paths = ["lib_f"], # Exclude by path pattern exclude_transitives = False, # Whether to exclude transitive deps ) ``` ## Attributes | Attribute | Type | Default | Description | |-----------|------|---------|-------------| | `deps` | `label_list` | `[]` | List of dependencies to include | | `runtime_deps` | `label_list` | `[]` | List of runtime dependencies to include | | `deps_exclude_labels` | `label_list` | `[]` | Dependencies to exclude from the build | | `deps_exclude_paths` | `string_list` | `[]` | patterns for excluding dependencies | | `exclude_transitives` | `bool` | `False` | If `True`, transitive dependencies of excluded dependencies are also removed | | `testonly` | `bool` | `False` | Restricts usage to test environments | | `verbose` | `bool` | `False` | Enable debug output | ## Key Features ### 1. Dual Exclusion Mechanisms - **Label-based**: Precise exclusion using Bazel labels - **Path-based**: Flexible exclusion using filename patterns ### 2. Transitive Dependency Control - `exclude_transitives=False`: Only excludes direct dependencies, preserves transitives - `exclude_transitives=True`: Excludes both direct and transitive dependencies of deps_exclude_labels - **Important**: `exclude_transitives` only removes transitive deps of deps specified in `deps_exclude_labels`, not those matched by `deps_exclude_paths`. ### 3. JAR Type Handling - Properly handles interface JARs (`-ijar`) and implementation JARs - Maintains distinction between compile-time and runtime JARs - Preserves transitive dependency relationships ### 4. Mixed Dependency Support - Supports projects with only compile-time dependencies - Supports projects with only runtime dependencies - Supports projects with mixed compile-time and runtime dependencies ## Examples ### Basic Filtering ```python deps_filter( name = "basic_filter", deps = [":base_lib"], deps_exclude_labels = [":unwanted_lib"], ) ``` ### Path-based Filtering ```python deps_filter( name = "path_filter", deps = [":base_lib"], deps_exclude_paths = ["unwanted", "deprecated"], ) ``` ### Path and Label-based Filtering ```python deps_filter( name = "mixed_filter", deps = [":compile_lib"], runtime_deps = [":runtime_lib"], deps_exclude_labels = [":unwanted_compile"], deps_exclude_paths = ["unwanted_runtime"], ) ``` ### With Transitive Exclusions ```python deps_filter( name = "transitive_filter", deps = [":base_lib"], deps_exclude_labels = [":problematic_lib"], exclude_transitives = True, # Also exclude transitives of problematic_lib testonly = True, # Restrict to test environments ) ``` ## Output The rule returns a `JavaInfo` provider with: - **Compile-time JARs**: Interface and implementation JARs for compilation - **Runtime JARs**: Implementation JARs needed at runtime - **Transitive dependencies**: Properly filtered transitive JARs ## Testing Comprehensive tests are available in `tests/internal_dependencies/` covering: - Compile-time only scenarios - Runtime only scenarios - Mixed dependency scenarios - Complex dependency graphs - Various exclusion patterns Run tests with: ```bash bazel test //tests/internal_dependencies/... ``` ## Integration with Other Targets The `deps_filter` rule is designed to be referenced by other Java targets: ```python deps_filter( name = "filtered_deps", deps = deps, runtime_deps = runtime_deps, deps_exclude_labels = ["@maven//:some_dep_you_dont_want"], deps_exclude_paths = ["javax-servlet"], exclude_transitives = True, ) java_library( name = "my_library", deps = [":filtered_deps"], # Use your filtered deps here! # ... other attributes ) ``` ## Use Cases - **Dependency pruning**: Remove unwanted dependencies from the classpath - **Security**: Exclude dependencies with known vulnerabilities - **Size optimization**: Reduce JAR size by excluding unnecessary dependencies - **Conflict resolution**: Exclude conflicting dependency versions - **Build optimization**: Remove dependencies that cause build issues - **Spring Boot applications**: Particularly useful for complex classpaths in Spring Boot apps ## Important: Bazel Query Limitations **Note:** The `bazel query "deps(target)"` command does not accurately reflect the filtered deps when using `deps_filter_rule`. This is due to how bazel processes dependency queries. ## Edge Cases and Behaviors ### 1. Empty Dependencies At least one of `deps` or `runtime_deps` must be non-empty: ```python # Fails: Error: atleast one of 'deps' or 'runtime_deps' must be non-empty deps_filter( name = "empty_deps", deps = [], runtime_deps = [], deps_exclude_labels = [], deps_exclude_paths = [], ) ``` ### 2. Duplicate Exclusions Duplicate labels or paths in exclusion lists are not allowed: ```python # Fails: Label '@@maven//:io_micrometer_micrometer_commons' is duplicated in the 'deps_exclude_labels' attribute of rule 'duplicates' deps_filter( name = "duplicates", deps = [":lib_a"], deps_exclude_labels = [ "@maven//:io_micrometer_micrometer_commons", "@maven//:io_micrometer_micrometer_commons", # Duplicate "@maven//:org_slf4j_jul_to_slf4j", ], deps_exclude_paths = [ "slf4j", ], ) ``` ### 3. Non-existent Dependencies Excluding non-existent dependencies will cause a build failure: ```python # Fails: Error: no such target '@@maven//:nonexistent_dependency': target 'nonexistent_dependency' not declared in package deps_filter( name = "nonexistent", deps = [":lib_a"], deps_exclude_labels = ["@maven//:nonexistent_dependency"], ) ``` ### 4. Complete Dependency Exclusion Excluding all dependencies from a target will cause a build failure: ```python # Fails: Error: org_springframework_boot_spring_boot_starter_data_jpa has no implementation jars left after filtering exclusions. Remove it from 'deps' and 'runtime_deps'. deps_filter( name = "exclude_all", deps = [ "@maven//:org_springframework_boot_spring_boot_starter_data_jpa", "@maven//:org_springframework_boot_spring_boot_starter_security", ], deps_exclude_labels = [ "@maven//:org_springframework_boot_spring_boot_starter_data_jpa", "@maven//:org_springframework_boot_spring_boot_starter_security", ], # Excluding all deps ) ``` ### 5. Filtering Removes All Implementation JARs (listed in `deps` or `runtime_deps`) When filtering removes all implementation JARs from a dependency, the build fails: ```python # Fails: Error: com_fasterxml_jackson_core_jackson_databind has no implementation jars left after filtering exclusions. Remove it from 'deps' and 'runtime_deps' deps_filter( name = "filtered_to_nothing", deps = [ ":lib_a", "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind", ], deps_exclude_paths = ["jackson"], # Removes all implementation JARs exclude_transitives = True, ) ``` ================================================ FILE: springboot/deps_filter_rules/dependencyset.bzl ================================================ load("//springboot/deps_filter_rules:deps_filter.bzl", "deps_filter") def dependencyset(name, items, deps_exclude_labels = [], deps_exclude_paths = [], exclude_transitives = False, verbose = False, testonly = False): # implement logic to add default exclusions. if "runtime_deps" in name: return deps_filter( name = name, runtime_deps = items, deps_exclude_labels = deps_exclude_labels, deps_exclude_paths = deps_exclude_paths, exclude_transitives = exclude_transitives, verbose = verbose, testonly = testonly, ) else: return deps_filter( name = name, deps = items, deps_exclude_labels = deps_exclude_labels, deps_exclude_paths = deps_exclude_paths, exclude_transitives = exclude_transitives, verbose = verbose, testonly = testonly, ) ================================================ FILE: springboot/deps_filter_rules/dependencyset.md ================================================ # dependencyset Macro A wrapper around `deps_filter` that scales dependency filtering across your entire monorepo. Enforces consistent dependency management patterns. ## Why dependencyset? For large monorepos with hundreds of services, managing exclusions at each `deps_filter` call is impractical. `dependencyset` enables: - **Centralized exclusions**: Security and platform teams maintain shared exclusion lists (CVEs, deprecated libs, etc.) - **Local flexibility**: Services and libraries can add target-level exclusions when needed - **Standardized usage**: All services must use `dependencyset`, ensuring consistent classpaths ## How It Works The `dependencyset` macro automatically detects whether to apply exclusions to `deps` or `runtime_deps` based on the target name: ```python load("@rules_spring//springboot/deps_filter_rules:dependencyset.bzl", "dependencyset") # Automatically treats as deps (compile-time) dependencyset( name = "deps", items = [":lib_a", ":lib_b"], deps_exclude_labels = [":local_exclude"], # Additional exclusions other than centralized exclusions ) # Automatically treats as runtime_deps (name contains "runtime_deps") dependencyset( name = "runtime_deps", items = [":lib_c", ":lib_d"], # Centralized exclusions automatically applied here ) ``` ## Before vs After ### Before: Manual Dependency Lists ```python deps = [ # list of deps ], runtime_deps = [ # list of runtime deps ], java_library( name = "base_lib", srcs = glob(["src/main/java/**/*.java"]), deps = [":deps"], runtime_deps = [":runtime_deps"], ) ``` ### After: Standardized Dependency Sets ```python load("@rules_spring//springboot/deps_filter_rules:dependencyset.bzl", "dependencyset") dependencyset( name = "deps", items = [ # list of deps ], # Centralized exclusions automatically applied # Optional: deps_exclude_labels = [":additional_exclusions"] ) dependencyset( name = "runtime_deps", items = [ # list of runtime deps ], ) java_library( name = "base_lib", srcs = glob(["src/main/java/**/*.java"]), deps = [":deps"], runtime_deps = [":runtime_deps"], ) ``` **Important**: This structure enforces all services/libs to use `dependencyset` instead of raw dependency lists. This standardized approach provides better control over dependencies across large monorepos. ## Problems It Helps Fix ✓ **Eliminates classpath conflicts** - Prevents duplicate classes from conflicting versions - Removes version skew issues ✓ **Stops test flakiness** - Aligns test and production classpaths - Eliminates "works in test, fails in prod" surprises ✓ **Accelerates security response** - Centralized CVE exclusions remove vulnerable jars automatically - Enables faster remediation across the fleet ✓ **Removes dependency noise** - Filters out unwanted transitives you don't actually use - Creates cleaner, smaller classpaths ✓ **Ensures consistent dependency hygiene** - Standardized patterns enforce clean classpaths everywhere - Provides centralized control with local flexibility ## Adoption Path 1. **Introduce dependencyset macro**: Add wrapper around `deps_filter` rule in your repo 2. **Seed central exclude lists**: Security + platform teams define shared exclusions 3. **Migrate targets**: Convert services/libs to use `dependencyset` 4. **Add target-level exclusions**: Allow local exclusions where needed ## Customization To add centralized exclusions, modify the `dependencyset` macro in your repository to include default exclusion lists: ```python def dependencyset(name, items, deps_exclude_labels = [], ...): # Add your centralized exclusions here central_excludes = [ "@maven//:vulnerable_lib", # ... more centralized exclusions ] deps_exclude_labels = central_excludes + deps_exclude_labels return deps_filter( name = name, items = items, deps_exclude_labels = deps_exclude_labels, # ... ) ``` ## See Also - [`deps_filter` rule documentation](README.md): The underlying rule that powers `dependencyset` - [dependencyset tests](../../tests/dependencyset/): Comprehensive test examples ================================================ FILE: springboot/deps_filter_rules/deps_filter.bzl ================================================ load("@bazel_tools//tools/jdk:toolchain_utils.bzl", "find_java_toolchain") def _filter_deps(deps_list, excludes, ctx, is_compile_time = False): """ Filters dependencies based on exclusion patterns. Args: deps_list: List of dependencies to filter excludes: Dictionary of paths that should be excluded ctx: The rule context containing exclusion patterns Returns: List of filtered dependencies that don't match any exclusion patterns """ filtered_deps = [] for dep in deps_list: dep_path = dep.path if is_compile_time: dep_path = dep_path.replace("-ijar.jar", ".jar") dep_path = dep_path.replace("-hjar.jar", ".jar") dep_path = dep_path.replace("/header_", "/processed_") if excludes.get(dep_path, None) != None: if ctx.attr.verbose: print("[DEBUG] excluded: " + dep_path) pass else: # Default to including the JAR unless a pattern match excludes it include = True for pattern in ctx.attr.deps_exclude_paths: if dep_path.find(pattern) > -1: include = False break if include: filtered_deps.append(dep) else: if ctx.attr.verbose: print("[DEBUG] excluded: " + dep_path) return filtered_deps def _pack_jars(jars, ctx, java_toolchain, label_name = ""): """ Packs multiple JARs into a single JAR. Args: jars: List of JARs to pack ctx: Rule context java_toolchain: Java toolchain to use label_name: Name for the output JAR Returns: The packed JAR """ if len(jars) == 0: return None if len(jars) == 1: return jars[0] if not label_name: fail("Error: label_name cannot be empty") return java_common.pack_sources( ctx.actions, output_source_jar = ctx.actions.declare_file(label_name), sources = jars, java_toolchain = java_toolchain, ) def _build_exclusion_set(excluded_deps, exclude_transitives): """Builds a set of JAR paths to exclude from dependencies. Args: excluded_deps: List of dependencies to exclude exclude_transitives: Whether to exclude transitive deps Returns: excludes: Dictionary of JAR paths to exclude """ excludes = {} for dep in excluded_deps: # Add direct JARs for jar in dep[JavaInfo].full_compile_jars.to_list() + dep[JavaInfo].compile_jars.to_list(): excludes[jar.path] = True # Add transitive JARs if exclude_transitives is set to True if exclude_transitives: for jar in dep[JavaInfo].transitive_compile_time_jars.to_list() + dep[JavaInfo].transitive_runtime_jars.to_list(): excludes[jar.path] = True return excludes def _create_filtered_java_info(filtered_jars, filtered_compile_jar, filtered_full_compile_jar): """ Creates a JavaInfo object with filtered JARs. Args: filtered_jars: Dictionary containing filtered JARs filtered_compile_jar: Filtered interace/header JAR filtered_full_compile_jar: Filtered implementation JAR Returns: JavaInfo object with filtered JARs """ return JavaInfo( source_jar = filtered_full_compile_jar, compile_jar = filtered_compile_jar, # Interface/Header JAR output_jar = filtered_full_compile_jar, # Implementation JAR # Note: filtered_transitive_compile_jars contains only interface jars (ijars) # Using impl_jar as output_jar to avoid interface jar output deps = [JavaInfo(source_jar = None, compile_jar = jar, output_jar = filtered_full_compile_jar) for jar in filtered_jars["transitive_compile_jars"]], runtime_deps = [JavaInfo(source_jar = jar, compile_jar = jar, output_jar = jar) for jar in filtered_jars["transitive_runtime_jars"]], ) def _check_jar(full_compile_jar, compile_jar): dep_path = compile_jar.path dep_path = dep_path.replace("-ijar.jar", ".jar") dep_path = dep_path.replace("-hjar.jar", ".jar") dep_path = dep_path.replace("/header_", "/processed_") if dep_path == full_compile_jar.path: return True return False def _get_compile_jar(full_compile_jar, index, compile_jars_list): if len(compile_jars_list) > index and _check_jar(full_compile_jar, compile_jars_list[index]): return compile_jars_list[index] for jar in compile_jars_list: if _check_jar(full_compile_jar, jar): return jar return None def _aggregate_deps(declared_deps, ctx, java_toolchain): """ Aggregates and processes dependencies, handling exclusions and transitive dependencies. Args: declared_deps: List of all explicitly declared direct dependencies to process ctx: The rule context containing exclusion settings java_toolchain: Java toolchain to use Returns: Tuple of (processed JavaInfo objects, filtered direct dependencies) """ # Build exclusion set from excluded labels excludes = _build_exclusion_set(ctx.attr.deps_exclude_labels, ctx.attr.exclude_transitives) # Process each dependency: # 1. Extract compile and transitive JARs # 2. Filter out excluded JARs # 3. Create new JavaInfo with filtered JARs output_java_info_list = [] output_direct_jars_list = [] for dep in declared_deps: # Example: lets say dep is A, and the dependency graph is: # # A (compile) # / \ # B C (transitive compile) # / \ # D E (transitive runtime) # # Initial sets: # - compile_jars = [A-i.jar] # - full_compile_jars = [A.jar] # - transitive_compile_jars = [A-i.jar, B-i.jar, C-i.jar] # - transitive_runtime_jars = [A.jar, B.jar, C.jar, D.jar, E.jar] # # If C.jar and D.jar are excluded: # - filtered_compile_jars = [A-i.jar] # - filtered_full_compile_jars = [A.jar] # - filtered_transitive_compile_jars = [A-i.jar, B-i.jar] # C-i.jar removed # - filtered_transitive_runtime_jars = [A.jar, B.jar, E.jar] # C.jar, D.jar removed # # If exclude_transitives=True and C.jar is excluded: # - filtered_compile_jars = [A-i.jar] # - filtered_full_compile_jars = [A.jar] # - filtered_transitive_compile_jars = [A-i.jar, B-i.jar] # - filtered_transitive_runtime_jars = [A.jar, B.jar] # E.jar dropped (reachable only via C) # # dep_java_info will be constructed with: # - source_jar = A.jar # - compile_jar = A-i.jar # - output_jar = A.jar # - deps = [JavaInfo for A-i.jar, B-i.jar] # - runtime_deps = [JavaInfo for A.jar, B.jar, E.jar] # E.jar not included if exclude_transitives=True # JAR Types: # - full_compile_jars: Implementation JARs (e.g., lib_A.jar) # - compile_jars: Interface/Header JARs (e.g., lib_A-ijar.jar) # - transitive_compile_jars: Interface JARs from transitive deps # - transitive_runtime_jars: Implementation JARs from transitive deps filtered_jars = { "compile_jars": _filter_deps(dep[JavaInfo].compile_jars.to_list(), excludes, ctx, is_compile_time = True), "full_compile_jars": _filter_deps(dep[JavaInfo].full_compile_jars.to_list(), excludes, ctx), "transitive_compile_jars": _filter_deps(dep[JavaInfo].transitive_compile_time_jars.to_list(), excludes, ctx, is_compile_time = True), "transitive_runtime_jars": _filter_deps(dep[JavaInfo].transitive_runtime_jars.to_list(), excludes, ctx), } if len(filtered_jars["full_compile_jars"]) == 0: fail("Error: " + dep.label.name + " has no implementation jars left after filtering exclusions. Remove it from 'deps' and 'runtime_deps'.") for index in range(len(filtered_jars["full_compile_jars"])): filtered_full_compile_jar = filtered_jars["full_compile_jars"][index] filtered_compile_jar = _get_compile_jar(filtered_full_compile_jar, index, filtered_jars["compile_jars"]) if filtered_compile_jar == None: print("[DEBUG] No compile jar found for:" + filtered_full_compile_jar.path + ". Check compile jars list:" + str(filtered_jars["compile_jars"])) # Create JavaInfo with filtered JARs java_info = _create_filtered_java_info(filtered_jars, filtered_compile_jar, filtered_full_compile_jar) output_java_info_list.append(java_info) output_direct_jars_list.append(filtered_full_compile_jar) return output_java_info_list, output_direct_jars_list def _deps_filter_impl(ctx): """ Implementation of the deps_filter rule that filters out specified dependencies and JARs. This rule filters out specified deps and JARs from the compile-time and runtime deps. It utilizes the 'deps_exclude_labels' attribute to omit specific JAR labels and the 'deps_exclude_paths' attribute to exclude deps based on partial paths in their filenames. If 'exclude_transitives' is set to `True` (default: `False`), any transitive deps solely required by the deps in 'deps_exclude_labels' are also excluded. These exclusions ensure the final collection includes only the necessary elements for the build process, eliminating problematic deps. """ if len(ctx.attr.deps) == 0 and len(ctx.attr.runtime_deps) == 0: fail("Error: atleast one of 'deps' or 'runtime_deps' must be non-empty") java_toolchain = find_java_toolchain(ctx, ctx.attr._java_toolchain) compile_deps_info, compile_jars = _aggregate_deps(ctx.attr.deps, ctx, java_toolchain) runtime_deps_info, runtime_jars = _aggregate_deps(ctx.attr.runtime_deps, ctx, java_toolchain) if len(compile_jars) == 0 and len(runtime_jars) == 0: fail("Error: The rule must return at least one compile-time or runtime JAR. Excluding all compile-time or runtime dependencies is not allowed.") if len(compile_jars) == 0: # Only runtime deps present output_jar = runtime_jars[0] return [ DefaultInfo(files = depset([])), JavaInfo( compile_jar = None, output_jar = output_jar, # exports = runtime_deps_info, runtime_deps = runtime_deps_info, ), ] else: # Compile-time deps present output_jar = compile_jars[0] return [ DefaultInfo(files = depset(compile_jars)), JavaInfo( source_jar = output_jar, compile_jar = None, output_jar = output_jar, exports = compile_deps_info, runtime_deps = compile_deps_info + runtime_deps_info, deps = compile_deps_info, ), ] # Rule definition for filtering dependencies deps_filter = rule( implementation = _deps_filter_impl, attrs = { "deps": attr.label_list(providers = [java_common.provider], allow_empty = True), "runtime_deps": attr.label_list(providers = [java_common.provider], allow_empty = True), "deps_exclude_labels": attr.label_list(providers = [java_common.provider], allow_empty = True), "deps_exclude_paths": attr.string_list(), "exclude_transitives": attr.bool(default = False), "verbose": attr.bool(default = False), "_java_toolchain": attr.label(default = "@bazel_tools//tools/jdk:current_java_toolchain"), }, toolchains = ["@bazel_tools//tools/jdk:toolchain_type"], ) def deps_filter_rule(name, deps, runtime_deps, deps_exclude_labels = [], deps_exclude_paths = [], exclude_transitives = False, testonly = False, verbose = False): # We will not be using this as we planned to use dependencyset for both deps and runtime_deps. # Keeping it here for now. deps_filter( name = name + "_compile", deps = deps, deps_exclude_labels = deps_exclude_labels, deps_exclude_paths = deps_exclude_paths, exclude_transitives = exclude_transitives, verbose = verbose, testonly = testonly, ) deps_filter( name = name + "_runtime", runtime_deps = runtime_deps, deps_exclude_labels = deps_exclude_labels, deps_exclude_paths = deps_exclude_paths, exclude_transitives = exclude_transitives, verbose = verbose, testonly = testonly, ) ================================================ FILE: springboot/deps_filter_rules/tests/README.md ================================================ # Testing Overview This directory contains comprehensive tests for the `deps_filter` Bazel rule and `dependencyset` macro. The test suites validate compile-time and runtime dependency filtering across synthetic internal graphs and real external libraries. ## Directory Structure ``` tests/ ├── depsfilter/ # Tests for deps_filter rule │ ├── internal_dependencies/ # Synthetic dependency graphs │ └── external_dependencies/ # Real external libraries ├── dependencyset/ # Tests for dependencyset macro │ ├── internal_dependencies/ │ └── external_dependencies/ ├── test_utils/ # Shared testing utilities │ ├── verification_utils.bzl # Starlark verification helpers │ ├── dependency_graph.txt # Pre-generated dependency graph │ └── src/ # Java test utilities └── external_deps/ # External dependency management ├── unmanaged_deps_filter.bzl # Maven dependency definitions └── unmanaged_deps_filter_install.json # Lock file ``` ## Detailed Documentation - **[Internal Dependencies Testing](internal_dependencies_testing.md)**: Comprehensive guide for internal dependency testing - **[External Dependencies Testing](external_dependencies_testing.md)**: Comprehensive guide for real external dependency testing ## What These Tests Verify ### Core Functionality - Correct JAR sets for all jar types: `compile_jars`, `full_compile_jars`, `transitive_compile_jars`, `transitive_runtime_jars` - Interface (compile time) vs implementation (runtime) JAR distinction (`-hjar` vs full JARs) - Mixed dependency graphs: compile-only, runtime-only, and mixed compile+runtime cases ### Exclusion Mechanisms - **Label-based exclusions**: Exclude dependencies by their Bazel label - **Path/pattern-based exclusions**: Exclude dependencies matching path patterns in JAR names - **`exclude_transitives`**: Control whether transitive dependencies are also excluded - **Multiple exclusions**: Combined label and path exclusions ### Edge Cases - Empty exclusion lists - Special characters in path patterns (dots, hyphens) - Case sensitivity in pattern matching - Multiple paths to the same dependency - Complex cross-branch dependency relationships ## Testing Approaches ### Starlark Testing - Rule/Macro Output Verification Starlark tests verify the `deps_filter` rule's and `dependencyset` macro's output. ### Java Testing - Runtime Classpath Verification Java tests verify that the correct JARs are available at runtime. More details in [internal dependencies testing](internal_dependencies_testing.md) and [external dependencies testing](external_dependencies_testing.md). ## Common Utilities ### test_utils/ - **`verification_utils.bzl`**: Starlark utilities for verifying JAR collections and exclusion counts - **`DependencyGraphAnalyzer`**: Java utility for parsing and analyzing Bazel dependency graphs - **`DepsFilterTestHelper`**: Java utility for computing runtime classpath dependencies ### external_deps/ - **`unmanaged_deps_filter.bzl`**: Defines external Maven dependencies (Spring Boot, Jakarta, etc.) - **`unmanaged_deps_filter_install.json`**: Lock file for pinned dependency versions ## Managing External Dependencies To update external dependencies: 1. Edit `external_deps/unmanaged_deps_filter.bzl` 2. Run: `bazel run @unpinned_unmanaged_deps_filter//:pin` ## Refreshing Dependency Graphs Some Java tests use a pre-generated graph file. To refresh: ```bash bazel query 'deps("//springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime:no_filtering")' --output=graph > dependency_graph.txt ``` ## Running Tests ```bash # Run all tests bazel test //springboot/deps_filter_rules/tests/... ``` ## Test Coverage Summary The comprehensive test suite ensures the `deps_filter` rule and `dependencyset` macro work correctly across: - Basic dependency filtering functionality - All exclusion mechanisms (label, path, transitive) - Interface vs implementation JAR distinction - Mixed compile-time and runtime dependencies - Complex dependency graph scenarios - Real-world external library integration - Edge cases and error conditions ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/external_dependencies/compile_and_runtime/BUILD ================================================ load("//springboot/deps_filter_rules:dependencyset.bzl", "dependencyset") load( "//springboot/deps_filter_rules/tests/dependencyset/external_dependencies/compile_and_runtime:compile_and_runtime_test.bzl", "no_filtering_test", "with_label_exclusions_test", "with_label_exclusions_with_exclude_transitives_test", "with_path_exclusions_test", "with_path_exclusions_with_exclude_transitives_test", "multiple_exclusions_with_exclude_transitives_test", "multiple_exclusions_without_exclude_transitives_test", "empty_exclusion_lists_test", "path_based_exclusions_comprehensive_test", "runtime_deps_only_test", "compile_deps_only_test", "single_dep_with_exclusions_test", "single_runtime_dep_with_exclusions_test", "one_compile_one_runtime_dep_test", "path_patterns_with_special_characters_test", "case_sensitive_pattern_matching_test", ) deps = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security", "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind", "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core", "@unmanaged_deps_filter//:jakarta_servlet_jsp_jakarta_servlet_jsp_api", ] runtime_deps = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator", ] test_deps = [ "@unmanaged_deps_filter//:junit_junit", "@unmanaged_deps_filter//:org_assertj_assertj_core", ] # Test 1: No filtering - baseline test dependencyset( name = "deps_no_filtering", items = deps, ) dependencyset( name = "runtime_deps_no_filtering", items = runtime_deps, ) java_library( name = "no_filtering_test_lib", srcs = ["src/main/java/com/depsfilter/A.java"], deps = [":deps_no_filtering"], runtime_deps = [":runtime_deps_no_filtering"], ) no_filtering_test( name = "no_filtering_test", test_lib = ":no_filtering_test_lib", ) java_test( name = "DepsFilterNoFilteringTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterNoFilteringTest.java" ], deps = [":no_filtering_test_lib", "//springboot/deps_filter_rules/tests/test_utils:test_utils"] + test_deps, ) # Test 2: Label-based exclusions without transitives dependencyset( name = "deps_with_label_exclusions", items = deps, deps_exclude_labels = [ "@unmanaged_deps_filter//:io_micrometer_micrometer_commons", "@unmanaged_deps_filter//:org_slf4j_jul_to_slf4j", ], ) dependencyset( name = "runtime_deps_with_label_exclusions", items = runtime_deps, deps_exclude_labels = [ "@unmanaged_deps_filter//:io_micrometer_micrometer_commons", "@unmanaged_deps_filter//:org_slf4j_jul_to_slf4j", ], ) java_library( name = "with_label_exclusions_test_lib", srcs = ["src/main/java/com/depsfilter/A.java"], deps = [":deps_with_label_exclusions"], runtime_deps = [":runtime_deps_with_label_exclusions"], ) with_label_exclusions_test( name = "with_label_exclusions_test", test_lib = ":with_label_exclusions_test_lib", ) java_test( name = "DepsFilterLabelExclusionsTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterLabelExclusionsTest.java" ], deps = [":with_label_exclusions_test_lib", "//springboot/deps_filter_rules/tests/test_utils:test_utils"] + test_deps, ) # Test 3: Label-based exclusions with exclude_transitives dependencyset( name = "deps_with_label_exclusions_with_exclude_transitives", items = deps, deps_exclude_labels = [ "@unmanaged_deps_filter//:io_micrometer_micrometer_commons", "@unmanaged_deps_filter//:org_slf4j_jul_to_slf4j", ], exclude_transitives = True, ) dependencyset( name = "runtime_deps_with_label_exclusions_with_exclude_transitives", items = runtime_deps, deps_exclude_labels = [ "@unmanaged_deps_filter//:io_micrometer_micrometer_commons", "@unmanaged_deps_filter//:org_slf4j_jul_to_slf4j", ], exclude_transitives = True, ) java_library( name = "with_label_exclusions_with_exclude_transitives_test_lib", srcs = ["src/main/java/com/depsfilter/A.java"], deps = [":deps_with_label_exclusions_with_exclude_transitives"], runtime_deps = [":runtime_deps_with_label_exclusions_with_exclude_transitives"], ) with_label_exclusions_with_exclude_transitives_test( name = "with_label_exclusions_with_exclude_transitives_test", test_lib = ":with_label_exclusions_with_exclude_transitives_test_lib", ) java_test( name = "DepsFilterExcludeTransitiveTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterExcludeTransitiveTest.java" ], deps = [":with_label_exclusions_with_exclude_transitives_test_lib", "//springboot/deps_filter_rules/tests/test_utils:test_utils"] + test_deps, ) # Test 4: Path-based exclusions without transitives dependencyset( name = "deps_with_path_exclusions", items = deps, deps_exclude_paths = [ "micrometer", "slf4j" ], ) dependencyset( name = "runtime_deps_with_path_exclusions", items = runtime_deps, deps_exclude_paths = [ "micrometer", "slf4j" ], ) java_library( name = "with_path_exclusions_test_lib", srcs = ["src/main/java/com/depsfilter/A.java"], deps = [":deps_with_path_exclusions"], runtime_deps = [":runtime_deps_with_path_exclusions"], ) with_path_exclusions_test( name = "with_path_exclusions_test", test_lib = ":with_path_exclusions_test_lib", ) java_test( name = "DepsFilterPathExclusionsTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterPathExclusionsTest.java" ], deps = [":with_path_exclusions_test_lib", "//springboot/deps_filter_rules/tests/test_utils:test_utils"] + test_deps, ) # Test 5: Path-based exclusions with exclude_transitives dependencyset( name = "deps_with_path_exclusions_with_exclude_transitives", items = deps, deps_exclude_paths = [ "micrometer", "slf4j" ], exclude_transitives = True, ) dependencyset( name = "runtime_deps_with_path_exclusions_with_exclude_transitives", items = runtime_deps, deps_exclude_paths = [ "micrometer", "slf4j" ], exclude_transitives = True, ) java_library( name = "with_path_exclusions_with_exclude_transitives_test_lib", srcs = ["src/main/java/com/depsfilter/A.java"], deps = [":deps_with_path_exclusions_with_exclude_transitives"], runtime_deps = [":runtime_deps_with_path_exclusions_with_exclude_transitives"], ) with_path_exclusions_with_exclude_transitives_test( name = "with_path_exclusions_with_exclude_transitives_test", test_lib = ":with_path_exclusions_with_exclude_transitives_test_lib", ) java_test( name = "DepsFilterPathExclusionsWithTransitivesTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterPathExclusionsWithTransitivesTest.java" ], deps = [":with_path_exclusions_with_exclude_transitives_test_lib", "//springboot/deps_filter_rules/tests/test_utils:test_utils"] + test_deps, ) # Test 6: Multiple exclusions with exclude_transitives (labels + patterns) dependencyset( name = "deps_multiple_exclusions_with_exclude_transitives", items = deps, deps_exclude_labels = [ "@unmanaged_deps_filter//:io_micrometer_micrometer_commons", "@unmanaged_deps_filter//:org_slf4j_jul_to_slf4j", ], deps_exclude_paths = [ "slf4j" ], exclude_transitives = True, ) dependencyset( name = "runtime_deps_multiple_exclusions_with_exclude_transitives", items = runtime_deps, deps_exclude_labels = [ "@unmanaged_deps_filter//:io_micrometer_micrometer_commons", "@unmanaged_deps_filter//:org_slf4j_jul_to_slf4j", ], deps_exclude_paths = [ "slf4j" ], exclude_transitives = True, ) java_library( name = "multiple_exclusions_with_exclude_transitives_test_lib", srcs = ["src/main/java/com/depsfilter/A.java"], deps = [":deps_multiple_exclusions_with_exclude_transitives"], runtime_deps = [":runtime_deps_multiple_exclusions_with_exclude_transitives"], ) multiple_exclusions_with_exclude_transitives_test( name = "multiple_exclusions_with_exclude_transitives_test", test_lib = ":multiple_exclusions_with_exclude_transitives_test_lib", ) java_test( name = "DepsFilterMultipleExclusionsWithTransitivesTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterMultipleExclusionsWithTransitivesTest.java" ], deps = [":multiple_exclusions_with_exclude_transitives_test_lib", "//springboot/deps_filter_rules/tests/test_utils:test_utils"] + test_deps, ) # Test 7: Multiple exclusions without exclude_transitives (labels + patterns) dependencyset( name = "deps_multiple_exclusions_without_exclude_transitives", items = deps, deps_exclude_labels = [ "@unmanaged_deps_filter//:io_micrometer_micrometer_commons", "@unmanaged_deps_filter//:org_slf4j_jul_to_slf4j", ], deps_exclude_paths = [ "slf4j", ], exclude_transitives = False, ) dependencyset( name = "runtime_deps_multiple_exclusions_without_exclude_transitives", items = runtime_deps, deps_exclude_labels = [ "@unmanaged_deps_filter//:io_micrometer_micrometer_commons", "@unmanaged_deps_filter//:org_slf4j_jul_to_slf4j", ], deps_exclude_paths = [ "slf4j", ], exclude_transitives = False, ) java_library( name = "multiple_exclusions_without_exclude_transitives_test_lib", srcs = ["src/main/java/com/depsfilter/A.java"], deps = [":deps_multiple_exclusions_without_exclude_transitives"], runtime_deps = [":runtime_deps_multiple_exclusions_without_exclude_transitives"], ) multiple_exclusions_without_exclude_transitives_test( name = "multiple_exclusions_without_exclude_transitives_test", test_lib = ":multiple_exclusions_without_exclude_transitives_test_lib", ) java_test( name = "DepsFilterMultipleExclusionsWithoutTransitivesTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterMultipleExclusionsWithoutTransitivesTest.java" ], deps = [":multiple_exclusions_without_exclude_transitives_test_lib", "//springboot/deps_filter_rules/tests/test_utils:test_utils"] + test_deps, ) # Test 8: Empty exclusion lists dependencyset( name = "deps_empty_exclusion_lists", items = deps, deps_exclude_labels = [], deps_exclude_paths = [], exclude_transitives = False, ) dependencyset( name = "runtime_deps_empty_exclusion_lists", items = runtime_deps, deps_exclude_labels = [], deps_exclude_paths = [], exclude_transitives = False, ) java_library( name = "empty_exclusion_lists_test_lib", srcs = ["src/main/java/com/depsfilter/A.java"], deps = [":deps_empty_exclusion_lists"], runtime_deps = [":runtime_deps_empty_exclusion_lists"], ) empty_exclusion_lists_test( name = "empty_exclusion_lists_test", test_lib = ":empty_exclusion_lists_test_lib", ) java_test( name = "DepsFilterEmptyExclusionsTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterEmptyExclusionsTest.java" ], deps = [":empty_exclusion_lists_test_lib", "//springboot/deps_filter_rules/tests/test_utils:test_utils"] + test_deps, ) # Test 9: Comprehensive path-based exclusions dependencyset( name = "deps_path_based_exclusions_comprehensive", items = deps, deps_exclude_labels = [], deps_exclude_paths = [ "micrometer", "slf4j", "logback" ], exclude_transitives = False, ) dependencyset( name = "runtime_deps_path_based_exclusions_comprehensive", items = runtime_deps, deps_exclude_labels = [], deps_exclude_paths = [ "micrometer", "slf4j", "logback" ], exclude_transitives = False, ) java_library( name = "path_based_exclusions_comprehensive_test_lib", srcs = ["src/main/java/com/depsfilter/A.java"], deps = [":deps_path_based_exclusions_comprehensive"], runtime_deps = [":runtime_deps_path_based_exclusions_comprehensive"], ) path_based_exclusions_comprehensive_test( name = "path_based_exclusions_comprehensive_test", test_lib = ":path_based_exclusions_comprehensive_test_lib", ) java_test( name = "DepsFilterPathBasedExclusionsComprehensiveTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterPathBasedExclusionsComprehensiveTest.java" ], deps = [":path_based_exclusions_comprehensive_test_lib", "//springboot/deps_filter_rules/tests/test_utils:test_utils"] + test_deps, ) # Test 10: Runtime deps only dependencyset( name = "runtime_deps_only", items = runtime_deps, deps_exclude_labels = [], deps_exclude_paths = [], exclude_transitives = False, ) java_library( name = "runtime_deps_only_test_lib", srcs = ["src/main/java/com/depsfilter/A.java"], runtime_deps = [":runtime_deps_only"], ) runtime_deps_only_test( name = "runtime_deps_only_test", test_lib = ":runtime_deps_only_test_lib", ) java_test( name = "DepsFilterRuntimeDepsOnlyTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterRuntimeDepsOnlyTest.java" ], deps = [":runtime_deps_only_test_lib", "//springboot/deps_filter_rules/tests/test_utils:test_utils"] + test_deps, ) # Test 11: Compile deps only dependencyset( name = "compile_deps_only", items = deps, deps_exclude_labels = [], deps_exclude_paths = [], exclude_transitives = False, ) java_library( name = "compile_deps_only_test_lib", srcs = ["src/main/java/com/depsfilter/A.java"], deps = [":compile_deps_only"], ) compile_deps_only_test( name = "compile_deps_only_test", test_lib = ":compile_deps_only_test_lib", ) java_test( name = "DepsFilterCompileDepsOnlyTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterCompileDepsOnlyTest.java" ], deps = [":compile_deps_only_test_lib", "//springboot/deps_filter_rules/tests/test_utils:test_utils"] + test_deps, ) # Test 12: Single dependency with exclusions dependencyset( name = "deps_single_dep_with_exclusions", items = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", ], deps_exclude_labels = [ "@unmanaged_deps_filter//:io_micrometer_micrometer_commons", ], deps_exclude_paths = [], exclude_transitives = False, ) java_library( name = "single_dep_with_exclusions_test_lib", srcs = ["src/main/java/com/depsfilter/A.java"], deps = [":deps_single_dep_with_exclusions"], ) single_dep_with_exclusions_test( name = "single_dep_with_exclusions_test", test_lib = ":single_dep_with_exclusions_test_lib", ) java_test( name = "DepsFilterSingleDepWithExclusionsTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterSingleDepWithExclusionsTest.java" ], deps = [":single_dep_with_exclusions_test_lib", "//springboot/deps_filter_rules/tests/test_utils:test_utils"] + test_deps, ) # Test 13: Single runtime dependency with exclusions dependencyset( name = "runtime_deps_single_runtime_dep_with_exclusions", items = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", ], deps_exclude_labels = [], deps_exclude_paths = [ "slf4j", ], exclude_transitives = False, ) java_library( name = "single_runtime_dep_with_exclusions_test_lib", srcs = ["src/main/java/com/depsfilter/A.java"], runtime_deps = [":runtime_deps_single_runtime_dep_with_exclusions"], ) single_runtime_dep_with_exclusions_test( name = "single_runtime_dep_with_exclusions_test", test_lib = ":single_runtime_dep_with_exclusions_test_lib", ) java_test( name = "DepsFilterSingleRuntimeDepWithExclusionsTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterSingleRuntimeDepWithExclusionsTest.java" ], deps = [":single_runtime_dep_with_exclusions_test_lib", "//springboot/deps_filter_rules/tests/test_utils:test_utils"] + test_deps, ) # Test 14: One compile dep and one runtime dep dependencyset( name = "deps_one_compile_one_runtime_dep", items = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", ], deps_exclude_labels = [], deps_exclude_paths = [], exclude_transitives = False, ) dependencyset( name = "runtime_deps_one_compile_one_runtime_dep", items = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", ], deps_exclude_labels = [], deps_exclude_paths = [], exclude_transitives = False, ) java_library( name = "one_compile_one_runtime_dep_test_lib", srcs = ["src/main/java/com/depsfilter/A.java"], deps = [":deps_one_compile_one_runtime_dep"], runtime_deps = [":runtime_deps_one_compile_one_runtime_dep"], ) one_compile_one_runtime_dep_test( name = "one_compile_one_runtime_dep_test", test_lib = ":one_compile_one_runtime_dep_test_lib", ) java_test( name = "DepsFilterOneCompileOneRuntimeDepTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterOneCompileOneRuntimeDepTest.java" ], deps = [":one_compile_one_runtime_dep_test_lib", "//springboot/deps_filter_rules/tests/test_utils:test_utils"] + test_deps, ) # Test 15: Path patterns with special characters dependencyset( name = "deps_path_patterns_with_special_characters", items = deps, deps_exclude_paths = [ "io.micrometer", "to-slf4j", ], exclude_transitives = True, ) dependencyset( name = "runtime_deps_path_patterns_with_special_characters", items = runtime_deps, deps_exclude_paths = [ "io.micrometer", "to-slf4j", ], exclude_transitives = True, ) java_library( name = "path_patterns_with_special_characters_test_lib", srcs = ["src/main/java/com/depsfilter/A.java"], deps = [":deps_path_patterns_with_special_characters"], runtime_deps = [":runtime_deps_path_patterns_with_special_characters"], ) path_patterns_with_special_characters_test( name = "path_patterns_with_special_characters_test", test_lib = ":path_patterns_with_special_characters_test_lib", ) java_test( name = "DepsFilterPathPatternsWithSpecialCharactersTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterPathPatternsWithSpecialCharactersTest.java" ], deps = [":path_patterns_with_special_characters_test_lib", "//springboot/deps_filter_rules/tests/test_utils:test_utils"] + test_deps, ) # Test 16: Case sensitive pattern matching dependencyset( name = "deps_case_sensitive_pattern_matching", items = deps, deps_exclude_labels = [], deps_exclude_paths = [ "SPRING", # Uppercase pattern "Jackson", # Mixed case pattern "HIBERNATE", # Uppercase pattern ], exclude_transitives = False, ) dependencyset( name = "runtime_deps_case_sensitive_pattern_matching", items = runtime_deps, deps_exclude_labels = [], deps_exclude_paths = [ "SPRING", # Uppercase pattern "Jackson", # Mixed case pattern "HIBERNATE", # Uppercase pattern ], exclude_transitives = False, ) java_library( name = "case_sensitive_pattern_matching_test_lib", srcs = ["src/main/java/com/depsfilter/A.java"], deps = [":deps_case_sensitive_pattern_matching"], runtime_deps = [":runtime_deps_case_sensitive_pattern_matching"], ) case_sensitive_pattern_matching_test( name = "case_sensitive_pattern_matching_test", test_lib = ":case_sensitive_pattern_matching_test_lib", ) java_test( name = "DepsFilterCaseSensitivePatternMatchingTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterCaseSensitivePatternMatchingTest.java" ], deps = [":case_sensitive_pattern_matching_test_lib", "//springboot/deps_filter_rules/tests/test_utils:test_utils"] + test_deps, ) ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/external_dependencies/compile_and_runtime/compile_and_runtime_test.bzl ================================================ load("@bazel_skylib//lib:unittest.bzl", "asserts", "unittest") load("//springboot/deps_filter_rules:deps_filter.bzl", "deps_filter") load("//springboot/deps_filter_rules/tests/test_utils:verification_utils.bzl", "verify_jars", "verify_runtime_and_compile_jars", "verify_jars_and_dropped_counts", "verify_dropped_counts", "compute_expected_jars", ) def _test_no_filtering(ctx): """ Tests deps without any filtering - baseline test. """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.test_lib[JavaInfo] test_lib_name = "no_filtering_test_lib" expected = compute_expected_jars(ctx, test_lib_name) verify_runtime_and_compile_jars( ctx, env, javainfo_filtered, expected_compile_jars = expected["compile_jars"], expected_full_compile_jars = expected["full_compile_jars"], expected_transitive_compile_jars = expected["transitive_compile_jars"], expected_transitive_runtime_jars = expected["transitive_runtime_jars"], ) verify_jars_and_dropped_counts(env, expected, expected_compile_dropped = "0", expected_full_compile_dropped = "0", expected_transitive_compile_dropped = "0", expected_transitive_runtime_dropped = "0") return unittest.end(env) no_filtering_test = unittest.make(_test_no_filtering, attrs = { "test_lib": attr.label(providers = [JavaInfo]), "deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security", "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind", "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core", "@unmanaged_deps_filter//:jakarta_servlet_jsp_jakarta_servlet_jsp_api", ], providers = [JavaInfo], ), "runtime_deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator", ], providers = [JavaInfo], ), "deps_exclude_labels": attr.label_list( default = [], ), "deps_exclude_paths": attr.string_list( default = [], ), }) def _test_with_label_exclusions(ctx): """ Tests deps with label-based exclusions (without transitives). """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.test_lib[JavaInfo] test_lib_name = "with_label_exclusions_test_lib" expected = compute_expected_jars(ctx, test_lib_name) verify_runtime_and_compile_jars( ctx, env, javainfo_filtered, expected_compile_jars = expected["compile_jars"], expected_full_compile_jars = expected["full_compile_jars"], expected_transitive_compile_jars = expected["transitive_compile_jars"], expected_transitive_runtime_jars = expected["transitive_runtime_jars"], ) # Verify dropped counts - label exclusions should drop direct JARs but not transitives when exclude_transitives=False dropped_counts = { "compile_jars_dropped": expected["compile_jars_dropped"], "full_compile_jars_dropped": expected["full_compile_jars_dropped"], "transitive_compile_jars_dropped": expected["transitive_compile_jars_dropped"], "transitive_runtime_jars_dropped": expected["transitive_runtime_jars_dropped"], } verify_dropped_counts(env, expected, expected_compile_dropped = "0", expected_full_compile_dropped = "0", expected_transitive_compile_dropped = ">0", expected_transitive_runtime_dropped = ">0") return unittest.end(env) with_label_exclusions_test = unittest.make(_test_with_label_exclusions, attrs = { "test_lib": attr.label(providers = [JavaInfo]), "deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security", "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind", "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core", "@unmanaged_deps_filter//:jakarta_servlet_jsp_jakarta_servlet_jsp_api", ], providers = [JavaInfo], ), "runtime_deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator", ], providers = [JavaInfo], ), "deps_exclude_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:io_micrometer_micrometer_commons", "@unmanaged_deps_filter//:org_slf4j_jul_to_slf4j", ], ), "deps_exclude_paths": attr.string_list( default = [], ), "exclude_transitives": attr.bool( default = False, ), }) def _test_with_label_exclusions_with_exclude_transitives(ctx): """ Tests deps with label-based exclusions including exclude_transitives. """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.test_lib[JavaInfo] test_lib_name = "with_label_exclusions_with_exclude_transitives_test_lib" expected = compute_expected_jars(ctx, test_lib_name) verify_runtime_and_compile_jars( ctx, env, javainfo_filtered, expected_compile_jars = expected["compile_jars"], expected_full_compile_jars = expected["full_compile_jars"], expected_transitive_compile_jars = expected["transitive_compile_jars"], expected_transitive_runtime_jars = expected["transitive_runtime_jars"], ) verify_jars_and_dropped_counts(env, expected, expected_compile_dropped = "0", expected_full_compile_dropped = "0", expected_transitive_compile_dropped = ">0", expected_transitive_runtime_dropped = ">0") return unittest.end(env) with_label_exclusions_with_exclude_transitives_test = unittest.make(_test_with_label_exclusions_with_exclude_transitives, attrs = { "test_lib": attr.label(providers = [JavaInfo]), "deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security", "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind", "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core", "@unmanaged_deps_filter//:jakarta_servlet_jsp_jakarta_servlet_jsp_api", ], providers = [JavaInfo], ), "runtime_deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator", ], providers = [JavaInfo], ), "deps_exclude_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:io_micrometer_micrometer_commons", "@unmanaged_deps_filter//:org_slf4j_jul_to_slf4j", ], ), "deps_exclude_paths": attr.string_list( default = [], ), "exclude_transitives": attr.bool( default = True, ), }) def _test_with_path_exclusions(ctx): """ Tests deps with path-based exclusions (without transitives). """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.test_lib[JavaInfo] test_lib_name = "with_path_exclusions_test_lib" expected = compute_expected_jars(ctx, test_lib_name) verify_runtime_and_compile_jars( ctx, env, javainfo_filtered, expected_compile_jars = expected["compile_jars"], expected_full_compile_jars = expected["full_compile_jars"], expected_transitive_compile_jars = expected["transitive_compile_jars"], expected_transitive_runtime_jars = expected["transitive_runtime_jars"], ) verify_dropped_counts(env, expected, expected_compile_dropped = "0", expected_full_compile_dropped = "0", expected_transitive_compile_dropped = ">0", expected_transitive_runtime_dropped = ">0") return unittest.end(env) with_path_exclusions_test = unittest.make(_test_with_path_exclusions, attrs = { "test_lib": attr.label(providers = [JavaInfo]), "deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security", "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind", "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core", "@unmanaged_deps_filter//:jakarta_servlet_jsp_jakarta_servlet_jsp_api", ], providers = [JavaInfo], ), "runtime_deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator", ], providers = [JavaInfo], ), "deps_exclude_labels": attr.label_list( default = [ ], ), "deps_exclude_paths": attr.string_list( default = [ "micrometer", "slf4j" ], ), "exclude_transitives": attr.bool( default = False, ), }) def _test_with_path_exclusions_with_exclude_transitives(ctx): """ Tests deps with path-based exclusions including exclude_transitives. """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.test_lib[JavaInfo] test_lib_name = "with_path_exclusions_with_exclude_transitives_test_lib" expected = compute_expected_jars(ctx, test_lib_name) verify_runtime_and_compile_jars( ctx, env, javainfo_filtered, expected_compile_jars = expected["compile_jars"], expected_full_compile_jars = expected["full_compile_jars"], expected_transitive_compile_jars = expected["transitive_compile_jars"], expected_transitive_runtime_jars = expected["transitive_runtime_jars"], ) verify_dropped_counts(env, expected, expected_compile_dropped = "0", expected_full_compile_dropped = "0", expected_transitive_compile_dropped = ">0", expected_transitive_runtime_dropped = ">0") return unittest.end(env) with_path_exclusions_with_exclude_transitives_test = unittest.make(_test_with_path_exclusions_with_exclude_transitives, attrs = { "test_lib": attr.label(providers = [JavaInfo]), "deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security", "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind", "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core", "@unmanaged_deps_filter//:jakarta_servlet_jsp_jakarta_servlet_jsp_api", ], providers = [JavaInfo], ), "runtime_deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator", ], providers = [JavaInfo], ), "deps_exclude_labels": attr.label_list( default = [ ], ), "deps_exclude_paths": attr.string_list( default = [ "micrometer", "slf4j" ], ), "exclude_transitives": attr.bool( default = True, ), }) def _test_multiple_exclusions_with_exclude_transitives(ctx): """ Tests multiple exclusion types (labels + paths) with exclude_transitives=True. """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.test_lib[JavaInfo] test_lib_name = "multiple_exclusions_with_exclude_transitives_test_lib" expected = compute_expected_jars(ctx, test_lib_name) verify_runtime_and_compile_jars( ctx, env, javainfo_filtered, expected_compile_jars = expected["compile_jars"], expected_full_compile_jars = expected["full_compile_jars"], expected_transitive_compile_jars = expected["transitive_compile_jars"], expected_transitive_runtime_jars = expected["transitive_runtime_jars"], ) verify_dropped_counts(env, expected, expected_compile_dropped = "0", expected_full_compile_dropped = "0", expected_transitive_compile_dropped = ">0", expected_transitive_runtime_dropped = ">0") return unittest.end(env) multiple_exclusions_with_exclude_transitives_test = unittest.make(_test_multiple_exclusions_with_exclude_transitives, attrs = { "test_lib": attr.label(providers = [JavaInfo]), "deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security", "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind", "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core", "@unmanaged_deps_filter//:jakarta_servlet_jsp_jakarta_servlet_jsp_api", ], providers = [JavaInfo], ), "runtime_deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator", ], providers = [JavaInfo], ), "deps_exclude_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:io_micrometer_micrometer_commons", "@unmanaged_deps_filter//:org_slf4j_jul_to_slf4j", ], ), "deps_exclude_paths": attr.string_list( default = [ "slf4j" ], ), "exclude_transitives": attr.bool( default = True, ), }) def _test_multiple_exclusions_without_exclude_transitives(ctx): """ Tests multiple exclusion types (labels + paths) with exclude_transitives=False. """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.test_lib[JavaInfo] test_lib_name = "multiple_exclusions_without_exclude_transitives_test_lib" expected = compute_expected_jars(ctx, test_lib_name) verify_runtime_and_compile_jars( ctx, env, javainfo_filtered, expected_compile_jars = expected["compile_jars"], expected_full_compile_jars = expected["full_compile_jars"], expected_transitive_compile_jars = expected["transitive_compile_jars"], expected_transitive_runtime_jars = expected["transitive_runtime_jars"], ) verify_dropped_counts(env, expected, expected_compile_dropped = "0", expected_full_compile_dropped = "0", expected_transitive_compile_dropped = ">0", expected_transitive_runtime_dropped = ">0") return unittest.end(env) multiple_exclusions_without_exclude_transitives_test = unittest.make(_test_multiple_exclusions_without_exclude_transitives, attrs = { "test_lib": attr.label(providers = [JavaInfo]), "deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security", "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind", "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core", "@unmanaged_deps_filter//:jakarta_servlet_jsp_jakarta_servlet_jsp_api", ], providers = [JavaInfo], ), "runtime_deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator", ], providers = [JavaInfo], ), "deps_exclude_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:io_micrometer_micrometer_commons", "@unmanaged_deps_filter//:org_slf4j_jul_to_slf4j", ], ), "deps_exclude_paths": attr.string_list( default = [ "slf4j" ], ), "exclude_transitives": attr.bool( default = False, ), }) def _test_empty_exclusion_lists(ctx): """ Tests behavior when exclusion lists are empty. """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.test_lib[JavaInfo] test_lib_name = "empty_exclusion_lists_test_lib" expected = compute_expected_jars(ctx, test_lib_name) verify_runtime_and_compile_jars( ctx, env, javainfo_filtered, expected_compile_jars = expected["compile_jars"], expected_full_compile_jars = expected["full_compile_jars"], expected_transitive_compile_jars = expected["transitive_compile_jars"], expected_transitive_runtime_jars = expected["transitive_runtime_jars"], ) verify_dropped_counts(env, expected, expected_compile_dropped = "0", expected_full_compile_dropped = "0", expected_transitive_compile_dropped = "0", expected_transitive_runtime_dropped = "0") return unittest.end(env) empty_exclusion_lists_test = unittest.make(_test_empty_exclusion_lists, attrs = { "test_lib": attr.label(providers = [JavaInfo]), "deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security", "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind", "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core", "@unmanaged_deps_filter//:jakarta_servlet_jsp_jakarta_servlet_jsp_api", ], providers = [JavaInfo], ), "runtime_deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator", ], providers = [JavaInfo], ), "deps_exclude_labels": attr.label_list( default = [], ), "deps_exclude_paths": attr.string_list( default = [], ), "exclude_transitives": attr.bool( default = False, ), }) def _test_path_based_exclusions_comprehensive(ctx): """ Tests comprehensive path-based exclusions with various patterns. """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.test_lib[JavaInfo] test_lib_name = "path_based_exclusions_comprehensive_test_lib" expected = compute_expected_jars(ctx, test_lib_name) verify_runtime_and_compile_jars( ctx, env, javainfo_filtered, expected_compile_jars = expected["compile_jars"], expected_full_compile_jars = expected["full_compile_jars"], expected_transitive_compile_jars = expected["transitive_compile_jars"], expected_transitive_runtime_jars = expected["transitive_runtime_jars"], ) # Additional verification: ensure excluded patterns are not present transitive_runtime_jars = [jar.basename for jar in javainfo_filtered.transitive_runtime_jars.to_list()] for pattern in ["micrometer", "slf4j", "logback"]: for jar in transitive_runtime_jars: asserts.true(env, pattern not in jar, "Excluded pattern '{}' found in JAR: {}".format(pattern, jar)) verify_dropped_counts(env, expected, expected_compile_dropped = "0", expected_full_compile_dropped = "0", expected_transitive_compile_dropped = ">0", expected_transitive_runtime_dropped = ">0") return unittest.end(env) path_based_exclusions_comprehensive_test = unittest.make(_test_path_based_exclusions_comprehensive, attrs = { "test_lib": attr.label(providers = [JavaInfo]), "deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security", "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind", "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core", "@unmanaged_deps_filter//:jakarta_servlet_jsp_jakarta_servlet_jsp_api", ], providers = [JavaInfo], ), "runtime_deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator", ], providers = [JavaInfo], ), "deps_exclude_labels": attr.label_list( default = [], ), "deps_exclude_paths": attr.string_list( default = [ "micrometer", "slf4j", "logback" ], ), "exclude_transitives": attr.bool( default = False, ), }) def _test_runtime_deps_only(ctx): """ Tests behavior when only runtime_deps are provided (no deps). """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.test_lib[JavaInfo] test_lib_name = "runtime_deps_only_test_lib" expected = compute_expected_jars(ctx, test_lib_name) verify_runtime_and_compile_jars( ctx, env, javainfo_filtered, expected_compile_jars = expected["compile_jars"], expected_full_compile_jars = expected["full_compile_jars"], expected_transitive_compile_jars = expected["transitive_compile_jars"], expected_transitive_runtime_jars = expected["transitive_runtime_jars"], ) verify_dropped_counts(env, expected, expected_compile_dropped = "0", expected_full_compile_dropped = "0", expected_transitive_compile_dropped = "0", expected_transitive_runtime_dropped = "0") return unittest.end(env) runtime_deps_only_test = unittest.make(_test_runtime_deps_only, attrs = { "test_lib": attr.label(providers = [JavaInfo]), "deps_labels": attr.label_list( default = [], ), "runtime_deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator", ], providers = [JavaInfo], ), "deps_exclude_labels": attr.label_list( default = [], ), "deps_exclude_paths": attr.string_list( default = [], ), "exclude_transitives": attr.bool( default = False, ), }) def _test_compile_deps_only(ctx): """ Tests behavior when only deps are provided (no runtime_deps). """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.test_lib[JavaInfo] test_lib_name = "compile_deps_only_test_lib" expected = compute_expected_jars(ctx, test_lib_name) verify_runtime_and_compile_jars( ctx, env, javainfo_filtered, expected_compile_jars = expected["compile_jars"], expected_full_compile_jars = expected["full_compile_jars"], expected_transitive_compile_jars = expected["transitive_compile_jars"], expected_transitive_runtime_jars = expected["transitive_runtime_jars"], ) # Compile deps should contribute to both compile and runtime JARs compile_jars = [jar.basename for jar in javainfo_filtered.compile_jars.to_list()] transitive_runtime_jars = [jar.basename for jar in javainfo_filtered.transitive_runtime_jars.to_list()] asserts.true(env, len(compile_jars) > 0, "Expected compile JARs when deps provided, got: {}".format(len(compile_jars))) asserts.true(env, len(transitive_runtime_jars) > 0, "Expected transitive runtime JARs when deps provided, got: {}".format(len(transitive_runtime_jars))) verify_dropped_counts(env, expected, expected_compile_dropped = "0", expected_full_compile_dropped = "0", expected_transitive_compile_dropped = "0", expected_transitive_runtime_dropped = "0") return unittest.end(env) compile_deps_only_test = unittest.make(_test_compile_deps_only, attrs = { "test_lib": attr.label(providers = [JavaInfo]), "deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security", "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind", "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core", "@unmanaged_deps_filter//:jakarta_servlet_jsp_jakarta_servlet_jsp_api", ], providers = [JavaInfo], ), "runtime_deps_labels": attr.label_list( default = [], ), "deps_exclude_labels": attr.label_list( default = [], ), "deps_exclude_paths": attr.string_list( default = [], ), "exclude_transitives": attr.bool( default = False, ), }) def _test_single_dep_with_exclusions(ctx): """ Tests behavior with a single dependency and exclusions. """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.test_lib[JavaInfo] test_lib_name = "single_dep_with_exclusions_test_lib" expected = compute_expected_jars(ctx, test_lib_name) verify_runtime_and_compile_jars( ctx, env, javainfo_filtered, expected_compile_jars = expected["compile_jars"], expected_full_compile_jars = expected["full_compile_jars"], expected_transitive_compile_jars = expected["transitive_compile_jars"], expected_transitive_runtime_jars = expected["transitive_runtime_jars"], ) verify_dropped_counts(env, expected, expected_compile_dropped = "0", expected_full_compile_dropped = "0", expected_transitive_compile_dropped = ">0", expected_transitive_runtime_dropped = ">0") return unittest.end(env) single_dep_with_exclusions_test = unittest.make(_test_single_dep_with_exclusions, attrs = { "test_lib": attr.label(providers = [JavaInfo]), "deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", ], providers = [JavaInfo], ), "runtime_deps_labels": attr.label_list( default = [], ), "deps_exclude_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:io_micrometer_micrometer_commons", ], ), "deps_exclude_paths": attr.string_list( default = [], ), "exclude_transitives": attr.bool( default = False, ), }) def _test_single_runtime_dep_with_exclusions(ctx): """ Tests behavior with a single runtime dependency and exclusions. """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.test_lib[JavaInfo] test_lib_name = "single_runtime_dep_with_exclusions_test_lib" expected = compute_expected_jars(ctx, test_lib_name) verify_runtime_and_compile_jars( ctx, env, javainfo_filtered, expected_compile_jars = expected["compile_jars"], expected_full_compile_jars = expected["full_compile_jars"], expected_transitive_compile_jars = expected["transitive_compile_jars"], expected_transitive_runtime_jars = expected["transitive_runtime_jars"], ) verify_dropped_counts(env, expected, expected_compile_dropped = "0", expected_full_compile_dropped = "0", expected_transitive_compile_dropped = "0", expected_transitive_runtime_dropped = ">0") return unittest.end(env) single_runtime_dep_with_exclusions_test = unittest.make(_test_single_runtime_dep_with_exclusions, attrs = { "test_lib": attr.label(providers = [JavaInfo]), "deps_labels": attr.label_list( default = [], ), "runtime_deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", ], providers = [JavaInfo], ), "deps_exclude_labels": attr.label_list( default = [], ), "deps_exclude_paths": attr.string_list( default = [ "slf4j", ], ), "exclude_transitives": attr.bool( default = False, ), }) def _test_one_compile_one_runtime_dep(ctx): """ Tests behavior with exactly one compile dep and one runtime dep. """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.test_lib[JavaInfo] test_lib_name = "one_compile_one_runtime_dep_test_lib" expected = compute_expected_jars(ctx, test_lib_name) verify_runtime_and_compile_jars( ctx, env, javainfo_filtered, expected_compile_jars = expected["compile_jars"], expected_full_compile_jars = expected["full_compile_jars"], expected_transitive_compile_jars = expected["transitive_compile_jars"], expected_transitive_runtime_jars = expected["transitive_runtime_jars"], ) verify_dropped_counts(env, expected, expected_compile_dropped = "0", expected_full_compile_dropped = "0", expected_transitive_compile_dropped = "0", expected_transitive_runtime_dropped = "0") return unittest.end(env) one_compile_one_runtime_dep_test = unittest.make(_test_one_compile_one_runtime_dep, attrs = { "test_lib": attr.label(providers = [JavaInfo]), "deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", ], providers = [JavaInfo], ), "runtime_deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", ], providers = [JavaInfo], ), "deps_exclude_labels": attr.label_list( default = [], ), "deps_exclude_paths": attr.string_list( default = [], ), "exclude_transitives": attr.bool( default = False, ), }) def _test_path_patterns_with_special_characters(ctx): """ Tests behavior with path patterns containing special characters. """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.test_lib[JavaInfo] test_lib_name = "path_patterns_with_special_characters_test_lib" expected = compute_expected_jars(ctx, test_lib_name) verify_runtime_and_compile_jars( ctx, env, javainfo_filtered, expected_compile_jars = expected["compile_jars"], expected_full_compile_jars = expected["full_compile_jars"], expected_transitive_compile_jars = expected["transitive_compile_jars"], expected_transitive_runtime_jars = expected["transitive_runtime_jars"], ) verify_dropped_counts(env, expected, expected_compile_dropped = "0", expected_full_compile_dropped = "0", expected_transitive_compile_dropped = ">0", expected_transitive_runtime_dropped = ">0") return unittest.end(env) path_patterns_with_special_characters_test = unittest.make(_test_path_patterns_with_special_characters, attrs = { "test_lib": attr.label(providers = [JavaInfo]), "deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security", "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind", "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core", "@unmanaged_deps_filter//:jakarta_servlet_jsp_jakarta_servlet_jsp_api", ], providers = [JavaInfo], ), "runtime_deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator", ], providers = [JavaInfo], ), "deps_exclude_labels": attr.label_list( default = [], ), "deps_exclude_paths": attr.string_list( default = [ "io.micrometer", # Pattern with dot "to-slf4j", # Pattern with hyphen ], ), "exclude_transitives": attr.bool( default = True, ), }) def _test_case_sensitive_pattern_matching(ctx): """ Tests case sensitivity in path pattern matching. """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.test_lib[JavaInfo] test_lib_name = "case_sensitive_pattern_matching_test_lib" expected = compute_expected_jars(ctx, test_lib_name) verify_runtime_and_compile_jars( ctx, env, javainfo_filtered, expected_compile_jars = expected["compile_jars"], expected_full_compile_jars = expected["full_compile_jars"], expected_transitive_compile_jars = expected["transitive_compile_jars"], expected_transitive_runtime_jars = expected["transitive_runtime_jars"], ) verify_dropped_counts(env, expected, expected_compile_dropped = "0", expected_full_compile_dropped = "0", expected_transitive_compile_dropped = "0", expected_transitive_runtime_dropped = "0") return unittest.end(env) case_sensitive_pattern_matching_test = unittest.make(_test_case_sensitive_pattern_matching, attrs = { "test_lib": attr.label(providers = [JavaInfo]), "deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security", "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind", "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core", "@unmanaged_deps_filter//:jakarta_servlet_jsp_jakarta_servlet_jsp_api", ], providers = [JavaInfo], ), "runtime_deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator", ], providers = [JavaInfo], ), "deps_exclude_labels": attr.label_list( default = [], ), "deps_exclude_paths": attr.string_list( default = [ "SPRING", # Uppercase pattern "Jackson", # Mixed case pattern "HIBERNATE", # Uppercase pattern ], ), "exclude_transitives": attr.bool( default = False, ), }) ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/external_dependencies/compile_and_runtime/src/main/java/com/depsfilter/A.java ================================================ package com.depsfilter; public class A { int a; public A() { a = 1; } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/external_dependencies/compile_and_runtime/src/test/java/com/depsfilter/DepsFilterCaseSensitivePatternMatchingTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.Set; import org.junit.BeforeClass; import org.junit.Test; public class DepsFilterCaseSensitivePatternMatchingTest { @BeforeClass public static void setUp() { DependencyGraphTestConfig.initialize(); } @Test public void testCaseSensitivePatternMatching() { Set availableDeps = Set.copyOf(DepsFilterTestHelper.computeClasspathDependencies()); Set excludedPatterns = Set.of("SPRING", "Jackson", "HIBERNATE"); Set expectedRuntimeDeps = DependencyGraphTestConfig.getExpectedJarsForPathExclusionsFiltered( excludedPatterns, false); expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/dependencyset/external_dependencies/compile_and_runtime/DepsFilterCaseSensitivePatternMatchingTest.jar"); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/dependencyset/external_dependencies/compile_and_runtime/libcase_sensitive_pattern_matching_test_lib.jar"); assertThat(availableDeps).isEqualTo(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/external_dependencies/compile_and_runtime/src/test/java/com/depsfilter/DepsFilterCompileDepsOnlyTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.Set; import org.junit.BeforeClass; import org.junit.Test; public class DepsFilterCompileDepsOnlyTest { @BeforeClass public static void setUp() { DependencyGraphTestConfig.initialize(); } @Test public void testCompileDepsOnly() { Set availableDeps = Set.copyOf(DepsFilterTestHelper.computeClasspathDependencies()); Set depsLabels = Set.of( "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security", "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind", "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core", "@unmanaged_deps_filter//:jakarta_servlet_jsp_jakarta_servlet_jsp_api" ); Set runtimeDepsLabels = Set.of(); Set excludedLabels = Set.of(); Set excludedPatterns = Set.of(); boolean excludeTransitives = false; Set expectedRuntimeDeps = DependencyGraphTestConfig.getExpectedJarsForCustomDepsFiltered( depsLabels, runtimeDepsLabels, excludedLabels, excludedPatterns, excludeTransitives); expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/dependencyset/external_dependencies/compile_and_runtime/DepsFilterCompileDepsOnlyTest.jar"); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/dependencyset/external_dependencies/compile_and_runtime/libcompile_deps_only_test_lib.jar"); assertThat(availableDeps).isEqualTo(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/external_dependencies/compile_and_runtime/src/test/java/com/depsfilter/DepsFilterEmptyExclusionsTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.Set; import org.junit.BeforeClass; import org.junit.Test; public class DepsFilterEmptyExclusionsTest { @BeforeClass public static void setUp() { DependencyGraphTestConfig.initialize(); } @Test public void testTransitivesExclusion() { Set availableDeps = Set.copyOf(DepsFilterTestHelper.computeClasspathDependencies()); Set expectedRuntimeDeps = DependencyGraphTestConfig.getExpectedJarsForNoFilteringFiltered(); expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/dependencyset/external_dependencies/compile_and_runtime/DepsFilterEmptyExclusionsTest.jar"); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/dependencyset/external_dependencies/compile_and_runtime/libempty_exclusion_lists_test_lib.jar"); assertThat(availableDeps).isEqualTo(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/external_dependencies/compile_and_runtime/src/test/java/com/depsfilter/DepsFilterExcludeTransitiveTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.Set; import org.junit.BeforeClass; import org.junit.Test; public class DepsFilterExcludeTransitiveTest { @BeforeClass public static void setUp() { DependencyGraphTestConfig.initialize(); } @Test public void testTransitivesExclusion() { Set availableDeps = Set.copyOf(DepsFilterTestHelper.computeClasspathDependencies()); Set excludedLabels = Set.of( "@unmanaged_deps_filter//:io_micrometer_micrometer_commons", "@unmanaged_deps_filter//:org_slf4j_jul_to_slf4j" ); Set expectedRuntimeDeps = DependencyGraphTestConfig.getExpectedJarsForLabelExclusionsFiltered( excludedLabels, true); expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/dependencyset/external_dependencies/compile_and_runtime/DepsFilterExcludeTransitiveTest.jar"); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/dependencyset/external_dependencies/compile_and_runtime/libwith_label_exclusions_with_exclude_transitives_test_lib.jar"); assertThat(availableDeps).isEqualTo(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/external_dependencies/compile_and_runtime/src/test/java/com/depsfilter/DepsFilterLabelExclusionsTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.Set; import java.util.HashSet; import org.junit.BeforeClass; import org.junit.Test; public class DepsFilterLabelExclusionsTest { @BeforeClass public static void setUp() { DependencyGraphTestConfig.initialize(); } @Test public void testLabelExclusions() { Set availableDeps = Set.copyOf(DepsFilterTestHelper.computeClasspathDependencies()); Set excludedLabels = Set.of( "@unmanaged_deps_filter//:io_micrometer_micrometer_commons", "@unmanaged_deps_filter//:org_slf4j_jul_to_slf4j" ); Set expectedRuntimeDeps = DependencyGraphTestConfig.getExpectedJarsForLabelExclusionsFiltered( excludedLabels, false); expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/dependencyset/external_dependencies/compile_and_runtime/DepsFilterLabelExclusionsTest.jar"); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/dependencyset/external_dependencies/compile_and_runtime/libwith_label_exclusions_test_lib.jar"); assertThat(availableDeps).isEqualTo(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/external_dependencies/compile_and_runtime/src/test/java/com/depsfilter/DepsFilterMultipleExclusionsWithTransitivesTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.Set; import org.junit.BeforeClass; import org.junit.Test; public class DepsFilterMultipleExclusionsWithTransitivesTest { @BeforeClass public static void setUp() { DependencyGraphTestConfig.initialize(); } @Test public void testMultipleExclusionsWithTransitives() { Set availableDeps = Set.copyOf(DepsFilterTestHelper.computeClasspathDependencies()); Set excludedLabels = Set.of( "@unmanaged_deps_filter//:io_micrometer_micrometer_commons", "@unmanaged_deps_filter//:org_slf4j_jul_to_slf4j" ); Set excludedPatterns = Set.of("slf4j"); Set expectedRuntimeDeps = DependencyGraphTestConfig.getExpectedJarsForMultipleExclusionsFiltered( excludedLabels, excludedPatterns, true); expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/dependencyset/external_dependencies/compile_and_runtime/DepsFilterMultipleExclusionsWithTransitivesTest.jar"); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/dependencyset/external_dependencies/compile_and_runtime/libmultiple_exclusions_with_exclude_transitives_test_lib.jar"); assertThat(availableDeps).isEqualTo(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/external_dependencies/compile_and_runtime/src/test/java/com/depsfilter/DepsFilterMultipleExclusionsWithoutTransitivesTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.Set; import org.junit.BeforeClass; import org.junit.Test; public class DepsFilterMultipleExclusionsWithoutTransitivesTest { @BeforeClass public static void setUp() { DependencyGraphTestConfig.initialize(); } @Test public void testMultipleExclusionsWithoutTransitives() { Set availableDeps = Set.copyOf(DepsFilterTestHelper.computeClasspathDependencies()); Set excludedLabels = Set.of( "@unmanaged_deps_filter//:io_micrometer_micrometer_commons", "@unmanaged_deps_filter//:org_slf4j_jul_to_slf4j" ); Set excludedPatterns = Set.of("slf4j"); Set expectedRuntimeDeps = DependencyGraphTestConfig.getExpectedJarsForMultipleExclusionsFiltered( excludedLabels, excludedPatterns, true); expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/dependencyset/external_dependencies/compile_and_runtime/DepsFilterMultipleExclusionsWithoutTransitivesTest.jar"); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/dependencyset/external_dependencies/compile_and_runtime/libmultiple_exclusions_without_exclude_transitives_test_lib.jar"); assertThat(availableDeps).isEqualTo(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/external_dependencies/compile_and_runtime/src/test/java/com/depsfilter/DepsFilterNoFilteringTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.Set; import org.junit.BeforeClass; import org.junit.Test; public class DepsFilterNoFilteringTest { @BeforeClass public static void setUp() { DependencyGraphTestConfig.initialize(); } @Test public void testNoFiltering() { Set availableDeps = Set.copyOf(DepsFilterTestHelper.computeClasspathDependencies()); Set expectedRuntimeDeps = DependencyGraphTestConfig.getExpectedJarsForNoFilteringFiltered(); expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/dependencyset/external_dependencies/compile_and_runtime/DepsFilterNoFilteringTest.jar"); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/dependencyset/external_dependencies/compile_and_runtime/libno_filtering_test_lib.jar"); assertThat(availableDeps).isEqualTo(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/external_dependencies/compile_and_runtime/src/test/java/com/depsfilter/DepsFilterOneCompileOneRuntimeDepTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.Set; import org.junit.BeforeClass; import org.junit.Test; public class DepsFilterOneCompileOneRuntimeDepTest { @BeforeClass public static void setUp() { DependencyGraphTestConfig.initialize(); } @Test public void testOneCompileOneRuntimeDep() { Set availableDeps = Set.copyOf(DepsFilterTestHelper.computeClasspathDependencies()); Set depsLabels = Set.of("@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa"); Set runtimeDepsLabels = Set.of("@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client"); Set excludedLabels = Set.of(); Set excludedPatterns = Set.of(); boolean excludeTransitives = false; Set expectedRuntimeDeps = DependencyGraphTestConfig.getExpectedJarsForCustomDepsFiltered( depsLabels, runtimeDepsLabels, excludedLabels, excludedPatterns, excludeTransitives); expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/dependencyset/external_dependencies/compile_and_runtime/DepsFilterOneCompileOneRuntimeDepTest.jar"); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/dependencyset/external_dependencies/compile_and_runtime/libone_compile_one_runtime_dep_test_lib.jar"); assertThat(availableDeps).isEqualTo(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/external_dependencies/compile_and_runtime/src/test/java/com/depsfilter/DepsFilterPathBasedExclusionsComprehensiveTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.Set; import org.junit.BeforeClass; import org.junit.Test; public class DepsFilterPathBasedExclusionsComprehensiveTest { @BeforeClass public static void setUp() { DependencyGraphTestConfig.initialize(); } @Test public void testPathBasedExclusionsComprehensive() { Set availableDeps = Set.copyOf(DepsFilterTestHelper.computeClasspathDependencies()); Set excludedPatterns = Set.of("micrometer", "slf4j", "logback"); Set expectedRuntimeDeps = DependencyGraphTestConfig.getExpectedJarsForPathExclusionsFiltered( excludedPatterns, false); expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/dependencyset/external_dependencies/compile_and_runtime/DepsFilterPathBasedExclusionsComprehensiveTest.jar"); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/dependencyset/external_dependencies/compile_and_runtime/libpath_based_exclusions_comprehensive_test_lib.jar"); assertThat(availableDeps).isEqualTo(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/external_dependencies/compile_and_runtime/src/test/java/com/depsfilter/DepsFilterPathExclusionsTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.Set; import org.junit.BeforeClass; import org.junit.Test; public class DepsFilterPathExclusionsTest { @BeforeClass public static void setUp() { DependencyGraphTestConfig.initialize(); } @Test public void testPathExclusions() { Set availableDeps = Set.copyOf(DepsFilterTestHelper.computeClasspathDependencies()); Set excludedPatterns = Set.of("micrometer", "slf4j"); Set expectedRuntimeDeps = DependencyGraphTestConfig.getExpectedJarsForPathExclusionsFiltered( excludedPatterns, false); expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/dependencyset/external_dependencies/compile_and_runtime/DepsFilterPathExclusionsTest.jar"); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/dependencyset/external_dependencies/compile_and_runtime/libwith_path_exclusions_test_lib.jar"); assertThat(availableDeps).isEqualTo(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/external_dependencies/compile_and_runtime/src/test/java/com/depsfilter/DepsFilterPathExclusionsWithTransitivesTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.Set; import org.junit.BeforeClass; import org.junit.Test; public class DepsFilterPathExclusionsWithTransitivesTest { @BeforeClass public static void setUp() { DependencyGraphTestConfig.initialize(); } @Test public void testPathExclusionsWithTransitives() { Set availableDeps = Set.copyOf(DepsFilterTestHelper.computeClasspathDependencies()); Set excludedPatterns = Set.of("micrometer", "slf4j"); Set expectedRuntimeDeps = DependencyGraphTestConfig.getExpectedJarsForPathExclusionsFiltered( excludedPatterns, true); expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/dependencyset/external_dependencies/compile_and_runtime/DepsFilterPathExclusionsWithTransitivesTest.jar"); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/dependencyset/external_dependencies/compile_and_runtime/libwith_path_exclusions_with_exclude_transitives_test_lib.jar"); assertThat(availableDeps).isEqualTo(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/external_dependencies/compile_and_runtime/src/test/java/com/depsfilter/DepsFilterPathPatternsWithSpecialCharactersTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.Set; import org.junit.BeforeClass; import org.junit.Test; public class DepsFilterPathPatternsWithSpecialCharactersTest { @BeforeClass public static void setUp() { DependencyGraphTestConfig.initialize(); } @Test public void testPathPatternsWithSpecialCharacters() { Set availableDeps = Set.copyOf(DepsFilterTestHelper.computeClasspathDependencies()); Set excludedPatterns = Set.of("io.micrometer", "to-slf4j"); Set expectedRuntimeDeps = DependencyGraphTestConfig.getExpectedJarsForPathExclusionsFiltered( excludedPatterns, true); expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/dependencyset/external_dependencies/compile_and_runtime/DepsFilterPathPatternsWithSpecialCharactersTest.jar"); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/dependencyset/external_dependencies/compile_and_runtime/libpath_patterns_with_special_characters_test_lib.jar"); assertThat(availableDeps).isEqualTo(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/external_dependencies/compile_and_runtime/src/test/java/com/depsfilter/DepsFilterRuntimeDepsOnlyTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.Set; import org.junit.BeforeClass; import org.junit.Test; public class DepsFilterRuntimeDepsOnlyTest { @BeforeClass public static void setUp() { DependencyGraphTestConfig.initialize(); } @Test public void testRuntimeDepsOnly() { Set availableDeps = Set.copyOf(DepsFilterTestHelper.computeClasspathDependencies()); Set depsLabels = Set.of(); Set runtimeDepsLabels = Set.of( "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator" ); Set excludedLabels = Set.of(); Set excludedPatterns = Set.of(); boolean excludeTransitives = false; Set expectedRuntimeDeps = DependencyGraphTestConfig.getExpectedJarsForCustomDepsFiltered( depsLabels, runtimeDepsLabels, excludedLabels, excludedPatterns, excludeTransitives); expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/dependencyset/external_dependencies/compile_and_runtime/DepsFilterRuntimeDepsOnlyTest.jar"); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/dependencyset/external_dependencies/compile_and_runtime/libruntime_deps_only_test_lib.jar"); assertThat(availableDeps).isEqualTo(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/external_dependencies/compile_and_runtime/src/test/java/com/depsfilter/DepsFilterSingleDepWithExclusionsTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.Set; import org.junit.BeforeClass; import org.junit.Test; public class DepsFilterSingleDepWithExclusionsTest { @BeforeClass public static void setUp() { DependencyGraphTestConfig.initialize(); } @Test public void testSingleDepWithExclusions() { Set availableDeps = Set.copyOf(DepsFilterTestHelper.computeClasspathDependencies()); Set depsLabels = Set.of("@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa"); Set runtimeDepsLabels = Set.of(); Set excludedLabels = Set.of("@unmanaged_deps_filter//:io_micrometer_micrometer_commons"); Set excludedPatterns = Set.of(); Set expectedRuntimeDeps = DependencyGraphTestConfig.getExpectedJarsForCustomDepsFiltered( depsLabels, runtimeDepsLabels, excludedLabels, excludedPatterns, false); expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/dependencyset/external_dependencies/compile_and_runtime/DepsFilterSingleDepWithExclusionsTest.jar"); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/dependencyset/external_dependencies/compile_and_runtime/libsingle_dep_with_exclusions_test_lib.jar"); assertThat(availableDeps).isEqualTo(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/external_dependencies/compile_and_runtime/src/test/java/com/depsfilter/DepsFilterSingleRuntimeDepWithExclusionsTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.Set; import org.junit.BeforeClass; import org.junit.Test; public class DepsFilterSingleRuntimeDepWithExclusionsTest { @BeforeClass public static void setUp() { DependencyGraphTestConfig.initialize(); } @Test public void testSingleRuntimeDepWithExclusions() { Set availableDeps = Set.copyOf(DepsFilterTestHelper.computeClasspathDependencies()); Set depsLabels = Set.of(); Set runtimeDepsLabels = Set.of("@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client"); Set excludedLabels = Set.of(); Set excludedPatterns = Set.of("slf4j"); boolean excludeTransitives = false; Set expectedRuntimeDeps = DependencyGraphTestConfig.getExpectedJarsForCustomDepsFiltered( depsLabels, runtimeDepsLabels, excludedLabels, excludedPatterns, excludeTransitives); expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/dependencyset/external_dependencies/compile_and_runtime/DepsFilterSingleRuntimeDepWithExclusionsTest.jar"); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/dependencyset/external_dependencies/compile_and_runtime/libsingle_runtime_dep_with_exclusions_test_lib.jar"); assertThat(availableDeps).isEqualTo(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_1/BUILD ================================================ load("//springboot/deps_filter_rules:dependencyset.bzl", "dependencyset") load( "//springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_1:compile_and_runtime_test.bzl", "no_filtering_test", "filtered_deps_test", "filtered_deps_exclude_transitive_test", "path_based_exclusions_test", "interface_implementation_jars_test", "multiple_exclusions_with_transitive_test", "multiple_exclusions_without_transitive_test", "empty_exclusion_lists_test", "multiple_paths_test", ) # Dependency Graph Structure: # base_lib # | # dependencyset # ("deps") ("runtime_deps") # / \ # A (c) I (r) # / \ | # / \ G (r) # / \ | # B (c) E (r) / # | | / # | | / # | F (c) # \ / # C (c) # | # D (r) java_library( name = "lib_a", srcs = ["src/main/java/com/depsfilter/A.java"], deps = [ ":lib_b", # A -> B (c) ], runtime_deps = [ ":lib_e", # A -> E (r) ], ) java_library( name = "lib_b", srcs = ["src/main/java/com/depsfilter/B.java"], deps = [":lib_c"], # B -> C (c) ) java_library( name = "lib_c", srcs = ["src/main/java/com/depsfilter/C.java"], runtime_deps = [":lib_d"], # C -> D (r) ) java_library( name = "lib_d", srcs = ["src/main/java/com/depsfilter/D.java"], ) java_library( name = "lib_e", srcs = ["src/main/java/com/depsfilter/E.java"], deps = [":lib_f"], # E -> F (c) ) java_library( name = "lib_f", srcs = ["src/main/java/com/depsfilter/F.java"], deps = [":lib_c"], # F -> C (c) ) java_library( name = "lib_g", srcs = ["src/main/java/com/depsfilter/G.java"], deps = [":lib_f"], # G -> F (c) ) java_library( name = "lib_i", srcs = ["src/main/java/com/depsfilter/I.java"], runtime_deps = [":lib_g"], # I -> G path ) # Consumer library that uses the filtered dependencies java_library( name = "base_lib", srcs = ["src/main/java/com/depsfilter/H.java"], deps = [":lib_a"], # base_lib -> A (c) runtime_deps = [":lib_i"], # base_lib -> I (r) ) # Test 1: No filtering dependencyset( name = "deps_no_filtering", items = [":lib_a"], ) dependencyset( name = "runtime_deps_no_filtering", items = [":lib_i"], ) java_library( name = "no_filtering_test_lib", srcs = ["src/main/java/com/depsfilter/H.java"], deps = [":deps_no_filtering"], runtime_deps = [":runtime_deps_no_filtering"], ) no_filtering_test( name = "deps_filter_no_filtering_test", java_library = ":base_lib", java_library_dependencyset = ":no_filtering_test_lib", ) # Test 2: Exclude by labels and exclude_transitives = False dependencyset( name = "deps_exclude_b_g", items = [":lib_a"], deps_exclude_labels = [":lib_b", ":lib_g"], ) dependencyset( name = "runtime_deps_exclude_b_g", items = [":lib_i"], deps_exclude_labels = [":lib_b", ":lib_g"], ) java_library( name = "exclude_b_g_test_lib", srcs = ["src/main/java/com/depsfilter/H.java"], deps = [":deps_exclude_b_g"], runtime_deps = [":runtime_deps_exclude_b_g"], ) filtered_deps_test( name = "deps_filter_exclude_b_g_test", test_lib = ":exclude_b_g_test_lib", ) # Test 3: Exclude by labels and exclude_transitives = True dependencyset( name = "deps_exclude_b_g_transitives", items = [":lib_a"], deps_exclude_labels = [":lib_b", ":lib_g"], exclude_transitives = True, ) dependencyset( name = "runtime_deps_exclude_b_g_transitives", items = [":lib_i"], deps_exclude_labels = [":lib_b", ":lib_g"], exclude_transitives = True, ) java_library( name = "exclude_b_g_transitives_test_lib", srcs = ["src/main/java/com/depsfilter/H.java"], deps = [":deps_exclude_b_g_transitives"], runtime_deps = [":runtime_deps_exclude_b_g_transitives"], ) filtered_deps_exclude_transitive_test( name = "deps_filter_exclude_b_g_exclude_transitive_test", test_lib = ":exclude_b_g_transitives_test_lib", ) # Test 4: Test for path-based exclusions dependencyset( name = "deps_exclude_paths", items = [":lib_a"], deps_exclude_paths = ["lib_b", "lib_f"], ) dependencyset( name = "runtime_deps_exclude_paths", items = [":lib_i"], deps_exclude_paths = ["lib_b", "lib_f"], ) java_library( name = "path_based_exclusions_test_lib", srcs = ["src/main/java/com/depsfilter/H.java"], deps = [":deps_exclude_paths"], runtime_deps = [":runtime_deps_exclude_paths"], ) path_based_exclusions_test( name = "deps_filter_path_based_exclusions_test", test_lib = ":path_based_exclusions_test_lib", ) # Test 5: Interface vs Implementation JARs dependencyset( name = "deps_interface_impl_exclude_b_g", items = [":lib_a"], deps_exclude_labels = [":lib_b", ":lib_g"], ) dependencyset( name = "runtime_deps_interface_impl_exclude_b_g", items = [":lib_i"], deps_exclude_labels = [":lib_b", ":lib_g"], ) java_library( name = "interface_impl_test_lib", srcs = ["src/main/java/com/depsfilter/H.java"], deps = [":deps_interface_impl_exclude_b_g"], runtime_deps = [":runtime_deps_interface_impl_exclude_b_g"], ) interface_implementation_jars_test( name = "deps_filter_interface_impl_test", test_lib = ":interface_impl_test_lib", ) # Test 6: Multiple exclusions with exclude_transitives=True dependencyset( name = "deps_multi_excl_transitives", items = [":lib_a"], deps_exclude_labels = [":lib_b"], deps_exclude_paths = ["lib_g"], exclude_transitives = True, ) dependencyset( name = "runtime_deps_multi_excl_transitives", items = [":lib_i"], deps_exclude_labels = [":lib_b"], deps_exclude_paths = ["lib_g"], exclude_transitives = True, ) java_library( name = "multiple_exclusions_with_transitive_test_lib", srcs = ["src/main/java/com/depsfilter/H.java"], deps = [":deps_multi_excl_transitives"], runtime_deps = [":runtime_deps_multi_excl_transitives"], ) multiple_exclusions_with_transitive_test( name = "multiple_exclusions_with_transitive_test", test_lib = ":multiple_exclusions_with_transitive_test_lib", ) # Test 7: Multiple exclusions with exclude_transitives=False dependencyset( name = "deps_multi_excl_no_transitives", items = [":lib_a"], deps_exclude_labels = [":lib_b"], deps_exclude_paths = ["lib_g"], exclude_transitives = False, ) dependencyset( name = "runtime_deps_multi_excl_no_transitives", items = [":lib_i"], deps_exclude_labels = [":lib_b"], deps_exclude_paths = ["lib_g"], exclude_transitives = False, ) java_library( name = "multiple_exclusions_without_transitive_test_lib", srcs = ["src/main/java/com/depsfilter/H.java"], deps = [":deps_multi_excl_no_transitives"], runtime_deps = [":runtime_deps_multi_excl_no_transitives"], ) multiple_exclusions_without_transitive_test( name = "multiple_exclusions_without_transitive_test", test_lib = ":multiple_exclusions_without_transitive_test_lib", ) # Test 8: Empty exclusion lists dependencyset( name = "deps_empty_exclusions", items = [":lib_a"], deps_exclude_paths = [], deps_exclude_labels = [], ) dependencyset( name = "runtime_deps_empty_exclusions", items = [":lib_i"], deps_exclude_paths = [], deps_exclude_labels = [], ) java_library( name = "empty_exclusion_lists_test_lib", srcs = ["src/main/java/com/depsfilter/H.java"], deps = [":deps_empty_exclusions"], runtime_deps = [":runtime_deps_empty_exclusions"], ) empty_exclusion_lists_test( name = "deps_filter_empty_exclusions_test", test_lib = ":empty_exclusion_lists_test_lib", ) # Test 9: Multiple paths handling dependencyset( name = "deps_multiple_paths_exclude_b_g", items = [":lib_a"], deps_exclude_labels = [":lib_b", ":lib_g"], ) dependencyset( name = "runtime_deps_multiple_paths_exclude_b_g", items = [":lib_i"], deps_exclude_labels = [":lib_b", ":lib_g"], ) java_library( name = "multiple_paths_test_lib", srcs = ["src/main/java/com/depsfilter/H.java"], deps = [":deps_multiple_paths_exclude_b_g"], runtime_deps = [":runtime_deps_multiple_paths_exclude_b_g"], ) multiple_paths_test( name = "deps_filter_multiple_paths_test", test_lib = ":multiple_paths_test_lib", ) toolchain( name = "unittest_toolchain", toolchain_type = "@bazel_skylib//toolchains/unittest:toolchain_type", toolchain = "@bazel_skylib//toolchains/unittest:toolchain", ) ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_1/compile_and_runtime_test.bzl ================================================ load("@bazel_skylib//lib:unittest.bzl", "asserts", "unittest") load("//springboot/deps_filter_rules/tests/test_utils:verification_utils.bzl", "verify_jars", "verify_runtime_and_compile_jars", "verify_jars_and_dropped_counts", "verify_dropped_counts", "update_jar_name" ) def _test_no_filtering(ctx): """ Tests that deps_filter preserves all dependencies when no exclusions are applied. Dependency Graph: test_lib | dependencyset ("deps") ("runtime_deps") / \\ A (c) I (r) / \\ | / \\ G (r) / \\ | B (c) E (r) / | | / | | / | F (c) \\ / C (c) | D (r) Expected: All JARs from java_library must match deps_filter: - full_compile_jars: Implementation JARs (e.g., liblib_a.jar) - compile_jars: Interface JARs (e.g., liblib_a-hjar.jar) - transitive_compile_time_jars: Interface JARs from transitive deps - transitive_runtime_jars: Implementation JARs from transitive deps """ env = unittest.begin(ctx) java_lib_info = ctx.attr.java_library[JavaInfo] deps_filter_info = ctx.attr.java_library_dependencyset[JavaInfo] # Verify all JAR fields match between java_library and deps_filter jar_fields = [ "full_compile_jars", # Implementation JARs "compile_jars", # Interface JARs "transitive_compile_time_jars", # Transitive interface JARs "transitive_runtime_jars" # Transitive implementation JARs ] for jar_field in jar_fields: java_lib_jars = getattr(java_lib_info, jar_field) deps_filter_jars = getattr(deps_filter_info, jar_field) asserts.equals(env, type(java_lib_jars), type(deps_filter_jars), "JAR type mismatch: {} vs deps_filter".format(jar_field)) java_lib_jars_list = [jar.basename for jar in java_lib_jars.to_list()] deps_filter_jars_list = [jar.basename for jar in deps_filter_jars.to_list()] # Normalize output jar naming difference between dependencyset consumer and base_lib update_jar_name("libno_filtering_test_lib", "libbase_lib", deps_filter_jars_list) asserts.equals(env, java_lib_jars_list, deps_filter_jars_list, "JAR contents mismatch: {} vs deps_filter".format(jar_field)) return unittest.end(env) no_filtering_test = unittest.make(_test_no_filtering, attrs = { "java_library": attr.label(providers = [JavaInfo]), "java_library_dependencyset": attr.label(providers = [JavaInfo]), }) def _test_filtered_deps(ctx): """ Tests basic dependency filtering with label-based exclusions. Dependency Graph: test_lib | dependencyset ("deps") ("runtime_deps") / \\ A (c) I (r) / \\ | / \\ G (r) / \\ | B (c) E (r) / | | / | | / | F (c) \\ / C (c) | D (r) Deps Dependencyset Input: items = [":lib_a"] Runtime Dependencyset Input: items = [":lib_i"] Dependencyset exclusions Input: deps_exclude_labels = [":lib_b", ":lib_g"] deps_exclude_paths = [] exclude_transitives = False Expected Output: JARs preserved: test_lib, A, I, E, F, C, D JARs excluded: B, G (by label, direct deps only, transitives preserved) Compile-time JARs: test_lib-hjar, A-hjar, C-hjar Runtime JARs: test_lib, A, I, E, F, C, D (all preserved deps + transitives) Reasoning: B,G excluded by label, but their transitives (C,D,F) are preserved """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.test_lib[JavaInfo] expected_compile_jars = [ "libexclude_b_g_test_lib-hjar.jar", ] expected_full_compile_jars = [ "libexclude_b_g_test_lib.jar", ] expected_transitive_runtime_jars = [ "libexclude_b_g_test_lib.jar", "liblib_a.jar", "liblib_i.jar", "liblib_e.jar", "liblib_f.jar", "liblib_c.jar", "liblib_d.jar" ] expected_transitive_compile_jars = [ "libexclude_b_g_test_lib-hjar.jar", "liblib_a-hjar.jar", "liblib_c-hjar.jar", ] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) filtered_deps_test = unittest.make(_test_filtered_deps, attrs = { "test_lib": attr.label(providers = [JavaInfo]), }) def _test_filtered_deps_exclude_transitive(ctx): """ Tests dependency filtering with transitive exclusions. Dependency Graph: test_lib | dependencyset ("deps") ("runtime_deps") / \\ A (c) I (r) / \\ | / \\ G (r) / \\ | B (c) E (r) / | | / | | / | F (c) \\ / C (c) | D (r) Deps Dependencyset Input: items = [":lib_a"] Runtime Dependencyset Input: items = [":lib_i"] Dependencyset exclusions Input: deps_exclude_labels = [":lib_b", ":lib_g"] deps_exclude_paths = [] exclude_transitives = True Expected Output: JARs preserved: test_lib, A, I, E JARs excluded: B, G (by label) and all their transitives Compile-time JARs: test_lib-hjar, A-hjar Runtime JARs: test_lib, A, I, E (only preserved deps, no transitives of excluded deps) Reasoning: B,G excluded by label with exclude_transitives=True, so C,D,F also excluded """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.test_lib[JavaInfo] expected_compile_jars = [ "libexclude_b_g_transitives_test_lib-hjar.jar", ] expected_full_compile_jars = [ "libexclude_b_g_transitives_test_lib.jar", ] expected_transitive_runtime_jars = [ "libexclude_b_g_transitives_test_lib.jar", "liblib_a.jar", "liblib_i.jar", "liblib_e.jar", ] expected_transitive_compile_jars = [ "libexclude_b_g_transitives_test_lib-hjar.jar", "liblib_a-hjar.jar", ] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) filtered_deps_exclude_transitive_test = unittest.make(_test_filtered_deps_exclude_transitive, attrs = { "test_lib": attr.label(providers = [JavaInfo]), }) def _test_path_based_exclusions(ctx): """ Tests filtering based on path patterns in deps_exclude_paths. Dependency Graph: test_lib | dependencyset ("deps") ("runtime_deps") / \\ A (c) I (r) / \\ | / \\ G (r) / \\ | B (c) E (r) / | | / | | / | F (c) \\ / C (c) | D (r) Deps Dependencyset Input: items = [":lib_a"] Runtime Dependencyset Input: items = [":lib_i"] Dependencyset exclusions Input: deps_exclude_labels = [] deps_exclude_paths = ["lib_b", "lib_f"] exclude_transitives = False Expected Output: JARs preserved: test_lib, A, I, E, C, D, G JARs excluded: B, F (by path pattern match, transitives may be preserved) Compile-time JARs: test_lib-hjar, A-hjar, C-hjar Runtime JARs: test_lib, A, I, E, C, D, G (all preserved deps + transitives not matching exclusion path patterns) Reasoning: B,F excluded by path pattern, but their transitives are preserved as they didn't match the pattern. """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.test_lib[JavaInfo] expected_compile_jars = [ "libpath_based_exclusions_test_lib-hjar.jar", ] expected_full_compile_jars = [ "libpath_based_exclusions_test_lib.jar", ] expected_transitive_runtime_jars = [ "libpath_based_exclusions_test_lib.jar", "liblib_a.jar", "liblib_i.jar", "liblib_e.jar", "liblib_c.jar", "liblib_d.jar", "liblib_g.jar" ] expected_transitive_compile_jars = [ "libpath_based_exclusions_test_lib-hjar.jar", "liblib_a-hjar.jar", "liblib_c-hjar.jar", ] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) path_based_exclusions_test = unittest.make(_test_path_based_exclusions, attrs = { "test_lib": attr.label(providers = [JavaInfo]), }) def _test_interface_implementation_jars(ctx): """ Tests proper handling of interface (-hjar) and implementation JARs. Dependency Graph: test_lib | dependencyset ("deps") ("runtime_deps") / \\ A (c) I (r) / \\ | / \\ G (r) / \\ | B (c) E (r) / | | / | | / | F (c) \\ / C (c) | D (r) Deps Dependencyset Input: items = [":lib_a"] Runtime Dependencyset Input: items = [":lib_i"] Dependencyset exclusions Input: deps_exclude_labels = [":lib_b", ":lib_g"] deps_exclude_paths = [] exclude_transitives = False Expected Output: compile_jars: libinterface_impl_test_lib-hjar.jar full_compile_jars: libinterface_impl_test_lib.jar """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.test_lib[JavaInfo] compile_jars = sorted([jar.basename for jar in javainfo_filtered.compile_jars.to_list()]) full_compile_jars = sorted([jar.basename for jar in javainfo_filtered.full_compile_jars.to_list()]) expected_compile_jars = ["libinterface_impl_test_lib-hjar.jar"] expected_full_compile_jars = ["libinterface_impl_test_lib.jar"] asserts.equals(env, compile_jars, expected_compile_jars) asserts.equals(env, full_compile_jars, expected_full_compile_jars) return unittest.end(env) interface_implementation_jars_test = unittest.make(_test_interface_implementation_jars, attrs = { "test_lib": attr.label(providers = [JavaInfo]), }) def _test_multiple_exclusions_with_transitive(ctx): """ Tests multiple exclusion levels with exclude_transitives=True. Dependency Graph: test_lib | dependencyset ("deps") ("runtime_deps") / \\ A (c) I (r) / \\ | / \\ G (r) / \\ | B (c) E (r) / | | / | | / | F (c) \\ / C (c) | D (r) Deps Dependencyset Input: items = [":lib_a"] Runtime Dependencyset Input: items = [":lib_i"] Dependencyset exclusions Input: deps_exclude_labels = [":lib_b"] deps_exclude_paths = ["lib_g"] exclude_transitives = True Expected Output: JARs preserved: test_lib, A, I, E, F JARs excluded: B and its transitives; G (not neccessarily its transitives as specified exclusion by path pattern is matched) Compile-time JARs: test_lib-hjar, A-hjar Runtime JARs: test_lib, A, I, E, F Reasoning: B excluded by label with exclude_transitives=True (C,D excluded); G excluded by exclusion path pattern (exclusion by path pattern doesn't exclude transitives) """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.test_lib[JavaInfo] expected_compile_jars = [ "libmultiple_exclusions_with_transitive_test_lib-hjar.jar", ] expected_full_compile_jars = [ "libmultiple_exclusions_with_transitive_test_lib.jar", ] expected_transitive_runtime_jars = [ "libmultiple_exclusions_with_transitive_test_lib.jar", "liblib_a.jar", "liblib_i.jar", "liblib_e.jar", "liblib_f.jar", ] expected_transitive_compile_jars = [ "libmultiple_exclusions_with_transitive_test_lib-hjar.jar", "liblib_a-hjar.jar", ] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) def _test_multiple_exclusions_without_transitive(ctx): """ Tests multiple exclusion levels with exclude_transitives=False. Dependency Graph: test_lib | dependencyset ("deps") ("runtime_deps") / \\ A (c) I (r) / \\ | / \\ G (r) / \\ | B (c) E (r) / | | / | | / | F (c) \\ / C (c) | D (r) Deps Dependencyset Input: items = [":lib_a"] Runtime Dependencyset Input: items = [":lib_i"] Dependencyset exclusions Input: deps_exclude_labels = [":lib_b"] deps_exclude_paths = ["lib_g"] exclude_transitives = False Expected Output: JARs preserved: test_lib, A, I, E, F, C, D JARs excluded: B (by label, direct only); G (by path pattern match, direct only) Compile-time JARs: test_lib-hjar, A-hjar, C-hjar Runtime JARs: test_lib, A, I, E, F, C, D Reasoning: B excluded by label (direct only, and its transitives are preserved); G excluded by exclusion path pattern (exclusion by path pattern doesn't exclude transitives) """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.test_lib[JavaInfo] expected_compile_jars = [ "libmultiple_exclusions_without_transitive_test_lib-hjar.jar", ] expected_full_compile_jars = [ "libmultiple_exclusions_without_transitive_test_lib.jar", ] expected_transitive_runtime_jars = [ "libmultiple_exclusions_without_transitive_test_lib.jar", "liblib_a.jar", "liblib_i.jar", "liblib_e.jar", "liblib_f.jar", "liblib_c.jar", "liblib_d.jar", ] expected_transitive_compile_jars = [ "libmultiple_exclusions_without_transitive_test_lib-hjar.jar", "liblib_a-hjar.jar", "liblib_c-hjar.jar", ] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) multiple_exclusions_with_transitive_test = unittest.make(_test_multiple_exclusions_with_transitive, attrs = { "test_lib": attr.label(providers = [JavaInfo]), }) multiple_exclusions_without_transitive_test = unittest.make(_test_multiple_exclusions_without_transitive, attrs = { "test_lib": attr.label(providers = [JavaInfo]), }) def _test_empty_exclusion_lists(ctx): """ Tests behavior when exclusion lists are empty. Dependency Graph: test_lib | dependencyset ("deps") ("runtime_deps") / \\ A (c) I (r) / \\ | / \\ G (r) / \\ | B (c) E (r) / | | / | | / | F (c) \\ / C (c) | D (r) Deps Dependencyset Input: items = [":lib_a"] Runtime Dependencyset Input: items = [":lib_i"] Dependencyset exclusions Input: deps_exclude_labels = [] deps_exclude_paths = [] exclude_transitives = False Expected Output: JARs preserved: test_lib, A, I, B, C, D, E, F, G Compile-time JARs: test_lib-hjar, A-hjar, B-hjar, C-hjar Runtime JARs: test_lib, A, I, B, C, D, E, F, G Reasoning: No exclusions applied, all dependencies preserved """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.test_lib[JavaInfo] expected_compile_jars = [ "libempty_exclusion_lists_test_lib-hjar.jar", ] expected_full_compile_jars = [ "libempty_exclusion_lists_test_lib.jar", ] expected_transitive_runtime_jars = [ "libempty_exclusion_lists_test_lib.jar", "liblib_a.jar", "liblib_i.jar", "liblib_b.jar", "liblib_c.jar", "liblib_d.jar", "liblib_e.jar", "liblib_f.jar", "liblib_g.jar" ] expected_transitive_compile_jars = [ "libempty_exclusion_lists_test_lib-hjar.jar", "liblib_a-hjar.jar", "liblib_b-hjar.jar", "liblib_c-hjar.jar", ] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) empty_exclusion_lists_test = unittest.make(_test_empty_exclusion_lists, attrs = { "test_lib": attr.label(providers = [JavaInfo]), }) def _test_multiple_paths(ctx): """ Tests handling of multiple paths to the same dependency. Dependency Graph: test_lib | dependencyset ("deps") ("runtime_deps") / \\ A (c) I (r) / \\ | / \\ G (r) / \\ | B (c) E (r) / | | / | | / | F (c) \\ / C (c) | D (r) Deps Dependencyset Input: items = [":lib_a"] Runtime Dependencyset Input: items = [":lib_i"] Dependencyset exclusions Input: deps_exclude_labels = [":lib_b", ":lib_g"] deps_exclude_paths = [] exclude_transitives = False Expected Output: JARs preserved: test_lib, A, I, E, F, C, D JARs excluded: B, G (not duplicated if reachable via multiple paths) Compile-time JARs: test_lib-hjar, A-hjar, C-hjar Runtime JARs: test_lib, A, I, E, F, C, D Reasoning: B,G excluded by label, but transitives are preserved as exclude_transitives = False """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.test_lib[JavaInfo] expected_compile_jars = [ "libmultiple_paths_test_lib-hjar.jar", ] expected_full_compile_jars = [ "libmultiple_paths_test_lib.jar", ] expected_transitive_runtime_jars = [ "libmultiple_paths_test_lib.jar", "liblib_a.jar", "liblib_i.jar", "liblib_e.jar", "liblib_f.jar", "liblib_c.jar", "liblib_d.jar" ] expected_transitive_compile_jars = [ "libmultiple_paths_test_lib-hjar.jar", "liblib_a-hjar.jar", "liblib_c-hjar.jar", ] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) multiple_paths_test = unittest.make(_test_multiple_paths, attrs = { "test_lib": attr.label(providers = [JavaInfo]), }) ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_1/src/main/java/com/depsfilter/A.java ================================================ package com.depsfilter; public class A { int a; private B b; // E is a runtime dependency, so no compile-time reference here public A() { a = 1; b = new B(); } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_1/src/main/java/com/depsfilter/B.java ================================================ package com.depsfilter; public class B { private C c; public B() { c = new C(); } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_1/src/main/java/com/depsfilter/C.java ================================================ package com.depsfilter; public class C { // D is a runtime dependency, so no compile-time reference here public C() { // No compile-time dependencies } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_1/src/main/java/com/depsfilter/D.java ================================================ package com.depsfilter; public class D { private int value; public D() { value = 4; } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_1/src/main/java/com/depsfilter/E.java ================================================ package com.depsfilter; public class E { private F f; public E() { f = new F(); } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_1/src/main/java/com/depsfilter/F.java ================================================ package com.depsfilter; public class F { private C c; public F() { c = new C(); } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_1/src/main/java/com/depsfilter/G.java ================================================ package com.depsfilter; public class G { private F f; public G() { f = new F(); } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_1/src/main/java/com/depsfilter/H.java ================================================ package com.depsfilter; public class H { private A a; // G is a runtime dependency, so no compile-time reference here public H() { a = new A(); } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_1/src/main/java/com/depsfilter/I.java ================================================ package com.depsfilter; public class I { public I() { int i = 1; } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/BUILD ================================================ load("//springboot/deps_filter_rules:dependencyset.bzl", "dependencyset") load( "//springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2:compile_and_runtime_test.bzl", "no_filtering_test", "filtered_deps_test", "filtered_deps_exclude_transitive_test", "path_based_exclusions_test", "interface_implementation_jars_test", "multiple_exclusions_with_transitive_test", "multiple_exclusions_without_transitive_test", "empty_exclusion_lists_test", "multiple_paths_test", ) # Dependency Graph Structure: # test_lib # | # dependencyset # / \ # ("deps") ("runtime_deps") # / \ / \ # J(r) A (c) H (r) I (c) # \ / \ | | # \ / \ G (r) | # \ / \ | / # B (c) E (r) / / # | | / / # | | / / # | | / / # | | / / # | F (c) # \ / # C (c) # | # D (r) java_library( name = "lib_a", srcs = ["src/main/java/com/depsfilter/A.java"], deps = [ ":lib_b", # A -> B (c) ], runtime_deps = [ ":lib_e", # A -> E (r) ], ) java_library( name = "lib_b", srcs = ["src/main/java/com/depsfilter/B.java"], deps = [":lib_c"], # B -> C (c) ) java_library( name = "lib_c", srcs = ["src/main/java/com/depsfilter/C.java"], runtime_deps = [":lib_d"], # C -> D (r) ) java_library( name = "lib_d", srcs = ["src/main/java/com/depsfilter/D.java"], ) java_library( name = "lib_e", srcs = ["src/main/java/com/depsfilter/E.java"], deps = [":lib_f"], # E -> F (c) ) java_library( name = "lib_f", srcs = ["src/main/java/com/depsfilter/F.java"], deps = [":lib_c"], # F -> C (c) ) java_library( name = "lib_g", srcs = ["src/main/java/com/depsfilter/G.java"], deps = [":lib_f"], # G -> F (c) ) java_library( name = "lib_h", srcs = ["src/main/java/com/depsfilter/H.java"], runtime_deps = [":lib_g"], # H -> G (r) ) java_library( name = "lib_i", srcs = ["src/main/java/com/depsfilter/H.java"], deps = [":lib_f"], # I -> F (c) ) java_library( name = "lib_j", srcs = ["src/main/java/com/depsfilter/J.java"], deps = [":lib_b"], # J -> B (c) ) test_deps = ["@unmanaged_deps_filter//:junit_junit", "@unmanaged_deps_filter//:org_assertj_assertj_core", ] # Test 1: No filtering dependencyset( name = "deps_no_filtering", items = [":lib_a", ":lib_i"], ) dependencyset( name = "runtime_deps_no_filtering", items = [":lib_h", ":lib_j"], ) java_library( name = "base_lib", srcs = ["src/main/java/com/depsfilter/H.java"], deps = [":lib_a", ":lib_i"], runtime_deps = [":lib_h", ":lib_j"], ) java_library( name = "no_filtering_test_lib", srcs = ["src/main/java/com/depsfilter/H.java"], deps = [":deps_no_filtering"], runtime_deps = [":runtime_deps_no_filtering"], ) no_filtering_test( name = "deps_filter_no_filtering_test", java_library = ":base_lib", java_library_dependencyset = ":no_filtering_test_lib", ) # Test 2: Exclude by labels and exclude_transitives = False dependencyset( name = "deps_exclude_b_g", items = [":lib_a", ":lib_i"], deps_exclude_labels = [":lib_b", ":lib_g"], ) dependencyset( name = "runtime_deps_exclude_b_g", items = [":lib_h", ":lib_j"], deps_exclude_labels = [":lib_b", ":lib_g"], ) java_library( name = "exclude_b_g_test_lib", srcs = ["src/main/java/com/depsfilter/H.java"], deps = [":deps_exclude_b_g"], runtime_deps = [":runtime_deps_exclude_b_g"], ) filtered_deps_test( name = "deps_filter_exclude_b_g_test", test_lib = ":exclude_b_g_test_lib", ) java_test( name = "DepsFilterFilteredDepsTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterTestHelper.java", "src/test/java/com/depsfilter/DepsFilterFilteredDepsTest.java" ], deps = [":exclude_b_g_test_lib"] + test_deps, ) # Test 3: Exclude by labels and exclude_transitives = True dependencyset( name = "deps_exclude_b_g_transitives", items = [":lib_a", ":lib_i"], deps_exclude_labels = [":lib_b", ":lib_g"], exclude_transitives = True, ) dependencyset( name = "runtime_deps_exclude_b_g_transitives", items = [":lib_h", ":lib_j"], deps_exclude_labels = [":lib_b", ":lib_g"], exclude_transitives = True, ) java_library( name = "exclude_b_g_transitives_test_lib", srcs = ["src/main/java/com/depsfilter/H.java"], deps = [":deps_exclude_b_g_transitives"], runtime_deps = [":runtime_deps_exclude_b_g_transitives"], ) filtered_deps_exclude_transitive_test( name = "deps_filter_exclude_b_g_exclude_transitive_test", test_lib = ":exclude_b_g_transitives_test_lib", ) java_test( name = "DepsFilterExcludeTransitiveTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterTestHelper.java", "src/test/java/com/depsfilter/DepsFilterExcludeTransitiveTest.java" ], deps = [":exclude_b_g_transitives_test_lib"] + test_deps, ) # Test 4: Test for path-based exclusions dependencyset( name = "deps_exclude_paths", items = [":lib_a", ":lib_i"], deps_exclude_paths = ["lib_b", "lib_f"], ) dependencyset( name = "runtime_deps_exclude_paths", items = [":lib_h", ":lib_j"], deps_exclude_paths = ["lib_b", "lib_f"], ) java_library( name = "path_based_exclusions_test_lib", srcs = ["src/main/java/com/depsfilter/H.java"], deps = [":deps_exclude_paths"], runtime_deps = [":runtime_deps_exclude_paths"], ) path_based_exclusions_test( name = "deps_filter_path_based_exclusions_test", test_lib = ":path_based_exclusions_test_lib", ) java_test( name = "DepsFilterPathBasedExclusionsTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterTestHelper.java", "src/test/java/com/depsfilter/DepsFilterPathBasedExclusionsTest.java" ], deps = [":path_based_exclusions_test_lib"] + test_deps, ) # Test 5: Interface vs Implementation JARs dependencyset( name = "deps_interface_impl_exclude_b_g", items = [":lib_a", ":lib_i"], deps_exclude_labels = [":lib_b", ":lib_g"], ) dependencyset( name = "runtime_deps_interface_impl_exclude_b_g", items = [":lib_h", ":lib_j"], deps_exclude_labels = [":lib_b", ":lib_g"], ) java_library( name = "interface_impl_test_lib", srcs = ["src/main/java/com/depsfilter/H.java"], deps = [":deps_interface_impl_exclude_b_g"], runtime_deps = [":runtime_deps_interface_impl_exclude_b_g"], ) interface_implementation_jars_test( name = "deps_filter_interface_impl_test", test_lib = ":interface_impl_test_lib", ) java_test( name = "DepsFilterInterfaceImplementationTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterTestHelper.java", "src/test/java/com/depsfilter/DepsFilterInterfaceImplementationTest.java" ], deps = [":interface_impl_test_lib"] + test_deps, ) # Test 6: Multiple exclusions with exclude_transitives=True dependencyset( name = "deps_multi_excl_transitives", items = [":lib_a", ":lib_i"], deps_exclude_labels = [":lib_b"], deps_exclude_paths = ["lib_g"], exclude_transitives = True, ) dependencyset( name = "runtime_deps_multi_excl_transitives", items = [":lib_h", ":lib_j"], deps_exclude_labels = [":lib_b"], deps_exclude_paths = ["lib_g"], exclude_transitives = True, ) java_library( name = "multiple_exclusions_with_transitive_test_lib", srcs = ["src/main/java/com/depsfilter/H.java"], deps = [":deps_multi_excl_transitives"], runtime_deps = [":runtime_deps_multi_excl_transitives"], ) multiple_exclusions_with_transitive_test( name = "multiple_exclusions_with_transitive_test", test_lib = ":multiple_exclusions_with_transitive_test_lib", ) java_test( name = "DepsFilterMultipleExclusionsWithTransitiveTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterTestHelper.java", "src/test/java/com/depsfilter/DepsFilterMultipleExclusionsWithTransitiveTest.java" ], deps = [":multiple_exclusions_with_transitive_test_lib"] + test_deps, ) # Test 7: Multiple exclusions with exclude_transitives=False dependencyset( name = "deps_multi_excl_no_transitives", items = [":lib_a", ":lib_i"], deps_exclude_labels = [":lib_b"], deps_exclude_paths = ["lib_g"], exclude_transitives = False, ) dependencyset( name = "runtime_deps_multi_excl_no_transitives", items = [":lib_h", ":lib_j"], deps_exclude_labels = [":lib_b"], deps_exclude_paths = ["lib_g"], exclude_transitives = False, ) java_library( name = "multiple_exclusions_without_transitive_test_lib", srcs = ["src/main/java/com/depsfilter/H.java"], deps = [":deps_multi_excl_no_transitives"], runtime_deps = [":runtime_deps_multi_excl_no_transitives"], ) multiple_exclusions_without_transitive_test( name = "multiple_exclusions_without_transitive_test", test_lib = ":multiple_exclusions_without_transitive_test_lib", ) java_test( name = "DepsFilterMultipleExclusionsWithoutTransitiveTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterTestHelper.java", "src/test/java/com/depsfilter/DepsFilterMultipleExclusionsWithoutTransitiveTest.java" ], deps = [":multiple_exclusions_without_transitive_test_lib"] + test_deps, ) # Test 8: Empty exclusion lists dependencyset( name = "deps_empty_exclusions", items = [":lib_a", ":lib_i"], deps_exclude_paths = [], deps_exclude_labels = [], ) dependencyset( name = "runtime_deps_empty_exclusions", items = [":lib_h", ":lib_j"], deps_exclude_paths = [], deps_exclude_labels = [], ) java_library( name = "empty_exclusion_lists_test_lib", srcs = ["src/main/java/com/depsfilter/H.java"], deps = [":deps_empty_exclusions"], runtime_deps = [":runtime_deps_empty_exclusions"], ) empty_exclusion_lists_test( name = "deps_filter_empty_exclusions_test", test_lib = ":empty_exclusion_lists_test_lib", ) java_test( name = "DepsFilterEmptyExclusionsTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterTestHelper.java", "src/test/java/com/depsfilter/DepsFilterEmptyExclusionsTest.java" ], deps = [":empty_exclusion_lists_test_lib"] + test_deps, ) # Test 9: Multiple paths handling dependencyset( name = "deps_multiple_paths_exclude_b_g", items = [":lib_a", ":lib_i"], deps_exclude_labels = [":lib_b", ":lib_g"], ) dependencyset( name = "runtime_deps_multiple_paths_exclude_b_g", items = [":lib_h", ":lib_j"], deps_exclude_labels = [":lib_b", ":lib_g"], ) java_library( name = "multiple_paths_test_lib", srcs = ["src/main/java/com/depsfilter/H.java"], deps = [":deps_multiple_paths_exclude_b_g"], runtime_deps = [":runtime_deps_multiple_paths_exclude_b_g"], ) multiple_paths_test( name = "deps_filter_multiple_paths_test", test_lib = ":multiple_paths_test_lib", ) java_test( name = "DepsFilterMultiplePathsTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterTestHelper.java", "src/test/java/com/depsfilter/DepsFilterMultiplePathsTest.java" ], deps = [":multiple_paths_test_lib"] + test_deps, ) toolchain( name = "unittest_toolchain", toolchain_type = "@bazel_skylib//toolchains/unittest:toolchain_type", toolchain = "@bazel_skylib//toolchains/unittest:toolchain", ) ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/compile_and_runtime_test.bzl ================================================ load("@bazel_skylib//lib:unittest.bzl", "asserts", "unittest") load("//springboot/deps_filter_rules/tests/test_utils:verification_utils.bzl", "verify_jars", "verify_runtime_and_compile_jars", "verify_jars_and_dropped_counts", "verify_dropped_counts", "update_jar_name", ) def _test_no_filtering(ctx): """ Tests that deps_filter preserves all dependencies when no exclusions are applied. Dependency Graph: test_lib | dependencyset / \\ ("deps") ("runtime_deps") / \\ / \\ J(r) A (c) H (r) I (c) \\ / \\ | | \\ / \\ G (r) | \\ / \\ | / B (c) E (r) / / | | / / | | / / | | / / | | / / | F (c) \\ / C (c) | D (r) Expected: All JARs from java_library must match deps_filter: - full_compile_jars: Implementation JARs (e.g., liblib_a.jar) - compile_jars: Interface JARs (e.g., liblib_a-hjar.jar) - transitive_compile_time_jars: Interface JARs from transitive deps - transitive_runtime_jars: Implementation JARs from transitive deps """ env = unittest.begin(ctx) java_lib_info = ctx.attr.java_library[JavaInfo] deps_filter_info = ctx.attr.java_library_dependencyset[JavaInfo] # Verify all JAR fields match between java_library and deps_filter jar_fields = [ "full_compile_jars", # Implementation JARs "compile_jars", # Interface JARs "transitive_compile_time_jars", # Transitive interface JARs "transitive_runtime_jars" # Transitive implementation JARs ] for jar_field in jar_fields: java_lib_jars = getattr(java_lib_info, jar_field) deps_filter_jars = getattr(deps_filter_info, jar_field) asserts.equals(env, type(java_lib_jars), type(deps_filter_jars), "JAR type mismatch: {} vs deps_filter".format(jar_field)) java_lib_jars_list = [jar.basename for jar in java_lib_jars.to_list()] deps_filter_jars_list = [jar.basename for jar in deps_filter_jars.to_list()] # Normalize output jar naming difference between dependencyset consumer and base_lib update_jar_name("libno_filtering_test_lib", "libbase_lib", deps_filter_jars_list) asserts.equals(env, java_lib_jars_list, deps_filter_jars_list, "JAR contents mismatch: {} vs deps_filter".format(jar_field)) return unittest.end(env) no_filtering_test = unittest.make(_test_no_filtering, attrs = { "java_library": attr.label(providers = [JavaInfo]), "java_library_dependencyset": attr.label(providers = [JavaInfo]), }) def _test_filtered_deps(ctx): """ Tests basic dependency filtering with label-based exclusions. Dependency Graph: test_lib | dependencyset / \\ ("deps") ("runtime_deps") / \\ / \\ J(r) A (c) H (r) I (c) \\ / \\ | | \\ / \\ G (r) | \\ / \\ | / B (c) E (r) / / | | / / | | / / | | / / | | / / | F (c) \\ / C (c) | D (r) Deps Dependencyset Input: items = [":lib_a", ":lib_i"], Runtime Dependencyset Input: items = [":lib_h", ":lib_j"], Dependencyset exclusions Input: deps_exclude_labels = [":lib_b", ":lib_g"] deps_exclude_paths = [] exclude_transitives = False Expected Output: JARs preserved: A, I, C, D, E, F, H, J JARs excluded: B, G (by label, direct deps only, transitives preserved) Compile-time JARs: A-hjar, I-hjar, C-hjar, F-hjar Runtime JARs: A, I, C, D, E, F, H, J Reasoning: B,G excluded by label, but their transitives (C,D,F) are preserved """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.test_lib[JavaInfo] expected_compile_jars = [ "libexclude_b_g_test_lib-hjar.jar", ] expected_full_compile_jars = [ "libexclude_b_g_test_lib.jar", ] expected_transitive_runtime_jars = [ "libexclude_b_g_test_lib.jar", "liblib_a.jar", "liblib_c.jar", "liblib_d.jar", "liblib_e.jar", "liblib_f.jar", "liblib_h.jar", "liblib_i.jar", "liblib_j.jar", ] expected_transitive_compile_jars = [ "libexclude_b_g_test_lib-hjar.jar", "liblib_a-hjar.jar", "liblib_c-hjar.jar", "liblib_f-hjar.jar", "liblib_i-hjar.jar", ] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) filtered_deps_test = unittest.make(_test_filtered_deps, attrs = { "test_lib": attr.label(providers = [JavaInfo]), }) def _test_filtered_deps_exclude_transitive(ctx): """ Tests dependency filtering with transitive exclusions. Dependency Graph: test_lib | dependencyset / \\ ("deps") ("runtime_deps") / \\ / \\ J(r) A (c) H (r) I (c) \\ / \\ | | \\ / \\ G (r) | \\ / \\ | / B (c) E (r) / / | | / / | | / / | | / / | | / / | F (c) \\ / C (c) | D (r) Deps Dependencyset Input: items = [":lib_a", ":lib_i"], Runtime Dependencyset Input: items = [":lib_h", ":lib_j"], Dependencyset exclusions Input: deps_exclude_labels = [":lib_b", ":lib_g"] deps_exclude_paths = [] exclude_transitives = True Expected Output: JARs preserved: A, I, E, H, J JARs excluded: B, G (by label) and all their transitives Compile-time JARs: A-hjar, I-hjar Runtime JARs: A, I, E, H, J (only preserved deps, no transitives of excluded deps) Reasoning: B,G excluded by label with exclude_transitives=True, so C,D,F also excluded """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.test_lib[JavaInfo] expected_compile_jars = [ "libexclude_b_g_transitives_test_lib-hjar.jar", ] expected_full_compile_jars = [ "libexclude_b_g_transitives_test_lib.jar", ] expected_transitive_runtime_jars = [ "libexclude_b_g_transitives_test_lib.jar", "liblib_a.jar", "liblib_e.jar", "liblib_h.jar", "liblib_i.jar", "liblib_j.jar", ] expected_transitive_compile_jars = [ "libexclude_b_g_transitives_test_lib-hjar.jar", "liblib_a-hjar.jar", "liblib_i-hjar.jar", ] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) filtered_deps_exclude_transitive_test = unittest.make(_test_filtered_deps_exclude_transitive, attrs = { "test_lib": attr.label(providers = [JavaInfo]), }) def _test_path_based_exclusions(ctx): """ Tests filtering based on path patterns in deps_exclude_paths. Dependency Graph: test_lib | dependencyset / \\ ("deps") ("runtime_deps") / \\ / \\ J(r) A (c) H (r) I (c) \\ / \\ | | \\ / \\ G (r) | \\ / \\ | / B (c) E (r) / / | | / / | | / / | | / / | | / / | F (c) \\ / C (c) | D (r) Deps Dependencyset Input: items = [":lib_a", ":lib_i"], Runtime Dependencyset Input: items = [":lib_h", ":lib_j"], Dependencyset exclusions Input: deps_exclude_labels = [] deps_exclude_paths = ["lib_b", "lib_f"] exclude_transitives = False ## IMPORTANT_FEATURE Expected Output: JARs preserved: A, I, C, D, E, G, H, J JARs excluded: B, F (by path pattern match, transitives may be preserved) Compile-time JARs: A-hjar, I-hjar, C-hjar Runtime JARs: A, I, C, D, E, G, H, J (all preserved deps + transitives not matching exclusion path patterns) Reasoning: B,F excluded by path pattern, but their transitives are preserved as they didn't match the pattern """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.test_lib[JavaInfo] expected_compile_jars = [ "libpath_based_exclusions_test_lib-hjar.jar", ] expected_full_compile_jars = [ "libpath_based_exclusions_test_lib.jar", ] expected_transitive_runtime_jars = [ "libpath_based_exclusions_test_lib.jar", "liblib_a.jar", "liblib_c.jar", "liblib_d.jar", "liblib_e.jar", "liblib_g.jar", "liblib_h.jar", "liblib_i.jar", "liblib_j.jar", ] expected_transitive_compile_jars = [ "libpath_based_exclusions_test_lib-hjar.jar", "liblib_a-hjar.jar", "liblib_c-hjar.jar", "liblib_i-hjar.jar", ] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) path_based_exclusions_test = unittest.make(_test_path_based_exclusions, attrs = { "test_lib": attr.label(providers = [JavaInfo]), }) def _test_interface_implementation_jars(ctx): """ Tests proper handling of interface (-hjar) and implementation JARs. Dependency Graph: test_lib | dependencyset / \\ ("deps") ("runtime_deps") / \\ / \\ J(r) A (c) H (r) I (c) \\ / \\ | | \\ / \\ G (r) | \\ / \\ | / B (c) E (r) / / | | / / | | / / | | / / | | / / | F (c) \\ / C (c) | D (r) Deps Dependencyset Input: items = [":lib_a", ":lib_i"], Runtime Dependencyset Input: items = [":lib_h", ":lib_j"], Dependencyset exclusions Input: deps_exclude_labels = [":lib_b", ":lib_g"] deps_exclude_paths = [] exclude_transitives = False Expected Output: compile_jars: liblib_a-hjar.jar, liblib_i-hjar.jar full_compile_jars: liblib_a.jar, liblib_i.jar """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.test_lib[JavaInfo] compile_jars = sorted([jar.basename for jar in javainfo_filtered.compile_jars.to_list()]) full_compile_jars = sorted([jar.basename for jar in javainfo_filtered.full_compile_jars.to_list()]) expected_compile_jars = [ "libinterface_impl_test_lib-hjar.jar", ] expected_full_compile_jars = [ "libinterface_impl_test_lib.jar", ] asserts.equals(env, compile_jars, expected_compile_jars) asserts.equals(env, full_compile_jars, expected_full_compile_jars) return unittest.end(env) interface_implementation_jars_test = unittest.make(_test_interface_implementation_jars, attrs = { "test_lib": attr.label(providers = [JavaInfo]), }) def _test_multiple_exclusions_with_transitive(ctx): """ Tests multiple exclusion levels with exclude_transitives=True. Dependency Graph: test_lib | dependencyset / \\ ("deps") ("runtime_deps") / \\ / \\ J(r) A (c) H (r) I (c) \\ / \\ | | \\ / \\ G (r) | \\ / \\ | / B (c) E (r) / / | | / / | | / / | | / / | | / / | F (c) \\ / C (c) | D (r) Deps Dependencyset Input: items = [":lib_a", ":lib_i"], Runtime Dependencyset Input: items = [":lib_h", ":lib_j"], Dependencyset exclusions Input: deps_exclude_labels = [":lib_b"] deps_exclude_paths = ["lib_g"] exclude_transitives = True Expected Output: JARs preserved: A, I, E, F, H, J JARs excluded: B and its transitives; G (not neccessarily its transitives as specified exclusion by path pattern is matched) Compile-time JARs: A-hjar, I-hjar, F-hjar Runtime JARs: A, I, E, F, H, J Reasoning: B excluded by label with exclude_transitives=True (C,D excluded); G excluded by exclusion path pattern (exclusion by path pattern doesn't exclude transitives) """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.test_lib[JavaInfo] expected_compile_jars = [ "libmultiple_exclusions_with_transitive_test_lib-hjar.jar", ] expected_full_compile_jars = [ "libmultiple_exclusions_with_transitive_test_lib.jar", ] expected_transitive_runtime_jars = [ "libmultiple_exclusions_with_transitive_test_lib.jar", "liblib_a.jar", "liblib_e.jar", "liblib_f.jar", "liblib_h.jar", "liblib_i.jar", "liblib_j.jar", ] expected_transitive_compile_jars = [ "libmultiple_exclusions_with_transitive_test_lib-hjar.jar", "liblib_a-hjar.jar", "liblib_f-hjar.jar", "liblib_i-hjar.jar", ] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) def _test_multiple_exclusions_without_transitive(ctx): """ Tests multiple exclusion levels with exclude_transitives=False. Dependency Graph: test_lib | dependencyset / \\ ("deps") ("runtime_deps") / \\ / \\ J(r) A (c) H (r) I (c) \\ / \\ | | \\ / \\ G (r) | \\ / \\ | / B (c) E (r) / / | | / / | | / / | | / / | | / / | F (c) \\ / C (c) | D (r) Deps Dependencyset Input: items = [":lib_a", ":lib_i"], Runtime Dependencyset Input: items = [":lib_h", ":lib_j"], Dependencyset exclusions Input: deps_exclude_labels = [":lib_b"] deps_exclude_paths = ["lib_g"] exclude_transitives = False Expected Output: JARs preserved: A, I, C, D, E, F, H, J JARs excluded: B (by label, direct only); G (by path pattern match, direct only) Compile-time JARs: A-hjar, I-hjar, C-hjar, F-hjar Runtime JARs: A, I, C, D, E, F, H, J Reasoning: B excluded by label (direct only, and its transitives are preserved); G excluded by exclusion path pattern (exclusion by path pattern doesn't exclude transitives) """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.test_lib[JavaInfo] expected_compile_jars = [ "libmultiple_exclusions_without_transitive_test_lib-hjar.jar", ] expected_full_compile_jars = [ "libmultiple_exclusions_without_transitive_test_lib.jar", ] expected_transitive_runtime_jars = [ "libmultiple_exclusions_without_transitive_test_lib.jar", "liblib_a.jar", "liblib_c.jar", "liblib_d.jar", "liblib_e.jar", "liblib_f.jar", "liblib_h.jar", "liblib_i.jar", "liblib_j.jar", ] expected_transitive_compile_jars = [ "libmultiple_exclusions_without_transitive_test_lib-hjar.jar", "liblib_a-hjar.jar", "liblib_c-hjar.jar", "liblib_f-hjar.jar", "liblib_i-hjar.jar", ] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) multiple_exclusions_with_transitive_test = unittest.make(_test_multiple_exclusions_with_transitive, attrs = { "test_lib": attr.label(providers = [JavaInfo]), }) multiple_exclusions_without_transitive_test = unittest.make(_test_multiple_exclusions_without_transitive, attrs = { "test_lib": attr.label(providers = [JavaInfo]), }) def _test_empty_exclusion_lists(ctx): """ Tests behavior when exclusion lists are empty. Dependency Graph: test_lib | dependencyset / \\ ("deps") ("runtime_deps") / \\ / \\ J(r) A (c) H (r) I (c) \\ / \\ | | \\ / \\ G (r) | \\ / \\ | / B (c) E (r) / / | | / / | | / / | | / / | | / / | F (c) \\ / C (c) | D (r) Deps Dependencyset Input: items = [":lib_a", ":lib_i"], Runtime Dependencyset Input: items = [":lib_h", ":lib_j"], Dependencyset exclusions Input: deps_exclude_labels = [] deps_exclude_paths = [] exclude_transitives = False Expected Output: JARs preserved: A, I, B, C, D, E, F, G, H, J Compile-time JARs: A-hjar, I-hjar, B-hjar, C-hjar, F-hjar Runtime JARs: A, I, B, C, D, E, F, G, H, J Reasoning: No exclusions applied, all dependencies preserved """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.test_lib[JavaInfo] expected_compile_jars = [ "libempty_exclusion_lists_test_lib-hjar.jar", ] expected_full_compile_jars = [ "libempty_exclusion_lists_test_lib.jar", ] expected_transitive_runtime_jars = [ "libempty_exclusion_lists_test_lib.jar", "liblib_a.jar", "liblib_b.jar", "liblib_c.jar", "liblib_d.jar", "liblib_e.jar", "liblib_f.jar", "liblib_g.jar", "liblib_h.jar", "liblib_i.jar", "liblib_j.jar", ] expected_transitive_compile_jars = [ "libempty_exclusion_lists_test_lib-hjar.jar", "liblib_a-hjar.jar", "liblib_b-hjar.jar", "liblib_c-hjar.jar", "liblib_f-hjar.jar", "liblib_i-hjar.jar", ] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) empty_exclusion_lists_test = unittest.make(_test_empty_exclusion_lists, attrs = { "test_lib": attr.label(providers = [JavaInfo]), }) def _test_multiple_paths(ctx): """ Tests handling of multiple paths to the same dependency. Dependency Graph: test_lib | dependencyset / \\ ("deps") ("runtime_deps") / \\ / \\ J(r) A (c) H (r) I (c) \\ / \\ | | \\ / \\ G (r) | \\ / \\ | / B (c) E (r) / / | | / / | | / / | | / / | | / / | F (c) \\ / C (c) | D (r) # IMPORTANT_FEATURE Deps Dependencyset Input: items = [":lib_a", ":lib_i"], Runtime Dependencyset Input: items = [":lib_h", ":lib_j"], Dependencyset exclusions Input: deps_exclude_labels = [":lib_b", ":lib_g"] deps_exclude_paths = [] exclude_transitives = False Expected Output: JARs preserved: A, I, C, D, E, F, H, J JARs excluded: B, G (not duplicated if reachable via multiple paths) Compile-time JARs: A-hjar, I-hjar, C-hjar, F-hjar Runtime JARs: A, I, C, D, E, F, H, J Reasoning: B,G excluded by label, but transitives are preserved as exclude_transitives = False """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.test_lib[JavaInfo] expected_compile_jars = [ "libmultiple_paths_test_lib-hjar.jar", ] expected_full_compile_jars = [ "libmultiple_paths_test_lib.jar", ] expected_transitive_runtime_jars = [ "libmultiple_paths_test_lib.jar", "liblib_a.jar", "liblib_c.jar", "liblib_d.jar", "liblib_e.jar", "liblib_f.jar", "liblib_h.jar", "liblib_i.jar", "liblib_j.jar", ] expected_transitive_compile_jars = [ "libmultiple_paths_test_lib-hjar.jar", "liblib_a-hjar.jar", "liblib_c-hjar.jar", "liblib_f-hjar.jar", "liblib_i-hjar.jar", ] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) multiple_paths_test = unittest.make(_test_multiple_paths, attrs = { "test_lib": attr.label(providers = [JavaInfo]), }) ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/src/main/java/com/depsfilter/A.java ================================================ package com.depsfilter; public class A { int a; private B b; // E is a runtime dependency, so no compile-time reference here public A() { a = 1; b = new B(); } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/src/main/java/com/depsfilter/B.java ================================================ package com.depsfilter; public class B { private C c; public B() { c = new C(); } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/src/main/java/com/depsfilter/C.java ================================================ package com.depsfilter; public class C { // D is a runtime dependency, so no compile-time reference here public C() { // No compile-time dependencies } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/src/main/java/com/depsfilter/D.java ================================================ package com.depsfilter; public class D { private int value; public D() { value = 4; } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/src/main/java/com/depsfilter/E.java ================================================ package com.depsfilter; public class E { private F f; public E() { f = new F(); } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/src/main/java/com/depsfilter/F.java ================================================ package com.depsfilter; public class F { private C c; public F() { c = new C(); } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/src/main/java/com/depsfilter/G.java ================================================ package com.depsfilter; public class G { private F f; public G() { f = new F(); } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/src/main/java/com/depsfilter/H.java ================================================ package com.depsfilter; public class H { public H() { int h = 1; } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/src/main/java/com/depsfilter/I.java ================================================ package com.depsfilter; public class I { private F; public I() { F = new F(); } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/src/main/java/com/depsfilter/J.java ================================================ package com.depsfilter; public class J { private B b; public J() { b = new B(); } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/src/test/java/com/depsfilter/DepsFilterEmptyExclusionsTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.ArrayList; import java.util.List; import org.junit.Test; public class DepsFilterEmptyExclusionsTest { @Test public void testTransitivesExclusion() { /* Checkout _test_empty_exclusion_lists in compile_and_runtime_2/compile_and_runtime_test.bzl */ // available deps at the runtime List availableDeps = DepsFilterTestHelper.computeClasspathDependencies(); // expected runtime deps List expectedRuntimeDeps = new ArrayList<>(DepsFilterTestHelper.getRuntimeDepsListBeforeExclusions()); expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); // Add test-specific JAR file expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/DepsFilterEmptyExclusionsTest.jar"); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/libempty_exclusion_lists_test_lib.jar"); // Verify that availableDeps contains exactly the same elements as expectedRuntimeDeps in any order assertThat(availableDeps).containsExactlyInAnyOrderElementsOf(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/src/test/java/com/depsfilter/DepsFilterExcludeTransitiveTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.ArrayList; import java.util.List; import org.junit.Test; public class DepsFilterExcludeTransitiveTest { @Test public void testTransitivesExclusion() { /* Checkout _test_filtered_deps_exclude_transitive in compile_and_runtime_2/compile_and_runtime_test.bzl */ // available deps at the runtime List availableDeps = DepsFilterTestHelper.computeClasspathDependencies(); // expected runtime deps based on bzl file expected_transitive_runtime_jars List expectedRuntimeDeps = new ArrayList<>(List.of( "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_a.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_e.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_h.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_i.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_j.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/DepsFilterExcludeTransitiveTest.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/libexclude_b_g_transitives_test_lib.jar" )); // Add test dependencies expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); // Verify that availableDeps contains exactly the same elements as expectedRuntimeDeps in any order assertThat(availableDeps).containsExactlyInAnyOrderElementsOf(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/src/test/java/com/depsfilter/DepsFilterFilteredDepsTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.ArrayList; import java.util.List; import org.junit.Test; public class DepsFilterFilteredDepsTest { @Test public void testFilteredDeps() { /* Checkout _test_filtered_deps in compile_and_runtime_2/compile_and_runtime_test.bzl */ // available deps at the runtime List availableDeps = DepsFilterTestHelper.computeClasspathDependencies(); // expected runtime deps based on bzl file expected_transitive_runtime_jars List expectedRuntimeDeps = new ArrayList<>(List.of( "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_a.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_c.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_d.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_e.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_f.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_h.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_i.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_j.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/DepsFilterFilteredDepsTest.jar" )); // Add test dependencies expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/libexclude_b_g_test_lib.jar"); // Verify that availableDeps contains exactly the same elements as expectedRuntimeDeps in any order assertThat(availableDeps).containsExactlyInAnyOrderElementsOf(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/src/test/java/com/depsfilter/DepsFilterInterfaceImplementationTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.ArrayList; import java.util.List; import org.junit.Test; public class DepsFilterInterfaceImplementationTest { @Test public void testInterfaceImplementationJars() { /* Checkout _test_interface_implementation_jars in compile_and_runtime_2/compile_and_runtime_test.bzl */ // available deps at the runtime List availableDeps = DepsFilterTestHelper.computeClasspathDependencies(); // expected runtime deps based on bzl file expected_transitive_runtime_jars // Note: This test uses the same configuration as filtered_deps test List expectedRuntimeDeps = new ArrayList<>(List.of( "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_a.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_c.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_d.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_e.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_f.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_h.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_i.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_j.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/DepsFilterInterfaceImplementationTest.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/libinterface_impl_test_lib.jar" )); // Add test dependencies expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); // Verify that availableDeps contains exactly the same elements as expectedRuntimeDeps in any order assertThat(availableDeps).containsExactlyInAnyOrderElementsOf(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/src/test/java/com/depsfilter/DepsFilterMultipleExclusionsWithTransitiveTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.ArrayList; import java.util.List; import org.junit.Test; public class DepsFilterMultipleExclusionsWithTransitiveTest { @Test public void testMultipleExclusionsWithTransitive() { /* Checkout _test_multiple_exclusions_with_transitive in compile_and_runtime_2/compile_and_runtime_test.bzl */ // available deps at the runtime List availableDeps = DepsFilterTestHelper.computeClasspathDependencies(); // expected runtime deps based on bzl file expected_transitive_runtime_jars List expectedRuntimeDeps = new ArrayList<>(List.of( "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_a.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_e.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_f.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_h.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_i.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_j.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/DepsFilterMultipleExclusionsWithTransitiveTest.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/libmultiple_exclusions_with_transitive_test_lib.jar" )); // Add test dependencies expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); // Verify that availableDeps contains exactly the same elements as expectedRuntimeDeps in any order assertThat(availableDeps).containsExactlyInAnyOrderElementsOf(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/src/test/java/com/depsfilter/DepsFilterMultipleExclusionsWithoutTransitiveTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.ArrayList; import java.util.List; import org.junit.Test; public class DepsFilterMultipleExclusionsWithoutTransitiveTest { @Test public void testMultipleExclusionsWithoutTransitive() { /* Checkout _test_multiple_exclusions_without_transitive in compile_and_runtime_2/compile_and_runtime_test.bzl */ // available deps at the runtime List availableDeps = DepsFilterTestHelper.computeClasspathDependencies(); // expected runtime deps based on bzl file expected_transitive_runtime_jars List expectedRuntimeDeps = new ArrayList<>(List.of( "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_a.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_c.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_d.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_e.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_f.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_h.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_i.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_j.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/DepsFilterMultipleExclusionsWithoutTransitiveTest.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/libmultiple_exclusions_without_transitive_test_lib.jar" )); // Add test dependencies expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); // Verify that availableDeps contains exactly the same elements as expectedRuntimeDeps in any order assertThat(availableDeps).containsExactlyInAnyOrderElementsOf(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/src/test/java/com/depsfilter/DepsFilterMultiplePathsTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.ArrayList; import java.util.List; import org.junit.Test; public class DepsFilterMultiplePathsTest { @Test public void testMultiplePaths() { /* Checkout _test_multiple_paths in compile_and_runtime_2/compile_and_runtime_test.bzl */ // available deps at the runtime List availableDeps = DepsFilterTestHelper.computeClasspathDependencies(); // expected runtime deps based on bzl file expected_transitive_runtime_jars List expectedRuntimeDeps = new ArrayList<>(List.of( "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_a.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_c.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_d.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_e.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_f.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_h.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_i.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_j.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/DepsFilterMultiplePathsTest.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/libmultiple_paths_test_lib.jar" )); // Add test dependencies expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); // Verify that availableDeps contains exactly the same elements as expectedRuntimeDeps in any order assertThat(availableDeps).containsExactlyInAnyOrderElementsOf(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/src/test/java/com/depsfilter/DepsFilterPathBasedExclusionsTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.ArrayList; import java.util.List; import org.junit.Test; public class DepsFilterPathBasedExclusionsTest { @Test public void testPathBasedExclusions() { /* Checkout _test_path_based_exclusions in compile_and_runtime_2/compile_and_runtime_test.bzl */ // available deps at the runtime List availableDeps = DepsFilterTestHelper.computeClasspathDependencies(); // expected runtime deps based on bzl file expected_transitive_runtime_jars List expectedRuntimeDeps = new ArrayList<>(List.of( "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_a.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_c.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_d.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_e.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_g.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_h.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_i.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_j.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/DepsFilterPathBasedExclusionsTest.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/libpath_based_exclusions_test_lib.jar" )); // Add test dependencies expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); // Verify that availableDeps contains exactly the same elements as expectedRuntimeDeps in any order assertThat(availableDeps).containsExactlyInAnyOrderElementsOf(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/src/test/java/com/depsfilter/DepsFilterTestHelper.java ================================================ package com.depsfilter; import java.util.ArrayList; import java.util.List; /** * Helper class containing common functionality for deps filter tests. * Provides shared methods and data that can be used across multiple test classes. */ public class DepsFilterTestHelper { /** * Computes the available dependencies from the current classpath. * @return List of available dependencies with "../" prefix removed */ public static List computeClasspathDependencies() { String classpath = System.getProperty("java.class.path"); String[] classpathEntries = classpath.split(System.getProperty("path.separator")); List availableDeps = new ArrayList<>(); for (String entry : classpathEntries) { availableDeps.add(entry.replace("../", "")); } return availableDeps; } /** * Returns the test dependencies required to run the tests. * These are the dependencies specified in the test target. * @return List of test dependencies */ public static List getTestDeps() { return List.of( "rules_jvm_external~~maven~unmanaged_deps_filter/junit/junit/4.13.2/processed_junit-4.13.2.jar", "rules_jvm_external~~maven~unmanaged_deps_filter/org/hamcrest/hamcrest-core/1.3/processed_hamcrest-core-1.3.jar", "rules_jvm_external~~maven~unmanaged_deps_filter/org/assertj/assertj-core/3.26.0/processed_assertj-core-3.26.0.jar", "rules_jvm_external~~maven~unmanaged_deps_filter/net/bytebuddy/byte-buddy/1.14.16/processed_byte-buddy-1.14.16.jar", "rules_java~~toolchains~remote_java_tools/java_tools/Runner_deploy.jar" ); } /** * Returns the runtime dependencies before exclusions. * These are the base runtime dependencies that would be available before any filtering. * @return List of runtime dependencies before exclusions */ public static List getRuntimeDepsListBeforeExclusions() { return new ArrayList<>(List.of( "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_a.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_b.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_c.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_d.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_e.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_f.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_g.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_h.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_i.jar", "springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_and_runtime_2/liblib_j.jar" )); } /** * Creates a complete list of runtime dependencies including test dependencies. * This combines the base runtime dependencies with test dependencies. * @return Complete list of runtime dependencies including test dependencies */ public static List getCompleteRuntimeDepsList() { List completeList = new ArrayList<>(getRuntimeDepsListBeforeExclusions()); completeList.addAll(getTestDeps()); return completeList; } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_time_only/BUILD ================================================ load("//springboot/deps_filter_rules:deps_filter.bzl", "deps_filter") load("//springboot/deps_filter_rules:dependencyset.bzl", "dependencyset") load( "//springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_time_only:compile_time_only_test.bzl", "no_filtering_test", "filtered_deps_test", "filtered_deps_exclude_transitive_test", "path_based_exclusions_test", "interface_implementation_jars_test", "multiple_exclusions_with_transitive_test", "multiple_exclusions_without_transitive_test", "empty_exclusion_lists_test", "multiple_paths_test", ) # Dependency Graph Structure: # base_lib # | # dependencyset("deps") # / \ # A I # / \ / # B E G # | | / # | F # \/ # C # | # D # java_library( name = "lib_a", srcs = ["src/main/java/com/depsfilter/A.java"], deps = [ ":lib_b", # A -> B ":lib_e", # A -> E ], ) java_library( name = "lib_b", srcs = ["src/main/java/com/depsfilter/B.java"], deps = [":lib_c"], # B -> C ) java_library( name = "lib_c", srcs = ["src/main/java/com/depsfilter/C.java"], deps = [":lib_d"], # B -> D ) java_library( name = "lib_d", srcs = ["src/main/java/com/depsfilter/D.java"], ) java_library( name = "lib_e", srcs = ["src/main/java/com/depsfilter/E.java"], deps = [":lib_f"], # E -> F ) java_library( name = "lib_f", srcs = ["src/main/java/com/depsfilter/F.java"], deps = [":lib_c"], # F -> C ) java_library( name = "lib_g", srcs = ["src/main/java/com/depsfilter/G.java"], deps = [":lib_f"], # G -> F path ) java_library( name = "lib_i", srcs = ["src/main/java/com/depsfilter/I.java"], deps = [":lib_g"], # I -> G path ) # Consumer library that uses the filtered dependencies java_library( name = "no_filtering_test_lib", srcs = ["src/main/java/com/depsfilter/H.java"], deps = [":no_filtering_test_dependencyset"], ) # Test 1: No filtering dependencyset( name = "no_filtering_test_dependencyset", items = ["lib_a",":lib_i"], ) java_library( name = "base_lib", srcs = ["src/main/java/com/depsfilter/H.java"], deps = [":lib_a", ":lib_i"], ) no_filtering_test( name = "no_filtering_test", java_library = ":base_lib", java_library_dependencyset = ":no_filtering_test_lib", ) # Test 2: Exclude by labels and exclude_transitives = False dependencyset( name = "deps_exclude_b_g", items = ["lib_a",":lib_i"], deps_exclude_labels = [":lib_b", ":lib_g"], ) java_library( name = "exclude_b_g_test_lib", srcs = ["src/main/java/com/depsfilter/H.java"], deps = [":deps_exclude_b_g"], ) filtered_deps_test( name = "deps_filter_exclude_b_g_test", test_lib = ":exclude_b_g_test_lib", ) # Test 3: Exclude by labels and exclude_transitives = True dependencyset( name = "deps_exclude_b_g_transitives", items = ["lib_a",":lib_i"], deps_exclude_labels = [":lib_b", ":lib_g"], exclude_transitives = True, ) java_library( name = "exclude_b_g_transitives_test_lib", srcs = ["src/main/java/com/depsfilter/H.java"], deps = [":deps_exclude_b_g_transitives"], ) filtered_deps_exclude_transitive_test( name = "deps_filter_exclude_b_g_exclude_transitive_test", test_lib = ":exclude_b_g_transitives_test_lib", ) # Test 4: Test for path-based exclusions dependencyset( name = "deps_exclude_paths", items = ["lib_a",":lib_i"], deps_exclude_paths = ["lib_b", "lib_f"], ) java_library( name = "exclude_paths_test_lib", srcs = ["src/main/java/com/depsfilter/H.java"], deps = [":deps_exclude_paths"], ) path_based_exclusions_test( name = "deps_filter_path_based_exclusions_test", test_lib = ":exclude_paths_test_lib", ) # Test 5: Interface vs Implementation JARs dependencyset( name = "deps_interface_impl_exclude_b_g", items = ["lib_a",":lib_i"], deps_exclude_labels = [":lib_b", ":lib_g"], ) java_library( name = "interface_impl_test_lib", srcs = ["src/main/java/com/depsfilter/H.java"], deps = [":deps_interface_impl_exclude_b_g"], ) interface_implementation_jars_test( name = "deps_filter_interface_impl_test", test_lib = ":interface_impl_test_lib", ) # Test 6: Multiple exclusions with exclude_transitives=True dependencyset( name = "deps_multi_excl_transitives", items = ["lib_a",":lib_i"], deps_exclude_labels = [":lib_b"], deps_exclude_paths = ["lib_g"], exclude_transitives = True, ) java_library( name = "multi_excl_transitives_test_lib", srcs = ["src/main/java/com/depsfilter/H.java"], deps = [":deps_multi_excl_transitives"], ) multiple_exclusions_with_transitive_test( name = "multiple_exclusions_with_transitive_test", test_lib = ":multi_excl_transitives_test_lib", ) # Test 7: Multiple exclusions with exclude_transitives=False dependencyset( name = "deps_multi_excl_no_transitives", items = ["lib_a",":lib_i"], deps_exclude_labels = [":lib_b"], deps_exclude_paths = ["lib_g"], exclude_transitives = False, ) java_library( name = "multi_excl_no_transitives_test_lib", srcs = ["src/main/java/com/depsfilter/H.java"], deps = [":deps_multi_excl_no_transitives"], ) multiple_exclusions_without_transitive_test( name = "multiple_exclusions_without_transitive_test", test_lib = ":multi_excl_no_transitives_test_lib", ) # Test 8: Empty exclusion lists dependencyset( name = "deps_empty_exclusions", items = ["lib_a",":lib_i"], deps_exclude_labels = [], deps_exclude_paths = [], ) java_library( name = "empty_exclusions_test_lib", srcs = ["src/main/java/com/depsfilter/H.java"], deps = [":deps_empty_exclusions"], ) empty_exclusion_lists_test( name = "deps_filter_empty_exclusions_test", test_lib = ":empty_exclusions_test_lib", ) # Test 9: Multiple paths handling dependencyset( name = "deps_multiple_paths_exclude_b_g", items = ["lib_a",":lib_i"], deps_exclude_labels = [":lib_b", ":lib_g"], ) java_library( name = "multiple_paths_test_lib", srcs = ["src/main/java/com/depsfilter/H.java"], deps = [":deps_multiple_paths_exclude_b_g"], ) multiple_paths_test( name = "deps_filter_multiple_paths_test", test_lib = ":multiple_paths_test_lib", ) toolchain( name = "unittest_toolchain", toolchain_type = "@bazel_skylib//toolchains/unittest:toolchain_type", toolchain = "@bazel_skylib//toolchains/unittest:toolchain", ) ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_time_only/compile_time_only_test.bzl ================================================ load("@bazel_skylib//lib:unittest.bzl", "asserts", "unittest") load("//springboot/deps_filter_rules/tests/test_utils:verification_utils.bzl", "verify_jars", "verify_runtime_and_compile_jars", "verify_jars_and_dropped_counts", "verify_dropped_counts", "update_jar_name", ) def _test_no_filtering(ctx): """ Tests that deps_filter preserves all dependencies when no exclusions are applied. Dependency Graph: test_lib | dependencyset("deps") / \\ A I / \\ / B E G | | / | F \\ C | D Expected: All JARs from java_library must match deps_filter: - full_compile_jars: Implementation JARs (e.g., liblib_a.jar) - compile_jars: Interface JARs (e.g., liblib_a-hjar.jar) - transitive_compile_time_jars: Interface JARs from transitive deps - transitive_runtime_jars: Implementation JARs from transitive deps """ env = unittest.begin(ctx) java_lib_info = ctx.attr.java_library[JavaInfo] deps_filter_info = ctx.attr.java_library_dependencyset[JavaInfo] # Verify all JAR fields match between java_library and deps_filter jar_fields = [ "full_compile_jars", # Implementation JARs "compile_jars", # Interface JARs "transitive_compile_time_jars", # Transitive interface JARs "transitive_runtime_jars" # Transitive implementation JARs ] for jar_field in jar_fields: java_lib_jars = getattr(java_lib_info, jar_field) deps_filter_jars = getattr(deps_filter_info, jar_field) asserts.equals(env, type(java_lib_jars), type(deps_filter_jars), "JAR type mismatch: {} vs deps_filter".format(jar_field)) java_lib_jars_list = [jar.basename for jar in java_lib_jars.to_list()] deps_filter_jars_list = [jar.basename for jar in deps_filter_jars.to_list()] # Normalize output jar naming difference between dependencyset consumer and base_lib update_jar_name("libno_filtering_test_lib", "libbase_lib", deps_filter_jars_list) asserts.equals(env, java_lib_jars_list, deps_filter_jars_list, "JAR contents mismatch: {} vs deps_filter".format(jar_field)) return unittest.end(env) no_filtering_test = unittest.make(_test_no_filtering, attrs = { "java_library": attr.label(providers = [JavaInfo]), "java_library_dependencyset": attr.label(providers = [JavaInfo]), }) def _test_filtered_deps(ctx): """ Tests basic dependency filtering with label-based exclusions. Dependency Graph: test_lib | dependencyset("deps") / \\ A I / \\ / B E G | | / | F \\ C | D Dependencyset Input: items = [":lib_a", ":lib_i"] deps_exclude_labels = [":lib_b", ":lib_g"] deps_exclude_paths = [] exclude_transitives = False Expected Output: JARs preserved: - test_lib, A, I, E, F, C, D (both runtime and compile-time) JARs excluded: - B, G and their transitive deps """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.test_lib[JavaInfo] expected_compile_jars = [ "libexclude_b_g_test_lib-hjar.jar", ] expected_full_compile_jars = [ "libexclude_b_g_test_lib.jar", ] expected_transitive_runtime_jars = [ "libexclude_b_g_test_lib.jar", "liblib_a.jar", "liblib_i.jar", "liblib_e.jar", "liblib_f.jar", "liblib_c.jar", "liblib_d.jar" ] expected_transitive_compile_jars = [ "libexclude_b_g_test_lib-hjar.jar", "liblib_a-hjar.jar", "liblib_i-hjar.jar", "liblib_e-hjar.jar", "liblib_f-hjar.jar", "liblib_c-hjar.jar", "liblib_d-hjar.jar" ] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) filtered_deps_test = unittest.make(_test_filtered_deps, attrs = { "test_lib": attr.label(providers = [JavaInfo]), }) def _test_filtered_deps_exclude_transitive(ctx): """ Tests dependency filtering with transitive exclusions. Dependency Graph: test_lib | dependencyset("deps") / \\ A I / \\ / B E G | | / | F \\ C | D Dependencyset Input: items = [":lib_a", ":lib_i"] deps_exclude_labels = [":lib_b", ":lib_g"] deps_exclude_paths = [] exclude_transitives = True Expected Output: JARs preserved: - test_lib, A, I, E (both runtime and compile-time) JARs excluded: - B, G and all transitive deps """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.test_lib[JavaInfo] expected_compile_jars = [ "libexclude_b_g_transitives_test_lib-hjar.jar", ] expected_full_compile_jars = [ "libexclude_b_g_transitives_test_lib.jar", ] expected_transitive_runtime_jars = [ "libexclude_b_g_transitives_test_lib.jar", "liblib_a.jar", "liblib_i.jar", "liblib_e.jar", ] expected_transitive_compile_jars = [ "libexclude_b_g_transitives_test_lib-hjar.jar", "liblib_a-hjar.jar", "liblib_i-hjar.jar", "liblib_e-hjar.jar", ] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) filtered_deps_exclude_transitive_test = unittest.make(_test_filtered_deps_exclude_transitive, attrs = { "test_lib": attr.label(providers = [JavaInfo]), }) def _test_path_based_exclusions(ctx): """ Tests filtering based on path patterns in deps_exclude_paths. Dependency Graph: test_lib | dependencyset("deps") / \\ A I / \\ / B E G | | / | F \\ C | D Dependencyset Input: items = [":lib_a", ":lib_i"] deps_exclude_labels = [] deps_exclude_paths = ["lib_b", "lib_f"] exclude_transitives = False Expected Output: JARs preserved: - All JARs not matching path patterns JARs excluded: - JARs matching paths "lib_b" and "lib_f" """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.test_lib[JavaInfo] expected_compile_jars = [ "libexclude_paths_test_lib-hjar.jar", ] expected_full_compile_jars = [ "libexclude_paths_test_lib.jar", ] expected_transitive_runtime_jars = [ "libexclude_paths_test_lib.jar", "liblib_a.jar", "liblib_i.jar", "liblib_e.jar", "liblib_c.jar", "liblib_d.jar", "liblib_g.jar" ] expected_transitive_compile_jars = [ "libexclude_paths_test_lib-hjar.jar", "liblib_a-hjar.jar", "liblib_i-hjar.jar", "liblib_e-hjar.jar", "liblib_c-hjar.jar", "liblib_d-hjar.jar", "liblib_g-hjar.jar" ] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) path_based_exclusions_test = unittest.make(_test_path_based_exclusions, attrs = { "test_lib": attr.label(providers = [JavaInfo]), }) def _test_interface_implementation_jars(ctx): """ Tests proper handling of interface (-hjar) and implementation JARs. Dependency Graph: test_lib | dependencyset("deps") / \\ A I / \\ / B E G | | / | F \\ C | D Dependencyset Input: items = [":lib_a", ":lib_i"] deps_exclude_labels = [":lib_b", ":lib_g"] deps_exclude_paths = [] exclude_transitives = False Expected Output: Interface JARs (compile_jars): - libinterface_impl_test_lib-hjar.jar Implementation JARs (full_compile_jars): - libinterface_impl_test_lib.jar """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.test_lib[JavaInfo] compile_jars = sorted([jar.basename for jar in javainfo_filtered.compile_jars.to_list()]) full_compile_jars = sorted([jar.basename for jar in javainfo_filtered.full_compile_jars.to_list()]) expected_compile_jars = ["libinterface_impl_test_lib-hjar.jar"] expected_full_compile_jars = ["libinterface_impl_test_lib.jar"] asserts.equals(env, compile_jars, expected_compile_jars) asserts.equals(env, full_compile_jars, expected_full_compile_jars) return unittest.end(env) interface_implementation_jars_test = unittest.make(_test_interface_implementation_jars, attrs = { "test_lib": attr.label(providers = [JavaInfo]), }) def _test_multiple_exclusions_with_transitive(ctx): """ Tests multiple exclusion levels with exclude_transitives=True. Dependency Graph: test_lib | dependencyset("deps") / \\ A I / \\ / B E G | | / | F \\ C | D Dependencyset Input: items = [":lib_a", ":lib_i"] deps_exclude_labels = [":lib_b"] deps_exclude_paths = ["lib_g"] exclude_transitives = True Expected Output: JARs preserved: - test_lib, A, I, E, F (both runtime and compile-time) JARs excluded: - B, G and all transitive deps """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.test_lib[JavaInfo] expected_compile_jars = [ "libmulti_excl_transitives_test_lib-hjar.jar", ] expected_full_compile_jars = [ "libmulti_excl_transitives_test_lib.jar", ] expected_transitive_runtime_jars = [ "libmulti_excl_transitives_test_lib.jar", "liblib_a.jar", "liblib_i.jar", "liblib_e.jar", "liblib_f.jar", ] expected_transitive_compile_jars = [ "libmulti_excl_transitives_test_lib-hjar.jar", "liblib_a-hjar.jar", "liblib_i-hjar.jar", "liblib_e-hjar.jar", "liblib_f-hjar.jar", ] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) def _test_multiple_exclusions_without_transitive(ctx): """ Tests multiple exclusion levels with exclude_transitives=False. Dependency Graph: test_lib | dependencyset("deps") / \\ A I / \\ / B E G | | / | F \\ C | D Dependencyset Input: items = [":lib_a", ":lib_i"] deps_exclude_labels = [":lib_b"] deps_exclude_paths = ["lib_g"] exclude_transitives = False Expected Output: JARs preserved: - test_lib, A, I, E, F, C, D (both runtime and compile-time) JARs excluded: - B, G (direct deps only) """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.test_lib[JavaInfo] expected_compile_jars = [ "libmulti_excl_no_transitives_test_lib-hjar.jar", ] expected_full_compile_jars = [ "libmulti_excl_no_transitives_test_lib.jar", ] expected_transitive_runtime_jars = [ "libmulti_excl_no_transitives_test_lib.jar", "liblib_a.jar", "liblib_i.jar", "liblib_e.jar", "liblib_f.jar", "liblib_c.jar", "liblib_d.jar", ] expected_transitive_compile_jars = [ "libmulti_excl_no_transitives_test_lib-hjar.jar", "liblib_a-hjar.jar", "liblib_i-hjar.jar", "liblib_e-hjar.jar", "liblib_f-hjar.jar", "liblib_c-hjar.jar", "liblib_d-hjar.jar", ] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) multiple_exclusions_with_transitive_test = unittest.make(_test_multiple_exclusions_with_transitive, attrs = { "test_lib": attr.label(providers = [JavaInfo]), }) multiple_exclusions_without_transitive_test = unittest.make(_test_multiple_exclusions_without_transitive, attrs = { "test_lib": attr.label(providers = [JavaInfo]), }) def _test_empty_exclusion_lists(ctx): """ Tests behavior when exclusion lists are empty. Dependency Graph: test_lib | dependencyset("deps") / \\ A I / \\ / B E G | | / | F \\ C | D Dependencyset Input: items = [":lib_a", ":lib_i"] deps_exclude_labels = [] deps_exclude_paths = [] exclude_transitives = False Expected Output: All JARs preserved: - test_lib, A, I, B, C, D, E, F, G (both runtime and compile-time) """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.test_lib[JavaInfo] expected_compile_jars = [ "libempty_exclusions_test_lib-hjar.jar", ] expected_full_compile_jars = [ "libempty_exclusions_test_lib.jar", ] expected_transitive_runtime_jars = [ "libempty_exclusions_test_lib.jar", "liblib_a.jar", "liblib_i.jar", "liblib_b.jar", "liblib_c.jar", "liblib_d.jar", "liblib_e.jar", "liblib_f.jar", "liblib_g.jar" ] expected_transitive_compile_jars = [ "libempty_exclusions_test_lib-hjar.jar", "liblib_a-hjar.jar", "liblib_i-hjar.jar", "liblib_b-hjar.jar", "liblib_c-hjar.jar", "liblib_d-hjar.jar", "liblib_e-hjar.jar", "liblib_f-hjar.jar", "liblib_g-hjar.jar" ] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) empty_exclusion_lists_test = unittest.make(_test_empty_exclusion_lists, attrs = { "test_lib": attr.label(providers = [JavaInfo]), }) def _test_multiple_paths(ctx): """ Tests handling of multiple paths to the same dependency. Dependency Graph: test_lib | dependencyset("deps") / \\ A I / \\ / B E G | | / | F \\ C | D Dependencyset Input: items = [":lib_a", ":lib_i"] deps_exclude_labels = [":lib_b", ":lib_g"] deps_exclude_paths = [] exclude_transitives = False Expected Output: JARs preserved: - test_lib, A, I, E, F, C, D (both runtime and compile-time) JARs excluded: - B, G Note: Dependencies not duplicated when reachable through multiple paths """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.test_lib[JavaInfo] expected_compile_jars = [ "libmultiple_paths_test_lib-hjar.jar", ] expected_full_compile_jars = [ "libmultiple_paths_test_lib.jar", ] expected_transitive_runtime_jars = [ "libmultiple_paths_test_lib.jar", "liblib_a.jar", "liblib_i.jar", "liblib_e.jar", "liblib_f.jar", "liblib_c.jar", "liblib_d.jar" ] expected_transitive_compile_jars = [ "libmultiple_paths_test_lib-hjar.jar", "liblib_a-hjar.jar", "liblib_i-hjar.jar", "liblib_e-hjar.jar", "liblib_f-hjar.jar", "liblib_c-hjar.jar", "liblib_d-hjar.jar" ] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) multiple_paths_test = unittest.make(_test_multiple_paths, attrs = { "test_lib": attr.label(providers = [JavaInfo]), }) ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_time_only/src/main/java/com/depsfilter/A.java ================================================ package com.depsfilter; public class A { int a; private B b; private E e; public A() { a = 1; b = new B(); e = new E(); } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_time_only/src/main/java/com/depsfilter/B.java ================================================ package com.depsfilter; public class B { private C c; public B() { c = new C(); } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_time_only/src/main/java/com/depsfilter/C.java ================================================ package com.depsfilter; public class C { private D d; public C() { d = new D(); } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_time_only/src/main/java/com/depsfilter/D.java ================================================ package com.depsfilter; public class D { private int value; public D() { value = 4; } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_time_only/src/main/java/com/depsfilter/E.java ================================================ package com.depsfilter; public class E { private F f; public E() { f = new F(); } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_time_only/src/main/java/com/depsfilter/F.java ================================================ package com.depsfilter; public class F { private C c; public F() { c = new C(); } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_time_only/src/main/java/com/depsfilter/G.java ================================================ package com.depsfilter; public class G { private F f; public G() { f = new F(); } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_time_only/src/main/java/com/depsfilter/H.java ================================================ package com.depsfilter; public class H { private A a; private I i; public H() { a = new A(); i = new I(); } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/compile_time_only/src/main/java/com/depsfilter/I.java ================================================ package com.depsfilter; public class I { private G g; public I() { g = new G(); } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/runtime_only/BUILD ================================================ load("//springboot/deps_filter_rules:dependencyset.bzl", "dependencyset") load( "//springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/runtime_only:runtime_only_test.bzl", "no_filtering_test", "filtered_deps_test", "filtered_deps_exclude_transitive_test", "path_based_exclusions_test", "interface_implementation_jars_test", "multiple_exclusions_with_transitive_test", "multiple_exclusions_without_transitive_test", "empty_exclusion_lists_test", "multiple_paths_test", ) # Dependency Graph Structure: # base_lib # | # dependencyset("runtime_deps") # / \ # A I # / \ / # B E G # | | / # | F # \/ # C # | # D # java_library( name = "lib_a", srcs = ["src/main/java/com/depsfilter/A.java"], runtime_deps = [ ":lib_b", # A -> B ":lib_e", # A -> E ], ) java_library( name = "lib_b", srcs = ["src/main/java/com/depsfilter/B.java"], runtime_deps = [":lib_c"], # B -> C ) java_library( name = "lib_c", srcs = ["src/main/java/com/depsfilter/C.java"], runtime_deps = [":lib_d"], # B -> D ) java_library( name = "lib_d", srcs = ["src/main/java/com/depsfilter/D.java"], ) java_library( name = "lib_e", srcs = ["src/main/java/com/depsfilter/E.java"], runtime_deps = [":lib_f"], # E -> F ) java_library( name = "lib_f", srcs = ["src/main/java/com/depsfilter/F.java"], runtime_deps = [":lib_c"], # F -> C ) java_library( name = "lib_g", srcs = ["src/main/java/com/depsfilter/G.java"], runtime_deps = [":lib_f"], # G -> F path ) java_library( name = "lib_i", srcs = ["src/main/java/com/depsfilter/I.java"], runtime_deps = [":lib_g"], # I -> G path ) # Consumer library that uses the filtered dependencies java_library( name = "base_lib", srcs = ["src/main/java/com/depsfilter/H.java"], runtime_deps = [":lib_a", ":lib_i"], ) # Test 1: No filtering dependencyset( name = "runtime_deps_no_filtering", items = [":lib_a", ":lib_i"], ) java_library( name = "runtime_no_filtering_test_lib", srcs = ["src/main/java/com/depsfilter/H.java"], runtime_deps = [":runtime_deps_no_filtering"], ) no_filtering_test( name = "deps_filter_no_filtering_test", java_library = ":base_lib", java_library_dependencyset = ":runtime_no_filtering_test_lib", ) # Test 2: Exclude by labels and exclude_transitives = False dependencyset( name = "runtime_deps_exclude_b_g", items = [":lib_a", ":lib_i"], deps_exclude_labels = [":lib_b", ":lib_g"], ) java_library( name = "runtime_exclude_b_g_test_lib", srcs = ["src/main/java/com/depsfilter/H.java"], runtime_deps = [":runtime_deps_exclude_b_g"], ) filtered_deps_test( name = "deps_filter_exclude_b_g_test", test_lib = ":runtime_exclude_b_g_test_lib", ) # Test 3: Exclude by labels and exclude_transitives = True dependencyset( name = "runtime_deps_exclude_b_g_transitives", items = [":lib_a", ":lib_i"], deps_exclude_labels = [":lib_b", ":lib_g"], exclude_transitives = True, ) java_library( name = "runtime_exclude_b_g_transitives_test_lib", srcs = ["src/main/java/com/depsfilter/H.java"], runtime_deps = [":runtime_deps_exclude_b_g_transitives"], ) filtered_deps_exclude_transitive_test( name = "deps_filter_exclude_b_g_exclude_transitive_test", test_lib = ":runtime_exclude_b_g_transitives_test_lib", ) # Test 4: Test for path-based exclusions dependencyset( name = "runtime_deps_exclude_paths", items = [":lib_a", ":lib_i"], deps_exclude_paths = ["lib_b", "lib_f"], ) java_library( name = "runtime_exclude_paths_test_lib", srcs = ["src/main/java/com/depsfilter/H.java"], runtime_deps = [":runtime_deps_exclude_paths"], ) path_based_exclusions_test( name = "deps_filter_path_based_exclusions_test", test_lib = ":runtime_exclude_paths_test_lib", ) # Test 5: Interface vs Implementation JARs dependencyset( name = "runtime_deps_interface_impl_exclude_b_g", items = [":lib_a", ":lib_i"], deps_exclude_labels = [":lib_b", ":lib_g"], ) java_library( name = "runtime_interface_impl_test_lib", srcs = ["src/main/java/com/depsfilter/H.java"], runtime_deps = [":runtime_deps_interface_impl_exclude_b_g"], ) interface_implementation_jars_test( name = "deps_filter_interface_impl_test", test_lib = ":runtime_interface_impl_test_lib", ) # Test 6: Multiple exclusions with exclude_transitives=True dependencyset( name = "runtime_deps_multi_excl_transitives", items = [":lib_a", ":lib_i"], deps_exclude_labels = [":lib_b"], deps_exclude_paths = ["lib_g"], exclude_transitives = True, ) java_library( name = "runtime_multi_excl_transitives_test_lib", srcs = ["src/main/java/com/depsfilter/H.java"], runtime_deps = [":runtime_deps_multi_excl_transitives"], ) multiple_exclusions_with_transitive_test( name = "multiple_exclusions_with_transitive_test", test_lib = ":runtime_multi_excl_transitives_test_lib", ) # Test 7: Multiple exclusions with exclude_transitives=False dependencyset( name = "runtime_deps_multi_excl_no_transitives", items = [":lib_a", ":lib_i"], deps_exclude_labels = [":lib_b"], deps_exclude_paths = ["lib_g"], exclude_transitives = False, ) java_library( name = "runtime_multi_excl_no_transitives_test_lib", srcs = ["src/main/java/com/depsfilter/H.java"], runtime_deps = [":runtime_deps_multi_excl_no_transitives"], ) multiple_exclusions_without_transitive_test( name = "multiple_exclusions_without_transitive_test", test_lib = ":runtime_multi_excl_no_transitives_test_lib", ) # Test 8: Empty exclusion lists dependencyset( name = "runtime_deps_empty_exclusions", items = [":lib_a", ":lib_i"], deps_exclude_paths = [], deps_exclude_labels = [], ) java_library( name = "runtime_empty_exclusions_test_lib", srcs = ["src/main/java/com/depsfilter/H.java"], runtime_deps = [":runtime_deps_empty_exclusions"], ) empty_exclusion_lists_test( name = "deps_filter_empty_exclusions_test", test_lib = ":runtime_empty_exclusions_test_lib", ) # Test 9: Multiple paths handling dependencyset( name = "runtime_deps_multiple_paths_exclude_b_g", items = [":lib_a", ":lib_i"], deps_exclude_labels = [":lib_b", ":lib_g"], ) java_library( name = "runtime_multiple_paths_test_lib", srcs = ["src/main/java/com/depsfilter/H.java"], runtime_deps = [":runtime_deps_multiple_paths_exclude_b_g"], ) multiple_paths_test( name = "deps_filter_multiple_paths_test", test_lib = ":runtime_multiple_paths_test_lib", ) toolchain( name = "unittest_toolchain", toolchain_type = "@bazel_skylib//toolchains/unittest:toolchain_type", toolchain = "@bazel_skylib//toolchains/unittest:toolchain", ) ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/runtime_only/runtime_only_test.bzl ================================================ load("@bazel_skylib//lib:unittest.bzl", "asserts", "unittest") load("//springboot/deps_filter_rules/tests/test_utils:verification_utils.bzl", "verify_jars", "verify_runtime_and_compile_jars", "verify_jars_and_dropped_counts", "verify_dropped_counts", "update_jar_name", ) def _test_no_filtering(ctx): """ Tests that deps_filter preserves all dependencies when no exclusions are applied. Dependency Graph: test_lib / \\ A G / \\ / B E / | | / | F \\ C | D Expected: All JARs from java_library must match deps_filter: - full_compile_jars: Implementation JARs (e.g., liblib_a.jar) - compile_jars: Interface JARs (e.g., liblib_a-hjar.jar) - transitive_compile_time_jars: Interface JARs from transitive deps - transitive_runtime_jars: Implementation JARs from transitive deps """ env = unittest.begin(ctx) java_lib_info = ctx.attr.java_library[JavaInfo] deps_filter_info = ctx.attr.java_library_dependencyset[JavaInfo] # Verify all JAR fields match between java_library and deps_filter jar_fields = [ "full_compile_jars", # Implementation JARs "compile_jars", # Interface JARs "transitive_compile_time_jars", # Transitive interface JARs "transitive_runtime_jars" # Transitive implementation JARs ] for jar_field in jar_fields: java_lib_jars = getattr(java_lib_info, jar_field) deps_filter_jars = getattr(deps_filter_info, jar_field) asserts.equals(env, type(java_lib_jars), type(deps_filter_jars), "JAR type mismatch: {} vs deps_filter".format(jar_field)) java_lib_jars_list = [jar.basename for jar in java_lib_jars.to_list()] deps_filter_jars_list = [jar.basename for jar in deps_filter_jars.to_list()] # Normalize output jar naming difference between dependencyset consumer and base_lib update_jar_name("libruntime_no_filtering_test_lib", "libbase_lib", deps_filter_jars_list) asserts.equals(env, java_lib_jars_list, deps_filter_jars_list, "JAR contents mismatch: {} vs deps_filter".format(jar_field)) return unittest.end(env) no_filtering_test = unittest.make(_test_no_filtering, attrs = { "java_library": attr.label(providers = [JavaInfo]), "java_library_dependencyset": attr.label(providers = [JavaInfo]), }) def _test_filtered_deps(ctx): """ Tests basic dependency filtering with label-based exclusions. Dependency Graph: test_lib | dependencyset("runtime_deps") / \\ A I / \\ / B E G | | / | F \\ C | D Dependencyset Input: items = [":lib_a", ":lib_i"] deps_exclude_labels = [":lib_b", ":lib_g"] deps_exclude_paths = [] exclude_transitives = False Expected Output: JARs preserved: - test_lib, A, I, E, F, C, D (runtime) - no compile-time jars present JARs excluded: - B, G and their transitive deps """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.test_lib[JavaInfo] expected_compile_jars = [ "libruntime_exclude_b_g_test_lib-hjar.jar", ] expected_full_compile_jars = [ "libruntime_exclude_b_g_test_lib.jar", ] expected_transitive_runtime_jars = [ "libruntime_exclude_b_g_test_lib.jar", "liblib_a.jar", "liblib_i.jar", "liblib_e.jar", "liblib_f.jar", "liblib_c.jar", "liblib_d.jar" ] expected_transitive_compile_jars = [ "libruntime_exclude_b_g_test_lib-hjar.jar", ] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) filtered_deps_test = unittest.make(_test_filtered_deps, attrs = { "test_lib": attr.label(providers = [JavaInfo]), }) def _test_filtered_deps_exclude_transitive(ctx): """ Tests dependency filtering with transitive exclusions. Dependency Graph: test_lib | dependencyset("runtime_deps") / \\ A I / \\ / B E G | | / | F \\ C | D Dependencyset Input: items = [":lib_a", ":lib_i"] deps_exclude_labels = [":lib_b", ":lib_g"] deps_exclude_paths = [] exclude_transitives = True Expected Output: JARs preserved: - test_lib, A, I, E (runtime) - no compile-time jars present JARs excluded: - B, G and all transitive deps """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.test_lib[JavaInfo] expected_compile_jars = [ "libruntime_exclude_b_g_transitives_test_lib-hjar.jar", ] expected_full_compile_jars = [ "libruntime_exclude_b_g_transitives_test_lib.jar", ] expected_transitive_runtime_jars = [ "libruntime_exclude_b_g_transitives_test_lib.jar", "liblib_a.jar", "liblib_i.jar", "liblib_e.jar", ] expected_transitive_compile_jars = [ "libruntime_exclude_b_g_transitives_test_lib-hjar.jar", ] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) filtered_deps_exclude_transitive_test = unittest.make(_test_filtered_deps_exclude_transitive, attrs = { "test_lib": attr.label(providers = [JavaInfo]), }) def _test_path_based_exclusions(ctx): """ Tests filtering based on path patterns in deps_exclude_paths. Dependency Graph: test_lib | dependencyset("runtime_deps") / \\ A I / \\ / B E G | | / | F \\ C | D Dependencyset Input: items = [":lib_a", ":lib_i"] deps_exclude_labels = [] deps_exclude_paths = ["lib_b", "lib_f"] exclude_transitives = False Expected Output: JARs preserved: - All JARs not matching path patterns JARs excluded: - JARs matching paths "lib_b" and "lib_f" """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.test_lib[JavaInfo] expected_compile_jars = [ "libruntime_exclude_paths_test_lib-hjar.jar", ] expected_full_compile_jars = [ "libruntime_exclude_paths_test_lib.jar", ] expected_transitive_runtime_jars = [ "libruntime_exclude_paths_test_lib.jar", "liblib_a.jar", "liblib_i.jar", "liblib_e.jar", "liblib_c.jar", "liblib_d.jar", "liblib_g.jar" ] expected_transitive_compile_jars = [ "libruntime_exclude_paths_test_lib-hjar.jar", ] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) path_based_exclusions_test = unittest.make(_test_path_based_exclusions, attrs = { "test_lib": attr.label(providers = [JavaInfo]), }) def _test_interface_implementation_jars(ctx): """ Tests proper handling of interface (-hjar) and implementation JARs. Dependency Graph: test_lib | dependencyset("runtime_deps") / \\ A I / \\ / B E G | | / | F \\ C | D Dependencyset Input: items = [":lib_a", ":lib_i"] deps_exclude_labels = [":lib_b", ":lib_g"] deps_exclude_paths = [] exclude_transitives = False Expected Output: Interface JARs (compile_jars): - [] Implementation JARs (full_compile_jars): - libtest_lib.jar """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.test_lib[JavaInfo] compile_jars = sorted([jar.basename for jar in javainfo_filtered.compile_jars.to_list()]) full_compile_jars = sorted([jar.basename for jar in javainfo_filtered.full_compile_jars.to_list()]) expected_compile_jars = [ "libruntime_interface_impl_test_lib-hjar.jar", ] expected_full_compile_jars = [ "libruntime_interface_impl_test_lib.jar", ] asserts.equals(env, compile_jars, expected_compile_jars) asserts.equals(env, full_compile_jars, expected_full_compile_jars) return unittest.end(env) interface_implementation_jars_test = unittest.make(_test_interface_implementation_jars, attrs = { "test_lib": attr.label(providers = [JavaInfo]), }) def _test_multiple_exclusions_with_transitive(ctx): """ Tests multiple exclusion levels with exclude_transitives=True. Dependency Graph: test_lib | dependencyset("runtime_deps") / \\ A I / \\ / B E G | | / | F \\ C | D Dependencyset Input: items = [":lib_a", ":lib_i"] deps_exclude_labels = [":lib_b"] deps_exclude_paths = ["lib_g"] exclude_transitives = True Expected Output: JARs preserved: - test_lib, A, I, E, F (runtime) - no compile-time jars present JARs excluded: - B, G and all transitive deps """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.test_lib[JavaInfo] expected_compile_jars = [ "libruntime_multi_excl_transitives_test_lib-hjar.jar", ] expected_full_compile_jars = [ "libruntime_multi_excl_transitives_test_lib.jar", ] expected_transitive_runtime_jars = [ "libruntime_multi_excl_transitives_test_lib.jar", "liblib_a.jar", "liblib_i.jar", "liblib_e.jar", "liblib_f.jar", ] expected_transitive_compile_jars = [ "libruntime_multi_excl_transitives_test_lib-hjar.jar", ] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) def _test_multiple_exclusions_without_transitive(ctx): """ Tests multiple exclusion levels with exclude_transitives=False. Dependency Graph: test_lib | dependencyset("runtime_deps") / \\ A I / \\ / B E G | | / | F \\ C | D Dependencyset Input: items = [":lib_a", ":lib_i"] deps_exclude_labels = [":lib_b"] deps_exclude_paths = ["lib_g"] exclude_transitives = False Expected Output: JARs preserved: - test_lib, A, I, E, F, C, D (runtime) - no compile-time jars present JARs excluded: - B, G (direct deps only) """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.test_lib[JavaInfo] expected_compile_jars = [ "libruntime_multi_excl_no_transitives_test_lib-hjar.jar", ] expected_full_compile_jars = [ "libruntime_multi_excl_no_transitives_test_lib.jar", ] expected_transitive_runtime_jars = [ "libruntime_multi_excl_no_transitives_test_lib.jar", "liblib_a.jar", "liblib_i.jar", "liblib_e.jar", "liblib_f.jar", "liblib_c.jar", "liblib_d.jar", ] expected_transitive_compile_jars = [ "libruntime_multi_excl_no_transitives_test_lib-hjar.jar", ] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) multiple_exclusions_with_transitive_test = unittest.make(_test_multiple_exclusions_with_transitive, attrs = { "test_lib": attr.label(providers = [JavaInfo]), }) multiple_exclusions_without_transitive_test = unittest.make(_test_multiple_exclusions_without_transitive, attrs = { "test_lib": attr.label(providers = [JavaInfo]), }) def _test_empty_exclusion_lists(ctx): """ Tests behavior when exclusion lists are empty. Dependency Graph: test_lib | dependencyset("runtime_deps") / \\ A I / \\ / B E G | | / | F \\ C | D Dependencyset Input: items = [":lib_a", ":lib_i"] deps_exclude_labels = [] deps_exclude_paths = [] exclude_transitives = False Expected Output: All JARs preserved: - test_lib, A, I, B, C, D, E, F, G (runtime) - no compile-time jars present """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.test_lib[JavaInfo] expected_compile_jars = [ "libruntime_empty_exclusions_test_lib-hjar.jar", ] expected_full_compile_jars = [ "libruntime_empty_exclusions_test_lib.jar", ] expected_transitive_runtime_jars = [ "libruntime_empty_exclusions_test_lib.jar", "liblib_a.jar", "liblib_i.jar", "liblib_b.jar", "liblib_c.jar", "liblib_d.jar", "liblib_e.jar", "liblib_f.jar", "liblib_g.jar" ] expected_transitive_compile_jars = [ "libruntime_empty_exclusions_test_lib-hjar.jar", ] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) empty_exclusion_lists_test = unittest.make(_test_empty_exclusion_lists, attrs = { "test_lib": attr.label(providers = [JavaInfo]), }) def _test_multiple_paths(ctx): """ Tests handling of multiple paths to the same dependency. Dependency Graph: test_lib | dependencyset("runtime_deps") / \\ A I / \\ / B E G | | / | F \\ C | D Dependencyset Input: items = [":lib_a", ":lib_i"] deps_exclude_labels = [":lib_b", ":lib_g"] deps_exclude_paths = [] exclude_transitives = False Expected Output: JARs preserved: - test_lib, A, I, E, F, C, D (runtime) - no compile-time jars present JARs excluded: - B, G Note: Dependencies not duplicated when reachable through multiple paths """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.test_lib[JavaInfo] expected_compile_jars = [ "libruntime_multiple_paths_test_lib-hjar.jar", ] expected_full_compile_jars = [ "libruntime_multiple_paths_test_lib.jar", ] expected_transitive_runtime_jars = [ "libruntime_multiple_paths_test_lib.jar", "liblib_a.jar", "liblib_i.jar", "liblib_e.jar", "liblib_f.jar", "liblib_c.jar", "liblib_d.jar" ] expected_transitive_compile_jars = [ "libruntime_multiple_paths_test_lib-hjar.jar", ] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) multiple_paths_test = unittest.make(_test_multiple_paths, attrs = { "test_lib": attr.label(providers = [JavaInfo]), }) ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/runtime_only/src/main/java/com/depsfilter/A.java ================================================ package com.depsfilter; public class A { public A() { int a = 1; } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/runtime_only/src/main/java/com/depsfilter/B.java ================================================ package com.depsfilter; public class B { public B() { int b = 1; } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/runtime_only/src/main/java/com/depsfilter/C.java ================================================ package com.depsfilter; public class C { public C() { int c = 1; } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/runtime_only/src/main/java/com/depsfilter/D.java ================================================ package com.depsfilter; public class D { public D() { int d = 1; } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/runtime_only/src/main/java/com/depsfilter/E.java ================================================ package com.depsfilter; public class E { public E() { int e = 1; } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/runtime_only/src/main/java/com/depsfilter/F.java ================================================ package com.depsfilter; public class F { public F() { int f = 1; } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/runtime_only/src/main/java/com/depsfilter/G.java ================================================ package com.depsfilter; public class G { public G() { int g = 1; } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/runtime_only/src/main/java/com/depsfilter/H.java ================================================ package com.depsfilter; public class H { public H() { int h = 1; } } ================================================ FILE: springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/runtime_only/src/main/java/com/depsfilter/I.java ================================================ package com.depsfilter; public class I { public I() { int i = 1; } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime/BUILD ================================================ load("//springboot/deps_filter_rules:deps_filter.bzl", "deps_filter") load( "//springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime:compile_and_runtime_test.bzl", "no_filtering_test", "with_label_exclusions_test", "with_label_exclusions_with_exclude_transitives_test", "with_path_exclusions_test", "with_path_exclusions_with_exclude_transitives_test", "multiple_exclusions_with_exclude_transitives_test", "multiple_exclusions_without_exclude_transitives_test", "empty_exclusion_lists_test", "path_based_exclusions_comprehensive_test", "runtime_deps_only_test", "compile_deps_only_test", "single_dep_with_exclusions_test", "single_runtime_dep_with_exclusions_test", "one_compile_one_runtime_dep_test", "path_patterns_with_special_characters_test", "case_sensitive_pattern_matching_test", ) deps = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security", "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind", "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core", "@unmanaged_deps_filter//:jakarta_servlet_jsp_jakarta_servlet_jsp_api", ] runtime_deps = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator", ] test_deps = [ "@unmanaged_deps_filter//:junit_junit", "@unmanaged_deps_filter//:org_assertj_assertj_core", ] # Test 1: No filtering - baseline test deps_filter( name = "no_filtering", deps = deps, runtime_deps = runtime_deps, ) no_filtering_test( name = "no_filtering_test", filtered = ":no_filtering", ) java_test( name = "DepsFilterNoFilteringTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterNoFilteringTest.java" ], deps = [":no_filtering", "//springboot/deps_filter_rules/tests/test_utils:test_utils"] + test_deps, ) # Test 2: Label-based exclusions without transitives deps_filter( name = "with_label_exclusions", deps = deps, runtime_deps = runtime_deps, deps_exclude_labels = [ "@unmanaged_deps_filter//:io_micrometer_micrometer_commons", "@unmanaged_deps_filter//:org_slf4j_jul_to_slf4j", ], ) with_label_exclusions_test( name = "with_label_exclusions_test", filtered = ":with_label_exclusions", ) java_test( name = "DepsFilterLabelExclusionsTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterLabelExclusionsTest.java" ], deps = [":with_label_exclusions", "//springboot/deps_filter_rules/tests/test_utils:test_utils"] + test_deps, ) # Test 3: Label-based exclusions with exclude_transitives deps_filter( name = "with_label_exclusions_with_exclude_transitives", deps = deps, runtime_deps = runtime_deps, deps_exclude_labels = [ "@unmanaged_deps_filter//:io_micrometer_micrometer_commons", "@unmanaged_deps_filter//:org_slf4j_jul_to_slf4j", ], exclude_transitives = True, ) with_label_exclusions_with_exclude_transitives_test( name = "with_label_exclusions_with_exclude_transitives_test", filtered = ":with_label_exclusions_with_exclude_transitives", ) java_test( name = "DepsFilterExcludeTransitiveTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterExcludeTransitiveTest.java" ], deps = [":with_label_exclusions_with_exclude_transitives", "//springboot/deps_filter_rules/tests/test_utils:test_utils"] + test_deps, ) # Test 4: Path-based exclusions without transitives deps_filter( name = "with_path_exclusions", deps = deps, runtime_deps = runtime_deps, deps_exclude_paths = [ "micrometer", "slf4j" ], ) with_path_exclusions_test( name = "with_path_exclusions_test", filtered = ":with_path_exclusions", ) java_test( name = "DepsFilterPathExclusionsTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterPathExclusionsTest.java" ], deps = [":with_path_exclusions", "//springboot/deps_filter_rules/tests/test_utils:test_utils"] + test_deps, ) # Test 5: Path-based exclusions with exclude_transitives deps_filter( name = "with_path_exclusions_with_exclude_transitives", deps = deps, runtime_deps = runtime_deps, deps_exclude_paths = [ "micrometer", "slf4j" ], exclude_transitives = True, ) with_path_exclusions_with_exclude_transitives_test( name = "with_path_exclusions_with_exclude_transitives_test", filtered = ":with_path_exclusions_with_exclude_transitives", ) java_test( name = "DepsFilterPathExclusionsWithTransitivesTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterPathExclusionsWithTransitivesTest.java" ], deps = [":with_path_exclusions_with_exclude_transitives", "//springboot/deps_filter_rules/tests/test_utils:test_utils"] + test_deps, ) # Test 6: Multiple exclusions with exclude_transitives (labels + patterns) deps_filter( name = "multiple_exclusions_with_exclude_transitives", deps = deps, runtime_deps = runtime_deps, deps_exclude_labels = [ "@unmanaged_deps_filter//:io_micrometer_micrometer_commons", "@unmanaged_deps_filter//:org_slf4j_jul_to_slf4j", ], deps_exclude_paths = [ "slf4j" ], exclude_transitives = True, ) multiple_exclusions_with_exclude_transitives_test( name = "multiple_exclusions_with_exclude_transitives_test", filtered = ":multiple_exclusions_with_exclude_transitives", ) java_test( name = "DepsFilterMultipleExclusionsWithTransitivesTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterMultipleExclusionsWithTransitivesTest.java" ], deps = [":multiple_exclusions_with_exclude_transitives", "//springboot/deps_filter_rules/tests/test_utils:test_utils"] + test_deps, ) # Test 7: Multiple exclusions without exclude_transitives (labels + patterns) deps_filter( name = "multiple_exclusions_without_exclude_transitives", deps = deps, runtime_deps = runtime_deps, deps_exclude_labels = [ "@unmanaged_deps_filter//:io_micrometer_micrometer_commons", "@unmanaged_deps_filter//:org_slf4j_jul_to_slf4j", ], deps_exclude_paths = [ "slf4j", ], exclude_transitives = True, ) multiple_exclusions_without_exclude_transitives_test( name = "multiple_exclusions_without_exclude_transitives_test", filtered = ":multiple_exclusions_without_exclude_transitives", ) java_test( name = "DepsFilterMultipleExclusionsWithoutTransitivesTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterMultipleExclusionsWithoutTransitivesTest.java" ], deps = [":multiple_exclusions_without_exclude_transitives", "//springboot/deps_filter_rules/tests/test_utils:test_utils"] + test_deps, ) # Test 8: Empty exclusion lists deps_filter( name = "empty_exclusion_lists", deps = deps, runtime_deps = runtime_deps, deps_exclude_labels = [], deps_exclude_paths = [], exclude_transitives = False, ) empty_exclusion_lists_test( name = "empty_exclusion_lists_test", filtered = ":empty_exclusion_lists", ) java_test( name = "DepsFilterEmptyExclusionsTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterEmptyExclusionsTest.java" ], deps = [":empty_exclusion_lists", "//springboot/deps_filter_rules/tests/test_utils:test_utils"] + test_deps, ) # Test 9: Comprehensive path-based exclusions deps_filter( name = "path_based_exclusions_comprehensive", deps = deps, runtime_deps = runtime_deps, deps_exclude_labels = [], deps_exclude_paths = [ "micrometer", "slf4j", "logback" ], exclude_transitives = False, ) path_based_exclusions_comprehensive_test( name = "path_based_exclusions_comprehensive_test", filtered = ":path_based_exclusions_comprehensive", ) java_test( name = "DepsFilterPathBasedExclusionsComprehensiveTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterPathBasedExclusionsComprehensiveTest.java" ], deps = [":path_based_exclusions_comprehensive", "//springboot/deps_filter_rules/tests/test_utils:test_utils"] + test_deps, ) # Test 10: Runtime deps only deps_filter( name = "runtime_deps_only", runtime_deps = runtime_deps, deps_exclude_labels = [], deps_exclude_paths = [], exclude_transitives = False, ) runtime_deps_only_test( name = "runtime_deps_only_test", filtered = ":runtime_deps_only", ) java_test( name = "DepsFilterRuntimeDepsOnlyTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterRuntimeDepsOnlyTest.java" ], deps = [":runtime_deps_only", "//springboot/deps_filter_rules/tests/test_utils:test_utils"] + test_deps, ) # Test 11: Compile deps only deps_filter( name = "compile_deps_only", deps = deps, runtime_deps = [], deps_exclude_labels = [], deps_exclude_paths = [], exclude_transitives = False, ) compile_deps_only_test( name = "compile_deps_only_test", filtered = ":compile_deps_only", ) java_test( name = "DepsFilterCompileDepsOnlyTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterCompileDepsOnlyTest.java" ], deps = [":compile_deps_only", "//springboot/deps_filter_rules/tests/test_utils:test_utils"] + test_deps, ) # Test 12: Single dependency with exclusions deps_filter( name = "single_dep_with_exclusions", deps = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", ], runtime_deps = [], deps_exclude_labels = [ "@unmanaged_deps_filter//:io_micrometer_micrometer_commons", ], deps_exclude_paths = [], exclude_transitives = False, ) single_dep_with_exclusions_test( name = "single_dep_with_exclusions_test", filtered = ":single_dep_with_exclusions", ) java_test( name = "DepsFilterSingleDepWithExclusionsTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterSingleDepWithExclusionsTest.java" ], deps = [":single_dep_with_exclusions", "//springboot/deps_filter_rules/tests/test_utils:test_utils"] + test_deps, ) # Test 13: Single runtime dependency with exclusions deps_filter( name = "single_runtime_dep_with_exclusions", deps = [], runtime_deps = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", ], deps_exclude_labels = [], deps_exclude_paths = [ "slf4j", ], exclude_transitives = False, ) single_runtime_dep_with_exclusions_test( name = "single_runtime_dep_with_exclusions_test", filtered = ":single_runtime_dep_with_exclusions", ) java_test( name = "DepsFilterSingleRuntimeDepWithExclusionsTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterSingleRuntimeDepWithExclusionsTest.java" ], deps = [":single_runtime_dep_with_exclusions", "//springboot/deps_filter_rules/tests/test_utils:test_utils"] + test_deps, ) # Test 14: One compile dep and one runtime dep deps_filter( name = "one_compile_one_runtime_dep", deps = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", ], runtime_deps = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", ], deps_exclude_labels = [], deps_exclude_paths = [], exclude_transitives = False, ) one_compile_one_runtime_dep_test( name = "one_compile_one_runtime_dep_test", filtered = ":one_compile_one_runtime_dep", ) java_test( name = "DepsFilterOneCompileOneRuntimeDepTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterOneCompileOneRuntimeDepTest.java" ], deps = [":one_compile_one_runtime_dep", "//springboot/deps_filter_rules/tests/test_utils:test_utils"] + test_deps, ) # Test 15: Path patterns with special characters deps_filter( name = "path_patterns_with_special_characters", deps = deps, runtime_deps = runtime_deps, deps_exclude_paths = [ "io.micrometer", "to-slf4j", ], exclude_transitives = True, ) path_patterns_with_special_characters_test( name = "path_patterns_with_special_characters_test", filtered = ":path_patterns_with_special_characters", ) java_test( name = "DepsFilterPathPatternsWithSpecialCharactersTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterPathPatternsWithSpecialCharactersTest.java" ], deps = [":path_patterns_with_special_characters", "//springboot/deps_filter_rules/tests/test_utils:test_utils"] + test_deps, ) # Test 16: Case sensitive pattern matching deps_filter( name = "case_sensitive_pattern_matching", deps = deps, runtime_deps = runtime_deps, deps_exclude_labels = [], deps_exclude_paths = [ "SPRING", # Uppercase pattern "Jackson", # Mixed case pattern "HIBERNATE", # Uppercase pattern ], exclude_transitives = False, ) case_sensitive_pattern_matching_test( name = "case_sensitive_pattern_matching_test", filtered = ":case_sensitive_pattern_matching", ) java_test( name = "DepsFilterCaseSensitivePatternMatchingTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterCaseSensitivePatternMatchingTest.java" ], deps = [":case_sensitive_pattern_matching", "//springboot/deps_filter_rules/tests/test_utils:test_utils"] + test_deps, ) # Toolchain for unittest toolchain( name = "unittest_toolchain", toolchain_type = "@bazel_skylib//toolchains/unittest:toolchain_type", toolchain = "@bazel_skylib//toolchains/unittest:toolchain", ) ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime/compile_and_runtime_test.bzl ================================================ load("@bazel_skylib//lib:unittest.bzl", "asserts", "unittest") load("//springboot/deps_filter_rules/tests/test_utils:verification_utils.bzl", "verify_jars", "verify_runtime_and_compile_jars", "verify_jars_and_dropped_counts", "verify_dropped_counts", "compute_expected_jars", ) def _test_no_filtering(ctx): """ Tests deps without any filtering - baseline test. """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] expected = compute_expected_jars(ctx) verify_runtime_and_compile_jars( ctx, env, javainfo_filtered, expected_compile_jars = expected["compile_jars"], expected_full_compile_jars = expected["full_compile_jars"], expected_transitive_compile_jars = expected["transitive_compile_jars"], expected_transitive_runtime_jars = expected["transitive_runtime_jars"], ) verify_jars_and_dropped_counts(env, expected, expected_compile_dropped = "0", expected_full_compile_dropped = "0", expected_transitive_compile_dropped = "0", expected_transitive_runtime_dropped = "0") return unittest.end(env) no_filtering_test = unittest.make(_test_no_filtering, attrs = { "filtered": attr.label(providers = [JavaInfo]), "deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security", "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind", "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core", "@unmanaged_deps_filter//:jakarta_servlet_jsp_jakarta_servlet_jsp_api", ], providers = [JavaInfo], ), "runtime_deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator", ], providers = [JavaInfo], ), "deps_exclude_labels": attr.label_list( default = [], ), "deps_exclude_paths": attr.string_list( default = [], ), }) def _test_with_label_exclusions(ctx): """ Tests deps with label-based exclusions (without transitives). """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] expected = compute_expected_jars(ctx) verify_runtime_and_compile_jars( ctx, env, javainfo_filtered, expected_compile_jars = expected["compile_jars"], expected_full_compile_jars = expected["full_compile_jars"], expected_transitive_compile_jars = expected["transitive_compile_jars"], expected_transitive_runtime_jars = expected["transitive_runtime_jars"], ) # Verify dropped counts - label exclusions should drop direct JARs but not transitives when exclude_transitives=False dropped_counts = { "compile_jars_dropped": expected["compile_jars_dropped"], "full_compile_jars_dropped": expected["full_compile_jars_dropped"], "transitive_compile_jars_dropped": expected["transitive_compile_jars_dropped"], "transitive_runtime_jars_dropped": expected["transitive_runtime_jars_dropped"], } verify_dropped_counts(env, expected, expected_compile_dropped = "0", expected_full_compile_dropped = "0", expected_transitive_compile_dropped = ">0", expected_transitive_runtime_dropped = ">0") return unittest.end(env) with_label_exclusions_test = unittest.make(_test_with_label_exclusions, attrs = { "filtered": attr.label(providers = [JavaInfo]), "deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security", "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind", "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core", "@unmanaged_deps_filter//:jakarta_servlet_jsp_jakarta_servlet_jsp_api", ], providers = [JavaInfo], ), "runtime_deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator", ], providers = [JavaInfo], ), "deps_exclude_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:io_micrometer_micrometer_commons", "@unmanaged_deps_filter//:org_slf4j_jul_to_slf4j", ], ), "deps_exclude_paths": attr.string_list( default = [], ), "exclude_transitives": attr.bool( default = False, ), }) def _test_with_label_exclusions_with_exclude_transitives(ctx): """ Tests deps with label-based exclusions including exclude_transitives. """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] expected = compute_expected_jars(ctx) verify_runtime_and_compile_jars( ctx, env, javainfo_filtered, expected_compile_jars = expected["compile_jars"], expected_full_compile_jars = expected["full_compile_jars"], expected_transitive_compile_jars = expected["transitive_compile_jars"], expected_transitive_runtime_jars = expected["transitive_runtime_jars"], ) verify_jars_and_dropped_counts(env, expected, expected_compile_dropped = "0", expected_full_compile_dropped = "0", expected_transitive_compile_dropped = ">0", expected_transitive_runtime_dropped = ">0") return unittest.end(env) with_label_exclusions_with_exclude_transitives_test = unittest.make(_test_with_label_exclusions_with_exclude_transitives, attrs = { "filtered": attr.label(providers = [JavaInfo]), "deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security", "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind", "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core", "@unmanaged_deps_filter//:jakarta_servlet_jsp_jakarta_servlet_jsp_api", ], providers = [JavaInfo], ), "runtime_deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator", ], providers = [JavaInfo], ), "deps_exclude_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:io_micrometer_micrometer_commons", "@unmanaged_deps_filter//:org_slf4j_jul_to_slf4j", ], ), "deps_exclude_paths": attr.string_list( default = [], ), "exclude_transitives": attr.bool( default = True, ), }) def _test_with_path_exclusions(ctx): """ Tests deps with path-based exclusions (without transitives). """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] expected = compute_expected_jars(ctx) verify_runtime_and_compile_jars( ctx, env, javainfo_filtered, expected_compile_jars = expected["compile_jars"], expected_full_compile_jars = expected["full_compile_jars"], expected_transitive_compile_jars = expected["transitive_compile_jars"], expected_transitive_runtime_jars = expected["transitive_runtime_jars"], ) verify_dropped_counts(env, expected, expected_compile_dropped = "0", expected_full_compile_dropped = "0", expected_transitive_compile_dropped = ">0", expected_transitive_runtime_dropped = ">0") return unittest.end(env) with_path_exclusions_test = unittest.make(_test_with_path_exclusions, attrs = { "filtered": attr.label(providers = [JavaInfo]), "deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security", "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind", "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core", "@unmanaged_deps_filter//:jakarta_servlet_jsp_jakarta_servlet_jsp_api", ], providers = [JavaInfo], ), "runtime_deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator", ], providers = [JavaInfo], ), "deps_exclude_labels": attr.label_list( default = [ ], ), "deps_exclude_paths": attr.string_list( default = [ "micrometer", "slf4j" ], ), "exclude_transitives": attr.bool( default = False, ), }) def _test_with_path_exclusions_with_exclude_transitives(ctx): """ Tests deps with path-based exclusions including exclude_transitives. """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] expected = compute_expected_jars(ctx) verify_runtime_and_compile_jars( ctx, env, javainfo_filtered, expected_compile_jars = expected["compile_jars"], expected_full_compile_jars = expected["full_compile_jars"], expected_transitive_compile_jars = expected["transitive_compile_jars"], expected_transitive_runtime_jars = expected["transitive_runtime_jars"], ) verify_dropped_counts(env, expected, expected_compile_dropped = "0", expected_full_compile_dropped = "0", expected_transitive_compile_dropped = ">0", expected_transitive_runtime_dropped = ">0") return unittest.end(env) with_path_exclusions_with_exclude_transitives_test = unittest.make(_test_with_path_exclusions_with_exclude_transitives, attrs = { "filtered": attr.label(providers = [JavaInfo]), "deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security", "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind", "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core", "@unmanaged_deps_filter//:jakarta_servlet_jsp_jakarta_servlet_jsp_api", ], providers = [JavaInfo], ), "runtime_deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator", ], providers = [JavaInfo], ), "deps_exclude_labels": attr.label_list( default = [ ], ), "deps_exclude_paths": attr.string_list( default = [ "micrometer", "slf4j" ], ), "exclude_transitives": attr.bool( default = True, ), }) def _test_multiple_exclusions_with_exclude_transitives(ctx): """ Tests multiple exclusion types (labels + paths) with exclude_transitives=True. """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] expected = compute_expected_jars(ctx) verify_runtime_and_compile_jars( ctx, env, javainfo_filtered, expected_compile_jars = expected["compile_jars"], expected_full_compile_jars = expected["full_compile_jars"], expected_transitive_compile_jars = expected["transitive_compile_jars"], expected_transitive_runtime_jars = expected["transitive_runtime_jars"], ) verify_dropped_counts(env, expected, expected_compile_dropped = "0", expected_full_compile_dropped = "0", expected_transitive_compile_dropped = ">0", expected_transitive_runtime_dropped = ">0") return unittest.end(env) multiple_exclusions_with_exclude_transitives_test = unittest.make(_test_multiple_exclusions_with_exclude_transitives, attrs = { "filtered": attr.label(providers = [JavaInfo]), "deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security", "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind", "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core", "@unmanaged_deps_filter//:jakarta_servlet_jsp_jakarta_servlet_jsp_api", ], providers = [JavaInfo], ), "runtime_deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator", ], providers = [JavaInfo], ), "deps_exclude_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:io_micrometer_micrometer_commons", "@unmanaged_deps_filter//:org_slf4j_jul_to_slf4j", ], ), "deps_exclude_paths": attr.string_list( default = [ "slf4j" ], ), "exclude_transitives": attr.bool( default = True, ), }) def _test_multiple_exclusions_without_exclude_transitives(ctx): """ Tests multiple exclusion types (labels + paths) with exclude_transitives=False. """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] expected = compute_expected_jars(ctx) verify_runtime_and_compile_jars( ctx, env, javainfo_filtered, expected_compile_jars = expected["compile_jars"], expected_full_compile_jars = expected["full_compile_jars"], expected_transitive_compile_jars = expected["transitive_compile_jars"], expected_transitive_runtime_jars = expected["transitive_runtime_jars"], ) verify_dropped_counts(env, expected, expected_compile_dropped = "0", expected_full_compile_dropped = "0", expected_transitive_compile_dropped = ">0", expected_transitive_runtime_dropped = ">0") return unittest.end(env) multiple_exclusions_without_exclude_transitives_test = unittest.make(_test_multiple_exclusions_without_exclude_transitives, attrs = { "filtered": attr.label(providers = [JavaInfo]), "deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security", "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind", "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core", "@unmanaged_deps_filter//:jakarta_servlet_jsp_jakarta_servlet_jsp_api", ], providers = [JavaInfo], ), "runtime_deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator", ], providers = [JavaInfo], ), "deps_exclude_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:io_micrometer_micrometer_commons", "@unmanaged_deps_filter//:org_slf4j_jul_to_slf4j", ], ), "deps_exclude_paths": attr.string_list( default = [ "slf4j" ], ), "exclude_transitives": attr.bool( default = False, ), }) def _test_empty_exclusion_lists(ctx): """ Tests behavior when exclusion lists are empty. """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] expected = compute_expected_jars(ctx) verify_runtime_and_compile_jars( ctx, env, javainfo_filtered, expected_compile_jars = expected["compile_jars"], expected_full_compile_jars = expected["full_compile_jars"], expected_transitive_compile_jars = expected["transitive_compile_jars"], expected_transitive_runtime_jars = expected["transitive_runtime_jars"], ) verify_dropped_counts(env, expected, expected_compile_dropped = "0", expected_full_compile_dropped = "0", expected_transitive_compile_dropped = "0", expected_transitive_runtime_dropped = "0") return unittest.end(env) empty_exclusion_lists_test = unittest.make(_test_empty_exclusion_lists, attrs = { "filtered": attr.label(providers = [JavaInfo]), "deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security", "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind", "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core", "@unmanaged_deps_filter//:jakarta_servlet_jsp_jakarta_servlet_jsp_api", ], providers = [JavaInfo], ), "runtime_deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator", ], providers = [JavaInfo], ), "deps_exclude_labels": attr.label_list( default = [], ), "deps_exclude_paths": attr.string_list( default = [], ), "exclude_transitives": attr.bool( default = False, ), }) def _test_path_based_exclusions_comprehensive(ctx): """ Tests comprehensive path-based exclusions with various patterns. """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] expected = compute_expected_jars(ctx) verify_runtime_and_compile_jars( ctx, env, javainfo_filtered, expected_compile_jars = expected["compile_jars"], expected_full_compile_jars = expected["full_compile_jars"], expected_transitive_compile_jars = expected["transitive_compile_jars"], expected_transitive_runtime_jars = expected["transitive_runtime_jars"], ) # Additional verification: ensure excluded patterns are not present transitive_runtime_jars = [jar.basename for jar in javainfo_filtered.transitive_runtime_jars.to_list()] for pattern in ["micrometer", "slf4j", "logback"]: for jar in transitive_runtime_jars: asserts.true(env, pattern not in jar, "Excluded pattern '{}' found in JAR: {}".format(pattern, jar)) verify_dropped_counts(env, expected, expected_compile_dropped = "0", expected_full_compile_dropped = "0", expected_transitive_compile_dropped = ">0", expected_transitive_runtime_dropped = ">0") return unittest.end(env) path_based_exclusions_comprehensive_test = unittest.make(_test_path_based_exclusions_comprehensive, attrs = { "filtered": attr.label(providers = [JavaInfo]), "deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security", "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind", "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core", "@unmanaged_deps_filter//:jakarta_servlet_jsp_jakarta_servlet_jsp_api", ], providers = [JavaInfo], ), "runtime_deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator", ], providers = [JavaInfo], ), "deps_exclude_labels": attr.label_list( default = [], ), "deps_exclude_paths": attr.string_list( default = [ "micrometer", "slf4j", "logback" ], ), "exclude_transitives": attr.bool( default = False, ), }) def _test_runtime_deps_only(ctx): """ Tests behavior when only runtime_deps are provided (no deps). """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] expected = compute_expected_jars(ctx) # Updating manually because the output_jar for 'runtime_deps' is a full_compile_jar if no 'deps' specified expected_full_compile_jars = ["processed_spring-boot-starter-oauth2-client-3.3.11.jar"] verify_runtime_and_compile_jars( ctx, env, javainfo_filtered, expected_compile_jars = expected["compile_jars"], expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected["transitive_compile_jars"], expected_transitive_runtime_jars = expected["transitive_runtime_jars"], ) # Runtime deps should not contribute to compile-time JARs compile_jars = [jar.basename for jar in javainfo_filtered.compile_jars.to_list()] full_compile_jars = [jar.basename for jar in javainfo_filtered.full_compile_jars.to_list()] asserts.equals(env, len(compile_jars), 0, "Expected no compile JARs when only runtime_deps provided, got: {}".format(len(compile_jars))) # Note: full_compile_jars is not empty because the output_jar is a full_compile_jar asserts.equals(env, len(full_compile_jars), 1, "Expected no full compile JARs when only runtime_deps provided, got: {}".format(len(full_compile_jars))) verify_dropped_counts(env, expected, expected_compile_dropped = "0", expected_full_compile_dropped = "0", expected_transitive_compile_dropped = "0", expected_transitive_runtime_dropped = "0") return unittest.end(env) runtime_deps_only_test = unittest.make(_test_runtime_deps_only, attrs = { "filtered": attr.label(providers = [JavaInfo]), "deps_labels": attr.label_list( default = [], ), "runtime_deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator", ], providers = [JavaInfo], ), "deps_exclude_labels": attr.label_list( default = [], ), "deps_exclude_paths": attr.string_list( default = [], ), "exclude_transitives": attr.bool( default = False, ), }) def _test_compile_deps_only(ctx): """ Tests behavior when only deps are provided (no runtime_deps). """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] expected = compute_expected_jars(ctx) verify_runtime_and_compile_jars( ctx, env, javainfo_filtered, expected_compile_jars = expected["compile_jars"], expected_full_compile_jars = expected["full_compile_jars"], expected_transitive_compile_jars = expected["transitive_compile_jars"], expected_transitive_runtime_jars = expected["transitive_runtime_jars"], ) # Compile deps should contribute to both compile and runtime JARs compile_jars = [jar.basename for jar in javainfo_filtered.compile_jars.to_list()] transitive_runtime_jars = [jar.basename for jar in javainfo_filtered.transitive_runtime_jars.to_list()] asserts.true(env, len(compile_jars) > 0, "Expected compile JARs when deps provided, got: {}".format(len(compile_jars))) asserts.true(env, len(transitive_runtime_jars) > 0, "Expected transitive runtime JARs when deps provided, got: {}".format(len(transitive_runtime_jars))) verify_dropped_counts(env, expected, expected_compile_dropped = "0", expected_full_compile_dropped = "0", expected_transitive_compile_dropped = "0", expected_transitive_runtime_dropped = "0") return unittest.end(env) compile_deps_only_test = unittest.make(_test_compile_deps_only, attrs = { "filtered": attr.label(providers = [JavaInfo]), "deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security", "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind", "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core", "@unmanaged_deps_filter//:jakarta_servlet_jsp_jakarta_servlet_jsp_api", ], providers = [JavaInfo], ), "runtime_deps_labels": attr.label_list( default = [], ), "deps_exclude_labels": attr.label_list( default = [], ), "deps_exclude_paths": attr.string_list( default = [], ), "exclude_transitives": attr.bool( default = False, ), }) def _test_single_dep_with_exclusions(ctx): """ Tests behavior with a single dependency and exclusions. """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] expected = compute_expected_jars(ctx) verify_runtime_and_compile_jars( ctx, env, javainfo_filtered, expected_compile_jars = expected["compile_jars"], expected_full_compile_jars = expected["full_compile_jars"], expected_transitive_compile_jars = expected["transitive_compile_jars"], expected_transitive_runtime_jars = expected["transitive_runtime_jars"], ) verify_dropped_counts(env, expected, expected_compile_dropped = "0", expected_full_compile_dropped = "0", expected_transitive_compile_dropped = ">0", expected_transitive_runtime_dropped = ">0") return unittest.end(env) single_dep_with_exclusions_test = unittest.make(_test_single_dep_with_exclusions, attrs = { "filtered": attr.label(providers = [JavaInfo]), "deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", ], providers = [JavaInfo], ), "runtime_deps_labels": attr.label_list( default = [], ), "deps_exclude_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:io_micrometer_micrometer_commons", ], ), "deps_exclude_paths": attr.string_list( default = [], ), "exclude_transitives": attr.bool( default = False, ), }) def _test_single_runtime_dep_with_exclusions(ctx): """ Tests behavior with a single runtime dependency and exclusions. """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] expected = compute_expected_jars(ctx) expected["full_compile_jars"] = ["processed_spring-boot-starter-oauth2-client-3.3.11.jar"] verify_runtime_and_compile_jars( ctx, env, javainfo_filtered, expected_compile_jars = expected["compile_jars"], expected_full_compile_jars = expected["full_compile_jars"], expected_transitive_compile_jars = expected["transitive_compile_jars"], expected_transitive_runtime_jars = expected["transitive_runtime_jars"], ) verify_dropped_counts(env, expected, expected_compile_dropped = "0", expected_full_compile_dropped = "0", expected_transitive_compile_dropped = "0", expected_transitive_runtime_dropped = ">0") return unittest.end(env) single_runtime_dep_with_exclusions_test = unittest.make(_test_single_runtime_dep_with_exclusions, attrs = { "filtered": attr.label(providers = [JavaInfo]), "deps_labels": attr.label_list( default = [], ), "runtime_deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", ], providers = [JavaInfo], ), "deps_exclude_labels": attr.label_list( default = [], ), "deps_exclude_paths": attr.string_list( default = [ "slf4j", ], ), "exclude_transitives": attr.bool( default = False, ), }) def _test_one_compile_one_runtime_dep(ctx): """ Tests behavior with exactly one compile dep and one runtime dep. """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] expected = compute_expected_jars(ctx) verify_runtime_and_compile_jars( ctx, env, javainfo_filtered, expected_compile_jars = expected["compile_jars"], expected_full_compile_jars = expected["full_compile_jars"], expected_transitive_compile_jars = expected["transitive_compile_jars"], expected_transitive_runtime_jars = expected["transitive_runtime_jars"], ) verify_dropped_counts(env, expected, expected_compile_dropped = "0", expected_full_compile_dropped = "0", expected_transitive_compile_dropped = "0", expected_transitive_runtime_dropped = "0") return unittest.end(env) one_compile_one_runtime_dep_test = unittest.make(_test_one_compile_one_runtime_dep, attrs = { "filtered": attr.label(providers = [JavaInfo]), "deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", ], providers = [JavaInfo], ), "runtime_deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", ], providers = [JavaInfo], ), "deps_exclude_labels": attr.label_list( default = [], ), "deps_exclude_paths": attr.string_list( default = [], ), "exclude_transitives": attr.bool( default = False, ), }) def _test_path_patterns_with_special_characters(ctx): """ Tests behavior with path patterns containing special characters. """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] expected = compute_expected_jars(ctx) verify_runtime_and_compile_jars( ctx, env, javainfo_filtered, expected_compile_jars = expected["compile_jars"], expected_full_compile_jars = expected["full_compile_jars"], expected_transitive_compile_jars = expected["transitive_compile_jars"], expected_transitive_runtime_jars = expected["transitive_runtime_jars"], ) verify_dropped_counts(env, expected, expected_compile_dropped = "0", expected_full_compile_dropped = "0", expected_transitive_compile_dropped = ">0", expected_transitive_runtime_dropped = ">0") return unittest.end(env) path_patterns_with_special_characters_test = unittest.make(_test_path_patterns_with_special_characters, attrs = { "filtered": attr.label(providers = [JavaInfo]), "deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security", "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind", "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core", "@unmanaged_deps_filter//:jakarta_servlet_jsp_jakarta_servlet_jsp_api", ], providers = [JavaInfo], ), "runtime_deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator", ], providers = [JavaInfo], ), "deps_exclude_labels": attr.label_list( default = [], ), "deps_exclude_paths": attr.string_list( default = [ "io.micrometer", # Pattern with dot "to-slf4j", # Pattern with hyphen ], ), "exclude_transitives": attr.bool( default = True, ), }) def _test_case_sensitive_pattern_matching(ctx): """ Tests case sensitivity in path pattern matching. """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] expected = compute_expected_jars(ctx) verify_runtime_and_compile_jars( ctx, env, javainfo_filtered, expected_compile_jars = expected["compile_jars"], expected_full_compile_jars = expected["full_compile_jars"], expected_transitive_compile_jars = expected["transitive_compile_jars"], expected_transitive_runtime_jars = expected["transitive_runtime_jars"], ) verify_dropped_counts(env, expected, expected_compile_dropped = "0", expected_full_compile_dropped = "0", expected_transitive_compile_dropped = "0", expected_transitive_runtime_dropped = "0") return unittest.end(env) case_sensitive_pattern_matching_test = unittest.make(_test_case_sensitive_pattern_matching, attrs = { "filtered": attr.label(providers = [JavaInfo]), "deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security", "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind", "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core", "@unmanaged_deps_filter//:jakarta_servlet_jsp_jakarta_servlet_jsp_api", ], providers = [JavaInfo], ), "runtime_deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator", ], providers = [JavaInfo], ), "deps_exclude_labels": attr.label_list( default = [], ), "deps_exclude_paths": attr.string_list( default = [ "SPRING", # Uppercase pattern "Jackson", # Mixed case pattern "HIBERNATE", # Uppercase pattern ], ), "exclude_transitives": attr.bool( default = False, ), }) ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime/src/test/java/com/depsfilter/DepsFilterCaseSensitivePatternMatchingTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.Set; import org.junit.BeforeClass; import org.junit.Test; public class DepsFilterCaseSensitivePatternMatchingTest { @BeforeClass public static void setUp() { DependencyGraphTestConfig.initialize(); } @Test public void testCaseSensitivePatternMatching() { Set availableDeps = Set.copyOf(DepsFilterTestHelper.computeClasspathDependencies()); Set excludedPatterns = Set.of("SPRING", "Jackson", "HIBERNATE"); Set expectedRuntimeDeps = DependencyGraphTestConfig.getExpectedJarsForPathExclusionsFiltered( excludedPatterns, false); expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime/DepsFilterCaseSensitivePatternMatchingTest.jar"); assertThat(availableDeps).isEqualTo(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime/src/test/java/com/depsfilter/DepsFilterCompileDepsOnlyTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.Set; import org.junit.BeforeClass; import org.junit.Test; public class DepsFilterCompileDepsOnlyTest { @BeforeClass public static void setUp() { DependencyGraphTestConfig.initialize(); } @Test public void testCompileDepsOnly() { Set availableDeps = Set.copyOf(DepsFilterTestHelper.computeClasspathDependencies()); Set depsLabels = Set.of( "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security", "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind", "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core", "@unmanaged_deps_filter//:jakarta_servlet_jsp_jakarta_servlet_jsp_api" ); Set runtimeDepsLabels = Set.of(); Set excludedLabels = Set.of(); Set excludedPatterns = Set.of(); boolean excludeTransitives = false; Set expectedRuntimeDeps = DependencyGraphTestConfig.getExpectedJarsForCustomDepsFiltered( depsLabels, runtimeDepsLabels, excludedLabels, excludedPatterns, excludeTransitives); expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime/DepsFilterCompileDepsOnlyTest.jar"); assertThat(availableDeps).isEqualTo(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime/src/test/java/com/depsfilter/DepsFilterEmptyExclusionsTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.Set; import org.junit.BeforeClass; import org.junit.Test; public class DepsFilterEmptyExclusionsTest { @BeforeClass public static void setUp() { DependencyGraphTestConfig.initialize(); } @Test public void testTransitivesExclusion() { Set availableDeps = Set.copyOf(DepsFilterTestHelper.computeClasspathDependencies()); Set expectedRuntimeDeps = DependencyGraphTestConfig.getExpectedJarsForNoFilteringFiltered(); expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime/DepsFilterEmptyExclusionsTest.jar"); assertThat(availableDeps).isEqualTo(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime/src/test/java/com/depsfilter/DepsFilterExcludeTransitiveTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.Set; import org.junit.BeforeClass; import org.junit.Test; public class DepsFilterExcludeTransitiveTest { @BeforeClass public static void setUp() { DependencyGraphTestConfig.initialize(); } @Test public void testTransitivesExclusion() { Set availableDeps = Set.copyOf(DepsFilterTestHelper.computeClasspathDependencies()); Set excludedLabels = Set.of( "@unmanaged_deps_filter//:io_micrometer_micrometer_commons", "@unmanaged_deps_filter//:org_slf4j_jul_to_slf4j" ); Set expectedRuntimeDeps = DependencyGraphTestConfig.getExpectedJarsForLabelExclusionsFiltered( excludedLabels, true); expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime/DepsFilterExcludeTransitiveTest.jar"); assertThat(availableDeps).isEqualTo(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime/src/test/java/com/depsfilter/DepsFilterLabelExclusionsTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.Set; import java.util.HashSet; import org.junit.BeforeClass; import org.junit.Test; public class DepsFilterLabelExclusionsTest { @BeforeClass public static void setUp() { DependencyGraphTestConfig.initialize(); } @Test public void testLabelExclusions() { Set availableDeps = Set.copyOf(DepsFilterTestHelper.computeClasspathDependencies()); Set excludedLabels = Set.of( "@unmanaged_deps_filter//:io_micrometer_micrometer_commons", "@unmanaged_deps_filter//:org_slf4j_jul_to_slf4j" ); Set expectedRuntimeDeps = DependencyGraphTestConfig.getExpectedJarsForLabelExclusionsFiltered( excludedLabels, false); expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime/DepsFilterLabelExclusionsTest.jar"); assertThat(availableDeps).isEqualTo(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime/src/test/java/com/depsfilter/DepsFilterMultipleExclusionsWithTransitivesTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.Set; import org.junit.BeforeClass; import org.junit.Test; public class DepsFilterMultipleExclusionsWithTransitivesTest { @BeforeClass public static void setUp() { DependencyGraphTestConfig.initialize(); } @Test public void testMultipleExclusionsWithTransitives() { Set availableDeps = Set.copyOf(DepsFilterTestHelper.computeClasspathDependencies()); Set excludedLabels = Set.of( "@unmanaged_deps_filter//:io_micrometer_micrometer_commons", "@unmanaged_deps_filter//:org_slf4j_jul_to_slf4j" ); Set excludedPatterns = Set.of("slf4j"); Set expectedRuntimeDeps = DependencyGraphTestConfig.getExpectedJarsForMultipleExclusionsFiltered( excludedLabels, excludedPatterns, true); expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime/DepsFilterMultipleExclusionsWithTransitivesTest.jar"); assertThat(availableDeps).isEqualTo(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime/src/test/java/com/depsfilter/DepsFilterMultipleExclusionsWithoutTransitivesTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.Set; import org.junit.BeforeClass; import org.junit.Test; public class DepsFilterMultipleExclusionsWithoutTransitivesTest { @BeforeClass public static void setUp() { DependencyGraphTestConfig.initialize(); } @Test public void testMultipleExclusionsWithoutTransitives() { Set availableDeps = Set.copyOf(DepsFilterTestHelper.computeClasspathDependencies()); Set excludedLabels = Set.of( "@unmanaged_deps_filter//:io_micrometer_micrometer_commons", "@unmanaged_deps_filter//:org_slf4j_jul_to_slf4j" ); Set excludedPatterns = Set.of("slf4j"); Set expectedRuntimeDeps = DependencyGraphTestConfig.getExpectedJarsForMultipleExclusionsFiltered( excludedLabels, excludedPatterns, true); expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime/DepsFilterMultipleExclusionsWithoutTransitivesTest.jar"); assertThat(availableDeps).isEqualTo(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime/src/test/java/com/depsfilter/DepsFilterNoFilteringTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.Set; import org.junit.BeforeClass; import org.junit.Test; public class DepsFilterNoFilteringTest { @BeforeClass public static void setUp() { DependencyGraphTestConfig.initialize(); } @Test public void testNoFiltering() { Set availableDeps = Set.copyOf(DepsFilterTestHelper.computeClasspathDependencies()); Set expectedRuntimeDeps = DependencyGraphTestConfig.getExpectedJarsForNoFilteringFiltered(); expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime/DepsFilterNoFilteringTest.jar"); assertThat(availableDeps).isEqualTo(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime/src/test/java/com/depsfilter/DepsFilterOneCompileOneRuntimeDepTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.Set; import org.junit.BeforeClass; import org.junit.Test; public class DepsFilterOneCompileOneRuntimeDepTest { @BeforeClass public static void setUp() { DependencyGraphTestConfig.initialize(); } @Test public void testOneCompileOneRuntimeDep() { Set availableDeps = Set.copyOf(DepsFilterTestHelper.computeClasspathDependencies()); Set depsLabels = Set.of("@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa"); Set runtimeDepsLabels = Set.of("@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client"); Set excludedLabels = Set.of(); Set excludedPatterns = Set.of(); boolean excludeTransitives = false; Set expectedRuntimeDeps = DependencyGraphTestConfig.getExpectedJarsForCustomDepsFiltered( depsLabels, runtimeDepsLabels, excludedLabels, excludedPatterns, excludeTransitives); expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime/DepsFilterOneCompileOneRuntimeDepTest.jar"); assertThat(availableDeps).isEqualTo(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime/src/test/java/com/depsfilter/DepsFilterPathBasedExclusionsComprehensiveTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.Set; import org.junit.BeforeClass; import org.junit.Test; public class DepsFilterPathBasedExclusionsComprehensiveTest { @BeforeClass public static void setUp() { DependencyGraphTestConfig.initialize(); } @Test public void testPathBasedExclusionsComprehensive() { Set availableDeps = Set.copyOf(DepsFilterTestHelper.computeClasspathDependencies()); Set excludedPatterns = Set.of("micrometer", "slf4j", "logback"); Set expectedRuntimeDeps = DependencyGraphTestConfig.getExpectedJarsForPathExclusionsFiltered( excludedPatterns, false); expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime/DepsFilterPathBasedExclusionsComprehensiveTest.jar"); assertThat(availableDeps).isEqualTo(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime/src/test/java/com/depsfilter/DepsFilterPathExclusionsTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.Set; import org.junit.BeforeClass; import org.junit.Test; public class DepsFilterPathExclusionsTest { @BeforeClass public static void setUp() { DependencyGraphTestConfig.initialize(); } @Test public void testPathExclusions() { Set availableDeps = Set.copyOf(DepsFilterTestHelper.computeClasspathDependencies()); Set excludedPatterns = Set.of("micrometer", "slf4j"); Set expectedRuntimeDeps = DependencyGraphTestConfig.getExpectedJarsForPathExclusionsFiltered( excludedPatterns, false); expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime/DepsFilterPathExclusionsTest.jar"); assertThat(availableDeps).isEqualTo(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime/src/test/java/com/depsfilter/DepsFilterPathExclusionsWithTransitivesTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.Set; import org.junit.BeforeClass; import org.junit.Test; public class DepsFilterPathExclusionsWithTransitivesTest { @BeforeClass public static void setUp() { DependencyGraphTestConfig.initialize(); } @Test public void testPathExclusionsWithTransitives() { Set availableDeps = Set.copyOf(DepsFilterTestHelper.computeClasspathDependencies()); Set excludedPatterns = Set.of("micrometer", "slf4j"); Set expectedRuntimeDeps = DependencyGraphTestConfig.getExpectedJarsForPathExclusionsFiltered( excludedPatterns, true); expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime/DepsFilterPathExclusionsWithTransitivesTest.jar"); assertThat(availableDeps).isEqualTo(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime/src/test/java/com/depsfilter/DepsFilterPathPatternsWithSpecialCharactersTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.Set; import org.junit.BeforeClass; import org.junit.Test; public class DepsFilterPathPatternsWithSpecialCharactersTest { @BeforeClass public static void setUp() { DependencyGraphTestConfig.initialize(); } @Test public void testPathPatternsWithSpecialCharacters() { Set availableDeps = Set.copyOf(DepsFilterTestHelper.computeClasspathDependencies()); Set excludedPatterns = Set.of("io.micrometer", "to-slf4j"); Set expectedRuntimeDeps = DependencyGraphTestConfig.getExpectedJarsForPathExclusionsFiltered( excludedPatterns, true); expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime/DepsFilterPathPatternsWithSpecialCharactersTest.jar"); assertThat(availableDeps).isEqualTo(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime/src/test/java/com/depsfilter/DepsFilterRuntimeDepsOnlyTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.Set; import org.junit.BeforeClass; import org.junit.Test; public class DepsFilterRuntimeDepsOnlyTest { @BeforeClass public static void setUp() { DependencyGraphTestConfig.initialize(); } @Test public void testRuntimeDepsOnly() { Set availableDeps = Set.copyOf(DepsFilterTestHelper.computeClasspathDependencies()); Set depsLabels = Set.of(); Set runtimeDepsLabels = Set.of( "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator" ); Set excludedLabels = Set.of(); Set excludedPatterns = Set.of(); boolean excludeTransitives = false; Set expectedRuntimeDeps = DependencyGraphTestConfig.getExpectedJarsForCustomDepsFiltered( depsLabels, runtimeDepsLabels, excludedLabels, excludedPatterns, excludeTransitives); expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime/DepsFilterRuntimeDepsOnlyTest.jar"); assertThat(availableDeps).isEqualTo(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime/src/test/java/com/depsfilter/DepsFilterSingleDepWithExclusionsTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.Set; import org.junit.BeforeClass; import org.junit.Test; public class DepsFilterSingleDepWithExclusionsTest { @BeforeClass public static void setUp() { DependencyGraphTestConfig.initialize(); } @Test public void testSingleDepWithExclusions() { Set availableDeps = Set.copyOf(DepsFilterTestHelper.computeClasspathDependencies()); Set depsLabels = Set.of("@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa"); Set runtimeDepsLabels = Set.of(); Set excludedLabels = Set.of("@unmanaged_deps_filter//:io_micrometer_micrometer_commons"); Set excludedPatterns = Set.of(); Set expectedRuntimeDeps = DependencyGraphTestConfig.getExpectedJarsForCustomDepsFiltered( depsLabels, runtimeDepsLabels, excludedLabels, excludedPatterns, false); expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime/DepsFilterSingleDepWithExclusionsTest.jar"); assertThat(availableDeps).isEqualTo(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime/src/test/java/com/depsfilter/DepsFilterSingleRuntimeDepWithExclusionsTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.Set; import org.junit.BeforeClass; import org.junit.Test; public class DepsFilterSingleRuntimeDepWithExclusionsTest { @BeforeClass public static void setUp() { DependencyGraphTestConfig.initialize(); } @Test public void testSingleRuntimeDepWithExclusions() { Set availableDeps = Set.copyOf(DepsFilterTestHelper.computeClasspathDependencies()); Set depsLabels = Set.of(); Set runtimeDepsLabels = Set.of("@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client"); Set excludedLabels = Set.of(); Set excludedPatterns = Set.of("slf4j"); boolean excludeTransitives = false; Set expectedRuntimeDeps = DependencyGraphTestConfig.getExpectedJarsForCustomDepsFiltered( depsLabels, runtimeDepsLabels, excludedLabels, excludedPatterns, excludeTransitives); expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime/DepsFilterSingleRuntimeDepWithExclusionsTest.jar"); assertThat(availableDeps).isEqualTo(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/BUILD ================================================ load("//springboot/deps_filter_rules:deps_filter.bzl", "deps_filter") load( "//springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library:compile_and_runtime_test.bzl", "no_filtering_test", "with_label_exclusions_test", "with_label_exclusions_with_exclude_transitives_test", "with_path_exclusions_test", "with_path_exclusions_with_exclude_transitives_test", "multiple_exclusions_with_exclude_transitives_test", "multiple_exclusions_without_exclude_transitives_test", "empty_exclusion_lists_test", "path_based_exclusions_comprehensive_test", "runtime_deps_only_A_test", "runtime_deps_only_B_test", "single_runtime_dep_with_exclusions_A_test", "single_runtime_dep_with_exclusions_B_test", "compile_deps_only_test", "single_dep_with_exclusions_test", "one_compile_one_runtime_dep_test", "path_patterns_with_special_characters_test", "case_sensitive_pattern_matching_test", ) deps = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security", "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind", "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core", "@unmanaged_deps_filter//:jakarta_servlet_jsp_jakarta_servlet_jsp_api", ] runtime_deps = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator", ] test_deps = [ "@unmanaged_deps_filter//:junit_junit", "@unmanaged_deps_filter//:org_assertj_assertj_core", ] # Setup libraries for testing java_library( name = "base_lib_with_deps_and_runtime_deps", srcs = ["src/main/java/com/depsfilter/A.java"], deps = deps, runtime_deps = runtime_deps, ) java_library( name = "base_lib_with_deps", srcs = ["src/main/java/com/depsfilter/A.java"], deps = deps, ) java_library( name = "base_lib_with_runtime_deps", srcs = ["src/main/java/com/depsfilter/A.java"], runtime_deps = runtime_deps, ) java_library( name = "base_lib_with_single_dep_and_runtime_dep", srcs = ["src/main/java/com/depsfilter/A.java"], deps = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", ], runtime_deps = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", ], ) java_library( name = "base_lib_with_single_dep", srcs = ["src/main/java/com/depsfilter/A.java"], deps = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", ], ) java_library( name = "base_lib_with_single_runtime_dep", srcs = ["src/main/java/com/depsfilter/A.java"], runtime_deps = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", ], ) # Test 1: No filtering - baseline test deps_filter( name = "no_filtering", deps = [":base_lib_with_deps_and_runtime_deps"], ) no_filtering_test( name = "no_filtering_test", filtered = ":no_filtering", ) java_test( name = "DepsFilterNoFilteringTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterNoFilteringTest.java" ], deps = [":no_filtering", "//springboot/deps_filter_rules/tests/test_utils:test_utils"] + test_deps, ) # Test 2: Label-based exclusions without transitives deps_filter( name = "with_label_exclusions", deps = [":base_lib_with_deps_and_runtime_deps"], deps_exclude_labels = [ "@unmanaged_deps_filter//:io_micrometer_micrometer_commons", "@unmanaged_deps_filter//:org_slf4j_jul_to_slf4j", ], ) with_label_exclusions_test( name = "with_label_exclusions_test", filtered = ":with_label_exclusions", ) java_test( name = "DepsFilterLabelExclusionsTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterLabelExclusionsTest.java" ], deps = [":with_label_exclusions", "//springboot/deps_filter_rules/tests/test_utils:test_utils"] + test_deps, ) # Test 3: Label-based exclusions with exclude_transitives deps_filter( name = "with_label_exclusions_with_exclude_transitives", deps = [":base_lib_with_deps_and_runtime_deps"], deps_exclude_labels = [ "@unmanaged_deps_filter//:io_micrometer_micrometer_commons", "@unmanaged_deps_filter//:org_slf4j_jul_to_slf4j", ], exclude_transitives = True, ) with_label_exclusions_with_exclude_transitives_test( name = "with_label_exclusions_with_exclude_transitives_test", filtered = ":with_label_exclusions_with_exclude_transitives", ) java_test( name = "DepsFilterExcludeTransitiveTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterExcludeTransitiveTest.java" ], deps = [":with_label_exclusions_with_exclude_transitives", "//springboot/deps_filter_rules/tests/test_utils:test_utils"] + test_deps, ) # Test 4: Path-based exclusions without transitives deps_filter( name = "with_path_exclusions", deps = [":base_lib_with_deps_and_runtime_deps"], deps_exclude_paths = [ "micrometer", "slf4j" ], ) with_path_exclusions_test( name = "with_path_exclusions_test", filtered = ":with_path_exclusions", ) java_test( name = "DepsFilterPathExclusionsTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterPathExclusionsTest.java" ], deps = [":with_path_exclusions", "//springboot/deps_filter_rules/tests/test_utils:test_utils"] + test_deps, ) # Test 5: Path-based exclusions with exclude_transitives deps_filter( name = "with_path_exclusions_with_exclude_transitives", deps = [":base_lib_with_deps_and_runtime_deps"], deps_exclude_paths = [ "micrometer", "slf4j" ], exclude_transitives = True, ) with_path_exclusions_with_exclude_transitives_test( name = "with_path_exclusions_with_exclude_transitives_test", filtered = ":with_path_exclusions_with_exclude_transitives", ) java_test( name = "DepsFilterPathExclusionsWithTransitivesTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterPathExclusionsWithTransitivesTest.java" ], deps = [":with_path_exclusions_with_exclude_transitives", "//springboot/deps_filter_rules/tests/test_utils:test_utils"] + test_deps, ) # Test 6: Multiple exclusions with exclude_transitives (labels + patterns) deps_filter( name = "multiple_exclusions_with_exclude_transitives", deps = [":base_lib_with_deps_and_runtime_deps"], deps_exclude_labels = [ "@unmanaged_deps_filter//:io_micrometer_micrometer_commons", "@unmanaged_deps_filter//:org_slf4j_jul_to_slf4j", ], deps_exclude_paths = [ "slf4j" ], exclude_transitives = True, ) multiple_exclusions_with_exclude_transitives_test( name = "multiple_exclusions_with_exclude_transitives_test", filtered = ":multiple_exclusions_with_exclude_transitives", ) java_test( name = "DepsFilterMultipleExclusionsWithTransitivesTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterMultipleExclusionsWithTransitivesTest.java" ], deps = [":multiple_exclusions_with_exclude_transitives", "//springboot/deps_filter_rules/tests/test_utils:test_utils"] + test_deps, ) # Test 7: Multiple exclusions without exclude_transitives (labels + patterns) deps_filter( name = "multiple_exclusions_without_exclude_transitives", deps = [":base_lib_with_deps_and_runtime_deps"], deps_exclude_labels = [ "@unmanaged_deps_filter//:io_micrometer_micrometer_commons", "@unmanaged_deps_filter//:org_slf4j_jul_to_slf4j", ], deps_exclude_paths = [ "slf4j", ], exclude_transitives = True, ) multiple_exclusions_without_exclude_transitives_test( name = "multiple_exclusions_without_exclude_transitives_test", filtered = ":multiple_exclusions_without_exclude_transitives", ) java_test( name = "DepsFilterMultipleExclusionsWithoutTransitivesTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterMultipleExclusionsWithoutTransitivesTest.java" ], deps = [":multiple_exclusions_without_exclude_transitives", "//springboot/deps_filter_rules/tests/test_utils:test_utils"] + test_deps, ) # Test 8: Empty exclusion lists deps_filter( name = "empty_exclusion_lists", deps = [":base_lib_with_deps_and_runtime_deps"], deps_exclude_labels = [], deps_exclude_paths = [], exclude_transitives = False, ) empty_exclusion_lists_test( name = "empty_exclusion_lists_test", filtered = ":empty_exclusion_lists", ) java_test( name = "DepsFilterEmptyExclusionsTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterEmptyExclusionsTest.java" ], deps = [":empty_exclusion_lists", "//springboot/deps_filter_rules/tests/test_utils:test_utils"] + test_deps, ) # Test 9: Comprehensive path-based exclusions deps_filter( name = "path_based_exclusions_comprehensive", deps = [":base_lib_with_deps_and_runtime_deps"], deps_exclude_labels = [], deps_exclude_paths = [ "micrometer", "slf4j", "logback" ], exclude_transitives = False, ) path_based_exclusions_comprehensive_test( name = "path_based_exclusions_comprehensive_test", filtered = ":path_based_exclusions_comprehensive", ) java_test( name = "DepsFilterPathBasedExclusionsComprehensiveTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterPathBasedExclusionsComprehensiveTest.java" ], deps = [":path_based_exclusions_comprehensive", "//springboot/deps_filter_rules/tests/test_utils:test_utils"] + test_deps, ) # Test 10.A: Runtime deps only deps_filter( name = "runtime_deps_only_A", runtime_deps = [":base_lib_with_runtime_deps"], deps_exclude_labels = [], deps_exclude_paths = [], exclude_transitives = False, ) runtime_deps_only_A_test( name = "runtime_deps_only_A_test", filtered = ":runtime_deps_only_A", ) java_test( name = "DepsFilterRuntimeDepsOnlyATest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterRuntimeDepsOnlyATest.java" ], deps = [":runtime_deps_only_A", "//springboot/deps_filter_rules/tests/test_utils:test_utils"] + test_deps, ) # Test 10.B: Runtime deps only deps_filter( name = "runtime_deps_only_B", deps = [":base_lib_with_runtime_deps"], deps_exclude_labels = [], deps_exclude_paths = [], exclude_transitives = False, ) runtime_deps_only_B_test( name = "runtime_deps_only_B_test", filtered = ":runtime_deps_only_B", ) java_test( name = "DepsFilterRuntimeDepsOnlyBTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterRuntimeDepsOnlyBTest.java" ], deps = [":runtime_deps_only_B", "//springboot/deps_filter_rules/tests/test_utils:test_utils"] + test_deps, ) # Test 11.A: Single runtime dependency with exclusions deps_filter( name = "single_runtime_dep_with_exclusions_A", runtime_deps = [":base_lib_with_single_runtime_dep",], deps_exclude_labels = [], deps_exclude_paths = [ "slf4j", ], exclude_transitives = False, ) single_runtime_dep_with_exclusions_A_test( name = "single_runtime_dep_with_exclusions_test_A", filtered = ":single_runtime_dep_with_exclusions_A", ) java_test( name = "DepsFilterSingleRuntimeDepWithExclusionsATest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterSingleRuntimeDepWithExclusionsATest.java" ], deps = [":single_runtime_dep_with_exclusions_A", "//springboot/deps_filter_rules/tests/test_utils:test_utils"] + test_deps, ) # Test 11.B: Single runtime dependency with exclusions deps_filter( name = "single_runtime_dep_with_exclusions_B", deps = [":base_lib_with_single_runtime_dep",], # runtime_deps = [], deps_exclude_labels = [], deps_exclude_paths = [ "slf4j", ], exclude_transitives = False, ) single_runtime_dep_with_exclusions_B_test( name = "single_runtime_dep_with_exclusions_test_B", filtered = ":single_runtime_dep_with_exclusions_B", ) java_test( name = "DepsFilterSingleRuntimeDepWithExclusionsBTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterSingleRuntimeDepWithExclusionsBTest.java" ], deps = [":single_runtime_dep_with_exclusions_B", "//springboot/deps_filter_rules/tests/test_utils:test_utils"] + test_deps, ) # Test 12: Compile deps only deps_filter( name = "compile_deps_only", deps = [":base_lib_with_deps"], runtime_deps = [], deps_exclude_labels = [], deps_exclude_paths = [], exclude_transitives = False, ) compile_deps_only_test( name = "compile_deps_only_test", filtered = ":compile_deps_only", ) java_test( name = "DepsFilterCompileDepsOnlyTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterCompileDepsOnlyTest.java" ], deps = [":compile_deps_only", "//springboot/deps_filter_rules/tests/test_utils:test_utils"] + test_deps, ) # Test 13: Single dependency with exclusions deps_filter( name = "single_dep_with_exclusions", deps = [":base_lib_with_single_dep"], runtime_deps = [], deps_exclude_labels = [ "@unmanaged_deps_filter//:io_micrometer_micrometer_commons", ], deps_exclude_paths = [], exclude_transitives = False, ) single_dep_with_exclusions_test( name = "single_dep_with_exclusions_test", filtered = ":single_dep_with_exclusions", ) java_test( name = "DepsFilterSingleDepWithExclusionsTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterSingleDepWithExclusionsTest.java" ], deps = [":single_dep_with_exclusions", "//springboot/deps_filter_rules/tests/test_utils:test_utils"] + test_deps, ) # Test 14: One compile dep and one runtime dep deps_filter( name = "one_compile_one_runtime_dep", deps = [":base_lib_with_single_dep_and_runtime_dep"], deps_exclude_labels = [], deps_exclude_paths = [], exclude_transitives = False, ) one_compile_one_runtime_dep_test( name = "one_compile_one_runtime_dep_test", filtered = ":one_compile_one_runtime_dep", ) java_test( name = "DepsFilterOneCompileOneRuntimeDepTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterOneCompileOneRuntimeDepTest.java" ], deps = [":one_compile_one_runtime_dep", "//springboot/deps_filter_rules/tests/test_utils:test_utils"] + test_deps, ) # Test 15: Path patterns with special characters deps_filter( name = "path_patterns_with_special_characters", deps = [":base_lib_with_deps_and_runtime_deps"], deps_exclude_paths = [ "io.micrometer", "to-slf4j", ], exclude_transitives = True, ) path_patterns_with_special_characters_test( name = "path_patterns_with_special_characters_test", filtered = ":path_patterns_with_special_characters", ) java_test( name = "DepsFilterPathPatternsWithSpecialCharactersTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterPathPatternsWithSpecialCharactersTest.java" ], deps = [":path_patterns_with_special_characters", "//springboot/deps_filter_rules/tests/test_utils:test_utils"] + test_deps, ) # Test 16: Case sensitive pattern matching deps_filter( name = "case_sensitive_pattern_matching", deps = [":base_lib_with_deps_and_runtime_deps"], deps_exclude_labels = [], deps_exclude_paths = [ "SPRING", # Uppercase pattern "Jackson", # Mixed case pattern "HIBERNATE", # Uppercase pattern ], exclude_transitives = False, ) case_sensitive_pattern_matching_test( name = "case_sensitive_pattern_matching_test", filtered = ":case_sensitive_pattern_matching", ) java_test( name = "DepsFilterCaseSensitivePatternMatchingTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterCaseSensitivePatternMatchingTest.java" ], deps = [":case_sensitive_pattern_matching", "//springboot/deps_filter_rules/tests/test_utils:test_utils"] + test_deps, ) # Toolchain for unittest toolchain( name = "unittest_toolchain", toolchain_type = "@bazel_skylib//toolchains/unittest:toolchain_type", toolchain = "@bazel_skylib//toolchains/unittest:toolchain", ) ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/compile_and_runtime_test.bzl ================================================ load("@bazel_skylib//lib:unittest.bzl", "asserts", "unittest") load("//springboot/deps_filter_rules/tests/test_utils:verification_utils.bzl", "verify_jars", "verify_runtime_and_compile_jars", "verify_jars_and_dropped_counts", "verify_dropped_counts", "compute_expected_jars", ) def _test_no_filtering(ctx): """ Tests deps without any filtering - baseline test. """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] test_lib_name = "base_lib_with_deps_and_runtime_deps" expected = compute_expected_jars(ctx, test_lib_name) verify_runtime_and_compile_jars( ctx, env, javainfo_filtered, expected_compile_jars = expected["compile_jars"], expected_full_compile_jars = expected["full_compile_jars"], expected_transitive_compile_jars = expected["transitive_compile_jars"], expected_transitive_runtime_jars = expected["transitive_runtime_jars"], ) verify_jars_and_dropped_counts(env, expected, expected_compile_dropped = "0", expected_full_compile_dropped = "0", expected_transitive_compile_dropped = "0", expected_transitive_runtime_dropped = "0") return unittest.end(env) no_filtering_test = unittest.make(_test_no_filtering, attrs = { "filtered": attr.label(providers = [JavaInfo]), "deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security", "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind", "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core", "@unmanaged_deps_filter//:jakarta_servlet_jsp_jakarta_servlet_jsp_api", ], providers = [JavaInfo], ), "runtime_deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator", ], providers = [JavaInfo], ), "deps_exclude_labels": attr.label_list( default = [], ), "deps_exclude_paths": attr.string_list( default = [], ), }) def _test_with_label_exclusions(ctx): """ Tests deps with label-based exclusions (without transitives). """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] test_lib_name = "base_lib_with_deps_and_runtime_deps" expected = compute_expected_jars(ctx, test_lib_name) verify_runtime_and_compile_jars( ctx, env, javainfo_filtered, expected_compile_jars = expected["compile_jars"], expected_full_compile_jars = expected["full_compile_jars"], expected_transitive_compile_jars = expected["transitive_compile_jars"], expected_transitive_runtime_jars = expected["transitive_runtime_jars"], ) # Verify dropped counts - label exclusions should drop direct JARs but not transitives when exclude_transitives=False dropped_counts = { "compile_jars_dropped": expected["compile_jars_dropped"], "full_compile_jars_dropped": expected["full_compile_jars_dropped"], "transitive_compile_jars_dropped": expected["transitive_compile_jars_dropped"], "transitive_runtime_jars_dropped": expected["transitive_runtime_jars_dropped"], } verify_dropped_counts(env, expected, expected_compile_dropped = "0", expected_full_compile_dropped = "0", expected_transitive_compile_dropped = ">0", expected_transitive_runtime_dropped = ">0") return unittest.end(env) with_label_exclusions_test = unittest.make(_test_with_label_exclusions, attrs = { "filtered": attr.label(providers = [JavaInfo]), "deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security", "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind", "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core", "@unmanaged_deps_filter//:jakarta_servlet_jsp_jakarta_servlet_jsp_api", ], providers = [JavaInfo], ), "runtime_deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator", ], providers = [JavaInfo], ), "deps_exclude_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:io_micrometer_micrometer_commons", "@unmanaged_deps_filter//:org_slf4j_jul_to_slf4j", ], ), "deps_exclude_paths": attr.string_list( default = [], ), "exclude_transitives": attr.bool( default = False, ), }) def _test_with_label_exclusions_with_exclude_transitives(ctx): """ Tests deps with label-based exclusions including exclude_transitives. """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] test_lib_name = "base_lib_with_deps_and_runtime_deps" expected = compute_expected_jars(ctx, test_lib_name) verify_runtime_and_compile_jars( ctx, env, javainfo_filtered, expected_compile_jars = expected["compile_jars"], expected_full_compile_jars = expected["full_compile_jars"], expected_transitive_compile_jars = expected["transitive_compile_jars"], expected_transitive_runtime_jars = expected["transitive_runtime_jars"], ) verify_jars_and_dropped_counts(env, expected, expected_compile_dropped = "0", expected_full_compile_dropped = "0", expected_transitive_compile_dropped = ">0", expected_transitive_runtime_dropped = ">0") return unittest.end(env) with_label_exclusions_with_exclude_transitives_test = unittest.make(_test_with_label_exclusions_with_exclude_transitives, attrs = { "filtered": attr.label(providers = [JavaInfo]), "deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security", "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind", "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core", "@unmanaged_deps_filter//:jakarta_servlet_jsp_jakarta_servlet_jsp_api", ], providers = [JavaInfo], ), "runtime_deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator", ], providers = [JavaInfo], ), "deps_exclude_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:io_micrometer_micrometer_commons", "@unmanaged_deps_filter//:org_slf4j_jul_to_slf4j", ], ), "deps_exclude_paths": attr.string_list( default = [], ), "exclude_transitives": attr.bool( default = True, ), }) def _test_with_path_exclusions(ctx): """ Tests deps with path-based exclusions (without transitives). """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] test_lib_name = "base_lib_with_deps_and_runtime_deps" expected = compute_expected_jars(ctx, test_lib_name) verify_runtime_and_compile_jars( ctx, env, javainfo_filtered, expected_compile_jars = expected["compile_jars"], expected_full_compile_jars = expected["full_compile_jars"], expected_transitive_compile_jars = expected["transitive_compile_jars"], expected_transitive_runtime_jars = expected["transitive_runtime_jars"], ) verify_dropped_counts(env, expected, expected_compile_dropped = "0", expected_full_compile_dropped = "0", expected_transitive_compile_dropped = ">0", expected_transitive_runtime_dropped = ">0") return unittest.end(env) with_path_exclusions_test = unittest.make(_test_with_path_exclusions, attrs = { "filtered": attr.label(providers = [JavaInfo]), "deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security", "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind", "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core", "@unmanaged_deps_filter//:jakarta_servlet_jsp_jakarta_servlet_jsp_api", ], providers = [JavaInfo], ), "runtime_deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator", ], providers = [JavaInfo], ), "deps_exclude_labels": attr.label_list( default = [ ], ), "deps_exclude_paths": attr.string_list( default = [ "micrometer", "slf4j" ], ), "exclude_transitives": attr.bool( default = False, ), }) def _test_with_path_exclusions_with_exclude_transitives(ctx): """ Tests deps with path-based exclusions including exclude_transitives. """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] test_lib_name = "base_lib_with_deps_and_runtime_deps" expected = compute_expected_jars(ctx, test_lib_name) verify_runtime_and_compile_jars( ctx, env, javainfo_filtered, expected_compile_jars = expected["compile_jars"], expected_full_compile_jars = expected["full_compile_jars"], expected_transitive_compile_jars = expected["transitive_compile_jars"], expected_transitive_runtime_jars = expected["transitive_runtime_jars"], ) verify_dropped_counts(env, expected, expected_compile_dropped = "0", expected_full_compile_dropped = "0", expected_transitive_compile_dropped = ">0", expected_transitive_runtime_dropped = ">0") return unittest.end(env) with_path_exclusions_with_exclude_transitives_test = unittest.make(_test_with_path_exclusions_with_exclude_transitives, attrs = { "filtered": attr.label(providers = [JavaInfo]), "deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security", "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind", "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core", "@unmanaged_deps_filter//:jakarta_servlet_jsp_jakarta_servlet_jsp_api", ], providers = [JavaInfo], ), "runtime_deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator", ], providers = [JavaInfo], ), "deps_exclude_labels": attr.label_list( default = [ ], ), "deps_exclude_paths": attr.string_list( default = [ "micrometer", "slf4j" ], ), "exclude_transitives": attr.bool( default = True, ), }) def _test_multiple_exclusions_with_exclude_transitives(ctx): """ Tests multiple exclusion types (labels + paths) with exclude_transitives=True. """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] test_lib_name = "base_lib_with_deps_and_runtime_deps" expected = compute_expected_jars(ctx, test_lib_name) verify_runtime_and_compile_jars( ctx, env, javainfo_filtered, expected_compile_jars = expected["compile_jars"], expected_full_compile_jars = expected["full_compile_jars"], expected_transitive_compile_jars = expected["transitive_compile_jars"], expected_transitive_runtime_jars = expected["transitive_runtime_jars"], ) verify_dropped_counts(env, expected, expected_compile_dropped = "0", expected_full_compile_dropped = "0", expected_transitive_compile_dropped = ">0", expected_transitive_runtime_dropped = ">0") return unittest.end(env) multiple_exclusions_with_exclude_transitives_test = unittest.make(_test_multiple_exclusions_with_exclude_transitives, attrs = { "filtered": attr.label(providers = [JavaInfo]), "deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security", "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind", "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core", "@unmanaged_deps_filter//:jakarta_servlet_jsp_jakarta_servlet_jsp_api", ], providers = [JavaInfo], ), "runtime_deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator", ], providers = [JavaInfo], ), "deps_exclude_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:io_micrometer_micrometer_commons", "@unmanaged_deps_filter//:org_slf4j_jul_to_slf4j", ], ), "deps_exclude_paths": attr.string_list( default = [ "slf4j" ], ), "exclude_transitives": attr.bool( default = True, ), }) def _test_multiple_exclusions_without_exclude_transitives(ctx): """ Tests multiple exclusion types (labels + paths) with exclude_transitives=False. """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] test_lib_name = "base_lib_with_deps_and_runtime_deps" expected = compute_expected_jars(ctx, test_lib_name) verify_runtime_and_compile_jars( ctx, env, javainfo_filtered, expected_compile_jars = expected["compile_jars"], expected_full_compile_jars = expected["full_compile_jars"], expected_transitive_compile_jars = expected["transitive_compile_jars"], expected_transitive_runtime_jars = expected["transitive_runtime_jars"], ) verify_dropped_counts(env, expected, expected_compile_dropped = "0", expected_full_compile_dropped = "0", expected_transitive_compile_dropped = ">0", expected_transitive_runtime_dropped = ">0") return unittest.end(env) multiple_exclusions_without_exclude_transitives_test = unittest.make(_test_multiple_exclusions_without_exclude_transitives, attrs = { "filtered": attr.label(providers = [JavaInfo]), "deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security", "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind", "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core", "@unmanaged_deps_filter//:jakarta_servlet_jsp_jakarta_servlet_jsp_api", ], providers = [JavaInfo], ), "runtime_deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator", ], providers = [JavaInfo], ), "deps_exclude_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:io_micrometer_micrometer_commons", "@unmanaged_deps_filter//:org_slf4j_jul_to_slf4j", ], ), "deps_exclude_paths": attr.string_list( default = [ "slf4j" ], ), "exclude_transitives": attr.bool( default = False, ), }) def _test_empty_exclusion_lists(ctx): """ Tests behavior when exclusion lists are empty. """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] test_lib_name = "base_lib_with_deps_and_runtime_deps" expected = compute_expected_jars(ctx, test_lib_name) verify_runtime_and_compile_jars( ctx, env, javainfo_filtered, expected_compile_jars = expected["compile_jars"], expected_full_compile_jars = expected["full_compile_jars"], expected_transitive_compile_jars = expected["transitive_compile_jars"], expected_transitive_runtime_jars = expected["transitive_runtime_jars"], ) verify_dropped_counts(env, expected, expected_compile_dropped = "0", expected_full_compile_dropped = "0", expected_transitive_compile_dropped = "0", expected_transitive_runtime_dropped = "0") return unittest.end(env) empty_exclusion_lists_test = unittest.make(_test_empty_exclusion_lists, attrs = { "filtered": attr.label(providers = [JavaInfo]), "deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security", "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind", "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core", "@unmanaged_deps_filter//:jakarta_servlet_jsp_jakarta_servlet_jsp_api", ], providers = [JavaInfo], ), "runtime_deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator", ], providers = [JavaInfo], ), "deps_exclude_labels": attr.label_list( default = [], ), "deps_exclude_paths": attr.string_list( default = [], ), "exclude_transitives": attr.bool( default = False, ), }) def _test_path_based_exclusions_comprehensive(ctx): """ Tests comprehensive path-based exclusions with various patterns. """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] test_lib_name = "base_lib_with_deps_and_runtime_deps" expected = compute_expected_jars(ctx, test_lib_name) verify_runtime_and_compile_jars( ctx, env, javainfo_filtered, expected_compile_jars = expected["compile_jars"], expected_full_compile_jars = expected["full_compile_jars"], expected_transitive_compile_jars = expected["transitive_compile_jars"], expected_transitive_runtime_jars = expected["transitive_runtime_jars"], ) # Additional verification: ensure excluded patterns are not present transitive_runtime_jars = [jar.basename for jar in javainfo_filtered.transitive_runtime_jars.to_list()] for pattern in ["micrometer", "slf4j", "logback"]: for jar in transitive_runtime_jars: asserts.true(env, pattern not in jar, "Excluded pattern '{}' found in JAR: {}".format(pattern, jar)) verify_dropped_counts(env, expected, expected_compile_dropped = "0", expected_full_compile_dropped = "0", expected_transitive_compile_dropped = ">0", expected_transitive_runtime_dropped = ">0") return unittest.end(env) path_based_exclusions_comprehensive_test = unittest.make(_test_path_based_exclusions_comprehensive, attrs = { "filtered": attr.label(providers = [JavaInfo]), "deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security", "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind", "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core", "@unmanaged_deps_filter//:jakarta_servlet_jsp_jakarta_servlet_jsp_api", ], providers = [JavaInfo], ), "runtime_deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator", ], providers = [JavaInfo], ), "deps_exclude_labels": attr.label_list( default = [], ), "deps_exclude_paths": attr.string_list( default = [ "micrometer", "slf4j", "logback" ], ), "exclude_transitives": attr.bool( default = False, ), }) def _test_runtime_deps_only_A(ctx): """ Tests behavior when only runtime_deps are provided (no deps). """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] test_lib_name = "base_lib_with_runtime_deps" expected = compute_expected_jars(ctx, test_lib_name) verify_runtime_and_compile_jars( ctx, env, javainfo_filtered, expected_compile_jars = [], expected_full_compile_jars = expected["full_compile_jars"], expected_transitive_compile_jars = [], expected_transitive_runtime_jars = expected["transitive_runtime_jars"], ) # Runtime deps should not contribute to compile-time JARs compile_jars = [jar.basename for jar in javainfo_filtered.compile_jars.to_list()] full_compile_jars = [jar.basename for jar in javainfo_filtered.full_compile_jars.to_list()] asserts.equals(env, len(compile_jars), 0, "Expected no compile JARs when only runtime_deps provided, got: {}".format(len(compile_jars))) # Note: full_compile_jars is not empty because the output_jar is a full_compile_jar asserts.equals(env, len(full_compile_jars), 1, "Expected no full compile JARs when only runtime_deps provided, got: {}".format(len(full_compile_jars))) verify_dropped_counts(env, expected, expected_compile_dropped = "0", expected_full_compile_dropped = "0", expected_transitive_compile_dropped = "0", expected_transitive_runtime_dropped = "0") return unittest.end(env) runtime_deps_only_A_test = unittest.make(_test_runtime_deps_only_A, attrs = { "filtered": attr.label(providers = [JavaInfo]), "deps_labels": attr.label_list( default = [], ), "runtime_deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator", ], providers = [JavaInfo], ), "deps_exclude_labels": attr.label_list( default = [], ), "deps_exclude_paths": attr.string_list( default = [], ), "exclude_transitives": attr.bool( default = False, ), }) def _test_runtime_deps_only_B(ctx): """ Tests behavior when only runtime_deps are provided (no deps). """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] test_lib_name = "base_lib_with_runtime_deps" expected = compute_expected_jars(ctx, test_lib_name) verify_runtime_and_compile_jars( ctx, env, javainfo_filtered, expected_compile_jars = expected["compile_jars"], expected_full_compile_jars = expected["full_compile_jars"], expected_transitive_compile_jars = expected["transitive_compile_jars"], expected_transitive_runtime_jars = expected["transitive_runtime_jars"], ) verify_dropped_counts(env, expected, expected_compile_dropped = "0", expected_full_compile_dropped = "0", expected_transitive_compile_dropped = "0", expected_transitive_runtime_dropped = "0") return unittest.end(env) runtime_deps_only_B_test = unittest.make(_test_runtime_deps_only_B, attrs = { "filtered": attr.label(providers = [JavaInfo]), "deps_labels": attr.label_list( default = [], ), "runtime_deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator", ], providers = [JavaInfo], ), "deps_exclude_labels": attr.label_list( default = [], ), "deps_exclude_paths": attr.string_list( default = [], ), "exclude_transitives": attr.bool( default = False, ), }) def _test_single_runtime_dep_with_exclusion_A(ctx): """ Tests behavior with a single runtime dependency and exclusions. """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] test_lib_name = "base_lib_with_single_runtime_dep" expected = compute_expected_jars(ctx, test_lib_name) verify_runtime_and_compile_jars( ctx, env, javainfo_filtered, expected_compile_jars = [], expected_full_compile_jars = expected["full_compile_jars"], expected_transitive_compile_jars = [], expected_transitive_runtime_jars = expected["transitive_runtime_jars"], ) # Runtime deps should not contribute to compile-time JARs compile_jars = [jar.basename for jar in javainfo_filtered.compile_jars.to_list()] full_compile_jars = [jar.basename for jar in javainfo_filtered.full_compile_jars.to_list()] asserts.equals(env, len(compile_jars), 0, "Expected no compile JARs when only runtime_deps provided, got: {}".format(len(compile_jars))) # Note: full_compile_jars is not empty because the output_jar is a full_compile_jar asserts.equals(env, len(full_compile_jars), 1, "Expected no full compile JARs when only runtime_deps provided, got: {}".format(len(full_compile_jars))) verify_dropped_counts(env, expected, expected_compile_dropped = "0", expected_full_compile_dropped = "0", expected_transitive_compile_dropped = "0", expected_transitive_runtime_dropped = ">0") return unittest.end(env) single_runtime_dep_with_exclusions_A_test = unittest.make(_test_single_runtime_dep_with_exclusion_A, attrs = { "filtered": attr.label(providers = [JavaInfo]), "deps_labels": attr.label_list( default = [], ), "runtime_deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", ], providers = [JavaInfo], ), "deps_exclude_labels": attr.label_list( default = [], ), "deps_exclude_paths": attr.string_list( default = [ "slf4j", ], ), "exclude_transitives": attr.bool( default = False, ), }) def _test_single_runtime_dep_with_exclusions_B(ctx): """ Tests behavior with a single runtime dependency and exclusions. """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] test_lib_name = "base_lib_with_single_runtime_dep" expected = compute_expected_jars(ctx, test_lib_name) verify_runtime_and_compile_jars( ctx, env, javainfo_filtered, expected_compile_jars = expected["compile_jars"], expected_full_compile_jars = expected["full_compile_jars"], expected_transitive_compile_jars = expected["transitive_compile_jars"], expected_transitive_runtime_jars = expected["transitive_runtime_jars"], ) verify_dropped_counts(env, expected, expected_compile_dropped = "0", expected_full_compile_dropped = "0", expected_transitive_compile_dropped = "0", expected_transitive_runtime_dropped = ">0") return unittest.end(env) single_runtime_dep_with_exclusions_B_test = unittest.make(_test_single_runtime_dep_with_exclusions_B, attrs = { "filtered": attr.label(providers = [JavaInfo]), "deps_labels": attr.label_list( default = [], ), "runtime_deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", ], providers = [JavaInfo], ), "deps_exclude_labels": attr.label_list( default = [], ), "deps_exclude_paths": attr.string_list( default = [ "slf4j", ], ), "exclude_transitives": attr.bool( default = False, ), }) def _test_compile_deps_only(ctx): """ Tests behavior when only deps are provided (no runtime_deps). """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] test_lib_name = "base_lib_with_deps" expected = compute_expected_jars(ctx, test_lib_name) verify_runtime_and_compile_jars( ctx, env, javainfo_filtered, expected_compile_jars = expected["compile_jars"], expected_full_compile_jars = expected["full_compile_jars"], expected_transitive_compile_jars = expected["transitive_compile_jars"], expected_transitive_runtime_jars = expected["transitive_runtime_jars"], ) # Compile deps should contribute to both compile and runtime JARs compile_jars = [jar.basename for jar in javainfo_filtered.compile_jars.to_list()] transitive_runtime_jars = [jar.basename for jar in javainfo_filtered.transitive_runtime_jars.to_list()] asserts.true(env, len(compile_jars) > 0, "Expected compile JARs when deps provided, got: {}".format(len(compile_jars))) asserts.true(env, len(transitive_runtime_jars) > 0, "Expected transitive runtime JARs when deps provided, got: {}".format(len(transitive_runtime_jars))) verify_dropped_counts(env, expected, expected_compile_dropped = "0", expected_full_compile_dropped = "0", expected_transitive_compile_dropped = "0", expected_transitive_runtime_dropped = "0") return unittest.end(env) compile_deps_only_test = unittest.make(_test_compile_deps_only, attrs = { "filtered": attr.label(providers = [JavaInfo]), "deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security", "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind", "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core", "@unmanaged_deps_filter//:jakarta_servlet_jsp_jakarta_servlet_jsp_api", ], providers = [JavaInfo], ), "runtime_deps_labels": attr.label_list( default = [], ), "deps_exclude_labels": attr.label_list( default = [], ), "deps_exclude_paths": attr.string_list( default = [], ), "exclude_transitives": attr.bool( default = False, ), }) def _test_single_dep_with_exclusions(ctx): """ Tests behavior with a single dependency and exclusions. """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] test_lib_name = "base_lib_with_single_dep" expected = compute_expected_jars(ctx, test_lib_name) verify_runtime_and_compile_jars( ctx, env, javainfo_filtered, expected_compile_jars = expected["compile_jars"], expected_full_compile_jars = expected["full_compile_jars"], expected_transitive_compile_jars = expected["transitive_compile_jars"], expected_transitive_runtime_jars = expected["transitive_runtime_jars"], ) verify_dropped_counts(env, expected, expected_compile_dropped = "0", expected_full_compile_dropped = "0", expected_transitive_compile_dropped = ">0", expected_transitive_runtime_dropped = ">0") return unittest.end(env) single_dep_with_exclusions_test = unittest.make(_test_single_dep_with_exclusions, attrs = { "filtered": attr.label(providers = [JavaInfo]), "deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", ], providers = [JavaInfo], ), "runtime_deps_labels": attr.label_list( default = [], ), "deps_exclude_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:io_micrometer_micrometer_commons", ], ), "deps_exclude_paths": attr.string_list( default = [], ), "exclude_transitives": attr.bool( default = False, ), }) def _test_one_compile_one_runtime_dep(ctx): """ Tests behavior with exactly one compile dep and one runtime dep. """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] test_lib_name = "base_lib_with_single_dep_and_runtime_dep" expected = compute_expected_jars(ctx, test_lib_name) verify_runtime_and_compile_jars( ctx, env, javainfo_filtered, expected_compile_jars = expected["compile_jars"], expected_full_compile_jars = expected["full_compile_jars"], expected_transitive_compile_jars = expected["transitive_compile_jars"], expected_transitive_runtime_jars = expected["transitive_runtime_jars"], ) verify_dropped_counts(env, expected, expected_compile_dropped = "0", expected_full_compile_dropped = "0", expected_transitive_compile_dropped = "0", expected_transitive_runtime_dropped = "0") return unittest.end(env) one_compile_one_runtime_dep_test = unittest.make(_test_one_compile_one_runtime_dep, attrs = { "filtered": attr.label(providers = [JavaInfo]), "deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", ], providers = [JavaInfo], ), "runtime_deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", ], providers = [JavaInfo], ), "deps_exclude_labels": attr.label_list( default = [], ), "deps_exclude_paths": attr.string_list( default = [], ), "exclude_transitives": attr.bool( default = False, ), }) def _test_path_patterns_with_special_characters(ctx): """ Tests behavior with path patterns containing special characters. """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] test_lib_name = "base_lib_with_deps_and_runtime_deps" expected = compute_expected_jars(ctx, test_lib_name) verify_runtime_and_compile_jars( ctx, env, javainfo_filtered, expected_compile_jars = expected["compile_jars"], expected_full_compile_jars = expected["full_compile_jars"], expected_transitive_compile_jars = expected["transitive_compile_jars"], expected_transitive_runtime_jars = expected["transitive_runtime_jars"], ) verify_dropped_counts(env, expected, expected_compile_dropped = "0", expected_full_compile_dropped = "0", expected_transitive_compile_dropped = ">0", expected_transitive_runtime_dropped = ">0") return unittest.end(env) path_patterns_with_special_characters_test = unittest.make(_test_path_patterns_with_special_characters, attrs = { "filtered": attr.label(providers = [JavaInfo]), "deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security", "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind", "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core", "@unmanaged_deps_filter//:jakarta_servlet_jsp_jakarta_servlet_jsp_api", ], providers = [JavaInfo], ), "runtime_deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator", ], providers = [JavaInfo], ), "deps_exclude_labels": attr.label_list( default = [], ), "deps_exclude_paths": attr.string_list( default = [ "io.micrometer", # Pattern with dot "to-slf4j", # Pattern with hyphen ], ), "exclude_transitives": attr.bool( default = True, ), }) def _test_case_sensitive_pattern_matching(ctx): """ Tests case sensitivity in path pattern matching. """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] test_lib_name = "base_lib_with_deps_and_runtime_deps" expected = compute_expected_jars(ctx, test_lib_name) verify_runtime_and_compile_jars( ctx, env, javainfo_filtered, expected_compile_jars = expected["compile_jars"], expected_full_compile_jars = expected["full_compile_jars"], expected_transitive_compile_jars = expected["transitive_compile_jars"], expected_transitive_runtime_jars = expected["transitive_runtime_jars"], ) verify_dropped_counts(env, expected, expected_compile_dropped = "0", expected_full_compile_dropped = "0", expected_transitive_compile_dropped = "0", expected_transitive_runtime_dropped = "0") return unittest.end(env) case_sensitive_pattern_matching_test = unittest.make(_test_case_sensitive_pattern_matching, attrs = { "filtered": attr.label(providers = [JavaInfo]), "deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security", "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind", "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core", "@unmanaged_deps_filter//:jakarta_servlet_jsp_jakarta_servlet_jsp_api", ], providers = [JavaInfo], ), "runtime_deps_labels": attr.label_list( default = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator", ], providers = [JavaInfo], ), "deps_exclude_labels": attr.label_list( default = [], ), "deps_exclude_paths": attr.string_list( default = [ "SPRING", # Uppercase pattern "Jackson", # Mixed case pattern "HIBERNATE", # Uppercase pattern ], ), "exclude_transitives": attr.bool( default = False, ), }) ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/src/main/java/com/depsfilter/A.java ================================================ package com.depsfilter; public class A { int a; public A() { a = 1; } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/src/test/java/com/depsfilter/DepsFilterCaseSensitivePatternMatchingTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.Set; import org.junit.BeforeClass; import org.junit.Test; public class DepsFilterCaseSensitivePatternMatchingTest { @BeforeClass public static void setUp() { DependencyGraphTestConfig.initialize(); } @Test public void testCaseSensitivePatternMatching() { Set availableDeps = Set.copyOf(DepsFilterTestHelper.computeClasspathDependencies()); Set excludedPatterns = Set.of("SPRING", "Jackson", "HIBERNATE"); Set expectedRuntimeDeps = DependencyGraphTestConfig.getExpectedJarsForPathExclusionsFiltered( excludedPatterns, false); expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/DepsFilterCaseSensitivePatternMatchingTest.jar"); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/libbase_lib_with_deps_and_runtime_deps.jar"); assertThat(availableDeps).isEqualTo(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/src/test/java/com/depsfilter/DepsFilterCompileDepsOnlyTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.Set; import org.junit.BeforeClass; import org.junit.Test; public class DepsFilterCompileDepsOnlyTest { @BeforeClass public static void setUp() { DependencyGraphTestConfig.initialize(); } @Test public void testCompileDepsOnly() { Set availableDeps = Set.copyOf(DepsFilterTestHelper.computeClasspathDependencies()); Set depsLabels = Set.of( "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security", "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind", "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core", "@unmanaged_deps_filter//:jakarta_servlet_jsp_jakarta_servlet_jsp_api" ); Set runtimeDepsLabels = Set.of(); Set excludedLabels = Set.of(); Set excludedPatterns = Set.of(); boolean excludeTransitives = false; Set expectedRuntimeDeps = DependencyGraphTestConfig.getExpectedJarsForCustomDepsFiltered( depsLabels, runtimeDepsLabels, excludedLabels, excludedPatterns, excludeTransitives); expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/DepsFilterCompileDepsOnlyTest.jar"); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/libbase_lib_with_deps.jar"); assertThat(availableDeps).isEqualTo(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/src/test/java/com/depsfilter/DepsFilterEmptyExclusionsTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.Set; import org.junit.BeforeClass; import org.junit.Test; public class DepsFilterEmptyExclusionsTest { @BeforeClass public static void setUp() { DependencyGraphTestConfig.initialize(); } @Test public void testEmptyExclusions() { Set availableDeps = Set.copyOf(DepsFilterTestHelper.computeClasspathDependencies()); Set expectedRuntimeDeps = DependencyGraphTestConfig.getExpectedJarsForNoFilteringFiltered(); expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/DepsFilterEmptyExclusionsTest.jar"); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/libbase_lib_with_deps_and_runtime_deps.jar"); assertThat(availableDeps).isEqualTo(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/src/test/java/com/depsfilter/DepsFilterExcludeTransitiveTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.Set; import org.junit.BeforeClass; import org.junit.Test; public class DepsFilterExcludeTransitiveTest { @BeforeClass public static void setUp() { DependencyGraphTestConfig.initialize(); } @Test public void testExcludeTransitive() { Set availableDeps = Set.copyOf(DepsFilterTestHelper.computeClasspathDependencies()); Set excludedLabels = Set.of( "@unmanaged_deps_filter//:io_micrometer_micrometer_commons", "@unmanaged_deps_filter//:org_slf4j_jul_to_slf4j" ); Set expectedRuntimeDeps = DependencyGraphTestConfig.getExpectedJarsForLabelExclusionsFiltered( excludedLabels, true); expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/DepsFilterExcludeTransitiveTest.jar"); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/libbase_lib_with_deps_and_runtime_deps.jar"); assertThat(availableDeps).isEqualTo(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/src/test/java/com/depsfilter/DepsFilterLabelExclusionsTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.Set; import java.util.HashSet; import org.junit.BeforeClass; import org.junit.Test; public class DepsFilterLabelExclusionsTest { @BeforeClass public static void setUp() { DependencyGraphTestConfig.initialize(); } @Test public void testLabelExclusions() { Set availableDeps = Set.copyOf(DepsFilterTestHelper.computeClasspathDependencies()); Set excludedLabels = Set.of( "@unmanaged_deps_filter//:io_micrometer_micrometer_commons", "@unmanaged_deps_filter//:org_slf4j_jul_to_slf4j" ); Set expectedRuntimeDeps = DependencyGraphTestConfig.getExpectedJarsForLabelExclusionsFiltered( excludedLabels, false); expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/DepsFilterLabelExclusionsTest.jar"); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/libbase_lib_with_deps_and_runtime_deps.jar"); assertThat(availableDeps).isEqualTo(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/src/test/java/com/depsfilter/DepsFilterMultipleExclusionsWithTransitivesTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.Set; import org.junit.BeforeClass; import org.junit.Test; public class DepsFilterMultipleExclusionsWithTransitivesTest { @BeforeClass public static void setUp() { DependencyGraphTestConfig.initialize(); } @Test public void testMultipleExclusionsWithTransitives() { Set availableDeps = Set.copyOf(DepsFilterTestHelper.computeClasspathDependencies()); Set excludedLabels = Set.of( "@unmanaged_deps_filter//:io_micrometer_micrometer_commons", "@unmanaged_deps_filter//:org_slf4j_jul_to_slf4j" ); Set excludedPatterns = Set.of("slf4j"); Set expectedRuntimeDeps = DependencyGraphTestConfig.getExpectedJarsForMultipleExclusionsFiltered( excludedLabels, excludedPatterns, true); expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/DepsFilterMultipleExclusionsWithTransitivesTest.jar"); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/libbase_lib_with_deps_and_runtime_deps.jar"); assertThat(availableDeps).isEqualTo(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/src/test/java/com/depsfilter/DepsFilterMultipleExclusionsWithoutTransitivesTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.Set; import org.junit.BeforeClass; import org.junit.Test; public class DepsFilterMultipleExclusionsWithoutTransitivesTest { @BeforeClass public static void setUp() { DependencyGraphTestConfig.initialize(); } @Test public void testMultipleExclusionsWithoutTransitives() { Set availableDeps = Set.copyOf(DepsFilterTestHelper.computeClasspathDependencies()); Set excludedLabels = Set.of( "@unmanaged_deps_filter//:io_micrometer_micrometer_commons", "@unmanaged_deps_filter//:org_slf4j_jul_to_slf4j" ); Set excludedPatterns = Set.of("slf4j"); Set expectedRuntimeDeps = DependencyGraphTestConfig.getExpectedJarsForMultipleExclusionsFiltered( excludedLabels, excludedPatterns, false); expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/DepsFilterMultipleExclusionsWithoutTransitivesTest.jar"); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/libbase_lib_with_deps_and_runtime_deps.jar"); assertThat(availableDeps).isEqualTo(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/src/test/java/com/depsfilter/DepsFilterNoFilteringTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.Set; import org.junit.BeforeClass; import org.junit.Test; public class DepsFilterNoFilteringTest { @BeforeClass public static void setUp() { DependencyGraphTestConfig.initialize(); } @Test public void testNoFiltering() { Set availableDeps = Set.copyOf(DepsFilterTestHelper.computeClasspathDependencies()); Set expectedRuntimeDeps = DependencyGraphTestConfig.getExpectedJarsForNoFilteringFiltered(); expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/DepsFilterNoFilteringTest.jar"); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/libbase_lib_with_deps_and_runtime_deps.jar"); assertThat(availableDeps).isEqualTo(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/src/test/java/com/depsfilter/DepsFilterOneCompileOneRuntimeDepTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.Set; import org.junit.BeforeClass; import org.junit.Test; public class DepsFilterOneCompileOneRuntimeDepTest { @BeforeClass public static void setUp() { DependencyGraphTestConfig.initialize(); } @Test public void testOneCompileOneRuntimeDep() { Set availableDeps = Set.copyOf(DepsFilterTestHelper.computeClasspathDependencies()); Set depsLabels = Set.of( "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa" ); Set runtimeDepsLabels = Set.of( "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client" ); Set excludedLabels = Set.of(); Set excludedPatterns = Set.of(); boolean excludeTransitives = false; Set expectedRuntimeDeps = DependencyGraphTestConfig.getExpectedJarsForCustomDepsFiltered( depsLabels, runtimeDepsLabels, excludedLabels, excludedPatterns, excludeTransitives); expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/DepsFilterOneCompileOneRuntimeDepTest.jar"); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/libbase_lib_with_single_dep_and_runtime_dep.jar"); assertThat(availableDeps).isEqualTo(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/src/test/java/com/depsfilter/DepsFilterPathBasedExclusionsComprehensiveTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.Set; import org.junit.BeforeClass; import org.junit.Test; public class DepsFilterPathBasedExclusionsComprehensiveTest { @BeforeClass public static void setUp() { DependencyGraphTestConfig.initialize(); } @Test public void testPathBasedExclusionsComprehensive() { Set availableDeps = Set.copyOf(DepsFilterTestHelper.computeClasspathDependencies()); Set excludedPatterns = Set.of("micrometer", "slf4j", "logback"); Set expectedRuntimeDeps = DependencyGraphTestConfig.getExpectedJarsForPathExclusionsFiltered( excludedPatterns, false); expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/DepsFilterPathBasedExclusionsComprehensiveTest.jar"); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/libbase_lib_with_deps_and_runtime_deps.jar"); assertThat(availableDeps).isEqualTo(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/src/test/java/com/depsfilter/DepsFilterPathExclusionsTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.Set; import org.junit.BeforeClass; import org.junit.Test; public class DepsFilterPathExclusionsTest { @BeforeClass public static void setUp() { DependencyGraphTestConfig.initialize(); } @Test public void testPathExclusions() { Set availableDeps = Set.copyOf(DepsFilterTestHelper.computeClasspathDependencies()); Set excludedPatterns = Set.of("micrometer", "slf4j"); Set expectedRuntimeDeps = DependencyGraphTestConfig.getExpectedJarsForPathExclusionsFiltered( excludedPatterns, false); expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/DepsFilterPathExclusionsTest.jar"); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/libbase_lib_with_deps_and_runtime_deps.jar"); assertThat(availableDeps).isEqualTo(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/src/test/java/com/depsfilter/DepsFilterPathExclusionsWithTransitivesTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.Set; import org.junit.BeforeClass; import org.junit.Test; public class DepsFilterPathExclusionsWithTransitivesTest { @BeforeClass public static void setUp() { DependencyGraphTestConfig.initialize(); } @Test public void testPathExclusionsWithTransitives() { Set availableDeps = Set.copyOf(DepsFilterTestHelper.computeClasspathDependencies()); Set excludedPatterns = Set.of("micrometer", "slf4j"); Set expectedRuntimeDeps = DependencyGraphTestConfig.getExpectedJarsForPathExclusionsFiltered( excludedPatterns, true); expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/DepsFilterPathExclusionsWithTransitivesTest.jar"); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/libbase_lib_with_deps_and_runtime_deps.jar"); assertThat(availableDeps).isEqualTo(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/src/test/java/com/depsfilter/DepsFilterPathPatternsWithSpecialCharactersTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.Set; import org.junit.BeforeClass; import org.junit.Test; public class DepsFilterPathPatternsWithSpecialCharactersTest { @BeforeClass public static void setUp() { DependencyGraphTestConfig.initialize(); } @Test public void testPathPatternsWithSpecialCharacters() { Set availableDeps = Set.copyOf(DepsFilterTestHelper.computeClasspathDependencies()); Set excludedPatterns = Set.of("io.micrometer", "to-slf4j"); Set expectedRuntimeDeps = DependencyGraphTestConfig.getExpectedJarsForPathExclusionsFiltered( excludedPatterns, true); expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/DepsFilterPathPatternsWithSpecialCharactersTest.jar"); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/libbase_lib_with_deps_and_runtime_deps.jar"); assertThat(availableDeps).isEqualTo(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/src/test/java/com/depsfilter/DepsFilterRuntimeDepsOnlyATest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.Set; import org.junit.BeforeClass; import org.junit.Test; public class DepsFilterRuntimeDepsOnlyATest { @BeforeClass public static void setUp() { DependencyGraphTestConfig.initialize(); } @Test public void testRuntimeDepsOnly() { Set availableDeps = Set.copyOf(DepsFilterTestHelper.computeClasspathDependencies()); Set depsLabels = Set.of(); Set runtimeDepsLabels = Set.of( "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator" ); Set excludedLabels = Set.of(); Set excludedPatterns = Set.of(); boolean excludeTransitives = false; Set expectedRuntimeDeps = DependencyGraphTestConfig.getExpectedJarsForCustomDepsFiltered( depsLabels, runtimeDepsLabels, excludedLabels, excludedPatterns, excludeTransitives); expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/DepsFilterRuntimeDepsOnlyATest.jar"); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/libbase_lib_with_runtime_deps.jar"); assertThat(availableDeps).isEqualTo(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/src/test/java/com/depsfilter/DepsFilterRuntimeDepsOnlyBTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.Set; import org.junit.BeforeClass; import org.junit.Test; public class DepsFilterRuntimeDepsOnlyBTest { @BeforeClass public static void setUp() { DependencyGraphTestConfig.initialize(); } @Test public void testRuntimeDepsOnly() { Set availableDeps = Set.copyOf(DepsFilterTestHelper.computeClasspathDependencies()); Set depsLabels = Set.of(); Set runtimeDepsLabels = Set.of( "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator" ); Set excludedLabels = Set.of(); Set excludedPatterns = Set.of(); boolean excludeTransitives = false; Set expectedRuntimeDeps = DependencyGraphTestConfig.getExpectedJarsForCustomDepsFiltered( depsLabels, runtimeDepsLabels, excludedLabels, excludedPatterns, excludeTransitives); expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/DepsFilterRuntimeDepsOnlyBTest.jar"); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/libbase_lib_with_runtime_deps.jar"); assertThat(availableDeps).isEqualTo(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/src/test/java/com/depsfilter/DepsFilterSingleDepWithExclusionsTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.Set; import org.junit.BeforeClass; import org.junit.Test; public class DepsFilterSingleDepWithExclusionsTest { @BeforeClass public static void setUp() { DependencyGraphTestConfig.initialize(); } @Test public void testSingleDepWithExclusions() { Set availableDeps = Set.copyOf(DepsFilterTestHelper.computeClasspathDependencies()); Set depsLabels = Set.of( "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa" ); Set runtimeDepsLabels = Set.of(); Set excludedLabels = Set.of( "@unmanaged_deps_filter//:io_micrometer_micrometer_commons" ); Set excludedPatterns = Set.of(); boolean excludeTransitives = false; Set expectedRuntimeDeps = DependencyGraphTestConfig.getExpectedJarsForCustomDepsFiltered( depsLabels, runtimeDepsLabels, excludedLabels, excludedPatterns, excludeTransitives); expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/DepsFilterSingleDepWithExclusionsTest.jar"); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/libbase_lib_with_single_dep.jar"); assertThat(availableDeps).isEqualTo(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/src/test/java/com/depsfilter/DepsFilterSingleRuntimeDepWithExclusionsATest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.Set; import org.junit.BeforeClass; import org.junit.Test; public class DepsFilterSingleRuntimeDepWithExclusionsATest { @BeforeClass public static void setUp() { DependencyGraphTestConfig.initialize(); } @Test public void testSingleRuntimeDepWithExclusions() { Set availableDeps = Set.copyOf(DepsFilterTestHelper.computeClasspathDependencies()); Set depsLabels = Set.of(); Set runtimeDepsLabels = Set.of("@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client"); Set excludedLabels = Set.of(); Set excludedPatterns = Set.of("slf4j"); boolean excludeTransitives = false; Set expectedRuntimeDeps = DependencyGraphTestConfig.getExpectedJarsForCustomDepsFiltered( depsLabels, runtimeDepsLabels, excludedLabels, excludedPatterns, excludeTransitives); expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/DepsFilterSingleRuntimeDepWithExclusionsATest.jar"); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/libbase_lib_with_single_runtime_dep.jar"); assertThat(availableDeps).isEqualTo(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/src/test/java/com/depsfilter/DepsFilterSingleRuntimeDepWithExclusionsBTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.Set; import org.junit.BeforeClass; import org.junit.Test; public class DepsFilterSingleRuntimeDepWithExclusionsBTest { @BeforeClass public static void setUp() { DependencyGraphTestConfig.initialize(); } @Test public void testSingleRuntimeDepWithExclusions() { Set availableDeps = Set.copyOf(DepsFilterTestHelper.computeClasspathDependencies()); Set depsLabels = Set.of(); Set runtimeDepsLabels = Set.of("@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client"); Set excludedLabels = Set.of(); Set excludedPatterns = Set.of("slf4j"); boolean excludeTransitives = false; Set expectedRuntimeDeps = DependencyGraphTestConfig.getExpectedJarsForCustomDepsFiltered( depsLabels, runtimeDepsLabels, excludedLabels, excludedPatterns, excludeTransitives); expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/DepsFilterSingleRuntimeDepWithExclusionsBTest.jar"); expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime_through_java_library/libbase_lib_with_single_runtime_dep.jar"); assertThat(availableDeps).isEqualTo(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_1/BUILD ================================================ load("//springboot/deps_filter_rules:deps_filter.bzl", "deps_filter") load( "//springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_1:compile_and_runtime_test.bzl", "no_filtering_test", "filtered_deps_test", "filtered_deps_exclude_transitive_test", "path_based_exclusions_test", "interface_implementation_jars_test", "multiple_exclusions_with_transitive_test", "multiple_exclusions_without_transitive_test", "empty_exclusion_lists_test", "multiple_paths_test", ) # Dependency Graph Structure: # base_lib # / \ # A (c) G (r) # / \ | # / \ | # / \ | # B (c) E (r) / # | | / # | | / # | F (c) # \ / # C (c) # | # D (r) java_library( name = "lib_a", srcs = ["src/main/java/com/depsfilter/A.java"], deps = [ ":lib_b", # A -> B (c) ], runtime_deps = [ ":lib_e", # A -> E (r) ], ) java_library( name = "lib_b", srcs = ["src/main/java/com/depsfilter/B.java"], deps = [":lib_c"], # B -> C (c) ) java_library( name = "lib_c", srcs = ["src/main/java/com/depsfilter/C.java"], runtime_deps = [":lib_d"], # C -> D (r) ) java_library( name = "lib_d", srcs = ["src/main/java/com/depsfilter/D.java"], ) java_library( name = "lib_e", srcs = ["src/main/java/com/depsfilter/E.java"], deps = [":lib_f"], # E -> F (c) ) java_library( name = "lib_f", srcs = ["src/main/java/com/depsfilter/F.java"], deps = [":lib_c"], # F -> C (c) ) java_library( name = "lib_g", srcs = ["src/main/java/com/depsfilter/G.java"], deps = [":lib_f"], # G -> F (c) ) # Consumer library that uses the filtered dependencies java_library( name = "base_lib", srcs = ["src/main/java/com/depsfilter/H.java"], deps = [":lib_a"], # base_lib -> A (c) runtime_deps = [":lib_g"], # base_lib -> G (r) ) # Test 1: No filtering deps_filter( name = "filtered_deps", deps = [":base_lib"], ) no_filtering_test( name = "deps_filter_no_filtering_test", java_library = ":base_lib", deps_filter = ":filtered_deps", ) # Test 2: Exclude by labels and exclude_transitives = False deps_filter( name = "filtered_deps_exclude_b_g", deps = [":base_lib"], deps_exclude_labels = [":lib_b", ":lib_g"], ) filtered_deps_test( name = "deps_filter_exclude_b_g_test", filtered = ":filtered_deps_exclude_b_g", ) # Test 3: Exclude by labels and exclude_transitives = True deps_filter( name = "filtered_deps_exclude_b_g_exclude_transitive", deps = [":base_lib"], deps_exclude_labels = [":lib_b", ":lib_g"], exclude_transitives = True, ) filtered_deps_exclude_transitive_test( name = "deps_filter_exclude_b_g_exclude_transitive_test", filtered = ":filtered_deps_exclude_b_g_exclude_transitive", ) # Test 4: Test for path-based exclusions deps_filter( name = "path_based_filtered_deps", deps = [":base_lib"], deps_exclude_paths = ["lib_b", "lib_f"], ) path_based_exclusions_test( name = "deps_filter_path_based_exclusions_test", filtered = ":path_based_filtered_deps", ) # Test 5: Interface vs Implementation JARs deps_filter( name = "interface_impl_filtered_deps", deps = [":base_lib"], deps_exclude_labels = [":lib_b", ":lib_g"], ) interface_implementation_jars_test( name = "deps_filter_interface_impl_test", filtered = ":interface_impl_filtered_deps", ) # Test 6: Multiple exclusions with exclude_transitives=True deps_filter( name = "multiple_exclusions_filtered_deps_1", deps = [":base_lib"], deps_exclude_labels = [":lib_b"], deps_exclude_paths = ["lib_g"], exclude_transitives = True, ) multiple_exclusions_with_transitive_test( name = "multiple_exclusions_with_transitive_test", filtered = ":multiple_exclusions_filtered_deps_1", ) # Test 7: Multiple exclusions with exclude_transitives=False deps_filter( name = "multiple_exclusions_filtered_deps_2", deps = [":base_lib"], deps_exclude_labels = [":lib_b"], deps_exclude_paths = ["lib_g"], exclude_transitives = False, ) multiple_exclusions_without_transitive_test( name = "multiple_exclusions_without_transitive_test", filtered = ":multiple_exclusions_filtered_deps_2", ) # Test 8: Empty exclusion lists deps_filter( name = "empty_exclusions_filtered_deps", deps = [":base_lib"], deps_exclude_paths = [], deps_exclude_labels = [], ) empty_exclusion_lists_test( name = "deps_filter_empty_exclusions_test", filtered = ":empty_exclusions_filtered_deps", ) # Test 9: Multiple paths handling deps_filter( name = "multiple_paths_filtered_deps", deps = [":base_lib"], deps_exclude_labels = [":lib_b", ":lib_g"], ) multiple_paths_test( name = "deps_filter_multiple_paths_test", filtered = ":multiple_paths_filtered_deps", ) toolchain( name = "unittest_toolchain", toolchain_type = "@bazel_skylib//toolchains/unittest:toolchain_type", toolchain = "@bazel_skylib//toolchains/unittest:toolchain", ) ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_1/compile_and_runtime_test.bzl ================================================ load("@bazel_skylib//lib:unittest.bzl", "asserts", "unittest") load("//springboot/deps_filter_rules/tests/test_utils:verification_utils.bzl", "verify_jars", "verify_runtime_and_compile_jars", "verify_jars_and_dropped_counts", "verify_dropped_counts" ) def _test_no_filtering(ctx): """ Tests that deps_filter preserves all dependencies when no exclusions are applied. Dependency Graph: base_lib / \\ A (c) G (r) / \\ | / \\ | / \\ | B (c) E (r) / | | / | | / | F (c) \\ / C (c) | D (r) Expected: All JARs from java_library must match deps_filter: - full_compile_jars: Implementation JARs (e.g., liblib_a.jar) - compile_jars: Interface JARs (e.g., liblib_a-hjar.jar) - transitive_compile_time_jars: Interface JARs from transitive deps - transitive_runtime_jars: Implementation JARs from transitive deps """ env = unittest.begin(ctx) java_lib_info = ctx.attr.java_library[JavaInfo] deps_filter_info = ctx.attr.deps_filter[JavaInfo] # Verify all JAR fields match between java_library and deps_filter jar_fields = [ "full_compile_jars", # Implementation JARs "compile_jars", # Interface JARs "transitive_compile_time_jars", # Transitive interface JARs "transitive_runtime_jars" # Transitive implementation JARs ] for jar_field in jar_fields: java_lib_jars = getattr(java_lib_info, jar_field) deps_filter_jars = getattr(deps_filter_info, jar_field) asserts.equals(env, type(java_lib_jars), type(deps_filter_jars), "JAR type mismatch: {} vs deps_filter".format(jar_field)) asserts.equals(env, java_lib_jars.to_list(), deps_filter_jars.to_list(), "JAR contents mismatch: {} vs deps_filter".format(jar_field)) return unittest.end(env) no_filtering_test = unittest.make(_test_no_filtering, attrs = { "java_library": attr.label(providers = [JavaInfo]), "deps_filter": attr.label(providers = [JavaInfo]), }) def _test_filtered_deps(ctx): """ Tests basic dependency filtering with label-based exclusions. Dependency Graph: base_lib / \\ A (c) G (r) / \\ | / \\ | / \\ | B (c) E (r) / | | / | | / | F (c) \\ / C (c) | D (r) Input: deps = [":base_lib"] deps_exclude_labels = [":lib_b", ":lib_g"] deps_exclude_paths = [] exclude_transitives = False Expected Output: JARs preserved: base_lib, A, E, F, C, D JARs excluded: B, G (by label, direct deps only, transitives preserved) Compile-time JARs: base_lib-hjar, A-hjar, C-hjar Runtime JARs: base_lib, A, E, F, C, D (all preserved deps + transitives) Reasoning: B,G excluded by label, but their transitives (C,D,F) are preserved """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] expected_compile_jars = [ "libbase_lib-hjar.jar", ] expected_full_compile_jars = [ "libbase_lib.jar", ] expected_transitive_runtime_jars = [ "libbase_lib.jar", "liblib_a.jar", "liblib_e.jar", "liblib_f.jar", "liblib_c.jar", "liblib_d.jar" ] expected_transitive_compile_jars = [ "libbase_lib-hjar.jar", "liblib_a-hjar.jar", "liblib_c-hjar.jar", ] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) filtered_deps_test = unittest.make(_test_filtered_deps, attrs = { "filtered": attr.label(providers = [JavaInfo]), }) def _test_filtered_deps_exclude_transitive(ctx): """ Tests dependency filtering with transitive exclusions. Dependency Graph: base_lib / \\ A (c) G (r) / \\ | / \\ | / \\ | B (c) E (r) / | | / | | / | F (c) \\ / C (c) | D (r) Input: deps = [":base_lib"] deps_exclude_labels = [":lib_b", ":lib_g"] deps_exclude_paths = [] exclude_transitives = True Expected Output: JARs preserved: base_lib, A, E JARs excluded: B, G (by label) and all their transitives Compile-time JARs: base_lib-hjar, A-hjar Runtime JARs: base_lib, A, E (only preserved deps, no transitives of excluded deps) Reasoning: B,G excluded by label with exclude_transitives=True, so C,D,F also excluded """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] expected_compile_jars = [ "libbase_lib-hjar.jar", ] expected_full_compile_jars = [ "libbase_lib.jar", ] expected_transitive_runtime_jars = [ "libbase_lib.jar", "liblib_a.jar", "liblib_e.jar", ] expected_transitive_compile_jars = [ "libbase_lib-hjar.jar", "liblib_a-hjar.jar", ] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) filtered_deps_exclude_transitive_test = unittest.make(_test_filtered_deps_exclude_transitive, attrs = { "filtered": attr.label(providers = [JavaInfo]), }) def _test_path_based_exclusions(ctx): """ Tests filtering based on path patterns in deps_exclude_paths. Dependency Graph: base_lib / \\ A (c) G (r) / \\ | / \\ | / \\ | B (c) E (r) / | | / | | / | F (c) \\ / C (c) | D (r) Input: deps = [":base_lib"] deps_exclude_labels = [] deps_exclude_paths = ["lib_b", "lib_f"] exclude_transitives = False Expected Output: JARs preserved: base_lib, A, E, C, D, G JARs excluded: B, F (by path pattern match, transitives may be preserved) Compile-time JARs: base_lib-hjar, A-hjar, C-hjar Runtime JARs: base_lib, A, E, C, D, G (all preserved deps + transitives not matching exclusion path patterns) Reasoning: B,F excluded by path pattern, but their transitives are preserved as they didn't match the pattern. """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] expected_compile_jars = [ "libbase_lib-hjar.jar", ] expected_full_compile_jars = [ "libbase_lib.jar", ] expected_transitive_runtime_jars = [ "libbase_lib.jar", "liblib_a.jar", "liblib_e.jar", "liblib_c.jar", "liblib_d.jar", "liblib_g.jar" ] expected_transitive_compile_jars = [ "libbase_lib-hjar.jar", "liblib_a-hjar.jar", "liblib_c-hjar.jar", ] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) path_based_exclusions_test = unittest.make(_test_path_based_exclusions, attrs = { "filtered": attr.label(providers = [JavaInfo]), }) def _test_interface_implementation_jars(ctx): """ Tests proper handling of interface (-hjar) and implementation JARs. Dependency Graph: base_lib / \\ A (c) G (r) / \\ | / \\ | / \\ | B (c) E (r) / | | / | | / | F (c) \\ / C (c) | D (r) Input: deps = [":base_lib"] deps_exclude_labels = [":lib_b", ":lib_g"] deps_exclude_paths = [] exclude_transitives = False Expected Output: compile_jars: libbase_lib-hjar.jar full_compile_jars: libbase_lib.jar """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] compile_jars = sorted([jar.basename for jar in javainfo_filtered.compile_jars.to_list()]) full_compile_jars = sorted([jar.basename for jar in javainfo_filtered.full_compile_jars.to_list()]) expected_compile_jars = ["libbase_lib-hjar.jar"] expected_full_compile_jars = ["libbase_lib.jar"] asserts.equals(env, compile_jars, expected_compile_jars) asserts.equals(env, full_compile_jars, expected_full_compile_jars) return unittest.end(env) interface_implementation_jars_test = unittest.make(_test_interface_implementation_jars, attrs = { "filtered": attr.label(providers = [JavaInfo]), }) def _test_multiple_exclusions_with_transitive(ctx): """ Tests multiple exclusion levels with exclude_transitives=True. Dependency Graph: base_lib / \\ A (c) G (r) / \\ | / \\ | / \\ | B (c) E (r) / | | / | | / | F (c) \\ / C (c) | D (r) Input: deps = [":base_lib"] deps_exclude_labels = [":lib_b"] deps_exclude_paths = ["lib_g"] exclude_transitives = True Expected Output: JARs preserved: base_lib, A, E, F JARs excluded: B and its transitives; G (not neccessarily its transitives as specified exclusion by path pattern is matched) Compile-time JARs: base_lib-hjar, A-hjar Runtime JARs: base_lib, A, E, F Reasoning: B excluded by label with exclude_transitives=True (C,D excluded); G excluded by exclusion path pattern (exclusion by path pattern doesn't exclude transitives) """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] expected_compile_jars = [ "libbase_lib-hjar.jar", ] expected_full_compile_jars = [ "libbase_lib.jar", ] expected_transitive_runtime_jars = [ "libbase_lib.jar", "liblib_a.jar", "liblib_e.jar", "liblib_f.jar", ] expected_transitive_compile_jars = [ "libbase_lib-hjar.jar", "liblib_a-hjar.jar", ] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) def _test_multiple_exclusions_without_transitive(ctx): """ Tests multiple exclusion levels with exclude_transitives=False. Dependency Graph: base_lib / \\ A (c) G (r) / \\ | / \\ | / \\ | B (c) E (r) / | | / | | / | F (c) \\ / C (c) | D (r) Input: deps = [":base_lib"] deps_exclude_labels = [":lib_b"] deps_exclude_paths = ["lib_g"] exclude_transitives = False Expected Output: JARs preserved: base_lib, A, E, F, C, D JARs excluded: B (by label, direct only); G (by path pattern match, direct only) Compile-time JARs: base_lib-hjar, A-hjar, C-hjar Runtime JARs: base_lib, A, E, F, C, D Reasoning: B excluded by label (direct only, and its transitives are preserved); G excluded by exclusion path pattern (exclusion by path pattern doesn't exclude transitives) """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] expected_compile_jars = [ "libbase_lib-hjar.jar", ] expected_full_compile_jars = [ "libbase_lib.jar", ] expected_transitive_runtime_jars = [ "libbase_lib.jar", "liblib_a.jar", "liblib_e.jar", "liblib_f.jar", "liblib_c.jar", "liblib_d.jar", ] expected_transitive_compile_jars = [ "libbase_lib-hjar.jar", "liblib_a-hjar.jar", "liblib_c-hjar.jar", ] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) multiple_exclusions_with_transitive_test = unittest.make(_test_multiple_exclusions_with_transitive, attrs = { "filtered": attr.label(providers = [JavaInfo]), }) multiple_exclusions_without_transitive_test = unittest.make(_test_multiple_exclusions_without_transitive, attrs = { "filtered": attr.label(providers = [JavaInfo]), }) def _test_empty_exclusion_lists(ctx): """ Tests behavior when exclusion lists are empty. Dependency Graph: base_lib / \\ A (c) G (r) / \\ | / \\ | / \\ | B (c) E (r) / | | / | | / | F (c) \\ / C (c) | D (r) Input: deps = [":base_lib"] deps_exclude_labels = [] deps_exclude_paths = [] exclude_transitives = False Expected Output: JARs preserved: base_lib, A, B, C, D, E, F, G Compile-time JARs: base_lib-hjar, A-hjar, B-hjar, C-hjar Runtime JARs: base_lib, A, B, C, D, E, F, G Reasoning: No exclusions applied, all dependencies preserved """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] expected_compile_jars = [ "libbase_lib-hjar.jar", ] expected_full_compile_jars = [ "libbase_lib.jar", ] expected_transitive_runtime_jars = [ "libbase_lib.jar", "liblib_a.jar", "liblib_b.jar", "liblib_c.jar", "liblib_d.jar", "liblib_e.jar", "liblib_f.jar", "liblib_g.jar" ] expected_transitive_compile_jars = [ "libbase_lib-hjar.jar", "liblib_a-hjar.jar", "liblib_b-hjar.jar", "liblib_c-hjar.jar", ] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) empty_exclusion_lists_test = unittest.make(_test_empty_exclusion_lists, attrs = { "filtered": attr.label(providers = [JavaInfo]), }) def _test_multiple_paths(ctx): """ Tests handling of multiple paths to the same dependency. Dependency Graph: base_lib / \\ A (c) G (r) / \\ | / \\ | / \\ | B (c) E (r) / | | / | | / | F (c) \\ / C (c) | D (r) Input: deps = [":base_lib"] deps_exclude_labels = [":lib_b", ":lib_g"] deps_exclude_paths = [] exclude_transitives = False Expected Output: JARs preserved: base_lib, A, E, F, C, D JARs excluded: B, G (not duplicated if reachable via multiple paths) Compile-time JARs: base_lib-hjar, A-hjar, C-hjar Runtime JARs: base_lib, A, E, F, C, D Reasoning: B,G excluded by label, but transitives are preserved as exclude_transitives = False """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] expected_compile_jars = [ "libbase_lib-hjar.jar", ] expected_full_compile_jars = [ "libbase_lib.jar", ] expected_transitive_runtime_jars = [ "libbase_lib.jar", "liblib_a.jar", "liblib_e.jar", "liblib_f.jar", "liblib_c.jar", "liblib_d.jar" ] expected_transitive_compile_jars = [ "libbase_lib-hjar.jar", "liblib_a-hjar.jar", "liblib_c-hjar.jar", ] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) multiple_paths_test = unittest.make(_test_multiple_paths, attrs = { "filtered": attr.label(providers = [JavaInfo]), }) ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_1/src/main/java/com/depsfilter/A.java ================================================ package com.depsfilter; public class A { int a; private B b; // E is a runtime dependency, so no compile-time reference here public A() { a = 1; b = new B(); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_1/src/main/java/com/depsfilter/B.java ================================================ package com.depsfilter; public class B { private C c; public B() { c = new C(); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_1/src/main/java/com/depsfilter/C.java ================================================ package com.depsfilter; public class C { // D is a runtime dependency, so no compile-time reference here public C() { // No compile-time dependencies } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_1/src/main/java/com/depsfilter/D.java ================================================ package com.depsfilter; public class D { private int value; public D() { value = 4; } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_1/src/main/java/com/depsfilter/E.java ================================================ package com.depsfilter; public class E { private F f; public E() { f = new F(); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_1/src/main/java/com/depsfilter/F.java ================================================ package com.depsfilter; public class F { private C c; public F() { c = new C(); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_1/src/main/java/com/depsfilter/G.java ================================================ package com.depsfilter; public class G { private F f; public G() { f = new F(); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_1/src/main/java/com/depsfilter/H.java ================================================ package com.depsfilter; public class H { private A a; // G is a runtime dependency, so no compile-time reference here public H() { a = new A(); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/BUILD ================================================ load("//springboot/deps_filter_rules:deps_filter.bzl", "deps_filter") load( "//springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2:compile_and_runtime_test.bzl", "filtered_deps_test", "filtered_deps_exclude_transitive_test", "path_based_exclusions_test", "interface_implementation_jars_test", "multiple_exclusions_with_transitive_test", "multiple_exclusions_without_transitive_test", "empty_exclusion_lists_test", "multiple_paths_test", ) # Dependency Graph Structure: # J(r) A (c) H (r) I (c) # \ / \ | | # \ / \ G (r) | # \ / \ | / # B (c) E (r) / / # | | / / # | | / / # | | / / # | | / / # | F (c) # \ / # C (c) # | # D (r) java_library( name = "lib_a", srcs = ["src/main/java/com/depsfilter/A.java"], deps = [ ":lib_b", # A -> B (c) ], runtime_deps = [ ":lib_e", # A -> E (r) ], ) java_library( name = "lib_b", srcs = ["src/main/java/com/depsfilter/B.java"], deps = [":lib_c"], # B -> C (c) ) java_library( name = "lib_c", srcs = ["src/main/java/com/depsfilter/C.java"], runtime_deps = [":lib_d"], # C -> D (r) ) java_library( name = "lib_d", srcs = ["src/main/java/com/depsfilter/D.java"], ) java_library( name = "lib_e", srcs = ["src/main/java/com/depsfilter/E.java"], deps = [":lib_f"], # E -> F (c) ) java_library( name = "lib_f", srcs = ["src/main/java/com/depsfilter/F.java"], deps = [":lib_c"], # F -> C (c) ) java_library( name = "lib_g", srcs = ["src/main/java/com/depsfilter/G.java"], deps = [":lib_f"], # G -> F (c) ) java_library( name = "lib_h", srcs = ["src/main/java/com/depsfilter/H.java"], runtime_deps = [":lib_g"], # H -> G (r) ) java_library( name = "lib_i", srcs = ["src/main/java/com/depsfilter/H.java"], deps = [":lib_f"], # I -> F (c) ) java_library( name = "lib_j", srcs = ["src/main/java/com/depsfilter/J.java"], deps = [":lib_b"], # J -> B (c) ) # Test 1: No filtering # deps_filter( # name = "filtered_deps", # deps = [":lib_a", ":lib_i"], # runtime_deps = [":lib_h", ":lib_j"], # ) # We can't test this because we can't compare base_lib with deps_filter without base_lib as a dep # Test 2: Exclude by labels and exclude_transitives = False deps_filter( name = "filtered_deps_exclude_b_g", deps = [":lib_a", ":lib_i"], runtime_deps = [":lib_h", ":lib_j"], deps_exclude_labels = [":lib_b", ":lib_g"], ) filtered_deps_test( name = "deps_filter_exclude_b_g_test", filtered = ":filtered_deps_exclude_b_g", ) # Test 3: Exclude by labels and exclude_transitives = True deps_filter( name = "filtered_deps_exclude_b_g_exclude_transitive", deps = [":lib_a", ":lib_i"], runtime_deps = [":lib_h", ":lib_j"], deps_exclude_labels = [":lib_b", ":lib_g"], exclude_transitives = True, ) filtered_deps_exclude_transitive_test( name = "deps_filter_exclude_b_g_exclude_transitive_test", filtered = ":filtered_deps_exclude_b_g_exclude_transitive", ) # Test 4: Test for path-based exclusions deps_filter( name = "path_based_filtered_deps", deps = [":lib_a", ":lib_i"], runtime_deps = [":lib_h", ":lib_j"], deps_exclude_paths = ["lib_b", "lib_f"], ) path_based_exclusions_test( name = "deps_filter_path_based_exclusions_test", filtered = ":path_based_filtered_deps", ) # Test 5: Interface vs Implementation JARs deps_filter( name = "interface_impl_filtered_deps", deps = [":lib_a", ":lib_i"], runtime_deps = [":lib_h", ":lib_j"], deps_exclude_labels = [":lib_b", ":lib_g"], ) interface_implementation_jars_test( name = "deps_filter_interface_impl_test", filtered = ":interface_impl_filtered_deps", ) # Test 6: Multiple exclusions with exclude_transitives=True deps_filter( name = "multiple_exclusions_filtered_deps_1", deps = [":lib_a", ":lib_i"], runtime_deps = [":lib_h", ":lib_j"], deps_exclude_labels = [":lib_b"], deps_exclude_paths = ["lib_g"], exclude_transitives = True, ) multiple_exclusions_with_transitive_test( name = "multiple_exclusions_with_transitive_test", filtered = ":multiple_exclusions_filtered_deps_1", ) # Test 7: Multiple exclusions with exclude_transitives=False deps_filter( name = "multiple_exclusions_filtered_deps_2", deps = [":lib_a", ":lib_i"], runtime_deps = [":lib_h", ":lib_j"], deps_exclude_labels = [":lib_b"], deps_exclude_paths = ["lib_g"], exclude_transitives = False, ) multiple_exclusions_without_transitive_test( name = "multiple_exclusions_without_transitive_test", filtered = ":multiple_exclusions_filtered_deps_2", ) # Test 8: Empty exclusion lists deps_filter( name = "empty_exclusions_filtered_deps", deps = [":lib_a", ":lib_i"], runtime_deps = [":lib_h", ":lib_j"], deps_exclude_paths = [], deps_exclude_labels = [], ) empty_exclusion_lists_test( name = "deps_filter_empty_exclusions_test", filtered = ":empty_exclusions_filtered_deps", ) # Test 9: Multiple paths handling deps_filter( name = "multiple_paths_filtered_deps", deps = [":lib_a", ":lib_i"], runtime_deps = [":lib_h", ":lib_j"], deps_exclude_labels = [":lib_b", ":lib_g"], ) multiple_paths_test( name = "deps_filter_multiple_paths_test", filtered = ":multiple_paths_filtered_deps", ) test_deps = ["@unmanaged_deps_filter//:junit_junit", "@unmanaged_deps_filter//:org_assertj_assertj_core", ] # Java test targets java_test( name = "DepsFilterEmptyExclusionsTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterTestHelper.java", "src/test/java/com/depsfilter/DepsFilterEmptyExclusionsTest.java" ], deps = [":empty_exclusions_filtered_deps"] + test_deps, ) java_test( name = "DepsFilterFilteredDepsTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterTestHelper.java", "src/test/java/com/depsfilter/DepsFilterFilteredDepsTest.java" ], deps = [":filtered_deps_exclude_b_g"] + test_deps, ) java_test( name = "DepsFilterExcludeTransitiveTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterTestHelper.java", "src/test/java/com/depsfilter/DepsFilterExcludeTransitiveTest.java" ], deps = [":filtered_deps_exclude_b_g_exclude_transitive"] + test_deps, ) java_test( name = "DepsFilterPathBasedExclusionsTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterTestHelper.java", "src/test/java/com/depsfilter/DepsFilterPathBasedExclusionsTest.java" ], deps = [":path_based_filtered_deps"] + test_deps, ) java_test( name = "DepsFilterInterfaceImplementationTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterTestHelper.java", "src/test/java/com/depsfilter/DepsFilterInterfaceImplementationTest.java" ], deps = [":interface_impl_filtered_deps"] + test_deps, ) java_test( name = "DepsFilterMultipleExclusionsWithTransitiveTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterTestHelper.java", "src/test/java/com/depsfilter/DepsFilterMultipleExclusionsWithTransitiveTest.java" ], deps = [":multiple_exclusions_filtered_deps_1"] + test_deps, ) java_test( name = "DepsFilterMultipleExclusionsWithoutTransitiveTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterTestHelper.java", "src/test/java/com/depsfilter/DepsFilterMultipleExclusionsWithoutTransitiveTest.java" ], deps = [":multiple_exclusions_filtered_deps_2"] + test_deps, ) java_test( name = "DepsFilterMultiplePathsTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterTestHelper.java", "src/test/java/com/depsfilter/DepsFilterMultiplePathsTest.java" ], deps = [":multiple_paths_filtered_deps"] + test_deps, ) # load("//tools/common/bazel/deps_filter:deps_filter.bzl", "deps_filter") # deps_filter( # name = "flattened_filtered_deps", # deps = [":filtered_deps"], # ) # deps_filter( # name = "flattened_java_libary", # deps = [":lib_a"], # runtime_deps = [":lib_g"], # ) toolchain( name = "unittest_toolchain", toolchain_type = "@bazel_skylib//toolchains/unittest:toolchain_type", toolchain = "@bazel_skylib//toolchains/unittest:toolchain", ) ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/compile_and_runtime_test.bzl ================================================ load("@bazel_skylib//lib:unittest.bzl", "asserts", "unittest") load("//springboot/deps_filter_rules/tests/test_utils:verification_utils.bzl", "verify_jars", "verify_runtime_and_compile_jars", "verify_jars_and_dropped_counts", "verify_dropped_counts" ) # def _test_no_filtering(ctx): # We can't test this because we can't compare base_lib with deps_filter without base_lib as a dep def _test_filtered_deps(ctx): """ Tests basic dependency filtering with label-based exclusions. Dependency Graph: J(r) A (c) H (r) I (c) \\ / \\ | | \\ / \\ G (r) | \\ / \\ | / B (c) E (r) / / | | / / | | / / | | / / | | / / | F (c) \\ / C (c) | D (r) Input: deps = [":lib_a", ":lib_i] runtime_deps = [":lib_h", ":lib_j"] deps_exclude_labels = [":lib_b", ":lib_g"] deps_exclude_paths = [] exclude_transitives = False Expected Output: JARs preserved: A, I, C, D, E, F, H, J JARs excluded: B, G (by label, direct deps only, transitives preserved) Compile-time JARs: A-hjar, I-hjar, C-hjar, F-hjar Runtime JARs: A, I, C, D, E, F, H, J Reasoning: B,G excluded by label, but their transitives (C,D,F) are preserved """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] expected_compile_jars = [ "liblib_a-hjar.jar", "liblib_i-hjar.jar", ] expected_full_compile_jars = [ "liblib_a.jar", "liblib_i.jar", ] expected_transitive_runtime_jars = [ "liblib_a.jar", "liblib_c.jar", "liblib_d.jar", "liblib_e.jar", "liblib_f.jar", "liblib_h.jar", "liblib_i.jar", "liblib_j.jar", ] expected_transitive_compile_jars = [ "liblib_a-hjar.jar", "liblib_c-hjar.jar", "liblib_f-hjar.jar", "liblib_i-hjar.jar", ] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) filtered_deps_test = unittest.make(_test_filtered_deps, attrs = { "filtered": attr.label(providers = [JavaInfo]), }) def _test_filtered_deps_exclude_transitive(ctx): """ Tests dependency filtering with transitive exclusions. Dependency Graph: J(r) A (c) H (r) I (c) \\ / \\ | | \\ / \\ G (r) | \\ / \\ | / B (c) E (r) / / | | / / | | / / | | / / | | / / | F (c) \\ / C (c) | D (r) Input: deps = [":lib_a", ":lib_i] runtime_deps = [":lib_h", ":lib_j"] deps_exclude_labels = [":lib_b", ":lib_g"] deps_exclude_paths = [] exclude_transitives = True Expected Output: JARs preserved: A, I, E, H, J JARs excluded: B, G (by label) and all their transitives Compile-time JARs: A-hjar, I-hjar Runtime JARs: A, I, E, H, J (only preserved deps, no transitives of excluded deps) Reasoning: B,G excluded by label with exclude_transitives=True, so C,D,F also excluded """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] expected_compile_jars = [ "liblib_a-hjar.jar", "liblib_i-hjar.jar", ] expected_full_compile_jars = [ "liblib_a.jar", "liblib_i.jar", ] expected_transitive_runtime_jars = [ "liblib_a.jar", "liblib_e.jar", "liblib_h.jar", "liblib_i.jar", "liblib_j.jar", ] expected_transitive_compile_jars = [ "liblib_a-hjar.jar", "liblib_i-hjar.jar", ] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) filtered_deps_exclude_transitive_test = unittest.make(_test_filtered_deps_exclude_transitive, attrs = { "filtered": attr.label(providers = [JavaInfo]), }) def _test_path_based_exclusions(ctx): """ Tests filtering based on path patterns in deps_exclude_paths. Dependency Graph: J(r) A (c) H (r) I (c) \\ / \\ | | \\ / \\ G (r) | \\ / \\ | / B (c) E (r) / / | | / / | | / / | | / / | | / / | F (c) \\ / C (c) | D (r) Input: deps = [":lib_a", ":lib_i] runtime_deps = [":lib_h", ":lib_j"] deps_exclude_labels = [] deps_exclude_paths = ["lib_b", "lib_f"] exclude_transitives = False ## IMPORTANT_FEATURE Expected Output: JARs preserved: A, I, C, D, E, G, H, J JARs excluded: B, F (by path pattern match, transitives may be preserved) Compile-time JARs: A-hjar, I-hjar, C-hjar Runtime JARs: A, I, C, D, E, G, H, J (all preserved deps + transitives not matching exclusion path patterns) Reasoning: B,F excluded by path pattern, but their transitives are preserved as they didn't match the pattern """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] expected_compile_jars = [ "liblib_a-hjar.jar", "liblib_i-hjar.jar", ] expected_full_compile_jars = [ "liblib_a.jar", "liblib_i.jar", ] expected_transitive_runtime_jars = [ "liblib_a.jar", "liblib_c.jar", "liblib_d.jar", "liblib_e.jar", "liblib_g.jar", "liblib_h.jar", "liblib_i.jar", "liblib_j.jar", ] expected_transitive_compile_jars = [ "liblib_a-hjar.jar", "liblib_c-hjar.jar", "liblib_i-hjar.jar", ] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) path_based_exclusions_test = unittest.make(_test_path_based_exclusions, attrs = { "filtered": attr.label(providers = [JavaInfo]), }) def _test_interface_implementation_jars(ctx): """ Tests proper handling of interface (-hjar) and implementation JARs. Dependency Graph: J(r) A (c) H (r) I (c) \\ / \\ | | \\ / \\ G (r) | \\ / \\ | / B (c) E (r) / / | | / / | | / / | | / / | | / / | F (c) \\ / C (c) | D (r) Input: deps = [":lib_a", ":lib_i] runtime_deps = [":lib_h", ":lib_j"] deps_exclude_labels = [":lib_b", ":lib_g"] deps_exclude_paths = [] exclude_transitives = False Expected Output: compile_jars: liblib_a-hjar.jar, liblib_i-hjar.jar full_compile_jars: liblib_a.jar, liblib_i.jar """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] compile_jars = sorted([jar.basename for jar in javainfo_filtered.compile_jars.to_list()]) full_compile_jars = sorted([jar.basename for jar in javainfo_filtered.full_compile_jars.to_list()]) expected_compile_jars = [ "liblib_a-hjar.jar", "liblib_i-hjar.jar", ] expected_full_compile_jars = [ "liblib_a.jar", "liblib_i.jar", ] asserts.equals(env, compile_jars, expected_compile_jars) asserts.equals(env, full_compile_jars, expected_full_compile_jars) return unittest.end(env) interface_implementation_jars_test = unittest.make(_test_interface_implementation_jars, attrs = { "filtered": attr.label(providers = [JavaInfo]), }) def _test_multiple_exclusions_with_transitive(ctx): """ Tests multiple exclusion levels with exclude_transitives=True. Dependency Graph: J(r) A (c) H (r) I (c) \\ / \\ | | \\ / \\ G (r) | \\ / \\ | / B (c) E (r) / / | | / / | | / / | | / / | | / / | F (c) \\ / C (c) | D (r) Input: deps = [":lib_a", ":lib_i] runtime_deps = [":lib_h", ":lib_j"] deps_exclude_labels = [":lib_b"] deps_exclude_paths = ["lib_g"] exclude_transitives = True Expected Output: JARs preserved: A, I, E, F, H, J JARs excluded: B and its transitives; G (not neccessarily its transitives as specified exclusion by path pattern is matched) Compile-time JARs: A-hjar, I-hjar, F-hjar Runtime JARs: A, I, E, F, H, J Reasoning: B excluded by label with exclude_transitives=True (C,D excluded); G excluded by exclusion path pattern (exclusion by path pattern doesn't exclude transitives) """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] expected_compile_jars = [ "liblib_a-hjar.jar", "liblib_i-hjar.jar", ] expected_full_compile_jars = [ "liblib_a.jar", "liblib_i.jar", ] expected_transitive_runtime_jars = [ "liblib_a.jar", "liblib_e.jar", "liblib_f.jar", "liblib_h.jar", "liblib_i.jar", "liblib_j.jar", ] expected_transitive_compile_jars = [ "liblib_a-hjar.jar", "liblib_f-hjar.jar", "liblib_i-hjar.jar", ] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) def _test_multiple_exclusions_without_transitive(ctx): """ Tests multiple exclusion levels with exclude_transitives=False. Dependency Graph: J(r) A (c) H (r) I (c) \\ / \\ | | \\ / \\ G (r) | \\ / \\ | / B (c) E (r) / / | | / / | | / / | | / / | | / / | F (c) \\ / C (c) | D (r) Input: deps = [":lib_a", ":lib_i] runtime_deps = [":lib_h", ":lib_j"] deps_exclude_labels = [":lib_b"] deps_exclude_paths = ["lib_g"] exclude_transitives = False Expected Output: JARs preserved: A, I, C, D, E, F, H, J JARs excluded: B (by label, direct only); G (by path pattern match, direct only) Compile-time JARs: A-hjar, I-hjar, C-hjar, F-hjar Runtime JARs: A, I, C, D, E, F, H, J Reasoning: B excluded by label (direct only, and its transitives are preserved); G excluded by exclusion path pattern (exclusion by path pattern doesn't exclude transitives) """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] expected_compile_jars = [ "liblib_a-hjar.jar", "liblib_i-hjar.jar", ] expected_full_compile_jars = [ "liblib_a.jar", "liblib_i.jar", ] expected_transitive_runtime_jars = [ "liblib_a.jar", "liblib_c.jar", "liblib_d.jar", "liblib_e.jar", "liblib_f.jar", "liblib_h.jar", "liblib_i.jar", "liblib_j.jar", ] expected_transitive_compile_jars = [ "liblib_a-hjar.jar", "liblib_c-hjar.jar", "liblib_f-hjar.jar", "liblib_i-hjar.jar", ] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) multiple_exclusions_with_transitive_test = unittest.make(_test_multiple_exclusions_with_transitive, attrs = { "filtered": attr.label(providers = [JavaInfo]), }) multiple_exclusions_without_transitive_test = unittest.make(_test_multiple_exclusions_without_transitive, attrs = { "filtered": attr.label(providers = [JavaInfo]), }) def _test_empty_exclusion_lists(ctx): """ Tests behavior when exclusion lists are empty. Dependency Graph: J(r) A (c) H (r) I (c) \\ / \\ | | \\ / \\ G (r) | \\ / \\ | / B (c) E (r) / / | | / / | | / / | | / / | | / / | F (c) \\ / C (c) | D (r) Input: deps = [":lib_a", ":lib_i] runtime_deps = [":lib_h", ":lib_j"] deps_exclude_labels = [] deps_exclude_paths = [] exclude_transitives = False Expected Output: JARs preserved: A, I, B, C, D, E, F, G, H, J Compile-time JARs: A-hjar, I-hjar, B-hjar, C-hjar, F-hjar Runtime JARs: A, I, B, C, D, E, F, G, H, J Reasoning: No exclusions applied, all dependencies preserved """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] expected_compile_jars = [ "liblib_a-hjar.jar", "liblib_i-hjar.jar", ] expected_full_compile_jars = [ "liblib_a.jar", "liblib_i.jar", ] expected_transitive_runtime_jars = [ "liblib_a.jar", "liblib_b.jar", "liblib_c.jar", "liblib_d.jar", "liblib_e.jar", "liblib_f.jar", "liblib_g.jar", "liblib_h.jar", "liblib_i.jar", "liblib_j.jar", ] expected_transitive_compile_jars = [ "liblib_a-hjar.jar", "liblib_b-hjar.jar", "liblib_c-hjar.jar", "liblib_f-hjar.jar", "liblib_i-hjar.jar", ] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) empty_exclusion_lists_test = unittest.make(_test_empty_exclusion_lists, attrs = { "filtered": attr.label(providers = [JavaInfo]), }) def _test_multiple_paths(ctx): """ Tests handling of multiple paths to the same dependency. Dependency Graph: J(r) A (c) H (r) I (c) \\ / \\ | | \\ / \\ G (r) | \\ / \\ | / B (c) E (r) / / | | / / | | / / | | / / | | / / | F (c) \\ / C (c) | D (r) # IMPORTANT_FEATURE Input: deps = [":lib_a", ":lib_i] runtime_deps = [":lib_h", ":lib_j"] deps_exclude_labels = [":lib_b", ":lib_g"] deps_exclude_paths = [] exclude_transitives = False Expected Output: JARs preserved: A, I, C, D, E, F, H, J JARs excluded: B, G (not duplicated if reachable via multiple paths) Compile-time JARs: A-hjar, I-hjar, C-hjar, F-hjar Runtime JARs: A, I, C, D, E, F, H, J Reasoning: B,G excluded by label, but transitives are preserved as exclude_transitives = False """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] expected_compile_jars = [ "liblib_a-hjar.jar", "liblib_i-hjar.jar", ] expected_full_compile_jars = [ "liblib_a.jar", "liblib_i.jar", ] expected_transitive_runtime_jars = [ "liblib_a.jar", "liblib_c.jar", "liblib_d.jar", "liblib_e.jar", "liblib_f.jar", "liblib_h.jar", "liblib_i.jar", "liblib_j.jar", ] expected_transitive_compile_jars = [ "liblib_a-hjar.jar", "liblib_c-hjar.jar", "liblib_f-hjar.jar", "liblib_i-hjar.jar", ] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) multiple_paths_test = unittest.make(_test_multiple_paths, attrs = { "filtered": attr.label(providers = [JavaInfo]), }) ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/src/main/java/com/depsfilter/A.java ================================================ package com.depsfilter; public class A { int a; private B b; // E is a runtime dependency, so no compile-time reference here public A() { a = 1; b = new B(); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/src/main/java/com/depsfilter/B.java ================================================ package com.depsfilter; public class B { private C c; public B() { c = new C(); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/src/main/java/com/depsfilter/C.java ================================================ package com.depsfilter; public class C { // D is a runtime dependency, so no compile-time reference here public C() { // No compile-time dependencies } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/src/main/java/com/depsfilter/D.java ================================================ package com.depsfilter; public class D { private int value; public D() { value = 4; } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/src/main/java/com/depsfilter/E.java ================================================ package com.depsfilter; public class E { private F f; public E() { f = new F(); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/src/main/java/com/depsfilter/F.java ================================================ package com.depsfilter; public class F { private C c; public F() { c = new C(); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/src/main/java/com/depsfilter/G.java ================================================ package com.depsfilter; public class G { private F f; public G() { f = new F(); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/src/main/java/com/depsfilter/H.java ================================================ package com.depsfilter; public class H { public H() { int h = 1; } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/src/main/java/com/depsfilter/I.java ================================================ package com.depsfilter; public class I { private F; public I() { F = new F(); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/src/main/java/com/depsfilter/J.java ================================================ package com.depsfilter; public class J { private B b; public J() { b = new B(); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/src/test/java/com/depsfilter/DepsFilterEmptyExclusionsTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.ArrayList; import java.util.List; import org.junit.Test; public class DepsFilterEmptyExclusionsTest { @Test public void testTransitivesExclusion() { /* Checkout _test_empty_exclusion_lists in compile_and_runtime_2/compile_and_runtime_test.bzl */ // available deps at the runtime List availableDeps = DepsFilterTestHelper.computeClasspathDependencies(); // expected runtime deps List expectedRuntimeDeps = new ArrayList<>(DepsFilterTestHelper.getRuntimeDepsListBeforeExclusions()); expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); // Add test-specific JAR file expectedRuntimeDeps.add("springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/DepsFilterEmptyExclusionsTest.jar"); // Verify that availableDeps contains exactly the same elements as expectedRuntimeDeps in any order assertThat(availableDeps).containsExactlyInAnyOrderElementsOf(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/src/test/java/com/depsfilter/DepsFilterExcludeTransitiveTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.ArrayList; import java.util.List; import org.junit.Test; public class DepsFilterExcludeTransitiveTest { @Test public void testTransitivesExclusion() { /* Checkout _test_filtered_deps_exclude_transitive in compile_and_runtime_2/compile_and_runtime_test.bzl */ // available deps at the runtime List availableDeps = DepsFilterTestHelper.computeClasspathDependencies(); // expected runtime deps based on bzl file expected_transitive_runtime_jars List expectedRuntimeDeps = new ArrayList<>(List.of( "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_a.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_e.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_h.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_i.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_j.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/DepsFilterExcludeTransitiveTest.jar" )); // Add test dependencies expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); // Verify that availableDeps contains exactly the same elements as expectedRuntimeDeps in any order assertThat(availableDeps).containsExactlyInAnyOrderElementsOf(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/src/test/java/com/depsfilter/DepsFilterFilteredDepsTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.ArrayList; import java.util.List; import org.junit.Test; public class DepsFilterFilteredDepsTest { @Test public void testFilteredDeps() { /* Checkout _test_filtered_deps in compile_and_runtime_2/compile_and_runtime_test.bzl */ // available deps at the runtime List availableDeps = DepsFilterTestHelper.computeClasspathDependencies(); // expected runtime deps based on bzl file expected_transitive_runtime_jars List expectedRuntimeDeps = new ArrayList<>(List.of( "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_a.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_c.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_d.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_e.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_f.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_h.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_i.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_j.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/DepsFilterFilteredDepsTest.jar" )); // Add test dependencies expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); // Verify that availableDeps contains exactly the same elements as expectedRuntimeDeps in any order assertThat(availableDeps).containsExactlyInAnyOrderElementsOf(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/src/test/java/com/depsfilter/DepsFilterInterfaceImplementationTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.ArrayList; import java.util.List; import org.junit.Test; public class DepsFilterInterfaceImplementationTest { @Test public void testInterfaceImplementationJars() { /* Checkout _test_interface_implementation_jars in compile_and_runtime_2/compile_and_runtime_test.bzl */ // available deps at the runtime List availableDeps = DepsFilterTestHelper.computeClasspathDependencies(); // expected runtime deps based on bzl file expected_transitive_runtime_jars // Note: This test uses the same configuration as filtered_deps test List expectedRuntimeDeps = new ArrayList<>(List.of( "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_a.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_c.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_d.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_e.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_f.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_h.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_i.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_j.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/DepsFilterInterfaceImplementationTest.jar" )); // Add test dependencies expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); // Verify that availableDeps contains exactly the same elements as expectedRuntimeDeps in any order assertThat(availableDeps).containsExactlyInAnyOrderElementsOf(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/src/test/java/com/depsfilter/DepsFilterMultipleExclusionsWithTransitiveTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.ArrayList; import java.util.List; import org.junit.Test; public class DepsFilterMultipleExclusionsWithTransitiveTest { @Test public void testMultipleExclusionsWithTransitive() { /* Checkout _test_multiple_exclusions_with_transitive in compile_and_runtime_2/compile_and_runtime_test.bzl */ // available deps at the runtime List availableDeps = DepsFilterTestHelper.computeClasspathDependencies(); // expected runtime deps based on bzl file expected_transitive_runtime_jars List expectedRuntimeDeps = new ArrayList<>(List.of( "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_a.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_e.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_f.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_h.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_i.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_j.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/DepsFilterMultipleExclusionsWithTransitiveTest.jar" )); // Add test dependencies expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); // Verify that availableDeps contains exactly the same elements as expectedRuntimeDeps in any order assertThat(availableDeps).containsExactlyInAnyOrderElementsOf(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/src/test/java/com/depsfilter/DepsFilterMultipleExclusionsWithoutTransitiveTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.ArrayList; import java.util.List; import org.junit.Test; public class DepsFilterMultipleExclusionsWithoutTransitiveTest { @Test public void testMultipleExclusionsWithoutTransitive() { /* Checkout _test_multiple_exclusions_without_transitive in compile_and_runtime_2/compile_and_runtime_test.bzl */ // available deps at the runtime List availableDeps = DepsFilterTestHelper.computeClasspathDependencies(); // expected runtime deps based on bzl file expected_transitive_runtime_jars List expectedRuntimeDeps = new ArrayList<>(List.of( "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_a.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_c.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_d.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_e.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_f.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_h.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_i.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_j.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/DepsFilterMultipleExclusionsWithoutTransitiveTest.jar" )); // Add test dependencies expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); // Verify that availableDeps contains exactly the same elements as expectedRuntimeDeps in any order assertThat(availableDeps).containsExactlyInAnyOrderElementsOf(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/src/test/java/com/depsfilter/DepsFilterMultiplePathsTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.ArrayList; import java.util.List; import org.junit.Test; public class DepsFilterMultiplePathsTest { @Test public void testMultiplePaths() { /* Checkout _test_multiple_paths in compile_and_runtime_2/compile_and_runtime_test.bzl */ // available deps at the runtime List availableDeps = DepsFilterTestHelper.computeClasspathDependencies(); // expected runtime deps based on bzl file expected_transitive_runtime_jars List expectedRuntimeDeps = new ArrayList<>(List.of( "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_a.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_c.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_d.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_e.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_f.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_h.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_i.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_j.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/DepsFilterMultiplePathsTest.jar" )); // Add test dependencies expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); // Verify that availableDeps contains exactly the same elements as expectedRuntimeDeps in any order assertThat(availableDeps).containsExactlyInAnyOrderElementsOf(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/src/test/java/com/depsfilter/DepsFilterPathBasedExclusionsTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.ArrayList; import java.util.List; import org.junit.Test; public class DepsFilterPathBasedExclusionsTest { @Test public void testPathBasedExclusions() { /* Checkout _test_path_based_exclusions in compile_and_runtime_2/compile_and_runtime_test.bzl */ // available deps at the runtime List availableDeps = DepsFilterTestHelper.computeClasspathDependencies(); // expected runtime deps based on bzl file expected_transitive_runtime_jars List expectedRuntimeDeps = new ArrayList<>(List.of( "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_a.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_c.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_d.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_e.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_g.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_h.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_i.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_j.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/DepsFilterPathBasedExclusionsTest.jar" )); // Add test dependencies expectedRuntimeDeps.addAll(DepsFilterTestHelper.getTestDeps()); // Verify that availableDeps contains exactly the same elements as expectedRuntimeDeps in any order assertThat(availableDeps).containsExactlyInAnyOrderElementsOf(expectedRuntimeDeps); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/src/test/java/com/depsfilter/DepsFilterTestHelper.java ================================================ package com.depsfilter; import java.util.ArrayList; import java.util.List; /** * Helper class containing common functionality for deps filter tests. * Provides shared methods and data that can be used across multiple test classes. */ public class DepsFilterTestHelper { /** * Computes the available dependencies from the current classpath. * @return List of available dependencies with "../" prefix removed */ public static List computeClasspathDependencies() { String classpath = System.getProperty("java.class.path"); String[] classpathEntries = classpath.split(System.getProperty("path.separator")); List availableDeps = new ArrayList<>(); for (String entry : classpathEntries) { availableDeps.add(entry.replace("../", "")); } return availableDeps; } /** * Returns the test dependencies required to run the tests. * These are the dependencies specified in the test target. * @return List of test dependencies */ public static List getTestDeps() { return List.of( "rules_jvm_external~~maven~unmanaged_deps_filter/junit/junit/4.13.2/processed_junit-4.13.2.jar", "rules_jvm_external~~maven~unmanaged_deps_filter/org/hamcrest/hamcrest-core/1.3/processed_hamcrest-core-1.3.jar", "rules_jvm_external~~maven~unmanaged_deps_filter/org/assertj/assertj-core/3.26.0/processed_assertj-core-3.26.0.jar", "rules_jvm_external~~maven~unmanaged_deps_filter/net/bytebuddy/byte-buddy/1.14.16/processed_byte-buddy-1.14.16.jar", "rules_java~~toolchains~remote_java_tools/java_tools/Runner_deploy.jar" ); } /** * Returns the runtime dependencies before exclusions. * These are the base runtime dependencies that would be available before any filtering. * @return List of runtime dependencies before exclusions */ public static List getRuntimeDepsListBeforeExclusions() { return new ArrayList<>(List.of( "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_a.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_b.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_c.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_d.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_e.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_f.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_g.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_h.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_i.jar", "springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_and_runtime_2/liblib_j.jar" )); } /** * Creates a complete list of runtime dependencies including test dependencies. * This combines the base runtime dependencies with test dependencies. * @return Complete list of runtime dependencies including test dependencies */ public static List getCompleteRuntimeDepsList() { List completeList = new ArrayList<>(getRuntimeDepsListBeforeExclusions()); completeList.addAll(getTestDeps()); return completeList; } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_time_only/BUILD ================================================ load("//springboot/deps_filter_rules:deps_filter.bzl", "deps_filter") load( "//springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_time_only:compile_time_only_test.bzl", "no_filtering_test", "filtered_deps_test", "filtered_deps_exclude_transitive_test", "path_based_exclusions_test", "interface_implementation_jars_test", "multiple_exclusions_with_transitive_test", "multiple_exclusions_without_transitive_test", "empty_exclusion_lists_test", "multiple_paths_test", ) # Dependency Graph Structure: # base_lib # / \ # A G # / \ / # B E / # | | / # | F # \/ # C # | # D # java_library( name = "lib_a", srcs = ["src/main/java/com/depsfilter/A.java"], deps = [ ":lib_b", # A -> B ":lib_e", # A -> E ], ) java_library( name = "lib_b", srcs = ["src/main/java/com/depsfilter/B.java"], deps = [":lib_c"], # B -> C ) java_library( name = "lib_c", srcs = ["src/main/java/com/depsfilter/C.java"], deps = [":lib_d"], # B -> D ) java_library( name = "lib_d", srcs = ["src/main/java/com/depsfilter/D.java"], ) java_library( name = "lib_e", srcs = ["src/main/java/com/depsfilter/E.java"], deps = [":lib_f"], # E -> F ) java_library( name = "lib_f", srcs = ["src/main/java/com/depsfilter/F.java"], deps = [":lib_c"], # F -> C ) java_library( name = "lib_g", srcs = ["src/main/java/com/depsfilter/G.java"], deps = [":lib_f"], # G -> F path ) # Consumer library that uses the filtered dependencies java_library( name = "base_lib", srcs = ["src/main/java/com/depsfilter/H.java"], deps = [":lib_a", ":lib_g"], ) # Test 1: No filtering deps_filter( name = "filtered_deps", deps = [":base_lib"], ) no_filtering_test( name = "deps_filter_no_filtering_test", java_library = ":base_lib", deps_filter = ":filtered_deps", # deps_filter with no exclusions ) # Test 2: Exclude by labels and exclude_transitives = False deps_filter( name = "filtered_deps_exclude_b_g", deps = [":base_lib"], deps_exclude_labels = [":lib_b", ":lib_g"], ) filtered_deps_test( name = "deps_filter_exclude_b_g_test", filtered = ":filtered_deps_exclude_b_g", ) # Test 3: Exclude by labels and exclude_transitives = True deps_filter( name = "filtered_deps_exclude_b_g_exclude_transitive", deps = [":base_lib"], deps_exclude_labels = [":lib_b", ":lib_g"], exclude_transitives = True, ) filtered_deps_exclude_transitive_test( name = "deps_filter_exclude_b_g_exclude_transitive_test", filtered = ":filtered_deps_exclude_b_g_exclude_transitive", ) # Test 4: Test for path-based exclusions deps_filter( name = "path_based_filtered_deps", deps = [":base_lib"], deps_exclude_paths = ["lib_b", "lib_f"], ) path_based_exclusions_test( name = "deps_filter_path_based_exclusions_test", filtered = ":path_based_filtered_deps", ) # Test 5: Interface vs Implementation JARs deps_filter( name = "interface_impl_filtered_deps", deps = [":base_lib"], deps_exclude_labels = [":lib_b", ":lib_g"], ) interface_implementation_jars_test( name = "deps_filter_interface_impl_test", filtered = ":interface_impl_filtered_deps", ) # Test 6: Multiple exclusions with exclude_transitives=True deps_filter( name = "multiple_exclusions_filtered_deps_1", deps = [":base_lib"], deps_exclude_labels = [":lib_b"], deps_exclude_paths = ["lib_g"], exclude_transitives = True, ) multiple_exclusions_with_transitive_test( name = "multiple_exclusions_with_transitive_test", filtered = ":multiple_exclusions_filtered_deps_1", ) # Test 7: Multiple exclusions with exclude_transitives=False deps_filter( name = "multiple_exclusions_filtered_deps_2", deps = [":base_lib"], deps_exclude_labels = [":lib_b"], deps_exclude_paths = ["lib_g"], exclude_transitives = False, ) multiple_exclusions_without_transitive_test( name = "multiple_exclusions_without_transitive_test", filtered = ":multiple_exclusions_filtered_deps_2", ) # Test 8: Empty exclusion lists deps_filter( name = "empty_exclusions_filtered_deps", deps = [":base_lib"], deps_exclude_paths = [], deps_exclude_labels = [], ) empty_exclusion_lists_test( name = "deps_filter_empty_exclusions_test", filtered = ":empty_exclusions_filtered_deps", ) # Test 9: Multiple paths handling deps_filter( name = "multiple_paths_filtered_deps", deps = [":base_lib"], deps_exclude_labels = [":lib_b", ":lib_g"], ) multiple_paths_test( name = "deps_filter_multiple_paths_test", filtered = ":multiple_paths_filtered_deps", ) # load("//tools/common/bazel/deps_filter:deps_filter.bzl", "deps_filter") # deps_filter( # name = "flattened_filtered_deps", # deps = [":filtered_deps"], # ) # deps_filter( # name = "flattened_java_libary", # deps = [":base_lib"], # ) toolchain( name = "unittest_toolchain", toolchain_type = "@bazel_skylib//toolchains/unittest:toolchain_type", toolchain = "@bazel_skylib//toolchains/unittest:toolchain", ) ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_time_only/compile_time_only_test.bzl ================================================ load("@bazel_skylib//lib:unittest.bzl", "asserts", "unittest") load("//springboot/deps_filter_rules/tests/test_utils:verification_utils.bzl", "verify_jars", "verify_runtime_and_compile_jars", "verify_jars_and_dropped_counts", "verify_dropped_counts" ) def _test_no_filtering(ctx): """ Tests that deps_filter preserves all dependencies when no exclusions are applied. Dependency Graph: base_lib / \\ A G / \\ / B E / | | / | F \\ C | D Expected: All JARs from java_library must match deps_filter: - full_compile_jars: Implementation JARs (e.g., liblib_a.jar) - compile_jars: Interface JARs (e.g., liblib_a-hjar.jar) - transitive_compile_time_jars: Interface JARs from transitive deps - transitive_runtime_jars: Implementation JARs from transitive deps """ env = unittest.begin(ctx) java_lib_info = ctx.attr.java_library[JavaInfo] deps_filter_info = ctx.attr.deps_filter[JavaInfo] # Verify all JAR fields match between java_library and deps_filter jar_fields = [ "full_compile_jars", # Implementation JARs "compile_jars", # Interface JARs "transitive_compile_time_jars", # Transitive interface JARs "transitive_runtime_jars" # Transitive implementation JARs ] for jar_field in jar_fields: java_lib_jars = getattr(java_lib_info, jar_field) deps_filter_jars = getattr(deps_filter_info, jar_field) asserts.equals(env, type(java_lib_jars), type(deps_filter_jars), "JAR type mismatch: {} vs deps_filter".format(jar_field)) asserts.equals(env, java_lib_jars.to_list(), deps_filter_jars.to_list(), "JAR contents mismatch: {} vs deps_filter".format(jar_field)) return unittest.end(env) no_filtering_test = unittest.make(_test_no_filtering, attrs = { "java_library": attr.label(providers = [JavaInfo]), "deps_filter": attr.label(providers = [JavaInfo]), }) def _test_filtered_deps(ctx): """ Tests basic dependency filtering with label-based exclusions. Dependency Graph: base_lib / \\ A G / \\ / B E / | | / | F \\ C | D Input: deps = [":base_lib"] deps_exclude_labels = [":lib_b", ":lib_g"] deps_exclude_paths = [] exclude_transitives = False Expected Output: JARs preserved: - base_lib, A, E, F, C, D (both runtime and compile-time) JARs excluded: - B, G and their transitive deps """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] expected_compile_jars = [ "libbase_lib-hjar.jar", ] expected_full_compile_jars = [ "libbase_lib.jar", ] expected_transitive_runtime_jars = [ "libbase_lib.jar", "liblib_a.jar", "liblib_e.jar", "liblib_f.jar", "liblib_c.jar", "liblib_d.jar" ] expected_transitive_compile_jars = [ "libbase_lib-hjar.jar", "liblib_a-hjar.jar", "liblib_e-hjar.jar", "liblib_f-hjar.jar", "liblib_c-hjar.jar", "liblib_d-hjar.jar" ] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) filtered_deps_test = unittest.make(_test_filtered_deps, attrs = { "filtered": attr.label(providers = [JavaInfo]), }) def _test_filtered_deps_exclude_transitive(ctx): """ Tests dependency filtering with transitive exclusions. Dependency Graph: base_lib / \\ A G / \\ / B E / | | / | F \\ C | D Input: deps = [":base_lib"] deps_exclude_labels = [":lib_b", ":lib_g"] deps_exclude_paths = [] exclude_transitives = True Expected Output: JARs preserved: - base_lib, A, E (both runtime and compile-time) JARs excluded: - B, G and all transitive deps """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] expected_compile_jars = [ "libbase_lib-hjar.jar", ] expected_full_compile_jars = [ "libbase_lib.jar", ] expected_transitive_runtime_jars = [ "libbase_lib.jar", "liblib_a.jar", "liblib_e.jar", ] expected_transitive_compile_jars = [ "libbase_lib-hjar.jar", "liblib_a-hjar.jar", "liblib_e-hjar.jar", ] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) filtered_deps_exclude_transitive_test = unittest.make(_test_filtered_deps_exclude_transitive, attrs = { "filtered": attr.label(providers = [JavaInfo]), }) def _test_path_based_exclusions(ctx): """ Tests filtering based on path patterns in deps_exclude_paths. Dependency Graph: base_lib / \\ A G / \\ / B E / | | / | F \\ C | D Input: deps = [":base_lib"] deps_exclude_labels = [] deps_exclude_paths = ["lib_b", "lib_f"] exclude_transitives = False Expected Output: JARs preserved: - All JARs not matching path patterns JARs excluded: - JARs matching paths "lib_b" and "lib_f" """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] expected_compile_jars = [ "libbase_lib-hjar.jar", ] expected_full_compile_jars = [ "libbase_lib.jar", ] expected_transitive_runtime_jars = [ "libbase_lib.jar", "liblib_a.jar", "liblib_e.jar", "liblib_c.jar", "liblib_d.jar", "liblib_g.jar" ] expected_transitive_compile_jars = [ "libbase_lib-hjar.jar", "liblib_a-hjar.jar", "liblib_e-hjar.jar", "liblib_c-hjar.jar", "liblib_d-hjar.jar", "liblib_g-hjar.jar" ] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) path_based_exclusions_test = unittest.make(_test_path_based_exclusions, attrs = { "filtered": attr.label(providers = [JavaInfo]), }) def _test_interface_implementation_jars(ctx): """ Tests proper handling of interface (-hjar) and implementation JARs. Dependency Graph: base_lib / \\ A G / \\ / B E / | | / | F \\ C | D Input: deps = [":base_lib"] deps_exclude_labels = [":lib_b", ":lib_g"] deps_exclude_paths = [] exclude_transitives = False Expected Output: Interface JARs (compile_jars): - libbase_lib-hjar.jar Implementation JARs (full_compile_jars): - libbase_lib.jar """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] compile_jars = sorted([jar.basename for jar in javainfo_filtered.compile_jars.to_list()]) full_compile_jars = sorted([jar.basename for jar in javainfo_filtered.full_compile_jars.to_list()]) expected_compile_jars = ["libbase_lib-hjar.jar"] expected_full_compile_jars = ["libbase_lib.jar"] asserts.equals(env, compile_jars, expected_compile_jars) asserts.equals(env, full_compile_jars, expected_full_compile_jars) return unittest.end(env) interface_implementation_jars_test = unittest.make(_test_interface_implementation_jars, attrs = { "filtered": attr.label(providers = [JavaInfo]), }) def _test_multiple_exclusions_with_transitive(ctx): """ Tests multiple exclusion levels with exclude_transitives=True. Dependency Graph: base_lib / \\ A G / \\ / B E / | | / | F \\ C | D Input: deps = [":base_lib"] deps_exclude_labels = [":lib_b"] deps_exclude_paths = ["lib_g"] exclude_transitives = True Expected Output: JARs preserved: - base_lib, A, E, F (both runtime and compile-time) JARs excluded: - B, G and all transitive deps """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] expected_compile_jars = [ "libbase_lib-hjar.jar", ] expected_full_compile_jars = [ "libbase_lib.jar", ] expected_transitive_runtime_jars = [ "libbase_lib.jar", "liblib_a.jar", "liblib_e.jar", "liblib_f.jar", ] expected_transitive_compile_jars = [ "libbase_lib-hjar.jar", "liblib_a-hjar.jar", "liblib_e-hjar.jar", "liblib_f-hjar.jar", ] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) def _test_multiple_exclusions_without_transitive(ctx): """ Tests multiple exclusion levels with exclude_transitives=False. Dependency Graph: base_lib / \\ A G / \\ / B E / | | / | F \\ C | D Input: deps = [":base_lib"] deps_exclude_labels = [":lib_b"] deps_exclude_paths = ["lib_g"] exclude_transitives = False Expected Output: JARs preserved: - base_lib, A, E, F, C, D (both runtime and compile-time) JARs excluded: - B, G (direct deps only) """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] expected_compile_jars = [ "libbase_lib-hjar.jar", ] expected_full_compile_jars = [ "libbase_lib.jar", ] expected_transitive_runtime_jars = [ "libbase_lib.jar", "liblib_a.jar", "liblib_e.jar", "liblib_f.jar", "liblib_c.jar", "liblib_d.jar", ] expected_transitive_compile_jars = [ "libbase_lib-hjar.jar", "liblib_a-hjar.jar", "liblib_e-hjar.jar", "liblib_f-hjar.jar", "liblib_c-hjar.jar", "liblib_d-hjar.jar", ] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) multiple_exclusions_with_transitive_test = unittest.make(_test_multiple_exclusions_with_transitive, attrs = { "filtered": attr.label(providers = [JavaInfo]), }) multiple_exclusions_without_transitive_test = unittest.make(_test_multiple_exclusions_without_transitive, attrs = { "filtered": attr.label(providers = [JavaInfo]), }) def _test_empty_exclusion_lists(ctx): """ Tests behavior when exclusion lists are empty. Dependency Graph: base_lib / \\ A G / \\ / B E / | | / | F \\ C | D Input: deps = [":base_lib"] deps_exclude_labels = [] deps_exclude_paths = [] exclude_transitives = False Expected Output: All JARs preserved: - base_lib, A, B, C, D, E, F, G (both runtime and compile-time) """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] expected_compile_jars = [ "libbase_lib-hjar.jar", ] expected_full_compile_jars = [ "libbase_lib.jar", ] expected_transitive_runtime_jars = [ "libbase_lib.jar", "liblib_a.jar", "liblib_b.jar", "liblib_c.jar", "liblib_d.jar", "liblib_e.jar", "liblib_f.jar", "liblib_g.jar" ] expected_transitive_compile_jars = [ "libbase_lib-hjar.jar", "liblib_a-hjar.jar", "liblib_b-hjar.jar", "liblib_c-hjar.jar", "liblib_d-hjar.jar", "liblib_e-hjar.jar", "liblib_f-hjar.jar", "liblib_g-hjar.jar" ] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) empty_exclusion_lists_test = unittest.make(_test_empty_exclusion_lists, attrs = { "filtered": attr.label(providers = [JavaInfo]), }) def _test_multiple_paths(ctx): """ Tests handling of multiple paths to the same dependency. Dependency Graph: base_lib / \\ A G / \\ / B E / | | / | F \\ C | D Input: deps = [":base_lib"] deps_exclude_labels = [":lib_b", ":lib_g"] deps_exclude_paths = [] exclude_transitives = False Expected Output: JARs preserved: - base_lib, A, E, F, C, D (both runtime and compile-time) JARs excluded: - B, G Note: Dependencies not duplicated when reachable through multiple paths """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] expected_compile_jars = [ "libbase_lib-hjar.jar", ] expected_full_compile_jars = [ "libbase_lib.jar", ] expected_transitive_runtime_jars = [ "libbase_lib.jar", "liblib_a.jar", "liblib_e.jar", "liblib_f.jar", "liblib_c.jar", "liblib_d.jar" ] expected_transitive_compile_jars = [ "libbase_lib-hjar.jar", "liblib_a-hjar.jar", "liblib_e-hjar.jar", "liblib_f-hjar.jar", "liblib_c-hjar.jar", "liblib_d-hjar.jar" ] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) multiple_paths_test = unittest.make(_test_multiple_paths, attrs = { "filtered": attr.label(providers = [JavaInfo]), }) ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_time_only/src/main/java/com/depsfilter/A.java ================================================ package com.depsfilter; public class A { int a; private B b; private E e; public A() { a = 1; b = new B(); e = new E(); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_time_only/src/main/java/com/depsfilter/B.java ================================================ package com.depsfilter; public class B { private C c; public B() { c = new C(); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_time_only/src/main/java/com/depsfilter/C.java ================================================ package com.depsfilter; public class C { private D d; public C() { d = new D(); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_time_only/src/main/java/com/depsfilter/D.java ================================================ package com.depsfilter; public class D { private int value; public D() { value = 4; } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_time_only/src/main/java/com/depsfilter/E.java ================================================ package com.depsfilter; public class E { private F f; public E() { f = new F(); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_time_only/src/main/java/com/depsfilter/F.java ================================================ package com.depsfilter; public class F { private C c; public F() { c = new C(); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_time_only/src/main/java/com/depsfilter/G.java ================================================ package com.depsfilter; public class G { private F f; public G() { f = new F(); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/compile_time_only/src/main/java/com/depsfilter/H.java ================================================ package com.depsfilter; public class H { private A a; private G g; public H() { a = new A(); g = new G(); } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/runtime_only/BUILD ================================================ load("//springboot/deps_filter_rules:deps_filter.bzl", "deps_filter") load( "//springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/runtime_only:runtime_only_test.bzl", "no_filtering_test", "filtered_deps_test", "filtered_deps_exclude_transitive_test", "path_based_exclusions_test", "interface_implementation_jars_test", "multiple_exclusions_with_transitive_test", "multiple_exclusions_without_transitive_test", "empty_exclusion_lists_test", "multiple_paths_test", ) # Dependency Graph Structure: # base_lib # / \ # A G # / \ / # B E / # | | / # | F # \/ # C # | # D # java_library( name = "lib_a", srcs = ["src/main/java/com/depsfilter/A.java"], runtime_deps = [ ":lib_b", # A -> B ":lib_e", # A -> E ], ) java_library( name = "lib_b", srcs = ["src/main/java/com/depsfilter/B.java"], runtime_deps = [":lib_c"], # B -> C ) java_library( name = "lib_c", srcs = ["src/main/java/com/depsfilter/C.java"], runtime_deps = [":lib_d"], # B -> D ) java_library( name = "lib_d", srcs = ["src/main/java/com/depsfilter/D.java"], ) java_library( name = "lib_e", srcs = ["src/main/java/com/depsfilter/E.java"], runtime_deps = [":lib_f"], # E -> F ) java_library( name = "lib_f", srcs = ["src/main/java/com/depsfilter/F.java"], runtime_deps = [":lib_c"], # F -> C ) java_library( name = "lib_g", srcs = ["src/main/java/com/depsfilter/G.java"], runtime_deps = [":lib_f"], # G -> F path ) # Consumer library that uses the filtered dependencies java_library( name = "base_lib", srcs = ["src/main/java/com/depsfilter/H.java"], runtime_deps = [":lib_a", ":lib_g"], ) # Test 1: No filtering deps_filter( name = "filtered_deps", deps = [":base_lib"], ) no_filtering_test( name = "deps_filter_no_filtering_test", java_library = ":base_lib", deps_filter = ":filtered_deps", # deps_filter with no exclusions ) # Test 2: Exclude by labels and exclude_transitives = False deps_filter( name = "filtered_deps_exclude_b_g", runtime_deps = [":base_lib"], deps_exclude_labels = [":lib_b", ":lib_g"], ) filtered_deps_test( name = "deps_filter_exclude_b_g_test", filtered = ":filtered_deps_exclude_b_g", ) # Test 3: Exclude by labels and exclude_transitives = True deps_filter( name = "filtered_deps_exclude_b_g_exclude_transitive", runtime_deps = [":base_lib"], deps_exclude_labels = [":lib_b", ":lib_g"], exclude_transitives = True, ) filtered_deps_exclude_transitive_test( name = "deps_filter_exclude_b_g_exclude_transitive_test", filtered = ":filtered_deps_exclude_b_g_exclude_transitive", ) # Test 4: Test for path-based exclusions deps_filter( name = "path_based_filtered_deps", runtime_deps = [":base_lib"], deps_exclude_paths = ["lib_b", "lib_f"], ) path_based_exclusions_test( name = "deps_filter_path_based_exclusions_test", filtered = ":path_based_filtered_deps", ) # Test 5: Interface vs Implementation JARs deps_filter( name = "interface_impl_filtered_deps", runtime_deps = [":base_lib"], deps_exclude_labels = [":lib_b", ":lib_g"], ) interface_implementation_jars_test( name = "deps_filter_interface_impl_test", filtered = ":interface_impl_filtered_deps", ) # Test 6: Multiple exclusions with exclude_transitives=True deps_filter( name = "multiple_exclusions_filtered_deps_1", runtime_deps = [":base_lib"], deps_exclude_labels = [":lib_b"], deps_exclude_paths = ["lib_g"], exclude_transitives = True, ) multiple_exclusions_with_transitive_test( name = "multiple_exclusions_with_transitive_test", filtered = ":multiple_exclusions_filtered_deps_1", ) # Test 7: Multiple exclusions with exclude_transitives=False deps_filter( name = "multiple_exclusions_filtered_deps_2", runtime_deps = [":base_lib"], deps_exclude_labels = [":lib_b"], deps_exclude_paths = ["lib_g"], exclude_transitives = False, ) multiple_exclusions_without_transitive_test( name = "multiple_exclusions_without_transitive_test", filtered = ":multiple_exclusions_filtered_deps_2", ) # Test 8: Empty exclusion lists deps_filter( name = "empty_exclusions_filtered_deps", runtime_deps = [":base_lib"], deps_exclude_paths = [], deps_exclude_labels = [], ) empty_exclusion_lists_test( name = "deps_filter_empty_exclusions_test", filtered = ":empty_exclusions_filtered_deps", ) # Test 9: Multiple paths handling deps_filter( name = "multiple_paths_filtered_deps", runtime_deps = [":base_lib"], deps_exclude_labels = [":lib_b", ":lib_g"], ) multiple_paths_test( name = "deps_filter_multiple_paths_test", filtered = ":multiple_paths_filtered_deps", ) toolchain( name = "unittest_toolchain", toolchain_type = "@bazel_skylib//toolchains/unittest:toolchain_type", toolchain = "@bazel_skylib//toolchains/unittest:toolchain", ) ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/runtime_only/runtime_only_test.bzl ================================================ load("@bazel_skylib//lib:unittest.bzl", "asserts", "unittest") load("//springboot/deps_filter_rules/tests/test_utils:verification_utils.bzl", "verify_jars", "verify_runtime_and_compile_jars", "verify_jars_and_dropped_counts", "verify_dropped_counts" ) def _test_no_filtering(ctx): """ Tests that deps_filter preserves all dependencies when no exclusions are applied. Dependency Graph: base_lib / \\ A G / \\ / B E / | | / | F \\ C | D Expected: All JARs from java_library must match deps_filter: - full_compile_jars: Implementation JARs (e.g., liblib_a.jar) - compile_jars: Interface JARs (e.g., liblib_a-hjar.jar) - transitive_compile_time_jars: Interface JARs from transitive deps - transitive_runtime_jars: Implementation JARs from transitive deps """ env = unittest.begin(ctx) java_lib_info = ctx.attr.java_library[JavaInfo] deps_filter_info = ctx.attr.deps_filter[JavaInfo] # Verify all JAR fields match between java_library and deps_filter jar_fields = [ "full_compile_jars", # Implementation JARs "compile_jars", # Interface JARs "transitive_compile_time_jars", # Transitive interface JARs "transitive_runtime_jars" # Transitive implementation JARs ] for jar_field in jar_fields: java_lib_jars = getattr(java_lib_info, jar_field) deps_filter_jars = getattr(deps_filter_info, jar_field) asserts.equals(env, type(java_lib_jars), type(deps_filter_jars), "JAR type mismatch: {} vs deps_filter".format(jar_field)) asserts.equals(env, java_lib_jars.to_list(), deps_filter_jars.to_list(), "JAR contents mismatch: {} vs deps_filter".format(jar_field)) return unittest.end(env) no_filtering_test = unittest.make(_test_no_filtering, attrs = { "java_library": attr.label(providers = [JavaInfo]), "deps_filter": attr.label(providers = [JavaInfo]), }) def _test_filtered_deps(ctx): """ Tests basic dependency filtering with label-based exclusions. Dependency Graph: base_lib / \\ A G / \\ / B E / | | / | F \\ C | D Input: deps = [":base_lib"] deps_exclude_labels = [":lib_b", ":lib_g"] deps_exclude_paths = [] exclude_transitives = False Expected Output: JARs preserved: - base_lib, A, E, F, C, D (runtime) - no compile-time jars present JARs excluded: - B, G and their transitive deps """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] expected_compile_jars = [] expected_full_compile_jars = [ "libbase_lib.jar", ] expected_transitive_runtime_jars = [ "libbase_lib.jar", "liblib_a.jar", "liblib_e.jar", "liblib_f.jar", "liblib_c.jar", "liblib_d.jar" ] expected_transitive_compile_jars = [] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) filtered_deps_test = unittest.make(_test_filtered_deps, attrs = { "filtered": attr.label(providers = [JavaInfo]), }) def _test_filtered_deps_exclude_transitive(ctx): """ Tests dependency filtering with transitive exclusions. Dependency Graph: base_lib / \\ A G / \\ / B E / | | / | F \\ C | D Input: deps = [":base_lib"] deps_exclude_labels = [":lib_b", ":lib_g"] deps_exclude_paths = [] exclude_transitives = True Expected Output: JARs preserved: - base_lib, A, E (runtime) - no compile-time jars present JARs excluded: - B, G and all transitive deps """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] expected_compile_jars = [] expected_full_compile_jars = [ "libbase_lib.jar", ] expected_transitive_runtime_jars = [ "libbase_lib.jar", "liblib_a.jar", "liblib_e.jar", ] expected_transitive_compile_jars = [] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) filtered_deps_exclude_transitive_test = unittest.make(_test_filtered_deps_exclude_transitive, attrs = { "filtered": attr.label(providers = [JavaInfo]), }) def _test_path_based_exclusions(ctx): """ Tests filtering based on path patterns in deps_exclude_paths. Dependency Graph: base_lib / \\ A G / \\ / B E / | | / | F \\ C | D Input: deps = [":base_lib"] deps_exclude_labels = [] deps_exclude_paths = ["lib_b", "lib_f"] exclude_transitives = False Expected Output: JARs preserved: - All JARs not matching path patterns JARs excluded: - JARs matching paths "lib_b" and "lib_f" """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] expected_compile_jars = [] expected_full_compile_jars = [ "libbase_lib.jar", ] expected_transitive_runtime_jars = [ "libbase_lib.jar", "liblib_a.jar", "liblib_e.jar", "liblib_c.jar", "liblib_d.jar", "liblib_g.jar" ] expected_transitive_compile_jars = [] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) path_based_exclusions_test = unittest.make(_test_path_based_exclusions, attrs = { "filtered": attr.label(providers = [JavaInfo]), }) def _test_interface_implementation_jars(ctx): """ Tests proper handling of interface (-hjar) and implementation JARs. Dependency Graph: base_lib / \\ A G / \\ / B E / | | / | F \\ C | D Input: deps = [":base_lib"] deps_exclude_labels = [":lib_b", ":lib_g"] deps_exclude_paths = [] exclude_transitives = False Expected Output: Interface JARs (compile_jars): - [] Implementation JARs (full_compile_jars): - libbase_lib.jar """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] compile_jars = sorted([jar.basename for jar in javainfo_filtered.compile_jars.to_list()]) full_compile_jars = sorted([jar.basename for jar in javainfo_filtered.full_compile_jars.to_list()]) expected_compile_jars = [] expected_full_compile_jars = ["libbase_lib.jar"] asserts.equals(env, compile_jars, expected_compile_jars) asserts.equals(env, full_compile_jars, expected_full_compile_jars) return unittest.end(env) interface_implementation_jars_test = unittest.make(_test_interface_implementation_jars, attrs = { "filtered": attr.label(providers = [JavaInfo]), }) def _test_multiple_exclusions_with_transitive(ctx): """ Tests multiple exclusion levels with exclude_transitives=True. Dependency Graph: base_lib / \\ A G / \\ / B E / | | / | F \\ C | D Input: deps = [":base_lib"] deps_exclude_labels = [":lib_b"] deps_exclude_paths = ["lib_g"] exclude_transitives = True Expected Output: JARs preserved: - base_lib, A, E, F (runtime) - no compile-time jars present JARs excluded: - B, G and all transitive deps """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] expected_compile_jars = [] expected_full_compile_jars = [ "libbase_lib.jar", ] expected_transitive_runtime_jars = [ "libbase_lib.jar", "liblib_a.jar", "liblib_e.jar", "liblib_f.jar", ] expected_transitive_compile_jars = [] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) def _test_multiple_exclusions_without_transitive(ctx): """ Tests multiple exclusion levels with exclude_transitives=False. Dependency Graph: base_lib / \\ A G / \\ / B E / | | / | F \\ C | D Input: deps = [":base_lib"] deps_exclude_labels = [":lib_b"] deps_exclude_paths = ["lib_g"] exclude_transitives = False Expected Output: JARs preserved: - base_lib, A, E, F, C, D (runtime) - no compile-time jars present JARs excluded: - B, G (direct deps only) """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] expected_compile_jars = [] expected_full_compile_jars = [ "libbase_lib.jar", ] expected_transitive_runtime_jars = [ "libbase_lib.jar", "liblib_a.jar", "liblib_e.jar", "liblib_f.jar", "liblib_c.jar", "liblib_d.jar", ] expected_transitive_compile_jars = [] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) multiple_exclusions_with_transitive_test = unittest.make(_test_multiple_exclusions_with_transitive, attrs = { "filtered": attr.label(providers = [JavaInfo]), }) multiple_exclusions_without_transitive_test = unittest.make(_test_multiple_exclusions_without_transitive, attrs = { "filtered": attr.label(providers = [JavaInfo]), }) def _test_empty_exclusion_lists(ctx): """ Tests behavior when exclusion lists are empty. Dependency Graph: base_lib / \\ A G / \\ / B E / | | / | F \\ C | D Input: deps = [":base_lib"] deps_exclude_labels = [] deps_exclude_paths = [] exclude_transitives = False Expected Output: All JARs preserved: - base_lib, A, B, C, D, E, F, G (runtime) - no compile-time jars present """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] expected_compile_jars = [] expected_full_compile_jars = [ "libbase_lib.jar", ] expected_transitive_runtime_jars = [ "libbase_lib.jar", "liblib_a.jar", "liblib_b.jar", "liblib_c.jar", "liblib_d.jar", "liblib_e.jar", "liblib_f.jar", "liblib_g.jar" ] expected_transitive_compile_jars = [] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) empty_exclusion_lists_test = unittest.make(_test_empty_exclusion_lists, attrs = { "filtered": attr.label(providers = [JavaInfo]), }) def _test_multiple_paths(ctx): """ Tests handling of multiple paths to the same dependency. Dependency Graph: base_lib / \\ A G / \\ / B E / | | / | F \\ C | D Input: deps = [":base_lib"] deps_exclude_labels = [":lib_b", ":lib_g"] deps_exclude_paths = [] exclude_transitives = False Expected Output: JARs preserved: - base_lib, A, E, F, C, D (runtime) - no compile-time jars present JARs excluded: - B, G Note: Dependencies not duplicated when reachable through multiple paths """ env = unittest.begin(ctx) javainfo_filtered = ctx.attr.filtered[JavaInfo] expected_compile_jars = [] expected_full_compile_jars = [ "libbase_lib.jar", ] expected_transitive_runtime_jars = [ "libbase_lib.jar", "liblib_a.jar", "liblib_e.jar", "liblib_f.jar", "liblib_c.jar", "liblib_d.jar" ] expected_transitive_compile_jars = [] verify_runtime_and_compile_jars(ctx, env, javainfo_filtered, expected_compile_jars = expected_compile_jars, expected_full_compile_jars = expected_full_compile_jars, expected_transitive_compile_jars = expected_transitive_compile_jars, expected_transitive_runtime_jars = expected_transitive_runtime_jars) return unittest.end(env) multiple_paths_test = unittest.make(_test_multiple_paths, attrs = { "filtered": attr.label(providers = [JavaInfo]), }) ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/runtime_only/src/main/java/com/depsfilter/A.java ================================================ package com.depsfilter; public class A { public A() { int a = 1; } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/runtime_only/src/main/java/com/depsfilter/B.java ================================================ package com.depsfilter; public class B { public B() { int b = 1; } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/runtime_only/src/main/java/com/depsfilter/C.java ================================================ package com.depsfilter; public class C { public C() { int c = 1; } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/runtime_only/src/main/java/com/depsfilter/D.java ================================================ package com.depsfilter; public class D { public D() { int d = 1; } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/runtime_only/src/main/java/com/depsfilter/E.java ================================================ package com.depsfilter; public class E { public E() { int e = 1; } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/runtime_only/src/main/java/com/depsfilter/F.java ================================================ package com.depsfilter; public class F { public F() { int f = 1; } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/runtime_only/src/main/java/com/depsfilter/G.java ================================================ package com.depsfilter; public class G { public G() { int g = 1; } } ================================================ FILE: springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/runtime_only/src/main/java/com/depsfilter/H.java ================================================ package com.depsfilter; public class H { public H() { int h = 1; } } ================================================ FILE: springboot/deps_filter_rules/tests/external_dependencies_testing.md ================================================ # External Dependencies Testing `external_dependencies` under both `depsfilter` and `dependencyset` contain comprehensive tests for the `deps_filter` rule and `dependencyset` macro using real external deps (Spring Boot, Jakarta libraries) to ensure correct filtering in complex dependency graphs. ## Purpose - Validate `deps_filter` and `dependencyset` with real-world, complex external deps - Dynamically verify results using bazel's dependency graph - Cover all exclusion mechanisms and multiple edge cases ## Directory Structure ``` tests/ ├── depsfilter/ │ └── external_dependencies/ │ ├── compile_and_runtime/ │ └── compile_and_runtime_through_java_library/ └── dependencyset/ └── external_dependencies/ └── compile_and_runtime/ ``` ## Testing Approach Similar testing scenarios are implemented using two different approaches: ### 1. Deps Filter Rule Testing **Pattern**: `external deps -> deps_filter() -> bazel starlark/java tests` **Example from compile_and_runtime**: ```bazel # Direct external deps in deps_filter deps_filter( name = "no_filtering", deps = deps, runtime_deps = runtime_deps, ) no_filtering_test( name = "no_filtering_test", filtered = ":no_filtering", ) java_test( name = "DepsFilterNoFilteringTest", size = "small", srcs = ["src/test/java/com/depsfilter/DepsFilterNoFilteringTest.java"], deps = [":no_filtering", "//springboot/deps_filter_rules/tests/test_utils:test_utils"] + test_deps, ) ``` **Example from compile_and_runtime_through_java_library**: ```bazel # External deps wrapped in java_library first java_library( name = "base_lib_with_deps_and_runtime_deps", srcs = ["src/main/java/com/depsfilter/A.java"], deps = deps, runtime_deps = runtime_deps, ) # Then filtered through deps_filter deps_filter( name = "no_filtering", deps = [":base_lib_with_deps_and_runtime_deps"], ) no_filtering_test( name = "no_filtering_test", filtered = ":no_filtering", ) java_test( name = "DepsFilterNoFilteringTest", size = "small", srcs = ["src/test/java/com/depsfilter/DepsFilterNoFilteringTest.java"], deps = [":no_filtering", "//springboot/deps_filter_rules/tests/test_utils:test_utils"] + test_deps, ) ``` ### 2. Dependencyset Macro Testing **Pattern**: `dependencyset("deps"), dependencyset("runtime_deps") -> java_library -> bazel starlark/java tests` **Consistent approach across all test scenarios**: ```bazel # Create filtered dependency sets dependencyset( name = "deps_no_filtering", items = deps, ) dependencyset( name = "runtime_deps_no_filtering", items = runtime_deps, ) # Create test library using filtered sets java_library( name = "no_filtering_test_lib", srcs = ["src/main/java/com/depsfilter/A.java"], deps = [":deps_no_filtering"], runtime_deps = [":runtime_deps_no_filtering"], ) # Test the filtered result no_filtering_test( name = "no_filtering_test", test_lib = ":no_filtering_test_lib", ) # Java test for runtime verification java_test( name = "DepsFilterNoFilteringTest", size = "small", srcs = ["src/test/java/com/depsfilter/DepsFilterNoFilteringTest.java"], deps = [":no_filtering_test_lib", "//springboot/deps_filter_rules/tests/test_utils:test_utils"] + test_deps, ) ``` ## Test Structure The testing is organized into two comprehensive test suites that focus on real external deps: ### `depsfilter/external_dependencies/` **Key Characteristics:** - Tests the `deps_filter` rule directly - Uses actual external libraries directly in deps_filter targets - Complex dependency graph with 100+ transitive deps - Tests both compile-time and runtime deps #### `compile_and_runtime/` - Uses actual external libraries directly in deps_filter targets - Tests both compile-time and runtime deps #### `compile_and_runtime_through_java_library/` - Uses actual external libraries wrapped in java_library targets - External deps are passed through java_library targets before testing - Tests the same scenarios but with an additional layer of indirection - More realistic testing scenario where external deps are consumed through internal libraries ### `dependencyset/external_dependencies/` **Key Characteristics:** - Tests the `dependencyset` macro - Uses actual external libraries through dependencyset targets - Tests the same scenarios as depsfilter but using the macro approach - Validates that dependencyset provides the same filtering capabilities #### `compile_and_runtime/` - Uses dependencyset macro to manage external deps - Tests both compile-time and runtime deps through dependencyset - Validates macro-level filtering behavior **Deps Used (for both approaches):** ```python # Compile-time Deps deps = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security", "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind", "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core", "@unmanaged_deps_filter//:jakarta_servlet_jsp_jakarta_servlet_jsp_api", ] # Runtime Deps runtime_deps = [ "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator", ] ``` ## Test Coverage Both test suites cover: - **No filtering**: Baseline test with all deps included - **Label-based exclusions**: Exclude specific deps by label (with and without transitives) - **Path-based exclusions**: Exclude deps by path patterns (with and without transitives) - **Multiple exclusions**: Combined label and path exclusions (with and without transitives) - **Empty exclusions**: Behavior with empty exclusion lists - **Comprehensive path-based exclusions**: Multiple path patterns, including common libraries (micrometer, slf4j, logback) - **Runtime deps only**: Only runtime deps, no compile-time deps - **Compile deps only**: Only compile-time deps, no runtime deps - **Single dependency with exclusions**: One dep with label/path exclusions - **Single runtime dependency with exclusions**: One runtime dep with exclusions - **One compile dep and one runtime dep** - **Path patterns with special characters**: Patterns with dots, hyphens, etc. - **Case sensitive pattern matching**: Patterns with different cases (upper, lower, mixed) ## Verification Approach We use two complementary testing strategies to ensure comprehensive validation: ### Java Testing - Runtime Classpath Verification Java tests verify that the correct JARs are available at runtime by: 1. **Computing Expected Deps**: - Parse `dependency_graph.txt` generated by bazel's `deps()` query - Build complete dependency graph using `DependencyGraphAnalyzer` - Apply exclusion logic (labels, paths, transitives) to simulate `deps_filter`/`dependencyset` behavior - Generate expected runtime classpath from filtered graph 2. **Obtaining Available Deps**: - Read actual runtime classpath using `System.getProperty("java.class.path")` - Parse and normalize classpath entries to JAR names 3. **Comparison**: - Compare expected runtime JARs vs actual available runtime JARs - Verify excluded deps are absent and required deps are present ```java // Compute expected runtime JARs Set expectedJars = DependencyGraphTestConfig .getExpectedJarsForLabelExclusionsFiltered(excludedLabels, excludeTransitives); // Get actual runtime classpath List availableDeps = DepsFilterTestHelper.computeClasspathDependencies(); // Compare expected vs available assertEquals(expectedJars, new HashSet<>(availableDeps)); ``` ### Starlark Testing - Rule/Macro Output Verification Starlark tests verify the `deps_filter` rule's and `dependencyset` macro's output by: 1. **Computing Expected Deps**: - Iterate through all `deps` and `runtime_deps` - Apply exclusion logic (label matching, path patterns, transitive handling) - Generate expected JAR lists for each of the four JAR types: `compile_jars`, `full_compile_jars`, `transitive_compile_jars`, `transitive_runtime_jars` 2. **Obtaining Available Deps**: - Extract JAR collections from the `deps_filter` rule's `JavaInfo` or `dependencyset` macro's output - Get all four JAR types: `compile_jars`, `full_compile_jars`, `transitive_compile_jars`, `transitive_runtime_jars` 3. **Comparison**: - Compare expected vs actual JARs for all four JAR types - Verify exclusion counts (number of jars excluded) and JAR contents match ```python # Verify all four JAR types def verify_jars(env, actual_jars, expected_jars, jar_field): asserts.equals(env, expected_jars, actual_jars, "JAR contents mismatch: {} vs deps_filter/dependencyset".format(jar_field)) ``` ## Test Verification Each Starlark test verifies the following JAR fields: - **`compile_jars`**: Interface JARs (e.g., `header_spring-boot-starter-data-jpa-3.3.11.jar`) - **`full_compile_jars`**: Implementation JARs (e.g., `processed_spring-boot-starter-data-jpa-3.3.11.jar`) - **`transitive_compile_time_jars`**: Transitive interface JARs - **`transitive_runtime_jars`**: Transitive implementation JARs ## Java Test Files Each test scenario includes corresponding java test files that: - Verify the jars available at runtime - Use centralized test helper (`DepsFilterTestHelper`) - Compute expected results from dependency graph ## Key Testing Concepts ### 1. Label-based Exclusions - Excludes deps by their label - Can optionally exclude transitive deps ### 2. Path-based Exclusions - Excludes deps matching path patterns in JAR names - Does not exclude transitives (`exclude_transitives = true` doesn't work) ### 3. Transitive Exclusion Behavior - `exclude_transitives=False`: Only excludes deps specified in `deps_exclude_labels`, preserves their transitives - `exclude_transitives=True`: Excludes both direct and transitive deps specified in `deps_exclude_labels` ### 4. Runtime Classpath Verification - Compare expected vs actual runtime classpath - Verify excluded deps are absent - Verify required deps are present - Handle complex transitive dependency scenarios ### 5. Rule vs Macro Testing - **deps_filter rule**: Tests direct rule usage with external deps - **dependencyset macro**: Tests macro-level dependency management - Both approaches should produce equivalent results for the same filtering criteria ================================================ FILE: springboot/deps_filter_rules/tests/external_deps/BUILD ================================================ ================================================ FILE: springboot/deps_filter_rules/tests/external_deps/unmanaged_deps_filter_install.json ================================================ { "__AUTOGENERATED_FILE_DO_NOT_MODIFY_THIS_FILE_MANUALLY": "THERE_IS_NO_DATA_ONLY_ZUUL", "__INPUT_ARTIFACTS_HASH": -1525867914, "__RESOLVED_ARTIFACTS_HASH": -640651985, "conflict_resolution": { "com.fasterxml.jackson.core:jackson-databind:2.17.2": "com.fasterxml.jackson.core:jackson-databind:2.17.3", "org.hibernate.orm:hibernate-core:6.4.4.Final": "org.hibernate.orm:hibernate-core:6.5.3.Final" }, "artifacts": { "ch.qos.logback:logback-classic": { "shasums": { "jar": "3e1533d0321f8815eef46750aee0111b41554f9a4644c3c4d2d404744b09f60f" }, "version": "1.5.18" }, "ch.qos.logback:logback-core": { "shasums": { "jar": "85139e7b57b464f8e5e36326dd81317648bed199ccc4f98cd42585f8d7571027" }, "version": "1.5.18" }, "com.fasterxml.jackson.core:jackson-annotations": { "shasums": { "jar": "2747f60343783a6ec8a68405c7c839fa0bbe30ee4e2459d21a1ac3b7365e1ed5" }, "version": "2.17.3" }, "com.fasterxml.jackson.core:jackson-core": { "shasums": { "jar": "19e03ee71f00a86255fa3c980560b231e1305486f6482c905601209014f5870c" }, "version": "2.17.3" }, "com.fasterxml.jackson.core:jackson-databind": { "shasums": { "jar": "93b13e709a0b620de42019180a75bc1fc4885c81fe5b6087a4aa248f91fb9a95" }, "version": "2.17.3" }, "com.fasterxml.jackson.datatype:jackson-datatype-jdk8": { "shasums": { "jar": "b7207c1df9d89e95efd23793d3a13b1295bec0d9be58b3582ea0dff6cb096fa2" }, "version": "2.17.3" }, "com.fasterxml.jackson.datatype:jackson-datatype-jsr310": { "shasums": { "jar": "b1e3e4be52f69ecf6442d8a07e96ddd200bacb1867cb47460ade87710552a9ee" }, "version": "2.17.3" }, "com.fasterxml.jackson.module:jackson-module-parameter-names": { "shasums": { "jar": "f736404f3a4dc554e7ec816caccfebc68e65d402c2de7ec3c4438f6895179467" }, "version": "2.17.3" }, "com.fasterxml:classmate": { "shasums": { "jar": "aab4de3006808c09d25dd4ff4a3611cfb63c95463cfd99e73d2e1680d229a33b" }, "version": "1.5.1" }, "com.github.stephenc.jcip:jcip-annotations": { "shasums": { "jar": "4fccff8382aafc589962c4edb262f6aa595e34f1e11e61057d1c6a96e8fc7323" }, "version": "1.0-1" }, "com.nimbusds:content-type": { "shasums": { "jar": "730f1816196145e88275093c147f2e6da3c3e541207acd3503a1b06129b9bea9" }, "version": "2.2" }, "com.nimbusds:lang-tag": { "shasums": { "jar": "e8c1c594e2425bdbea2d860de55c69b69fc5d59454452449a0f0913c2a5b8a31" }, "version": "1.7" }, "com.nimbusds:nimbus-jose-jwt": { "shasums": { "jar": "12ae4a3a260095d7aeba2adea7ae396e8b9570db8b7b409e09a824c219cc0444" }, "version": "9.37.3" }, "com.nimbusds:oauth2-oidc-sdk": { "shasums": { "jar": "fee94eae5c4388e1de7fba84e3ada2b92d17bbbb28c630d4258a6f0615c1f303" }, "version": "9.43.6" }, "com.sun.istack:istack-commons-runtime": { "shasums": { "jar": "7e8148c5bf5d5ae6f8c4534c1873f82e80bf7f9164fd09ee573df0013918dcd3" }, "version": "4.1.1" }, "com.zaxxer:HikariCP": { "shasums": { "jar": "a47a6ee62379694ee52c30036f0931b72f9aee2a801d590341ed82bd839e2134" }, "version": "5.1.0" }, "io.micrometer:micrometer-commons": { "shasums": { "jar": "8613395fb4914819610d0b24ccf7345b30ee40e7bc08699cfcfb746bb2cb881d" }, "version": "1.13.13" }, "io.micrometer:micrometer-core": { "shasums": { "jar": "fac100f175ac8e123b87a8dad897717eb81356f086ff1b75aa7a31e8742ca800" }, "version": "1.13.13" }, "io.micrometer:micrometer-jakarta9": { "shasums": { "jar": "5a7f576795be64a1e73b2cacf7ff33afb480b466c4fa9e05c3f447684143473d" }, "version": "1.13.13" }, "io.micrometer:micrometer-observation": { "shasums": { "jar": "35b40b485eb0514ff57fa15cbcd3c0cc850a1c72421cb7090e97e8e191167b99" }, "version": "1.13.13" }, "io.netty:netty-buffer": { "shasums": { "jar": "32226218d854c2e51d4935a7ebe4663b72ecb9af4da881b86bf518e61aed48d3" }, "version": "4.1.119.Final" }, "io.netty:netty-codec": { "shasums": { "jar": "c497934a057444b126a86e06f2b509188e48ca6c5a5e14c182a02f1e8c8d5fdb" }, "version": "4.1.119.Final" }, "io.netty:netty-codec-dns": { "shasums": { "jar": "8893bb399849629eecaa1fa12d48aad73161721b7ce75fdeb72e6e40c549ad55" }, "version": "4.1.119.Final" }, "io.netty:netty-codec-http": { "shasums": { "jar": "ff48db63e44e273e677832e52cc2a1ce2670da796f22af129a8bd4c3786a2d34" }, "version": "4.1.119.Final" }, "io.netty:netty-codec-http2": { "shasums": { "jar": "5ea89af402b6f59715a84780c4cd0388f4e602e339a5b7b888c17ce9f5537d1a" }, "version": "4.1.119.Final" }, "io.netty:netty-codec-socks": { "shasums": { "jar": "a85103bb1a32cf56b8d77e57f6647a859751cab6be189085df76eed18bb54c9a" }, "version": "4.1.119.Final" }, "io.netty:netty-common": { "shasums": { "jar": "991a69b1594dcad9926e268e7e94530cfdaa89feef42af26922a302d3e2e9212" }, "version": "4.1.119.Final" }, "io.netty:netty-handler": { "shasums": { "jar": "9b49be98e36bb79a2025ffb5159aec87da2720cfa545f56de39c3bc108587b1b" }, "version": "4.1.119.Final" }, "io.netty:netty-handler-proxy": { "shasums": { "jar": "7a35e62259a43e5dbdc2e402934b1f64084ce73aecf7b42ce647c918a6e5f617" }, "version": "4.1.119.Final" }, "io.netty:netty-resolver": { "shasums": { "jar": "3b6c9f9f6f360747213d154971dec1fc8852820dc1a98d055ff09d09676f8836" }, "version": "4.1.119.Final" }, "io.netty:netty-resolver-dns": { "shasums": { "jar": "119e1dae4b207197ec6a4b434894894930b0b089a2459a88706d1407cf975b09" }, "version": "4.1.119.Final" }, "io.netty:netty-resolver-dns-classes-macos": { "shasums": { "jar": "c707e72bb03de399a0594c2ed0b017b5eaa2b7ae31892d1944d835deb61a3c1f" }, "version": "4.1.119.Final" }, "io.netty:netty-resolver-dns-native-macos": { "shasums": { "osx-x86_64": "7a1be00ce8dbce562cdb5b59f977aabfd003a62e1b0861eb1b48c0634ec5e8b0" }, "version": "4.1.119.Final" }, "io.netty:netty-transport": { "shasums": { "jar": "c0921ea0e79c3b936daabe08a26e926642a4ad24951d6115fb43362c21dfeb10" }, "version": "4.1.119.Final" }, "io.netty:netty-transport-classes-epoll": { "shasums": { "jar": "38edbceb4d0f3c1c87bc8db9f812d317342c9c8e95a4a052fb796a2f78ad098e" }, "version": "4.1.119.Final" }, "io.netty:netty-transport-native-epoll": { "shasums": { "linux-x86_64": "12557923a5069e736a9305c73a87b303ba9e89b32da3ec95dea6a856f3fd6397" }, "version": "4.1.119.Final" }, "io.netty:netty-transport-native-unix-common": { "shasums": { "jar": "8ae5618f69326e6d17b77b0140f9d277118dbd23906ca07638bc01365728c650" }, "version": "4.1.119.Final" }, "io.projectreactor.netty:reactor-netty-core": { "shasums": { "jar": "d4d7d3519945d869ce352a3642d32f433425efe499a7efe54735c4cf36074091" }, "version": "1.1.29" }, "io.projectreactor.netty:reactor-netty-http": { "shasums": { "jar": "bd1740369bfb4b462db5f46452fed326659094fa6dd7172cb4a5a3dc8300f281" }, "version": "1.1.29" }, "io.projectreactor:reactor-core": { "shasums": { "jar": "0fcbd5f71537c7256c876ffd54fd6f2528ca1bee88544d29d2cc591e1c471b0d" }, "version": "3.6.15" }, "io.smallrye:jandex": { "shasums": { "jar": "dee12fa1787d5523ed1a02d6c63b19e7aef6ac560f7c6d70595db01aa37e041e" }, "version": "3.1.2" }, "jakarta.activation:jakarta.activation-api": { "shasums": { "jar": "33bae3f0f12dbb5a7afc81d802a130359cdb44bbc7fb4b213f49b349d0491a04" }, "version": "2.1.1" }, "jakarta.annotation:jakarta.annotation-api": { "shasums": { "jar": "5f65fdaf424eee2b55e1d882ba9bb376be93fb09b37b808be6e22e8851c909fe" }, "version": "2.1.1" }, "jakarta.inject:jakarta.inject-api": { "shasums": { "jar": "f7dc98062fccf14126abb751b64fab12c312566e8cbdc8483598bffcea93af7c" }, "version": "2.0.1" }, "jakarta.persistence:jakarta.persistence-api": { "shasums": { "jar": "475389446d35c6f46c565728b756dc508c284644ea2690644e0d8e7e339d42fd" }, "version": "3.1.0" }, "jakarta.servlet.jsp:jakarta.servlet.jsp-api": { "shasums": { "jar": "429b24f0049baaad272f4e719fec564739ff33798741f4c94bcb3510944cc5e5" }, "version": "3.1.1" }, "jakarta.transaction:jakarta.transaction-api": { "shasums": { "jar": "50c0a7c760c13ae6c042acf182b28f0047413db95b4636fb8879bcffab5ba875" }, "version": "2.0.1" }, "jakarta.xml.bind:jakarta.xml.bind-api": { "shasums": { "jar": "57e3796ad5753640088f5f9d3c53c183f2c250b7dad90529ea3e19a5515aa122" }, "version": "4.0.0" }, "junit:junit": { "shasums": { "jar": "8e495b634469d64fb8acfa3495a065cbacc8a0fff55ce1e31007be4c16dc57d3" }, "version": "4.13.2" }, "net.bytebuddy:byte-buddy": { "shasums": { "jar": "5add6c7b294b2b2ac60c9a4b54f924cd65e4f10ccfed75d2a99d621d6c5f0a8d" }, "version": "1.14.16" }, "net.minidev:accessors-smart": { "shasums": { "jar": "9b8a7bc43861d6156c021166d941fb7dddbe4463e2fa5ee88077e4b01452a836" }, "version": "2.5.2" }, "net.minidev:json-smart": { "shasums": { "jar": "4fbdedb0105cedc7f766b95c297d2e88fb6a560da48f3bbaa0cc538ea8b7bf71" }, "version": "2.5.2" }, "org.antlr:antlr4-runtime": { "shasums": { "jar": "bd7f7b5d07bc0b047f10915b32ca4bb1de9e57d8049098882e4453c88c076a5d" }, "version": "4.13.0" }, "org.apache.logging.log4j:log4j-api": { "shasums": { "jar": "92ec1fd36ab3bc09de6198d2d7c0914685c0f7127ea931acc32fd2ecdd82ea89" }, "version": "2.23.1" }, "org.apache.logging.log4j:log4j-to-slf4j": { "shasums": { "jar": "7937a84055156910234e3b42868f55e68ff4b7becbb6ffd10146f72f5bf54dd5" }, "version": "2.23.1" }, "org.aspectj:aspectjweaver": { "shasums": { "jar": "75e4227fb7dc5f97c3d4689cd1c2439f4db0bd18cea2fa242c4656cd93c599aa" }, "version": "1.9.24" }, "org.assertj:assertj-core": { "shasums": { "jar": "b0f1b425899001fb6cc856f35318d133b3c4902d6ecdecb0834791268567094f" }, "version": "3.26.0" }, "org.eclipse.angus:angus-activation": { "shasums": { "jar": "3a12d321a0f35aa9458ff9b6ee93a3de76b78e3f18b077c81721473d83079147" }, "version": "2.0.0" }, "org.glassfish.jaxb:jaxb-core": { "shasums": { "jar": "d7ff2954ad78480bbab9391cccff3a22f42a82b6e09aeca1c7d502411c470ccd" }, "version": "4.0.2" }, "org.glassfish.jaxb:jaxb-runtime": { "shasums": { "jar": "1bc271e61b71ca4bd89eb053f3d2c91d478211b02a8982cb520f216fe0e9a939" }, "version": "4.0.2" }, "org.glassfish.jaxb:txw2": { "shasums": { "jar": "ea71912e4f0a42530f77c9840ae90019c46402dedfdf007cff03797429a0cf0c" }, "version": "4.0.2" }, "org.hamcrest:hamcrest-core": { "shasums": { "jar": "66fdef91e9739348df7a096aa384a5685f4e875584cce89386a7a47251c4d8e9" }, "version": "1.3" }, "org.hdrhistogram:HdrHistogram": { "shasums": { "jar": "22d1d4316c4ec13a68b559e98c8256d69071593731da96136640f864fa14fad8" }, "version": "2.2.2" }, "org.hibernate.common:hibernate-commons-annotations": { "shasums": { "jar": "cd974e0a8481fafdbaf9b4a0f08bb5a6c969b0365482763eedf77e6fd7f493b7" }, "version": "6.0.6.Final" }, "org.hibernate.orm:hibernate-core": { "shasums": { "jar": "f79b5e5029a72e2f0ba7542591fba8305c9edbc0dbdc974541f2376ff1203422" }, "version": "6.5.3.Final" }, "org.jboss.logging:jboss-logging": { "shasums": { "jar": "7bb135b081952f6d32d83374619ae5201b05ca3bf862a28dd111016ce19b2c07" }, "version": "3.5.0.Final" }, "org.latencyutils:LatencyUtils": { "shasums": { "jar": "a32a9ffa06b2f4e01c5360f8f9df7bc5d9454a5d373cd8f361347fa5a57165ec" }, "version": "2.0.3" }, "org.ow2.asm:asm": { "shasums": { "jar": "8cadd43ac5eb6d09de05faecca38b917a040bb9139c7edeb4cc81c740b713281" }, "version": "9.7.1" }, "org.reactivestreams:reactive-streams": { "shasums": { "jar": "f75ca597789b3dac58f61857b9ac2e1034a68fa672db35055a8fb4509e325f28" }, "version": "1.0.4" }, "org.slf4j:jul-to-slf4j": { "shasums": { "jar": "a7afcd23b9cfd1475e55c94f943b808c5922035e7e2c2a5c65a487a4106bc538" }, "version": "2.0.17" }, "org.springframework.boot:spring-boot": { "shasums": { "jar": "272efd80096c864ad93edb9c08f450cc37f7f997505a1b0c458587b71a3e6268" }, "version": "3.3.11" }, "org.springframework.boot:spring-boot-actuator": { "shasums": { "jar": "71e5276161f7c12762db6ab300f58d2245c9b08bfb1812575c4b002b332ebceb" }, "version": "3.3.11" }, "org.springframework.boot:spring-boot-actuator-autoconfigure": { "shasums": { "jar": "93890fa4ef7910a898a9e232b4ea1cc4bd8eb6ab4142223ae8d51fca6d6e1f74" }, "version": "3.3.11" }, "org.springframework.boot:spring-boot-autoconfigure": { "shasums": { "jar": "1208dc518180e167fa88ec446b884c83e34dd725710d99a74f641b9365a18c06" }, "version": "3.3.11" }, "org.springframework.boot:spring-boot-starter": { "shasums": { "jar": "b291bc2f379336f694dffed5ce336e8edce9da8a15219db06a11f09320c5dc55" }, "version": "3.3.11" }, "org.springframework.boot:spring-boot-starter-actuator": { "shasums": { "jar": "5c1dfa56fcb647787bcd6a4fe366088f1e5ad17c64d305037b79992e04b1a228" }, "version": "3.3.11" }, "org.springframework.boot:spring-boot-starter-aop": { "shasums": { "jar": "1cf976b4b25c6b760aee40f0ebd124cc204ccc0e7552611caa72c071d6111498" }, "version": "3.3.11" }, "org.springframework.boot:spring-boot-starter-data-jpa": { "shasums": { "jar": "5d7c8a837febe81036be3fdd1e6c3a6c2a23f40bdea49cd32b3f1eae7082288f" }, "version": "3.3.11" }, "org.springframework.boot:spring-boot-starter-jdbc": { "shasums": { "jar": "5ac7ad87c798228c3fe49b795fecc51157c34f491da3955231ff2297796e7c7d" }, "version": "3.3.11" }, "org.springframework.boot:spring-boot-starter-json": { "shasums": { "jar": "92ba33d0391aa614374908b20d1f36d6f1c0f4f826653f3ee3a2aacfbe9f49f1" }, "version": "3.3.11" }, "org.springframework.boot:spring-boot-starter-logging": { "shasums": { "jar": "a1d67dff13759a3026a2b4553a31f6a7ce36b023a64c089d8fb5f8c0b57ef845" }, "version": "3.3.11" }, "org.springframework.boot:spring-boot-starter-oauth2-client": { "shasums": { "jar": "3c6a465d3c50ca0ecca27aeb855337f57f874b169e6016257b85cf3caa071af4" }, "version": "3.3.11" }, "org.springframework.boot:spring-boot-starter-reactor-netty": { "shasums": { "jar": "e74d7a7b7c4f27228aaf8c11b44cb16a70625872d6d289e37b6fdae35aa01667" }, "version": "3.3.11" }, "org.springframework.boot:spring-boot-starter-security": { "shasums": { "jar": "5bf38ff034ab0ba4bc0dbd283b179d891d5474de589023fa4353573bde7465a1" }, "version": "3.3.11" }, "org.springframework.boot:spring-boot-starter-webflux": { "shasums": { "jar": "b94a72c52df6de912200da66a3428db2704bdd65906cf33076fba4b69c878e99" }, "version": "3.3.11" }, "org.springframework.data:spring-data-commons": { "shasums": { "jar": "9b83476c0317eff9efb322147822a80f1d5856d12d854526354d93755c440efd" }, "version": "3.3.11" }, "org.springframework.data:spring-data-jpa": { "shasums": { "jar": "fe1585a655384ae6ccc7772cebf2d55f1b2156cff574be0a313f959387bee6ef" }, "version": "3.3.11" }, "org.springframework.security:spring-security-config": { "shasums": { "jar": "c2b2eb838107c4f6f06a26ae4d6bf895d8661b82299bf382d7fa8aeb23540c88" }, "version": "6.3.9" }, "org.springframework.security:spring-security-core": { "shasums": { "jar": "c3b06c4c7e4cc437363785b94d5ac57af5a08ff54046bfecf4c387220660be06" }, "version": "6.3.9" }, "org.springframework.security:spring-security-crypto": { "shasums": { "jar": "73487877b5a8254800e659a42c0311fe5c26fe9cb780d8ff9d4bca04fd10c1e8" }, "version": "6.3.9" }, "org.springframework.security:spring-security-oauth2-client": { "shasums": { "jar": "d838f0f7e32a6fe61bdc115d01cafa3e34a9264a55f1a45454127ffad3ddf38f" }, "version": "6.3.9" }, "org.springframework.security:spring-security-oauth2-core": { "shasums": { "jar": "01ea819beeea787b7811b219044a4267bf68752661b3d5342714ff2fab01b4a2" }, "version": "6.3.9" }, "org.springframework.security:spring-security-oauth2-jose": { "shasums": { "jar": "c907f67c092fda877a6293201b46f8a324fcb3ed0e1c27de7035622e12f99303" }, "version": "6.3.9" }, "org.springframework.security:spring-security-web": { "shasums": { "jar": "0d452463f5a860da963873842e72dbb96c0198513d19d186cd15fadb111344ab" }, "version": "6.3.9" }, "org.springframework:spring-aop": { "shasums": { "jar": "82bf739839ef60d10562958d7dc087380429845eeeef054315c2efe7b54f2483" }, "version": "6.1.19" }, "org.springframework:spring-aspects": { "shasums": { "jar": "d08965039bedb8f8fdd8a53030d295ea521e36ac6dc3f63af9f53496389213af" }, "version": "6.1.19" }, "org.springframework:spring-beans": { "shasums": { "jar": "84150f8f35ddbf8369a64b657657778486bdae3286557be54b8b3d9f010fad06" }, "version": "6.1.19" }, "org.springframework:spring-context": { "shasums": { "jar": "656af67029d5ba799cfe30b24446645e91c8cf13b5ca726f12c184c5fe78bf74" }, "version": "6.1.19" }, "org.springframework:spring-core": { "shasums": { "jar": "a46e9b693d6be2cce3bc3f2b6ed144c4a7198dcc5c355ca3c63b383d8e911800" }, "version": "6.1.19" }, "org.springframework:spring-expression": { "shasums": { "jar": "b7e3261e447920172dbfa6e9d82f69be084ebed7e156274564b729a0fa2e61ae" }, "version": "6.1.19" }, "org.springframework:spring-jcl": { "shasums": { "jar": "076ebc259dd90ee15bf5f971dc97a04d0432a134178bd7c9d6cf5f15b6085291" }, "version": "6.1.19" }, "org.springframework:spring-jdbc": { "shasums": { "jar": "67bb0c275ac3a9b32e156e2ae637cd0831e37f794c62dc2e271ec6a66c9fa35b" }, "version": "6.1.19" }, "org.springframework:spring-orm": { "shasums": { "jar": "278fea298e0614f4d4a87f732e678a8893b9cf2b5a08ac725127eb793ab814bc" }, "version": "6.1.19" }, "org.springframework:spring-tx": { "shasums": { "jar": "1885574985d8c15c87dbdeb1fc75216dc57e648cc803ac576a53dc8d614a2c2d" }, "version": "6.1.19" }, "org.springframework:spring-web": { "shasums": { "jar": "163d2155b9ac25eb56b26fd5bf667192c4290992bc0444f90033a81f5f6e887e" }, "version": "6.1.19" }, "org.springframework:spring-webflux": { "shasums": { "jar": "5b36df8cb148e5003df7f2bf2fc713c002c883108f27d92a89461c3909d09346" }, "version": "6.1.19" } }, "dependencies": { "ch.qos.logback:logback-classic": [ "ch.qos.logback:logback-core" ], "com.fasterxml.jackson.core:jackson-databind": [ "com.fasterxml.jackson.core:jackson-annotations", "com.fasterxml.jackson.core:jackson-core" ], "com.fasterxml.jackson.datatype:jackson-datatype-jdk8": [ "com.fasterxml.jackson.core:jackson-core", "com.fasterxml.jackson.core:jackson-databind" ], "com.fasterxml.jackson.datatype:jackson-datatype-jsr310": [ "com.fasterxml.jackson.core:jackson-annotations", "com.fasterxml.jackson.core:jackson-core", "com.fasterxml.jackson.core:jackson-databind" ], "com.fasterxml.jackson.module:jackson-module-parameter-names": [ "com.fasterxml.jackson.core:jackson-core", "com.fasterxml.jackson.core:jackson-databind" ], "com.nimbusds:nimbus-jose-jwt": [ "com.github.stephenc.jcip:jcip-annotations" ], "com.nimbusds:oauth2-oidc-sdk": [ "com.github.stephenc.jcip:jcip-annotations", "com.nimbusds:content-type", "com.nimbusds:lang-tag", "com.nimbusds:nimbus-jose-jwt", "net.minidev:json-smart" ], "io.micrometer:micrometer-core": [ "io.micrometer:micrometer-commons", "io.micrometer:micrometer-observation", "org.hdrhistogram:HdrHistogram", "org.latencyutils:LatencyUtils" ], "io.micrometer:micrometer-jakarta9": [ "io.micrometer:micrometer-commons", "io.micrometer:micrometer-core", "io.micrometer:micrometer-observation" ], "io.micrometer:micrometer-observation": [ "io.micrometer:micrometer-commons" ], "io.netty:netty-buffer": [ "io.netty:netty-common" ], "io.netty:netty-codec": [ "io.netty:netty-buffer", "io.netty:netty-common", "io.netty:netty-transport" ], "io.netty:netty-codec-dns": [ "io.netty:netty-buffer", "io.netty:netty-codec", "io.netty:netty-common", "io.netty:netty-transport" ], "io.netty:netty-codec-http": [ "io.netty:netty-buffer", "io.netty:netty-codec", "io.netty:netty-common", "io.netty:netty-handler", "io.netty:netty-transport" ], "io.netty:netty-codec-http2": [ "io.netty:netty-buffer", "io.netty:netty-codec", "io.netty:netty-codec-http", "io.netty:netty-common", "io.netty:netty-handler", "io.netty:netty-transport" ], "io.netty:netty-codec-socks": [ "io.netty:netty-buffer", "io.netty:netty-codec", "io.netty:netty-common", "io.netty:netty-transport" ], "io.netty:netty-handler": [ "io.netty:netty-buffer", "io.netty:netty-codec", "io.netty:netty-common", "io.netty:netty-resolver", "io.netty:netty-transport", "io.netty:netty-transport-native-unix-common" ], "io.netty:netty-handler-proxy": [ "io.netty:netty-buffer", "io.netty:netty-codec", "io.netty:netty-codec-http", "io.netty:netty-codec-socks", "io.netty:netty-common", "io.netty:netty-transport" ], "io.netty:netty-resolver": [ "io.netty:netty-common" ], "io.netty:netty-resolver-dns": [ "io.netty:netty-buffer", "io.netty:netty-codec", "io.netty:netty-codec-dns", "io.netty:netty-common", "io.netty:netty-handler", "io.netty:netty-resolver", "io.netty:netty-transport" ], "io.netty:netty-resolver-dns-classes-macos": [ "io.netty:netty-common", "io.netty:netty-resolver-dns", "io.netty:netty-transport-native-unix-common" ], "io.netty:netty-resolver-dns-native-macos:jar:osx-x86_64": [ "io.netty:netty-resolver-dns-classes-macos" ], "io.netty:netty-transport": [ "io.netty:netty-buffer", "io.netty:netty-common", "io.netty:netty-resolver" ], "io.netty:netty-transport-classes-epoll": [ "io.netty:netty-buffer", "io.netty:netty-common", "io.netty:netty-transport", "io.netty:netty-transport-native-unix-common" ], "io.netty:netty-transport-native-epoll:jar:linux-x86_64": [ "io.netty:netty-buffer", "io.netty:netty-common", "io.netty:netty-transport", "io.netty:netty-transport-classes-epoll", "io.netty:netty-transport-native-unix-common" ], "io.netty:netty-transport-native-unix-common": [ "io.netty:netty-buffer", "io.netty:netty-common", "io.netty:netty-transport" ], "io.projectreactor.netty:reactor-netty-core": [ "io.netty:netty-handler", "io.netty:netty-handler-proxy", "io.netty:netty-resolver-dns", "io.netty:netty-resolver-dns-native-macos:jar:osx-x86_64", "io.netty:netty-transport-native-epoll:jar:linux-x86_64", "io.projectreactor:reactor-core" ], "io.projectreactor.netty:reactor-netty-http": [ "io.netty:netty-codec-http", "io.netty:netty-codec-http2", "io.netty:netty-resolver-dns", "io.netty:netty-resolver-dns-native-macos:jar:osx-x86_64", "io.netty:netty-transport-native-epoll:jar:linux-x86_64", "io.projectreactor.netty:reactor-netty-core", "io.projectreactor:reactor-core" ], "io.projectreactor:reactor-core": [ "org.reactivestreams:reactive-streams" ], "jakarta.xml.bind:jakarta.xml.bind-api": [ "jakarta.activation:jakarta.activation-api" ], "junit:junit": [ "org.hamcrest:hamcrest-core" ], "net.minidev:accessors-smart": [ "org.ow2.asm:asm" ], "net.minidev:json-smart": [ "net.minidev:accessors-smart" ], "org.apache.logging.log4j:log4j-to-slf4j": [ "org.apache.logging.log4j:log4j-api" ], "org.assertj:assertj-core": [ "net.bytebuddy:byte-buddy" ], "org.eclipse.angus:angus-activation": [ "jakarta.activation:jakarta.activation-api" ], "org.glassfish.jaxb:jaxb-core": [ "com.sun.istack:istack-commons-runtime", "jakarta.activation:jakarta.activation-api", "jakarta.xml.bind:jakarta.xml.bind-api", "org.eclipse.angus:angus-activation", "org.glassfish.jaxb:txw2" ], "org.glassfish.jaxb:jaxb-runtime": [ "org.glassfish.jaxb:jaxb-core" ], "org.hibernate.orm:hibernate-core": [ "com.fasterxml:classmate", "io.smallrye:jandex", "jakarta.inject:jakarta.inject-api", "jakarta.persistence:jakarta.persistence-api", "jakarta.transaction:jakarta.transaction-api", "jakarta.xml.bind:jakarta.xml.bind-api", "net.bytebuddy:byte-buddy", "org.antlr:antlr4-runtime", "org.glassfish.jaxb:jaxb-runtime", "org.hibernate.common:hibernate-commons-annotations", "org.jboss.logging:jboss-logging" ], "org.springframework.boot:spring-boot": [ "org.springframework:spring-context", "org.springframework:spring-core" ], "org.springframework.boot:spring-boot-actuator": [ "org.springframework.boot:spring-boot" ], "org.springframework.boot:spring-boot-actuator-autoconfigure": [ "com.fasterxml.jackson.core:jackson-databind", "com.fasterxml.jackson.datatype:jackson-datatype-jsr310", "org.springframework.boot:spring-boot", "org.springframework.boot:spring-boot-actuator", "org.springframework.boot:spring-boot-autoconfigure" ], "org.springframework.boot:spring-boot-autoconfigure": [ "org.springframework.boot:spring-boot" ], "org.springframework.boot:spring-boot-starter": [ "jakarta.annotation:jakarta.annotation-api", "org.springframework.boot:spring-boot", "org.springframework.boot:spring-boot-autoconfigure", "org.springframework.boot:spring-boot-starter-logging", "org.springframework:spring-core" ], "org.springframework.boot:spring-boot-starter-actuator": [ "io.micrometer:micrometer-jakarta9", "io.micrometer:micrometer-observation", "org.springframework.boot:spring-boot-actuator-autoconfigure", "org.springframework.boot:spring-boot-starter" ], "org.springframework.boot:spring-boot-starter-aop": [ "org.aspectj:aspectjweaver", "org.springframework.boot:spring-boot-starter", "org.springframework:spring-aop" ], "org.springframework.boot:spring-boot-starter-data-jpa": [ "org.hibernate.orm:hibernate-core", "org.springframework.boot:spring-boot-starter-aop", "org.springframework.boot:spring-boot-starter-jdbc", "org.springframework.data:spring-data-jpa", "org.springframework:spring-aspects" ], "org.springframework.boot:spring-boot-starter-jdbc": [ "com.zaxxer:HikariCP", "org.springframework.boot:spring-boot-starter", "org.springframework:spring-jdbc" ], "org.springframework.boot:spring-boot-starter-json": [ "com.fasterxml.jackson.core:jackson-databind", "com.fasterxml.jackson.datatype:jackson-datatype-jdk8", "com.fasterxml.jackson.datatype:jackson-datatype-jsr310", "com.fasterxml.jackson.module:jackson-module-parameter-names", "org.springframework.boot:spring-boot-starter", "org.springframework:spring-web" ], "org.springframework.boot:spring-boot-starter-logging": [ "ch.qos.logback:logback-classic", "org.apache.logging.log4j:log4j-to-slf4j", "org.slf4j:jul-to-slf4j" ], "org.springframework.boot:spring-boot-starter-oauth2-client": [ "org.springframework.boot:spring-boot-starter", "org.springframework.security:spring-security-config", "org.springframework.security:spring-security-core", "org.springframework.security:spring-security-oauth2-client", "org.springframework.security:spring-security-oauth2-jose" ], "org.springframework.boot:spring-boot-starter-reactor-netty": [ "io.projectreactor.netty:reactor-netty-http" ], "org.springframework.boot:spring-boot-starter-security": [ "org.springframework.boot:spring-boot-starter", "org.springframework.security:spring-security-config", "org.springframework.security:spring-security-web", "org.springframework:spring-aop" ], "org.springframework.boot:spring-boot-starter-webflux": [ "org.springframework.boot:spring-boot-starter", "org.springframework.boot:spring-boot-starter-json", "org.springframework.boot:spring-boot-starter-reactor-netty", "org.springframework:spring-web", "org.springframework:spring-webflux" ], "org.springframework.data:spring-data-commons": [ "org.springframework:spring-beans", "org.springframework:spring-core" ], "org.springframework.data:spring-data-jpa": [ "jakarta.annotation:jakarta.annotation-api", "org.antlr:antlr4-runtime", "org.springframework.data:spring-data-commons", "org.springframework:spring-aop", "org.springframework:spring-beans", "org.springframework:spring-context", "org.springframework:spring-core", "org.springframework:spring-orm", "org.springframework:spring-tx" ], "org.springframework.security:spring-security-config": [ "org.springframework.security:spring-security-core", "org.springframework:spring-aop", "org.springframework:spring-beans", "org.springframework:spring-context", "org.springframework:spring-core" ], "org.springframework.security:spring-security-core": [ "io.micrometer:micrometer-observation", "org.springframework.security:spring-security-crypto", "org.springframework:spring-aop", "org.springframework:spring-beans", "org.springframework:spring-context", "org.springframework:spring-core", "org.springframework:spring-expression" ], "org.springframework.security:spring-security-oauth2-client": [ "com.nimbusds:oauth2-oidc-sdk", "org.springframework.security:spring-security-core", "org.springframework.security:spring-security-oauth2-core", "org.springframework.security:spring-security-web", "org.springframework:spring-core" ], "org.springframework.security:spring-security-oauth2-core": [ "org.springframework.security:spring-security-core", "org.springframework:spring-core", "org.springframework:spring-web" ], "org.springframework.security:spring-security-oauth2-jose": [ "com.nimbusds:nimbus-jose-jwt", "org.springframework.security:spring-security-core", "org.springframework.security:spring-security-oauth2-core", "org.springframework:spring-core" ], "org.springframework.security:spring-security-web": [ "org.springframework.security:spring-security-core", "org.springframework:spring-aop", "org.springframework:spring-beans", "org.springframework:spring-context", "org.springframework:spring-core", "org.springframework:spring-expression", "org.springframework:spring-web" ], "org.springframework:spring-aop": [ "org.springframework:spring-beans", "org.springframework:spring-core" ], "org.springframework:spring-aspects": [ "org.aspectj:aspectjweaver" ], "org.springframework:spring-beans": [ "org.springframework:spring-core" ], "org.springframework:spring-context": [ "io.micrometer:micrometer-observation", "org.springframework:spring-aop", "org.springframework:spring-beans", "org.springframework:spring-core", "org.springframework:spring-expression" ], "org.springframework:spring-core": [ "org.springframework:spring-jcl" ], "org.springframework:spring-expression": [ "org.springframework:spring-core" ], "org.springframework:spring-jdbc": [ "org.springframework:spring-beans", "org.springframework:spring-core", "org.springframework:spring-tx" ], "org.springframework:spring-orm": [ "org.springframework:spring-beans", "org.springframework:spring-core", "org.springframework:spring-jdbc", "org.springframework:spring-tx" ], "org.springframework:spring-tx": [ "org.springframework:spring-beans", "org.springframework:spring-core" ], "org.springframework:spring-web": [ "io.micrometer:micrometer-observation", "org.springframework:spring-beans", "org.springframework:spring-core" ], "org.springframework:spring-webflux": [ "io.projectreactor:reactor-core", "org.springframework:spring-beans", "org.springframework:spring-core", "org.springframework:spring-web" ] }, "packages": { "ch.qos.logback:logback-classic": [ "ch.qos.logback.classic", "ch.qos.logback.classic.boolex", "ch.qos.logback.classic.encoder", "ch.qos.logback.classic.filter", "ch.qos.logback.classic.helpers", "ch.qos.logback.classic.html", "ch.qos.logback.classic.joran", "ch.qos.logback.classic.joran.action", "ch.qos.logback.classic.joran.sanity", "ch.qos.logback.classic.joran.serializedModel", "ch.qos.logback.classic.jul", "ch.qos.logback.classic.layout", "ch.qos.logback.classic.log4j", "ch.qos.logback.classic.model", "ch.qos.logback.classic.model.processor", "ch.qos.logback.classic.model.util", "ch.qos.logback.classic.net", "ch.qos.logback.classic.net.server", "ch.qos.logback.classic.pattern", "ch.qos.logback.classic.pattern.color", "ch.qos.logback.classic.selector", "ch.qos.logback.classic.selector.servlet", "ch.qos.logback.classic.servlet", "ch.qos.logback.classic.sift", "ch.qos.logback.classic.spi", "ch.qos.logback.classic.turbo", "ch.qos.logback.classic.tyler", "ch.qos.logback.classic.util" ], "ch.qos.logback:logback-core": [ "ch.qos.logback.core", "ch.qos.logback.core.boolex", "ch.qos.logback.core.encoder", "ch.qos.logback.core.filter", "ch.qos.logback.core.helpers", "ch.qos.logback.core.hook", "ch.qos.logback.core.html", "ch.qos.logback.core.joran", "ch.qos.logback.core.joran.action", "ch.qos.logback.core.joran.conditional", "ch.qos.logback.core.joran.event", "ch.qos.logback.core.joran.node", "ch.qos.logback.core.joran.sanity", "ch.qos.logback.core.joran.spi", "ch.qos.logback.core.joran.util", "ch.qos.logback.core.joran.util.beans", "ch.qos.logback.core.layout", "ch.qos.logback.core.model", "ch.qos.logback.core.model.conditional", "ch.qos.logback.core.model.processor", "ch.qos.logback.core.model.processor.conditional", "ch.qos.logback.core.model.util", "ch.qos.logback.core.net", "ch.qos.logback.core.net.server", "ch.qos.logback.core.net.ssl", "ch.qos.logback.core.pattern", "ch.qos.logback.core.pattern.color", "ch.qos.logback.core.pattern.parser", "ch.qos.logback.core.pattern.util", "ch.qos.logback.core.property", "ch.qos.logback.core.read", "ch.qos.logback.core.recovery", "ch.qos.logback.core.rolling", "ch.qos.logback.core.rolling.helper", "ch.qos.logback.core.sift", "ch.qos.logback.core.spi", "ch.qos.logback.core.status", "ch.qos.logback.core.subst", "ch.qos.logback.core.testUtil", "ch.qos.logback.core.util" ], "com.fasterxml.jackson.core:jackson-annotations": [ "com.fasterxml.jackson.annotation" ], "com.fasterxml.jackson.core:jackson-core": [ "com.fasterxml.jackson.core", "com.fasterxml.jackson.core.async", "com.fasterxml.jackson.core.base", "com.fasterxml.jackson.core.exc", "com.fasterxml.jackson.core.filter", "com.fasterxml.jackson.core.format", "com.fasterxml.jackson.core.io", "com.fasterxml.jackson.core.io.doubleparser", "com.fasterxml.jackson.core.io.schubfach", "com.fasterxml.jackson.core.json", "com.fasterxml.jackson.core.json.async", "com.fasterxml.jackson.core.sym", "com.fasterxml.jackson.core.type", "com.fasterxml.jackson.core.util" ], "com.fasterxml.jackson.core:jackson-databind": [ "com.fasterxml.jackson.databind", "com.fasterxml.jackson.databind.annotation", "com.fasterxml.jackson.databind.cfg", "com.fasterxml.jackson.databind.deser", "com.fasterxml.jackson.databind.deser.impl", "com.fasterxml.jackson.databind.deser.std", "com.fasterxml.jackson.databind.exc", "com.fasterxml.jackson.databind.ext", "com.fasterxml.jackson.databind.introspect", "com.fasterxml.jackson.databind.jdk14", "com.fasterxml.jackson.databind.json", "com.fasterxml.jackson.databind.jsonFormatVisitors", "com.fasterxml.jackson.databind.jsonschema", "com.fasterxml.jackson.databind.jsontype", "com.fasterxml.jackson.databind.jsontype.impl", "com.fasterxml.jackson.databind.module", "com.fasterxml.jackson.databind.node", "com.fasterxml.jackson.databind.ser", "com.fasterxml.jackson.databind.ser.impl", "com.fasterxml.jackson.databind.ser.std", "com.fasterxml.jackson.databind.type", "com.fasterxml.jackson.databind.util", "com.fasterxml.jackson.databind.util.internal" ], "com.fasterxml.jackson.datatype:jackson-datatype-jdk8": [ "com.fasterxml.jackson.datatype.jdk8" ], "com.fasterxml.jackson.datatype:jackson-datatype-jsr310": [ "com.fasterxml.jackson.datatype.jsr310", "com.fasterxml.jackson.datatype.jsr310.deser", "com.fasterxml.jackson.datatype.jsr310.deser.key", "com.fasterxml.jackson.datatype.jsr310.ser", "com.fasterxml.jackson.datatype.jsr310.ser.key", "com.fasterxml.jackson.datatype.jsr310.util" ], "com.fasterxml.jackson.module:jackson-module-parameter-names": [ "com.fasterxml.jackson.module.paramnames" ], "com.fasterxml:classmate": [ "com.fasterxml.classmate", "com.fasterxml.classmate.members", "com.fasterxml.classmate.types", "com.fasterxml.classmate.util" ], "com.github.stephenc.jcip:jcip-annotations": [ "net.jcip.annotations" ], "com.nimbusds:content-type": [ "com.nimbusds.common.contenttype" ], "com.nimbusds:lang-tag": [ "com.nimbusds.langtag" ], "com.nimbusds:nimbus-jose-jwt": [ "com.nimbusds.jose", "com.nimbusds.jose.crypto", "com.nimbusds.jose.crypto.bc", "com.nimbusds.jose.crypto.factories", "com.nimbusds.jose.crypto.impl", "com.nimbusds.jose.crypto.opts", "com.nimbusds.jose.crypto.utils", "com.nimbusds.jose.jca", "com.nimbusds.jose.jwk", "com.nimbusds.jose.jwk.gen", "com.nimbusds.jose.jwk.source", "com.nimbusds.jose.mint", "com.nimbusds.jose.proc", "com.nimbusds.jose.produce", "com.nimbusds.jose.shaded.gson", "com.nimbusds.jose.shaded.gson.annotations", "com.nimbusds.jose.shaded.gson.internal", "com.nimbusds.jose.shaded.gson.internal.bind", "com.nimbusds.jose.shaded.gson.internal.bind.util", "com.nimbusds.jose.shaded.gson.internal.reflect", "com.nimbusds.jose.shaded.gson.internal.sql", "com.nimbusds.jose.shaded.gson.reflect", "com.nimbusds.jose.shaded.gson.stream", "com.nimbusds.jose.util", "com.nimbusds.jose.util.cache", "com.nimbusds.jose.util.events", "com.nimbusds.jose.util.health", "com.nimbusds.jwt", "com.nimbusds.jwt.proc", "com.nimbusds.jwt.util" ], "com.nimbusds:oauth2-oidc-sdk": [ "com.nimbusds.oauth2.sdk", "com.nimbusds.oauth2.sdk.as", "com.nimbusds.oauth2.sdk.assertions", "com.nimbusds.oauth2.sdk.assertions.jwt", "com.nimbusds.oauth2.sdk.assertions.saml2", "com.nimbusds.oauth2.sdk.auth", "com.nimbusds.oauth2.sdk.auth.verifier", "com.nimbusds.oauth2.sdk.ciba", "com.nimbusds.oauth2.sdk.client", "com.nimbusds.oauth2.sdk.device", "com.nimbusds.oauth2.sdk.dpop", "com.nimbusds.oauth2.sdk.dpop.verifiers", "com.nimbusds.oauth2.sdk.http", "com.nimbusds.oauth2.sdk.id", "com.nimbusds.oauth2.sdk.jarm", "com.nimbusds.oauth2.sdk.jose", "com.nimbusds.oauth2.sdk.pkce", "com.nimbusds.oauth2.sdk.token", "com.nimbusds.oauth2.sdk.tokenexchange", "com.nimbusds.oauth2.sdk.util", "com.nimbusds.oauth2.sdk.util.date", "com.nimbusds.oauth2.sdk.util.singleuse", "com.nimbusds.oauth2.sdk.util.tls", "com.nimbusds.openid.connect.sdk", "com.nimbusds.openid.connect.sdk.assurance", "com.nimbusds.openid.connect.sdk.assurance.claims", "com.nimbusds.openid.connect.sdk.assurance.evidences", "com.nimbusds.openid.connect.sdk.assurance.evidences.attachment", "com.nimbusds.openid.connect.sdk.assurance.request", "com.nimbusds.openid.connect.sdk.claims", "com.nimbusds.openid.connect.sdk.federation", "com.nimbusds.openid.connect.sdk.federation.api", "com.nimbusds.openid.connect.sdk.federation.config", "com.nimbusds.openid.connect.sdk.federation.entities", "com.nimbusds.openid.connect.sdk.federation.policy", "com.nimbusds.openid.connect.sdk.federation.policy.factories", "com.nimbusds.openid.connect.sdk.federation.policy.language", "com.nimbusds.openid.connect.sdk.federation.policy.operations", "com.nimbusds.openid.connect.sdk.federation.registration", "com.nimbusds.openid.connect.sdk.federation.trust", "com.nimbusds.openid.connect.sdk.federation.trust.constraints", "com.nimbusds.openid.connect.sdk.federation.trust.marks", "com.nimbusds.openid.connect.sdk.id", "com.nimbusds.openid.connect.sdk.op", "com.nimbusds.openid.connect.sdk.rp", "com.nimbusds.openid.connect.sdk.rp.statement", "com.nimbusds.openid.connect.sdk.token", "com.nimbusds.openid.connect.sdk.validators", "com.nimbusds.secevent.sdk.claims" ], "com.sun.istack:istack-commons-runtime": [ "com.sun.istack", "com.sun.istack.localization", "com.sun.istack.logging" ], "com.zaxxer:HikariCP": [ "com.zaxxer.hikari", "com.zaxxer.hikari.hibernate", "com.zaxxer.hikari.metrics", "com.zaxxer.hikari.metrics.dropwizard", "com.zaxxer.hikari.metrics.micrometer", "com.zaxxer.hikari.metrics.prometheus", "com.zaxxer.hikari.pool", "com.zaxxer.hikari.util" ], "io.micrometer:micrometer-commons": [ "io.micrometer.common", "io.micrometer.common.annotation", "io.micrometer.common.docs", "io.micrometer.common.lang", "io.micrometer.common.util", "io.micrometer.common.util.internal.logging" ], "io.micrometer:micrometer-core": [ "io.micrometer.core.annotation", "io.micrometer.core.aop", "io.micrometer.core.instrument", "io.micrometer.core.instrument.binder", "io.micrometer.core.instrument.binder.cache", "io.micrometer.core.instrument.binder.commonspool2", "io.micrometer.core.instrument.binder.db", "io.micrometer.core.instrument.binder.grpc", "io.micrometer.core.instrument.binder.http", "io.micrometer.core.instrument.binder.httpcomponents", "io.micrometer.core.instrument.binder.httpcomponents.hc5", "io.micrometer.core.instrument.binder.hystrix", "io.micrometer.core.instrument.binder.jdk", "io.micrometer.core.instrument.binder.jersey.server", "io.micrometer.core.instrument.binder.jetty", "io.micrometer.core.instrument.binder.jpa", "io.micrometer.core.instrument.binder.jvm", "io.micrometer.core.instrument.binder.kafka", "io.micrometer.core.instrument.binder.logging", "io.micrometer.core.instrument.binder.mongodb", "io.micrometer.core.instrument.binder.netty4", "io.micrometer.core.instrument.binder.okhttp3", "io.micrometer.core.instrument.binder.system", "io.micrometer.core.instrument.binder.tomcat", "io.micrometer.core.instrument.composite", "io.micrometer.core.instrument.config", "io.micrometer.core.instrument.config.validate", "io.micrometer.core.instrument.cumulative", "io.micrometer.core.instrument.distribution", "io.micrometer.core.instrument.distribution.pause", "io.micrometer.core.instrument.docs", "io.micrometer.core.instrument.dropwizard", "io.micrometer.core.instrument.internal", "io.micrometer.core.instrument.kotlin", "io.micrometer.core.instrument.logging", "io.micrometer.core.instrument.noop", "io.micrometer.core.instrument.observation", "io.micrometer.core.instrument.push", "io.micrometer.core.instrument.search", "io.micrometer.core.instrument.simple", "io.micrometer.core.instrument.step", "io.micrometer.core.instrument.util", "io.micrometer.core.ipc.http", "io.micrometer.core.lang", "io.micrometer.core.util.internal.logging" ], "io.micrometer:micrometer-jakarta9": [ "io.micrometer.jakarta9.instrument.jms" ], "io.micrometer:micrometer-observation": [ "io.micrometer.observation", "io.micrometer.observation.annotation", "io.micrometer.observation.aop", "io.micrometer.observation.contextpropagation", "io.micrometer.observation.docs", "io.micrometer.observation.transport" ], "io.netty:netty-buffer": [ "io.netty.buffer", "io.netty.buffer.search" ], "io.netty:netty-codec": [ "io.netty.handler.codec", "io.netty.handler.codec.base64", "io.netty.handler.codec.bytes", "io.netty.handler.codec.compression", "io.netty.handler.codec.json", "io.netty.handler.codec.marshalling", "io.netty.handler.codec.protobuf", "io.netty.handler.codec.serialization", "io.netty.handler.codec.string", "io.netty.handler.codec.xml" ], "io.netty:netty-codec-dns": [ "io.netty.handler.codec.dns" ], "io.netty:netty-codec-http": [ "io.netty.handler.codec.http", "io.netty.handler.codec.http.cookie", "io.netty.handler.codec.http.cors", "io.netty.handler.codec.http.multipart", "io.netty.handler.codec.http.websocketx", "io.netty.handler.codec.http.websocketx.extensions", "io.netty.handler.codec.http.websocketx.extensions.compression", "io.netty.handler.codec.rtsp", "io.netty.handler.codec.spdy" ], "io.netty:netty-codec-http2": [ "io.netty.handler.codec.http2" ], "io.netty:netty-codec-socks": [ "io.netty.handler.codec.socks", "io.netty.handler.codec.socksx", "io.netty.handler.codec.socksx.v4", "io.netty.handler.codec.socksx.v5" ], "io.netty:netty-common": [ "io.netty.util", "io.netty.util.collection", "io.netty.util.concurrent", "io.netty.util.internal", "io.netty.util.internal.logging", "io.netty.util.internal.shaded.org.jctools.counters", "io.netty.util.internal.shaded.org.jctools.maps", "io.netty.util.internal.shaded.org.jctools.queues", "io.netty.util.internal.shaded.org.jctools.queues.atomic", "io.netty.util.internal.shaded.org.jctools.queues.atomic.unpadded", "io.netty.util.internal.shaded.org.jctools.queues.unpadded", "io.netty.util.internal.shaded.org.jctools.util", "io.netty.util.internal.svm" ], "io.netty:netty-handler": [ "io.netty.handler.address", "io.netty.handler.flow", "io.netty.handler.flush", "io.netty.handler.ipfilter", "io.netty.handler.logging", "io.netty.handler.pcap", "io.netty.handler.ssl", "io.netty.handler.ssl.ocsp", "io.netty.handler.ssl.util", "io.netty.handler.stream", "io.netty.handler.timeout", "io.netty.handler.traffic" ], "io.netty:netty-handler-proxy": [ "io.netty.handler.proxy" ], "io.netty:netty-resolver": [ "io.netty.resolver" ], "io.netty:netty-resolver-dns": [ "io.netty.resolver.dns" ], "io.netty:netty-resolver-dns-classes-macos": [ "io.netty.resolver.dns.macos" ], "io.netty:netty-transport": [ "io.netty.bootstrap", "io.netty.channel", "io.netty.channel.embedded", "io.netty.channel.group", "io.netty.channel.internal", "io.netty.channel.local", "io.netty.channel.nio", "io.netty.channel.oio", "io.netty.channel.pool", "io.netty.channel.socket", "io.netty.channel.socket.nio", "io.netty.channel.socket.oio" ], "io.netty:netty-transport-classes-epoll": [ "io.netty.channel.epoll" ], "io.netty:netty-transport-native-unix-common": [ "io.netty.channel.unix" ], "io.projectreactor.netty:reactor-netty-core": [ "reactor.netty", "reactor.netty.channel", "reactor.netty.contextpropagation", "reactor.netty.internal.shaded.reactor.pool", "reactor.netty.internal.shaded.reactor.pool.decorators", "reactor.netty.internal.shaded.reactor.pool.introspection", "reactor.netty.internal.util", "reactor.netty.observability", "reactor.netty.resources", "reactor.netty.tcp", "reactor.netty.transport", "reactor.netty.transport.logging", "reactor.netty.udp" ], "io.projectreactor.netty:reactor-netty-http": [ "reactor.netty.http", "reactor.netty.http.client", "reactor.netty.http.logging", "reactor.netty.http.observability", "reactor.netty.http.server", "reactor.netty.http.server.logging", "reactor.netty.http.websocket" ], "io.projectreactor:reactor-core": [ "reactor.adapter", "reactor.core", "reactor.core.observability", "reactor.core.publisher", "reactor.core.scheduler", "reactor.util", "reactor.util.annotation", "reactor.util.concurrent", "reactor.util.context", "reactor.util.function", "reactor.util.retry" ], "io.smallrye:jandex": [ "org.jboss.jandex" ], "jakarta.activation:jakarta.activation-api": [ "jakarta.activation", "jakarta.activation.spi" ], "jakarta.annotation:jakarta.annotation-api": [ "jakarta.annotation", "jakarta.annotation.security", "jakarta.annotation.sql" ], "jakarta.inject:jakarta.inject-api": [ "jakarta.inject" ], "jakarta.persistence:jakarta.persistence-api": [ "jakarta.persistence", "jakarta.persistence.criteria", "jakarta.persistence.metamodel", "jakarta.persistence.spi" ], "jakarta.servlet.jsp:jakarta.servlet.jsp-api": [ "jakarta.servlet.jsp", "jakarta.servlet.jsp.el", "jakarta.servlet.jsp.tagext" ], "jakarta.transaction:jakarta.transaction-api": [ "jakarta.transaction" ], "jakarta.xml.bind:jakarta.xml.bind-api": [ "jakarta.xml.bind", "jakarta.xml.bind.annotation", "jakarta.xml.bind.annotation.adapters", "jakarta.xml.bind.attachment", "jakarta.xml.bind.helpers", "jakarta.xml.bind.util" ], "junit:junit": [ "junit.extensions", "junit.framework", "junit.runner", "junit.textui", "org.junit", "org.junit.experimental", "org.junit.experimental.categories", "org.junit.experimental.max", "org.junit.experimental.results", "org.junit.experimental.runners", "org.junit.experimental.theories", "org.junit.experimental.theories.internal", "org.junit.experimental.theories.suppliers", "org.junit.function", "org.junit.internal", "org.junit.internal.builders", "org.junit.internal.management", "org.junit.internal.matchers", "org.junit.internal.requests", "org.junit.internal.runners", "org.junit.internal.runners.model", "org.junit.internal.runners.rules", "org.junit.internal.runners.statements", "org.junit.matchers", "org.junit.rules", "org.junit.runner", "org.junit.runner.manipulation", "org.junit.runner.notification", "org.junit.runners", "org.junit.runners.model", "org.junit.runners.parameterized", "org.junit.validator" ], "net.bytebuddy:byte-buddy": [ "net.bytebuddy", "net.bytebuddy.agent.builder", "net.bytebuddy.asm", "net.bytebuddy.build", "net.bytebuddy.description", "net.bytebuddy.description.annotation", "net.bytebuddy.description.enumeration", "net.bytebuddy.description.field", "net.bytebuddy.description.method", "net.bytebuddy.description.modifier", "net.bytebuddy.description.type", "net.bytebuddy.dynamic", "net.bytebuddy.dynamic.loading", "net.bytebuddy.dynamic.scaffold", "net.bytebuddy.dynamic.scaffold.inline", "net.bytebuddy.dynamic.scaffold.subclass", "net.bytebuddy.implementation", "net.bytebuddy.implementation.attribute", "net.bytebuddy.implementation.auxiliary", "net.bytebuddy.implementation.bind", "net.bytebuddy.implementation.bind.annotation", "net.bytebuddy.implementation.bytecode", "net.bytebuddy.implementation.bytecode.assign", "net.bytebuddy.implementation.bytecode.assign.primitive", "net.bytebuddy.implementation.bytecode.assign.reference", "net.bytebuddy.implementation.bytecode.collection", "net.bytebuddy.implementation.bytecode.constant", "net.bytebuddy.implementation.bytecode.member", "net.bytebuddy.jar.asm", "net.bytebuddy.jar.asm.commons", "net.bytebuddy.jar.asm.signature", "net.bytebuddy.matcher", "net.bytebuddy.pool", "net.bytebuddy.utility", "net.bytebuddy.utility.dispatcher", "net.bytebuddy.utility.nullability", "net.bytebuddy.utility.privilege", "net.bytebuddy.utility.visitor" ], "net.minidev:accessors-smart": [ "net.minidev.asm", "net.minidev.asm.ex" ], "net.minidev:json-smart": [ "net.minidev.json", "net.minidev.json.annotate", "net.minidev.json.parser", "net.minidev.json.reader", "net.minidev.json.writer" ], "org.antlr:antlr4-runtime": [ "org.antlr.v4.runtime", "org.antlr.v4.runtime.atn", "org.antlr.v4.runtime.dfa", "org.antlr.v4.runtime.misc", "org.antlr.v4.runtime.tree", "org.antlr.v4.runtime.tree.pattern", "org.antlr.v4.runtime.tree.xpath" ], "org.apache.logging.log4j:log4j-api": [ "org.apache.logging.log4j", "org.apache.logging.log4j.internal", "org.apache.logging.log4j.message", "org.apache.logging.log4j.simple", "org.apache.logging.log4j.spi", "org.apache.logging.log4j.status", "org.apache.logging.log4j.util", "org.apache.logging.log4j.util.internal" ], "org.apache.logging.log4j:log4j-to-slf4j": [ "org.apache.logging.slf4j" ], "org.aspectj:aspectjweaver": [ "aj.org.objectweb.asm", "aj.org.objectweb.asm.commons", "aj.org.objectweb.asm.signature", "org.aspectj.apache.bcel", "org.aspectj.apache.bcel.classfile", "org.aspectj.apache.bcel.classfile.annotation", "org.aspectj.apache.bcel.generic", "org.aspectj.apache.bcel.util", "org.aspectj.asm", "org.aspectj.asm.internal", "org.aspectj.bridge", "org.aspectj.bridge.context", "org.aspectj.internal.lang.annotation", "org.aspectj.internal.lang.reflect", "org.aspectj.lang", "org.aspectj.lang.annotation", "org.aspectj.lang.annotation.control", "org.aspectj.lang.internal.lang", "org.aspectj.lang.reflect", "org.aspectj.runtime", "org.aspectj.runtime.internal", "org.aspectj.runtime.internal.cflowstack", "org.aspectj.runtime.reflect", "org.aspectj.util", "org.aspectj.weaver", "org.aspectj.weaver.ast", "org.aspectj.weaver.bcel", "org.aspectj.weaver.bcel.asm", "org.aspectj.weaver.internal.tools", "org.aspectj.weaver.loadtime", "org.aspectj.weaver.loadtime.definition", "org.aspectj.weaver.ltw", "org.aspectj.weaver.model", "org.aspectj.weaver.patterns", "org.aspectj.weaver.reflect", "org.aspectj.weaver.tools", "org.aspectj.weaver.tools.cache" ], "org.assertj:assertj-core": [ "org.assertj.core.annotations", "org.assertj.core.api", "org.assertj.core.api.exception", "org.assertj.core.api.filter", "org.assertj.core.api.iterable", "org.assertj.core.api.junit.jupiter", "org.assertj.core.api.recursive", "org.assertj.core.api.recursive.assertion", "org.assertj.core.api.recursive.comparison", "org.assertj.core.condition", "org.assertj.core.configuration", "org.assertj.core.data", "org.assertj.core.description", "org.assertj.core.error", "org.assertj.core.error.array2d", "org.assertj.core.error.future", "org.assertj.core.error.uri", "org.assertj.core.extractor", "org.assertj.core.groups", "org.assertj.core.internal", "org.assertj.core.matcher", "org.assertj.core.presentation", "org.assertj.core.util", "org.assertj.core.util.diff", "org.assertj.core.util.diff.myers", "org.assertj.core.util.introspection", "org.assertj.core.util.xml" ], "org.eclipse.angus:angus-activation": [ "org.eclipse.angus.activation", "org.eclipse.angus.activation.nativeimage" ], "org.glassfish.jaxb:jaxb-core": [ "org.glassfish.jaxb.core", "org.glassfish.jaxb.core.annotation", "org.glassfish.jaxb.core.api", "org.glassfish.jaxb.core.api.impl", "org.glassfish.jaxb.core.marshaller", "org.glassfish.jaxb.core.unmarshaller", "org.glassfish.jaxb.core.util", "org.glassfish.jaxb.core.v2", "org.glassfish.jaxb.core.v2.model.annotation", "org.glassfish.jaxb.core.v2.model.core", "org.glassfish.jaxb.core.v2.model.impl", "org.glassfish.jaxb.core.v2.model.nav", "org.glassfish.jaxb.core.v2.model.util", "org.glassfish.jaxb.core.v2.runtime", "org.glassfish.jaxb.core.v2.runtime.unmarshaller", "org.glassfish.jaxb.core.v2.schemagen.episode", "org.glassfish.jaxb.core.v2.util" ], "org.glassfish.jaxb:jaxb-runtime": [ "org.glassfish.jaxb.runtime", "org.glassfish.jaxb.runtime.api", "org.glassfish.jaxb.runtime.marshaller", "org.glassfish.jaxb.runtime.unmarshaller", "org.glassfish.jaxb.runtime.util", "org.glassfish.jaxb.runtime.v2", "org.glassfish.jaxb.runtime.v2.model.annotation", "org.glassfish.jaxb.runtime.v2.model.impl", "org.glassfish.jaxb.runtime.v2.model.runtime", "org.glassfish.jaxb.runtime.v2.runtime", "org.glassfish.jaxb.runtime.v2.runtime.output", "org.glassfish.jaxb.runtime.v2.runtime.property", "org.glassfish.jaxb.runtime.v2.runtime.reflect", "org.glassfish.jaxb.runtime.v2.runtime.reflect.opt", "org.glassfish.jaxb.runtime.v2.runtime.unmarshaller", "org.glassfish.jaxb.runtime.v2.schemagen", "org.glassfish.jaxb.runtime.v2.schemagen.xmlschema", "org.glassfish.jaxb.runtime.v2.util" ], "org.glassfish.jaxb:txw2": [ "com.sun.xml.txw2", "com.sun.xml.txw2.annotation", "com.sun.xml.txw2.output" ], "org.hamcrest:hamcrest-core": [ "org.hamcrest", "org.hamcrest.core", "org.hamcrest.internal" ], "org.hdrhistogram:HdrHistogram": [ "org.HdrHistogram", "org.HdrHistogram.packedarray" ], "org.hibernate.common:hibernate-commons-annotations": [ "org.hibernate.annotations.common.annotationfactory", "org.hibernate.annotations.common.reflection", "org.hibernate.annotations.common.reflection.java", "org.hibernate.annotations.common.reflection.java.generics" ], "org.hibernate.orm:hibernate-core": [ "org.hibernate", "org.hibernate.action.internal", "org.hibernate.action.spi", "org.hibernate.annotations", "org.hibernate.annotations.processing", "org.hibernate.binder", "org.hibernate.binder.internal", "org.hibernate.boot", "org.hibernate.boot.archive.internal", "org.hibernate.boot.archive.scan.internal", "org.hibernate.boot.archive.scan.spi", "org.hibernate.boot.archive.spi", "org.hibernate.boot.beanvalidation", "org.hibernate.boot.cfgxml.internal", "org.hibernate.boot.cfgxml.spi", "org.hibernate.boot.internal", "org.hibernate.boot.jaxb", "org.hibernate.boot.jaxb.cfg.spi", "org.hibernate.boot.jaxb.hbm.internal", "org.hibernate.boot.jaxb.hbm.spi", "org.hibernate.boot.jaxb.hbm.transform", "org.hibernate.boot.jaxb.internal", "org.hibernate.boot.jaxb.internal.stax", "org.hibernate.boot.jaxb.mapping", "org.hibernate.boot.jaxb.mapping.marshall", "org.hibernate.boot.jaxb.spi", "org.hibernate.boot.model", "org.hibernate.boot.model.convert.internal", "org.hibernate.boot.model.convert.spi", "org.hibernate.boot.model.internal", "org.hibernate.boot.model.naming", "org.hibernate.boot.model.process.internal", "org.hibernate.boot.model.process.spi", "org.hibernate.boot.model.relational", "org.hibernate.boot.model.relational.internal", "org.hibernate.boot.model.source.internal", "org.hibernate.boot.model.source.internal.annotations", "org.hibernate.boot.model.source.internal.hbm", "org.hibernate.boot.model.source.spi", "org.hibernate.boot.query", "org.hibernate.boot.registry", "org.hibernate.boot.registry.classloading.internal", "org.hibernate.boot.registry.classloading.spi", "org.hibernate.boot.registry.internal", "org.hibernate.boot.registry.selector", "org.hibernate.boot.registry.selector.internal", "org.hibernate.boot.registry.selector.spi", "org.hibernate.boot.spi", "org.hibernate.boot.xsd", "org.hibernate.bytecode", "org.hibernate.bytecode.enhance", "org.hibernate.bytecode.enhance.internal.bytebuddy", "org.hibernate.bytecode.enhance.internal.tracker", "org.hibernate.bytecode.enhance.spi", "org.hibernate.bytecode.enhance.spi.interceptor", "org.hibernate.bytecode.internal", "org.hibernate.bytecode.internal.bytebuddy", "org.hibernate.bytecode.internal.none", "org.hibernate.bytecode.spi", "org.hibernate.cache", "org.hibernate.cache.cfg.internal", "org.hibernate.cache.cfg.spi", "org.hibernate.cache.internal", "org.hibernate.cache.spi", "org.hibernate.cache.spi.access", "org.hibernate.cache.spi.entry", "org.hibernate.cache.spi.support", "org.hibernate.cfg", "org.hibernate.classic", "org.hibernate.collection.internal", "org.hibernate.collection.spi", "org.hibernate.context", "org.hibernate.context.internal", "org.hibernate.context.spi", "org.hibernate.dialect", "org.hibernate.dialect.aggregate", "org.hibernate.dialect.function", "org.hibernate.dialect.function.array", "org.hibernate.dialect.hint", "org.hibernate.dialect.identity", "org.hibernate.dialect.lock", "org.hibernate.dialect.pagination", "org.hibernate.dialect.sequence", "org.hibernate.dialect.temptable", "org.hibernate.dialect.unique", "org.hibernate.engine", "org.hibernate.engine.config.internal", "org.hibernate.engine.config.spi", "org.hibernate.engine.internal", "org.hibernate.engine.jdbc", "org.hibernate.engine.jdbc.batch", "org.hibernate.engine.jdbc.batch.internal", "org.hibernate.engine.jdbc.batch.spi", "org.hibernate.engine.jdbc.connections.internal", "org.hibernate.engine.jdbc.connections.spi", "org.hibernate.engine.jdbc.cursor.internal", "org.hibernate.engine.jdbc.cursor.spi", "org.hibernate.engine.jdbc.dialect.internal", "org.hibernate.engine.jdbc.dialect.spi", "org.hibernate.engine.jdbc.env.internal", "org.hibernate.engine.jdbc.env.spi", "org.hibernate.engine.jdbc.internal", "org.hibernate.engine.jdbc.mutation", "org.hibernate.engine.jdbc.mutation.group", "org.hibernate.engine.jdbc.mutation.internal", "org.hibernate.engine.jdbc.mutation.spi", "org.hibernate.engine.jdbc.spi", "org.hibernate.engine.jndi", "org.hibernate.engine.jndi.internal", "org.hibernate.engine.jndi.spi", "org.hibernate.engine.profile", "org.hibernate.engine.profile.internal", "org.hibernate.engine.query", "org.hibernate.engine.query.internal", "org.hibernate.engine.query.spi", "org.hibernate.engine.spi", "org.hibernate.engine.transaction.internal", "org.hibernate.engine.transaction.internal.jta", "org.hibernate.engine.transaction.jta.platform.internal", "org.hibernate.engine.transaction.jta.platform.spi", "org.hibernate.engine.transaction.spi", "org.hibernate.event.internal", "org.hibernate.event.service.internal", "org.hibernate.event.service.spi", "org.hibernate.event.spi", "org.hibernate.exception", "org.hibernate.exception.internal", "org.hibernate.exception.spi", "org.hibernate.generator", "org.hibernate.generator.internal", "org.hibernate.generator.values", "org.hibernate.generator.values.internal", "org.hibernate.grammars.graph", "org.hibernate.grammars.hql", "org.hibernate.grammars.importsql", "org.hibernate.grammars.ordering", "org.hibernate.graph", "org.hibernate.graph.internal", "org.hibernate.graph.internal.parse", "org.hibernate.graph.spi", "org.hibernate.id", "org.hibernate.id.enhanced", "org.hibernate.id.factory", "org.hibernate.id.factory.internal", "org.hibernate.id.factory.spi", "org.hibernate.id.insert", "org.hibernate.id.uuid", "org.hibernate.integrator.internal", "org.hibernate.integrator.spi", "org.hibernate.internal", "org.hibernate.internal.build", "org.hibernate.internal.log", "org.hibernate.internal.util", "org.hibernate.internal.util.beans", "org.hibernate.internal.util.collections", "org.hibernate.internal.util.compare", "org.hibernate.internal.util.config", "org.hibernate.internal.util.securitymanager", "org.hibernate.internal.util.type", "org.hibernate.internal.util.xml", "org.hibernate.jdbc", "org.hibernate.jpa", "org.hibernate.jpa.boot.internal", "org.hibernate.jpa.boot.spi", "org.hibernate.jpa.event.internal", "org.hibernate.jpa.event.spi", "org.hibernate.jpa.internal", "org.hibernate.jpa.internal.enhance", "org.hibernate.jpa.internal.util", "org.hibernate.jpa.spi", "org.hibernate.loader", "org.hibernate.loader.ast.internal", "org.hibernate.loader.ast.spi", "org.hibernate.loader.internal", "org.hibernate.mapping", "org.hibernate.metadata", "org.hibernate.metamodel", "org.hibernate.metamodel.internal", "org.hibernate.metamodel.mapping", "org.hibernate.metamodel.mapping.internal", "org.hibernate.metamodel.mapping.ordering", "org.hibernate.metamodel.mapping.ordering.ast", "org.hibernate.metamodel.model.domain", "org.hibernate.metamodel.model.domain.internal", "org.hibernate.metamodel.model.domain.spi", "org.hibernate.metamodel.spi", "org.hibernate.persister.collection", "org.hibernate.persister.collection.mutation", "org.hibernate.persister.entity", "org.hibernate.persister.entity.mutation", "org.hibernate.persister.internal", "org.hibernate.persister.spi", "org.hibernate.persister.walking.spi", "org.hibernate.pretty", "org.hibernate.procedure", "org.hibernate.procedure.internal", "org.hibernate.procedure.spi", "org.hibernate.property.access.internal", "org.hibernate.property.access.spi", "org.hibernate.proxy", "org.hibernate.proxy.map", "org.hibernate.proxy.pojo", "org.hibernate.proxy.pojo.bytebuddy", "org.hibernate.query", "org.hibernate.query.criteria", "org.hibernate.query.criteria.internal", "org.hibernate.query.criteria.spi", "org.hibernate.query.derived", "org.hibernate.query.hql", "org.hibernate.query.hql.internal", "org.hibernate.query.hql.spi", "org.hibernate.query.internal", "org.hibernate.query.named", "org.hibernate.query.procedure", "org.hibernate.query.results", "org.hibernate.query.results.complete", "org.hibernate.query.results.dynamic", "org.hibernate.query.results.implicit", "org.hibernate.query.spi", "org.hibernate.query.sql", "org.hibernate.query.sql.internal", "org.hibernate.query.sql.spi", "org.hibernate.query.sqm", "org.hibernate.query.sqm.function", "org.hibernate.query.sqm.internal", "org.hibernate.query.sqm.mutation.internal", "org.hibernate.query.sqm.mutation.internal.cte", "org.hibernate.query.sqm.mutation.internal.inline", "org.hibernate.query.sqm.mutation.internal.temptable", "org.hibernate.query.sqm.mutation.spi", "org.hibernate.query.sqm.produce.function", "org.hibernate.query.sqm.produce.function.internal", "org.hibernate.query.sqm.spi", "org.hibernate.query.sqm.sql", "org.hibernate.query.sqm.sql.internal", "org.hibernate.query.sqm.tree", "org.hibernate.query.sqm.tree.cte", "org.hibernate.query.sqm.tree.delete", "org.hibernate.query.sqm.tree.domain", "org.hibernate.query.sqm.tree.expression", "org.hibernate.query.sqm.tree.from", "org.hibernate.query.sqm.tree.insert", "org.hibernate.query.sqm.tree.jpa", "org.hibernate.query.sqm.tree.predicate", "org.hibernate.query.sqm.tree.select", "org.hibernate.query.sqm.tree.update", "org.hibernate.relational", "org.hibernate.relational.internal", "org.hibernate.resource.beans.container.internal", "org.hibernate.resource.beans.container.spi", "org.hibernate.resource.beans.internal", "org.hibernate.resource.beans.spi", "org.hibernate.resource.jdbc", "org.hibernate.resource.jdbc.internal", "org.hibernate.resource.jdbc.spi", "org.hibernate.resource.transaction", "org.hibernate.resource.transaction.backend.jdbc.internal", "org.hibernate.resource.transaction.backend.jdbc.spi", "org.hibernate.resource.transaction.backend.jta.internal", "org.hibernate.resource.transaction.backend.jta.internal.synchronization", "org.hibernate.resource.transaction.internal", "org.hibernate.resource.transaction.spi", "org.hibernate.result", "org.hibernate.result.internal", "org.hibernate.result.spi", "org.hibernate.service", "org.hibernate.service.internal", "org.hibernate.service.spi", "org.hibernate.spi", "org.hibernate.sql", "org.hibernate.sql.ast", "org.hibernate.sql.ast.internal", "org.hibernate.sql.ast.spi", "org.hibernate.sql.ast.tree", "org.hibernate.sql.ast.tree.cte", "org.hibernate.sql.ast.tree.delete", "org.hibernate.sql.ast.tree.expression", "org.hibernate.sql.ast.tree.from", "org.hibernate.sql.ast.tree.insert", "org.hibernate.sql.ast.tree.predicate", "org.hibernate.sql.ast.tree.select", "org.hibernate.sql.ast.tree.update", "org.hibernate.sql.exec", "org.hibernate.sql.exec.internal", "org.hibernate.sql.exec.spi", "org.hibernate.sql.model", "org.hibernate.sql.model.ast", "org.hibernate.sql.model.ast.builder", "org.hibernate.sql.model.internal", "org.hibernate.sql.model.jdbc", "org.hibernate.sql.results", "org.hibernate.sql.results.caching", "org.hibernate.sql.results.caching.internal", "org.hibernate.sql.results.graph", "org.hibernate.sql.results.graph.basic", "org.hibernate.sql.results.graph.collection", "org.hibernate.sql.results.graph.collection.internal", "org.hibernate.sql.results.graph.embeddable", "org.hibernate.sql.results.graph.embeddable.internal", "org.hibernate.sql.results.graph.entity", "org.hibernate.sql.results.graph.entity.internal", "org.hibernate.sql.results.graph.instantiation", "org.hibernate.sql.results.graph.instantiation.internal", "org.hibernate.sql.results.graph.internal", "org.hibernate.sql.results.graph.tuple", "org.hibernate.sql.results.internal", "org.hibernate.sql.results.internal.domain", "org.hibernate.sql.results.jdbc.internal", "org.hibernate.sql.results.jdbc.spi", "org.hibernate.sql.results.spi", "org.hibernate.stat", "org.hibernate.stat.internal", "org.hibernate.stat.spi", "org.hibernate.tool.schema", "org.hibernate.tool.schema.extract.internal", "org.hibernate.tool.schema.extract.spi", "org.hibernate.tool.schema.internal", "org.hibernate.tool.schema.internal.exec", "org.hibernate.tool.schema.internal.script", "org.hibernate.tool.schema.spi", "org.hibernate.transform", "org.hibernate.tuple", "org.hibernate.tuple.component", "org.hibernate.tuple.entity", "org.hibernate.type", "org.hibernate.type.descriptor", "org.hibernate.type.descriptor.converter", "org.hibernate.type.descriptor.converter.internal", "org.hibernate.type.descriptor.converter.spi", "org.hibernate.type.descriptor.java", "org.hibernate.type.descriptor.java.spi", "org.hibernate.type.descriptor.jdbc", "org.hibernate.type.descriptor.jdbc.internal", "org.hibernate.type.descriptor.jdbc.spi", "org.hibernate.type.descriptor.sql", "org.hibernate.type.descriptor.sql.internal", "org.hibernate.type.descriptor.sql.spi", "org.hibernate.type.format", "org.hibernate.type.format.jackson", "org.hibernate.type.format.jakartajson", "org.hibernate.type.format.jaxb", "org.hibernate.type.internal", "org.hibernate.type.spi", "org.hibernate.usertype", "org.hibernate.usertype.internal" ], "org.jboss.logging:jboss-logging": [ "org.jboss.logging" ], "org.latencyutils:LatencyUtils": [ "org.LatencyUtils" ], "org.ow2.asm:asm": [ "org.objectweb.asm", "org.objectweb.asm.signature" ], "org.reactivestreams:reactive-streams": [ "org.reactivestreams" ], "org.slf4j:jul-to-slf4j": [ "org.slf4j.bridge" ], "org.springframework.boot:spring-boot": [ "org.springframework.boot", "org.springframework.boot.admin", "org.springframework.boot.ansi", "org.springframework.boot.availability", "org.springframework.boot.builder", "org.springframework.boot.cloud", "org.springframework.boot.context", "org.springframework.boot.context.annotation", "org.springframework.boot.context.config", "org.springframework.boot.context.event", "org.springframework.boot.context.logging", "org.springframework.boot.context.metrics.buffering", "org.springframework.boot.context.properties", "org.springframework.boot.context.properties.bind", "org.springframework.boot.context.properties.bind.handler", "org.springframework.boot.context.properties.bind.validation", "org.springframework.boot.context.properties.source", "org.springframework.boot.convert", "org.springframework.boot.diagnostics", "org.springframework.boot.diagnostics.analyzer", "org.springframework.boot.env", "org.springframework.boot.flyway", "org.springframework.boot.info", "org.springframework.boot.io", "org.springframework.boot.jackson", "org.springframework.boot.jdbc", "org.springframework.boot.jdbc.init", "org.springframework.boot.jdbc.metadata", "org.springframework.boot.jms", "org.springframework.boot.jooq", "org.springframework.boot.json", "org.springframework.boot.liquibase", "org.springframework.boot.logging", "org.springframework.boot.logging.java", "org.springframework.boot.logging.log4j2", "org.springframework.boot.logging.logback", "org.springframework.boot.origin", "org.springframework.boot.orm.jpa", "org.springframework.boot.orm.jpa.hibernate", "org.springframework.boot.r2dbc", "org.springframework.boot.r2dbc.init", "org.springframework.boot.reactor", "org.springframework.boot.rsocket.context", "org.springframework.boot.rsocket.messaging", "org.springframework.boot.rsocket.netty", "org.springframework.boot.rsocket.server", "org.springframework.boot.security.reactive", "org.springframework.boot.security.servlet", "org.springframework.boot.sql.init", "org.springframework.boot.sql.init.dependency", "org.springframework.boot.ssl", "org.springframework.boot.ssl.jks", "org.springframework.boot.ssl.pem", "org.springframework.boot.system", "org.springframework.boot.task", "org.springframework.boot.type.classreading", "org.springframework.boot.util", "org.springframework.boot.validation", "org.springframework.boot.validation.beanvalidation", "org.springframework.boot.web.client", "org.springframework.boot.web.codec", "org.springframework.boot.web.context", "org.springframework.boot.web.embedded.jetty", "org.springframework.boot.web.embedded.netty", "org.springframework.boot.web.embedded.tomcat", "org.springframework.boot.web.embedded.undertow", "org.springframework.boot.web.error", "org.springframework.boot.web.reactive.context", "org.springframework.boot.web.reactive.error", "org.springframework.boot.web.reactive.filter", "org.springframework.boot.web.reactive.function.client", "org.springframework.boot.web.reactive.result.view", "org.springframework.boot.web.reactive.server", "org.springframework.boot.web.server", "org.springframework.boot.web.servlet", "org.springframework.boot.web.servlet.context", "org.springframework.boot.web.servlet.error", "org.springframework.boot.web.servlet.filter", "org.springframework.boot.web.servlet.server", "org.springframework.boot.web.servlet.support", "org.springframework.boot.web.servlet.view", "org.springframework.boot.webservices.client" ], "org.springframework.boot:spring-boot-actuator": [ "org.springframework.boot.actuate.amqp", "org.springframework.boot.actuate.audit", "org.springframework.boot.actuate.audit.listener", "org.springframework.boot.actuate.availability", "org.springframework.boot.actuate.beans", "org.springframework.boot.actuate.cache", "org.springframework.boot.actuate.cassandra", "org.springframework.boot.actuate.context", "org.springframework.boot.actuate.context.properties", "org.springframework.boot.actuate.couchbase", "org.springframework.boot.actuate.data.elasticsearch", "org.springframework.boot.actuate.data.mongo", "org.springframework.boot.actuate.data.redis", "org.springframework.boot.actuate.elasticsearch", "org.springframework.boot.actuate.endpoint", "org.springframework.boot.actuate.endpoint.annotation", "org.springframework.boot.actuate.endpoint.invoke", "org.springframework.boot.actuate.endpoint.invoke.convert", "org.springframework.boot.actuate.endpoint.invoke.reflect", "org.springframework.boot.actuate.endpoint.invoker.cache", "org.springframework.boot.actuate.endpoint.jackson", "org.springframework.boot.actuate.endpoint.jmx", "org.springframework.boot.actuate.endpoint.jmx.annotation", "org.springframework.boot.actuate.endpoint.web", "org.springframework.boot.actuate.endpoint.web.annotation", "org.springframework.boot.actuate.endpoint.web.jersey", "org.springframework.boot.actuate.endpoint.web.reactive", "org.springframework.boot.actuate.endpoint.web.servlet", "org.springframework.boot.actuate.env", "org.springframework.boot.actuate.flyway", "org.springframework.boot.actuate.hazelcast", "org.springframework.boot.actuate.health", "org.springframework.boot.actuate.influx", "org.springframework.boot.actuate.info", "org.springframework.boot.actuate.integration", "org.springframework.boot.actuate.jdbc", "org.springframework.boot.actuate.jms", "org.springframework.boot.actuate.ldap", "org.springframework.boot.actuate.liquibase", "org.springframework.boot.actuate.logging", "org.springframework.boot.actuate.mail", "org.springframework.boot.actuate.management", "org.springframework.boot.actuate.metrics", "org.springframework.boot.actuate.metrics.amqp", "org.springframework.boot.actuate.metrics.annotation", "org.springframework.boot.actuate.metrics.cache", "org.springframework.boot.actuate.metrics.data", "org.springframework.boot.actuate.metrics.export.prometheus", "org.springframework.boot.actuate.metrics.http", "org.springframework.boot.actuate.metrics.jdbc", "org.springframework.boot.actuate.metrics.r2dbc", "org.springframework.boot.actuate.metrics.startup", "org.springframework.boot.actuate.metrics.system", "org.springframework.boot.actuate.metrics.web.client", "org.springframework.boot.actuate.metrics.web.jetty", "org.springframework.boot.actuate.metrics.web.reactive.client", "org.springframework.boot.actuate.metrics.web.tomcat", "org.springframework.boot.actuate.neo4j", "org.springframework.boot.actuate.quartz", "org.springframework.boot.actuate.r2dbc", "org.springframework.boot.actuate.sbom", "org.springframework.boot.actuate.scheduling", "org.springframework.boot.actuate.security", "org.springframework.boot.actuate.session", "org.springframework.boot.actuate.startup", "org.springframework.boot.actuate.system", "org.springframework.boot.actuate.web.exchanges", "org.springframework.boot.actuate.web.exchanges.reactive", "org.springframework.boot.actuate.web.exchanges.servlet", "org.springframework.boot.actuate.web.mappings", "org.springframework.boot.actuate.web.mappings.reactive", "org.springframework.boot.actuate.web.mappings.servlet" ], "org.springframework.boot:spring-boot-actuator-autoconfigure": [ "org.springframework.boot.actuate.autoconfigure", "org.springframework.boot.actuate.autoconfigure.amqp", "org.springframework.boot.actuate.autoconfigure.audit", "org.springframework.boot.actuate.autoconfigure.availability", "org.springframework.boot.actuate.autoconfigure.beans", "org.springframework.boot.actuate.autoconfigure.cache", "org.springframework.boot.actuate.autoconfigure.cassandra", "org.springframework.boot.actuate.autoconfigure.cloudfoundry", "org.springframework.boot.actuate.autoconfigure.cloudfoundry.reactive", "org.springframework.boot.actuate.autoconfigure.cloudfoundry.servlet", "org.springframework.boot.actuate.autoconfigure.condition", "org.springframework.boot.actuate.autoconfigure.context", "org.springframework.boot.actuate.autoconfigure.context.properties", "org.springframework.boot.actuate.autoconfigure.couchbase", "org.springframework.boot.actuate.autoconfigure.data.elasticsearch", "org.springframework.boot.actuate.autoconfigure.data.mongo", "org.springframework.boot.actuate.autoconfigure.data.redis", "org.springframework.boot.actuate.autoconfigure.elasticsearch", "org.springframework.boot.actuate.autoconfigure.endpoint", "org.springframework.boot.actuate.autoconfigure.endpoint.condition", "org.springframework.boot.actuate.autoconfigure.endpoint.expose", "org.springframework.boot.actuate.autoconfigure.endpoint.jackson", "org.springframework.boot.actuate.autoconfigure.endpoint.jmx", "org.springframework.boot.actuate.autoconfigure.endpoint.web", "org.springframework.boot.actuate.autoconfigure.endpoint.web.jersey", "org.springframework.boot.actuate.autoconfigure.endpoint.web.reactive", "org.springframework.boot.actuate.autoconfigure.endpoint.web.servlet", "org.springframework.boot.actuate.autoconfigure.env", "org.springframework.boot.actuate.autoconfigure.flyway", "org.springframework.boot.actuate.autoconfigure.hazelcast", "org.springframework.boot.actuate.autoconfigure.health", "org.springframework.boot.actuate.autoconfigure.influx", "org.springframework.boot.actuate.autoconfigure.info", "org.springframework.boot.actuate.autoconfigure.integration", "org.springframework.boot.actuate.autoconfigure.jdbc", "org.springframework.boot.actuate.autoconfigure.jms", "org.springframework.boot.actuate.autoconfigure.ldap", "org.springframework.boot.actuate.autoconfigure.liquibase", "org.springframework.boot.actuate.autoconfigure.logging", "org.springframework.boot.actuate.autoconfigure.mail", "org.springframework.boot.actuate.autoconfigure.management", "org.springframework.boot.actuate.autoconfigure.metrics", "org.springframework.boot.actuate.autoconfigure.metrics.amqp", "org.springframework.boot.actuate.autoconfigure.metrics.cache", "org.springframework.boot.actuate.autoconfigure.metrics.data", "org.springframework.boot.actuate.autoconfigure.metrics.export", "org.springframework.boot.actuate.autoconfigure.metrics.export.appoptics", "org.springframework.boot.actuate.autoconfigure.metrics.export.atlas", "org.springframework.boot.actuate.autoconfigure.metrics.export.datadog", "org.springframework.boot.actuate.autoconfigure.metrics.export.dynatrace", "org.springframework.boot.actuate.autoconfigure.metrics.export.elastic", "org.springframework.boot.actuate.autoconfigure.metrics.export.ganglia", "org.springframework.boot.actuate.autoconfigure.metrics.export.graphite", "org.springframework.boot.actuate.autoconfigure.metrics.export.humio", "org.springframework.boot.actuate.autoconfigure.metrics.export.influx", "org.springframework.boot.actuate.autoconfigure.metrics.export.jmx", "org.springframework.boot.actuate.autoconfigure.metrics.export.kairos", "org.springframework.boot.actuate.autoconfigure.metrics.export.newrelic", "org.springframework.boot.actuate.autoconfigure.metrics.export.otlp", "org.springframework.boot.actuate.autoconfigure.metrics.export.prometheus", "org.springframework.boot.actuate.autoconfigure.metrics.export.properties", "org.springframework.boot.actuate.autoconfigure.metrics.export.signalfx", "org.springframework.boot.actuate.autoconfigure.metrics.export.simple", "org.springframework.boot.actuate.autoconfigure.metrics.export.stackdriver", "org.springframework.boot.actuate.autoconfigure.metrics.export.statsd", "org.springframework.boot.actuate.autoconfigure.metrics.export.wavefront", "org.springframework.boot.actuate.autoconfigure.metrics.integration", "org.springframework.boot.actuate.autoconfigure.metrics.jdbc", "org.springframework.boot.actuate.autoconfigure.metrics.jersey", "org.springframework.boot.actuate.autoconfigure.metrics.mongo", "org.springframework.boot.actuate.autoconfigure.metrics.orm.jpa", "org.springframework.boot.actuate.autoconfigure.metrics.r2dbc", "org.springframework.boot.actuate.autoconfigure.metrics.redis", "org.springframework.boot.actuate.autoconfigure.metrics.startup", "org.springframework.boot.actuate.autoconfigure.metrics.task", "org.springframework.boot.actuate.autoconfigure.metrics.web.jetty", "org.springframework.boot.actuate.autoconfigure.metrics.web.tomcat", "org.springframework.boot.actuate.autoconfigure.neo4j", "org.springframework.boot.actuate.autoconfigure.observation", "org.springframework.boot.actuate.autoconfigure.observation.batch", "org.springframework.boot.actuate.autoconfigure.observation.graphql", "org.springframework.boot.actuate.autoconfigure.observation.web.client", "org.springframework.boot.actuate.autoconfigure.observation.web.reactive", "org.springframework.boot.actuate.autoconfigure.observation.web.servlet", "org.springframework.boot.actuate.autoconfigure.opentelemetry", "org.springframework.boot.actuate.autoconfigure.quartz", "org.springframework.boot.actuate.autoconfigure.r2dbc", "org.springframework.boot.actuate.autoconfigure.sbom", "org.springframework.boot.actuate.autoconfigure.scheduling", "org.springframework.boot.actuate.autoconfigure.security.reactive", "org.springframework.boot.actuate.autoconfigure.security.servlet", "org.springframework.boot.actuate.autoconfigure.session", "org.springframework.boot.actuate.autoconfigure.startup", "org.springframework.boot.actuate.autoconfigure.system", "org.springframework.boot.actuate.autoconfigure.tracing", "org.springframework.boot.actuate.autoconfigure.tracing.otlp", "org.springframework.boot.actuate.autoconfigure.tracing.prometheus", "org.springframework.boot.actuate.autoconfigure.tracing.wavefront", "org.springframework.boot.actuate.autoconfigure.tracing.zipkin", "org.springframework.boot.actuate.autoconfigure.wavefront", "org.springframework.boot.actuate.autoconfigure.web", "org.springframework.boot.actuate.autoconfigure.web.exchanges", "org.springframework.boot.actuate.autoconfigure.web.jersey", "org.springframework.boot.actuate.autoconfigure.web.mappings", "org.springframework.boot.actuate.autoconfigure.web.reactive", "org.springframework.boot.actuate.autoconfigure.web.server", "org.springframework.boot.actuate.autoconfigure.web.servlet" ], "org.springframework.boot:spring-boot-autoconfigure": [ "org.springframework.boot.autoconfigure", "org.springframework.boot.autoconfigure.admin", "org.springframework.boot.autoconfigure.amqp", "org.springframework.boot.autoconfigure.aop", "org.springframework.boot.autoconfigure.availability", "org.springframework.boot.autoconfigure.batch", "org.springframework.boot.autoconfigure.cache", "org.springframework.boot.autoconfigure.cassandra", "org.springframework.boot.autoconfigure.codec", "org.springframework.boot.autoconfigure.condition", "org.springframework.boot.autoconfigure.context", "org.springframework.boot.autoconfigure.couchbase", "org.springframework.boot.autoconfigure.dao", "org.springframework.boot.autoconfigure.data", "org.springframework.boot.autoconfigure.data.cassandra", "org.springframework.boot.autoconfigure.data.couchbase", "org.springframework.boot.autoconfigure.data.elasticsearch", "org.springframework.boot.autoconfigure.data.jdbc", "org.springframework.boot.autoconfigure.data.jpa", "org.springframework.boot.autoconfigure.data.ldap", "org.springframework.boot.autoconfigure.data.mongo", "org.springframework.boot.autoconfigure.data.neo4j", "org.springframework.boot.autoconfigure.data.r2dbc", "org.springframework.boot.autoconfigure.data.redis", "org.springframework.boot.autoconfigure.data.rest", "org.springframework.boot.autoconfigure.data.web", "org.springframework.boot.autoconfigure.diagnostics.analyzer", "org.springframework.boot.autoconfigure.domain", "org.springframework.boot.autoconfigure.elasticsearch", "org.springframework.boot.autoconfigure.flyway", "org.springframework.boot.autoconfigure.freemarker", "org.springframework.boot.autoconfigure.graphql", "org.springframework.boot.autoconfigure.graphql.data", "org.springframework.boot.autoconfigure.graphql.reactive", "org.springframework.boot.autoconfigure.graphql.rsocket", "org.springframework.boot.autoconfigure.graphql.security", "org.springframework.boot.autoconfigure.graphql.servlet", "org.springframework.boot.autoconfigure.groovy.template", "org.springframework.boot.autoconfigure.gson", "org.springframework.boot.autoconfigure.h2", "org.springframework.boot.autoconfigure.hateoas", "org.springframework.boot.autoconfigure.hazelcast", "org.springframework.boot.autoconfigure.http", "org.springframework.boot.autoconfigure.http.codec", "org.springframework.boot.autoconfigure.influx", "org.springframework.boot.autoconfigure.info", "org.springframework.boot.autoconfigure.integration", "org.springframework.boot.autoconfigure.jackson", "org.springframework.boot.autoconfigure.jdbc", "org.springframework.boot.autoconfigure.jdbc.metadata", "org.springframework.boot.autoconfigure.jersey", "org.springframework.boot.autoconfigure.jms", "org.springframework.boot.autoconfigure.jms.activemq", "org.springframework.boot.autoconfigure.jms.artemis", "org.springframework.boot.autoconfigure.jmx", "org.springframework.boot.autoconfigure.jooq", "org.springframework.boot.autoconfigure.jsonb", "org.springframework.boot.autoconfigure.kafka", "org.springframework.boot.autoconfigure.ldap", "org.springframework.boot.autoconfigure.ldap.embedded", "org.springframework.boot.autoconfigure.liquibase", "org.springframework.boot.autoconfigure.logging", "org.springframework.boot.autoconfigure.mail", "org.springframework.boot.autoconfigure.mongo", "org.springframework.boot.autoconfigure.mustache", "org.springframework.boot.autoconfigure.neo4j", "org.springframework.boot.autoconfigure.netty", "org.springframework.boot.autoconfigure.orm.jpa", "org.springframework.boot.autoconfigure.pulsar", "org.springframework.boot.autoconfigure.quartz", "org.springframework.boot.autoconfigure.r2dbc", "org.springframework.boot.autoconfigure.reactor", "org.springframework.boot.autoconfigure.reactor.netty", "org.springframework.boot.autoconfigure.rsocket", "org.springframework.boot.autoconfigure.security", "org.springframework.boot.autoconfigure.security.oauth2.client", "org.springframework.boot.autoconfigure.security.oauth2.client.reactive", "org.springframework.boot.autoconfigure.security.oauth2.client.servlet", "org.springframework.boot.autoconfigure.security.oauth2.resource", "org.springframework.boot.autoconfigure.security.oauth2.resource.reactive", "org.springframework.boot.autoconfigure.security.oauth2.resource.servlet", "org.springframework.boot.autoconfigure.security.oauth2.server.servlet", "org.springframework.boot.autoconfigure.security.reactive", "org.springframework.boot.autoconfigure.security.rsocket", "org.springframework.boot.autoconfigure.security.saml2", "org.springframework.boot.autoconfigure.security.servlet", "org.springframework.boot.autoconfigure.sendgrid", "org.springframework.boot.autoconfigure.service.connection", "org.springframework.boot.autoconfigure.session", "org.springframework.boot.autoconfigure.sql.init", "org.springframework.boot.autoconfigure.ssl", "org.springframework.boot.autoconfigure.task", "org.springframework.boot.autoconfigure.template", "org.springframework.boot.autoconfigure.thread", "org.springframework.boot.autoconfigure.thymeleaf", "org.springframework.boot.autoconfigure.transaction", "org.springframework.boot.autoconfigure.transaction.jta", "org.springframework.boot.autoconfigure.validation", "org.springframework.boot.autoconfigure.web", "org.springframework.boot.autoconfigure.web.client", "org.springframework.boot.autoconfigure.web.embedded", "org.springframework.boot.autoconfigure.web.format", "org.springframework.boot.autoconfigure.web.reactive", "org.springframework.boot.autoconfigure.web.reactive.error", "org.springframework.boot.autoconfigure.web.reactive.function.client", "org.springframework.boot.autoconfigure.web.servlet", "org.springframework.boot.autoconfigure.web.servlet.error", "org.springframework.boot.autoconfigure.webservices", "org.springframework.boot.autoconfigure.webservices.client", "org.springframework.boot.autoconfigure.websocket.reactive", "org.springframework.boot.autoconfigure.websocket.servlet" ], "org.springframework.data:spring-data-commons": [ "org.springframework.data.annotation", "org.springframework.data.aot", "org.springframework.data.auditing", "org.springframework.data.auditing.config", "org.springframework.data.config", "org.springframework.data.convert", "org.springframework.data.crossstore", "org.springframework.data.domain", "org.springframework.data.domain.jaxb", "org.springframework.data.expression", "org.springframework.data.geo", "org.springframework.data.geo.format", "org.springframework.data.history", "org.springframework.data.mapping", "org.springframework.data.mapping.callback", "org.springframework.data.mapping.context", "org.springframework.data.mapping.model", "org.springframework.data.projection", "org.springframework.data.querydsl", "org.springframework.data.querydsl.aot", "org.springframework.data.querydsl.binding", "org.springframework.data.repository", "org.springframework.data.repository.aot.hint", "org.springframework.data.repository.cdi", "org.springframework.data.repository.config", "org.springframework.data.repository.core", "org.springframework.data.repository.core.support", "org.springframework.data.repository.history", "org.springframework.data.repository.history.support", "org.springframework.data.repository.init", "org.springframework.data.repository.kotlin", "org.springframework.data.repository.query", "org.springframework.data.repository.query.parser", "org.springframework.data.repository.reactive", "org.springframework.data.repository.support", "org.springframework.data.repository.util", "org.springframework.data.spel", "org.springframework.data.spel.spi", "org.springframework.data.support", "org.springframework.data.transaction", "org.springframework.data.type", "org.springframework.data.type.classreading", "org.springframework.data.util", "org.springframework.data.web", "org.springframework.data.web.aot", "org.springframework.data.web.config", "org.springframework.data.web.querydsl" ], "org.springframework.data:spring-data-jpa": [ "org.springframework.data.jpa.convert", "org.springframework.data.jpa.convert.threeten", "org.springframework.data.jpa.domain", "org.springframework.data.jpa.domain.support", "org.springframework.data.jpa.mapping", "org.springframework.data.jpa.projection", "org.springframework.data.jpa.provider", "org.springframework.data.jpa.repository", "org.springframework.data.jpa.repository.aot", "org.springframework.data.jpa.repository.cdi", "org.springframework.data.jpa.repository.config", "org.springframework.data.jpa.repository.query", "org.springframework.data.jpa.repository.support", "org.springframework.data.jpa.support", "org.springframework.data.jpa.util" ], "org.springframework.security:spring-security-config": [ "org.springframework.security.config", "org.springframework.security.config.annotation", "org.springframework.security.config.annotation.authentication", "org.springframework.security.config.annotation.authentication.builders", "org.springframework.security.config.annotation.authentication.configuration", "org.springframework.security.config.annotation.authentication.configurers.ldap", "org.springframework.security.config.annotation.authentication.configurers.provisioning", "org.springframework.security.config.annotation.authentication.configurers.userdetails", "org.springframework.security.config.annotation.configuration", "org.springframework.security.config.annotation.method.configuration", "org.springframework.security.config.annotation.rsocket", "org.springframework.security.config.annotation.web", "org.springframework.security.config.annotation.web.builders", "org.springframework.security.config.annotation.web.configuration", "org.springframework.security.config.annotation.web.configurers", "org.springframework.security.config.annotation.web.configurers.oauth2.client", "org.springframework.security.config.annotation.web.configurers.oauth2.server.resource", "org.springframework.security.config.annotation.web.configurers.saml2", "org.springframework.security.config.annotation.web.headers", "org.springframework.security.config.annotation.web.messaging", "org.springframework.security.config.annotation.web.oauth2.client", "org.springframework.security.config.annotation.web.oauth2.login", "org.springframework.security.config.annotation.web.oauth2.resourceserver", "org.springframework.security.config.annotation.web.reactive", "org.springframework.security.config.annotation.web.saml2", "org.springframework.security.config.annotation.web.servlet.configuration", "org.springframework.security.config.annotation.web.session", "org.springframework.security.config.annotation.web.socket", "org.springframework.security.config.aot.hint", "org.springframework.security.config.authentication", "org.springframework.security.config.core", "org.springframework.security.config.core.userdetails", "org.springframework.security.config.crypto", "org.springframework.security.config.debug", "org.springframework.security.config.http", "org.springframework.security.config.ldap", "org.springframework.security.config.method", "org.springframework.security.config.oauth2.client", "org.springframework.security.config.provisioning", "org.springframework.security.config.saml2", "org.springframework.security.config.web.server", "org.springframework.security.config.websocket" ], "org.springframework.security:spring-security-core": [ "org.springframework.security.access", "org.springframework.security.access.annotation", "org.springframework.security.access.event", "org.springframework.security.access.expression", "org.springframework.security.access.expression.method", "org.springframework.security.access.hierarchicalroles", "org.springframework.security.access.intercept", "org.springframework.security.access.intercept.aopalliance", "org.springframework.security.access.intercept.aspectj", "org.springframework.security.access.method", "org.springframework.security.access.prepost", "org.springframework.security.access.vote", "org.springframework.security.aot.hint", "org.springframework.security.authentication", "org.springframework.security.authentication.dao", "org.springframework.security.authentication.event", "org.springframework.security.authentication.jaas", "org.springframework.security.authentication.jaas.event", "org.springframework.security.authentication.jaas.memory", "org.springframework.security.authentication.password", "org.springframework.security.authorization", "org.springframework.security.authorization.event", "org.springframework.security.authorization.method", "org.springframework.security.concurrent", "org.springframework.security.context", "org.springframework.security.converter", "org.springframework.security.core", "org.springframework.security.core.annotation", "org.springframework.security.core.authority", "org.springframework.security.core.authority.mapping", "org.springframework.security.core.context", "org.springframework.security.core.parameters", "org.springframework.security.core.session", "org.springframework.security.core.token", "org.springframework.security.core.userdetails", "org.springframework.security.core.userdetails.cache", "org.springframework.security.core.userdetails.jdbc", "org.springframework.security.core.userdetails.memory", "org.springframework.security.jackson2", "org.springframework.security.provisioning", "org.springframework.security.scheduling", "org.springframework.security.task", "org.springframework.security.util" ], "org.springframework.security:spring-security-crypto": [ "org.springframework.security.crypto.argon2", "org.springframework.security.crypto.bcrypt", "org.springframework.security.crypto.codec", "org.springframework.security.crypto.encrypt", "org.springframework.security.crypto.factory", "org.springframework.security.crypto.keygen", "org.springframework.security.crypto.password", "org.springframework.security.crypto.scrypt", "org.springframework.security.crypto.util" ], "org.springframework.security:spring-security-oauth2-client": [ "org.springframework.security.oauth2.client", "org.springframework.security.oauth2.client.annotation", "org.springframework.security.oauth2.client.aot.hint", "org.springframework.security.oauth2.client.authentication", "org.springframework.security.oauth2.client.endpoint", "org.springframework.security.oauth2.client.http", "org.springframework.security.oauth2.client.jackson2", "org.springframework.security.oauth2.client.oidc.authentication", "org.springframework.security.oauth2.client.oidc.authentication.logout", "org.springframework.security.oauth2.client.oidc.server.session", "org.springframework.security.oauth2.client.oidc.session", "org.springframework.security.oauth2.client.oidc.userinfo", "org.springframework.security.oauth2.client.oidc.web.logout", "org.springframework.security.oauth2.client.oidc.web.server.logout", "org.springframework.security.oauth2.client.registration", "org.springframework.security.oauth2.client.userinfo", "org.springframework.security.oauth2.client.web", "org.springframework.security.oauth2.client.web.method.annotation", "org.springframework.security.oauth2.client.web.reactive.function.client", "org.springframework.security.oauth2.client.web.reactive.result.method.annotation", "org.springframework.security.oauth2.client.web.server", "org.springframework.security.oauth2.client.web.server.authentication" ], "org.springframework.security:spring-security-oauth2-core": [ "org.springframework.security.oauth2.core", "org.springframework.security.oauth2.core.authorization", "org.springframework.security.oauth2.core.converter", "org.springframework.security.oauth2.core.endpoint", "org.springframework.security.oauth2.core.http.converter", "org.springframework.security.oauth2.core.oidc", "org.springframework.security.oauth2.core.oidc.endpoint", "org.springframework.security.oauth2.core.oidc.user", "org.springframework.security.oauth2.core.user", "org.springframework.security.oauth2.core.web.reactive.function" ], "org.springframework.security:spring-security-oauth2-jose": [ "org.springframework.security.oauth2.jose", "org.springframework.security.oauth2.jose.jws", "org.springframework.security.oauth2.jwt" ], "org.springframework.security:spring-security-web": [ "org.springframework.security.web", "org.springframework.security.web.access", "org.springframework.security.web.access.channel", "org.springframework.security.web.access.expression", "org.springframework.security.web.access.intercept", "org.springframework.security.web.aot.hint", "org.springframework.security.web.authentication", "org.springframework.security.web.authentication.logout", "org.springframework.security.web.authentication.password", "org.springframework.security.web.authentication.preauth", "org.springframework.security.web.authentication.preauth.j2ee", "org.springframework.security.web.authentication.preauth.websphere", "org.springframework.security.web.authentication.preauth.x509", "org.springframework.security.web.authentication.rememberme", "org.springframework.security.web.authentication.session", "org.springframework.security.web.authentication.switchuser", "org.springframework.security.web.authentication.ui", "org.springframework.security.web.authentication.www", "org.springframework.security.web.bind.annotation", "org.springframework.security.web.bind.support", "org.springframework.security.web.context", "org.springframework.security.web.context.request.async", "org.springframework.security.web.context.support", "org.springframework.security.web.csrf", "org.springframework.security.web.debug", "org.springframework.security.web.firewall", "org.springframework.security.web.header", "org.springframework.security.web.header.writers", "org.springframework.security.web.header.writers.frameoptions", "org.springframework.security.web.http", "org.springframework.security.web.jaasapi", "org.springframework.security.web.jackson2", "org.springframework.security.web.method.annotation", "org.springframework.security.web.reactive.result.method.annotation", "org.springframework.security.web.reactive.result.view", "org.springframework.security.web.savedrequest", "org.springframework.security.web.server", "org.springframework.security.web.server.authentication", "org.springframework.security.web.server.authentication.logout", "org.springframework.security.web.server.authorization", "org.springframework.security.web.server.context", "org.springframework.security.web.server.csrf", "org.springframework.security.web.server.firewall", "org.springframework.security.web.server.header", "org.springframework.security.web.server.jackson2", "org.springframework.security.web.server.savedrequest", "org.springframework.security.web.server.transport", "org.springframework.security.web.server.ui", "org.springframework.security.web.server.util.matcher", "org.springframework.security.web.servlet.support.csrf", "org.springframework.security.web.servlet.util.matcher", "org.springframework.security.web.servletapi", "org.springframework.security.web.session", "org.springframework.security.web.util", "org.springframework.security.web.util.matcher" ], "org.springframework:spring-aop": [ "org.aopalliance.aop", "org.aopalliance.intercept", "org.springframework.aop", "org.springframework.aop.aspectj", "org.springframework.aop.aspectj.annotation", "org.springframework.aop.aspectj.autoproxy", "org.springframework.aop.config", "org.springframework.aop.framework", "org.springframework.aop.framework.adapter", "org.springframework.aop.framework.autoproxy", "org.springframework.aop.framework.autoproxy.target", "org.springframework.aop.interceptor", "org.springframework.aop.scope", "org.springframework.aop.support", "org.springframework.aop.support.annotation", "org.springframework.aop.target", "org.springframework.aop.target.dynamic" ], "org.springframework:spring-aspects": [ "org.springframework.beans.factory.aspectj", "org.springframework.cache.aspectj", "org.springframework.context.annotation.aspectj", "org.springframework.scheduling.aspectj", "org.springframework.transaction.aspectj" ], "org.springframework:spring-beans": [ "org.springframework.beans", "org.springframework.beans.factory", "org.springframework.beans.factory.annotation", "org.springframework.beans.factory.aot", "org.springframework.beans.factory.config", "org.springframework.beans.factory.groovy", "org.springframework.beans.factory.parsing", "org.springframework.beans.factory.serviceloader", "org.springframework.beans.factory.support", "org.springframework.beans.factory.wiring", "org.springframework.beans.factory.xml", "org.springframework.beans.propertyeditors", "org.springframework.beans.support" ], "org.springframework:spring-context": [ "org.springframework.cache", "org.springframework.cache.annotation", "org.springframework.cache.concurrent", "org.springframework.cache.config", "org.springframework.cache.interceptor", "org.springframework.cache.support", "org.springframework.context", "org.springframework.context.annotation", "org.springframework.context.aot", "org.springframework.context.config", "org.springframework.context.event", "org.springframework.context.expression", "org.springframework.context.i18n", "org.springframework.context.index", "org.springframework.context.support", "org.springframework.context.weaving", "org.springframework.ejb.config", "org.springframework.format", "org.springframework.format.annotation", "org.springframework.format.datetime", "org.springframework.format.datetime.standard", "org.springframework.format.number", "org.springframework.format.number.money", "org.springframework.format.support", "org.springframework.instrument.classloading", "org.springframework.instrument.classloading.glassfish", "org.springframework.instrument.classloading.jboss", "org.springframework.instrument.classloading.tomcat", "org.springframework.jmx", "org.springframework.jmx.access", "org.springframework.jmx.export", "org.springframework.jmx.export.annotation", "org.springframework.jmx.export.assembler", "org.springframework.jmx.export.metadata", "org.springframework.jmx.export.naming", "org.springframework.jmx.export.notification", "org.springframework.jmx.support", "org.springframework.jndi", "org.springframework.jndi.support", "org.springframework.scheduling", "org.springframework.scheduling.annotation", "org.springframework.scheduling.concurrent", "org.springframework.scheduling.config", "org.springframework.scheduling.support", "org.springframework.scripting", "org.springframework.scripting.bsh", "org.springframework.scripting.config", "org.springframework.scripting.groovy", "org.springframework.scripting.support", "org.springframework.stereotype", "org.springframework.ui", "org.springframework.ui.context", "org.springframework.ui.context.support", "org.springframework.validation", "org.springframework.validation.annotation", "org.springframework.validation.beanvalidation", "org.springframework.validation.method", "org.springframework.validation.support" ], "org.springframework:spring-core": [ "org.springframework.aot", "org.springframework.aot.generate", "org.springframework.aot.hint", "org.springframework.aot.hint.annotation", "org.springframework.aot.hint.predicate", "org.springframework.aot.hint.support", "org.springframework.aot.nativex", "org.springframework.aot.nativex.feature", "org.springframework.aot.nativex.substitution", "org.springframework.asm", "org.springframework.cglib", "org.springframework.cglib.beans", "org.springframework.cglib.core", "org.springframework.cglib.core.internal", "org.springframework.cglib.proxy", "org.springframework.cglib.reflect", "org.springframework.cglib.transform", "org.springframework.cglib.transform.impl", "org.springframework.cglib.util", "org.springframework.core", "org.springframework.core.annotation", "org.springframework.core.codec", "org.springframework.core.convert", "org.springframework.core.convert.converter", "org.springframework.core.convert.support", "org.springframework.core.env", "org.springframework.core.io", "org.springframework.core.io.buffer", "org.springframework.core.io.support", "org.springframework.core.log", "org.springframework.core.metrics", "org.springframework.core.metrics.jfr", "org.springframework.core.serializer", "org.springframework.core.serializer.support", "org.springframework.core.style", "org.springframework.core.task", "org.springframework.core.task.support", "org.springframework.core.type", "org.springframework.core.type.classreading", "org.springframework.core.type.filter", "org.springframework.javapoet", "org.springframework.lang", "org.springframework.objenesis", "org.springframework.objenesis.instantiator", "org.springframework.objenesis.instantiator.android", "org.springframework.objenesis.instantiator.annotations", "org.springframework.objenesis.instantiator.basic", "org.springframework.objenesis.instantiator.gcj", "org.springframework.objenesis.instantiator.perc", "org.springframework.objenesis.instantiator.sun", "org.springframework.objenesis.instantiator.util", "org.springframework.objenesis.strategy", "org.springframework.util", "org.springframework.util.backoff", "org.springframework.util.comparator", "org.springframework.util.concurrent", "org.springframework.util.function", "org.springframework.util.unit", "org.springframework.util.xml" ], "org.springframework:spring-expression": [ "org.springframework.expression", "org.springframework.expression.common", "org.springframework.expression.spel", "org.springframework.expression.spel.ast", "org.springframework.expression.spel.standard", "org.springframework.expression.spel.support" ], "org.springframework:spring-jcl": [ "org.apache.commons.logging", "org.apache.commons.logging.impl" ], "org.springframework:spring-jdbc": [ "org.springframework.jdbc", "org.springframework.jdbc.config", "org.springframework.jdbc.core", "org.springframework.jdbc.core.metadata", "org.springframework.jdbc.core.namedparam", "org.springframework.jdbc.core.simple", "org.springframework.jdbc.core.support", "org.springframework.jdbc.datasource", "org.springframework.jdbc.datasource.embedded", "org.springframework.jdbc.datasource.init", "org.springframework.jdbc.datasource.lookup", "org.springframework.jdbc.object", "org.springframework.jdbc.support", "org.springframework.jdbc.support.incrementer", "org.springframework.jdbc.support.lob", "org.springframework.jdbc.support.rowset", "org.springframework.jdbc.support.xml" ], "org.springframework:spring-orm": [ "org.springframework.orm", "org.springframework.orm.hibernate5", "org.springframework.orm.hibernate5.support", "org.springframework.orm.jpa", "org.springframework.orm.jpa.persistenceunit", "org.springframework.orm.jpa.support", "org.springframework.orm.jpa.vendor" ], "org.springframework:spring-tx": [ "org.springframework.dao", "org.springframework.dao.annotation", "org.springframework.dao.support", "org.springframework.jca.endpoint", "org.springframework.jca.support", "org.springframework.transaction", "org.springframework.transaction.annotation", "org.springframework.transaction.config", "org.springframework.transaction.event", "org.springframework.transaction.interceptor", "org.springframework.transaction.jta", "org.springframework.transaction.reactive", "org.springframework.transaction.support" ], "org.springframework:spring-web": [ "org.springframework.http", "org.springframework.http.client", "org.springframework.http.client.observation", "org.springframework.http.client.reactive", "org.springframework.http.client.support", "org.springframework.http.codec", "org.springframework.http.codec.cbor", "org.springframework.http.codec.json", "org.springframework.http.codec.multipart", "org.springframework.http.codec.protobuf", "org.springframework.http.codec.support", "org.springframework.http.codec.xml", "org.springframework.http.converter", "org.springframework.http.converter.cbor", "org.springframework.http.converter.feed", "org.springframework.http.converter.json", "org.springframework.http.converter.protobuf", "org.springframework.http.converter.smile", "org.springframework.http.converter.support", "org.springframework.http.converter.xml", "org.springframework.http.server", "org.springframework.http.server.observation", "org.springframework.http.server.reactive", "org.springframework.http.server.reactive.observation", "org.springframework.http.support", "org.springframework.web", "org.springframework.web.accept", "org.springframework.web.bind", "org.springframework.web.bind.annotation", "org.springframework.web.bind.support", "org.springframework.web.client", "org.springframework.web.client.support", "org.springframework.web.context", "org.springframework.web.context.annotation", "org.springframework.web.context.request", "org.springframework.web.context.request.async", "org.springframework.web.context.support", "org.springframework.web.cors", "org.springframework.web.cors.reactive", "org.springframework.web.filter", "org.springframework.web.filter.reactive", "org.springframework.web.jsf", "org.springframework.web.jsf.el", "org.springframework.web.method", "org.springframework.web.method.annotation", "org.springframework.web.method.support", "org.springframework.web.multipart", "org.springframework.web.multipart.support", "org.springframework.web.server", "org.springframework.web.server.adapter", "org.springframework.web.server.handler", "org.springframework.web.server.i18n", "org.springframework.web.server.session", "org.springframework.web.service", "org.springframework.web.service.annotation", "org.springframework.web.service.invoker", "org.springframework.web.util", "org.springframework.web.util.pattern" ], "org.springframework:spring-webflux": [ "org.springframework.web.reactive", "org.springframework.web.reactive.accept", "org.springframework.web.reactive.config", "org.springframework.web.reactive.function", "org.springframework.web.reactive.function.client", "org.springframework.web.reactive.function.client.support", "org.springframework.web.reactive.function.server", "org.springframework.web.reactive.function.server.support", "org.springframework.web.reactive.handler", "org.springframework.web.reactive.resource", "org.springframework.web.reactive.result", "org.springframework.web.reactive.result.condition", "org.springframework.web.reactive.result.method", "org.springframework.web.reactive.result.method.annotation", "org.springframework.web.reactive.result.view", "org.springframework.web.reactive.result.view.freemarker", "org.springframework.web.reactive.result.view.script", "org.springframework.web.reactive.server", "org.springframework.web.reactive.socket", "org.springframework.web.reactive.socket.adapter", "org.springframework.web.reactive.socket.client", "org.springframework.web.reactive.socket.server", "org.springframework.web.reactive.socket.server.support", "org.springframework.web.reactive.socket.server.upgrade" ] }, "repositories": { "https://repo1.maven.org/maven2/": [ "ch.qos.logback:logback-classic", "ch.qos.logback:logback-core", "com.fasterxml.jackson.core:jackson-annotations", "com.fasterxml.jackson.core:jackson-core", "com.fasterxml.jackson.core:jackson-databind", "com.fasterxml.jackson.datatype:jackson-datatype-jdk8", "com.fasterxml.jackson.datatype:jackson-datatype-jsr310", "com.fasterxml.jackson.module:jackson-module-parameter-names", "com.fasterxml:classmate", "com.github.stephenc.jcip:jcip-annotations", "com.nimbusds:content-type", "com.nimbusds:lang-tag", "com.nimbusds:nimbus-jose-jwt", "com.nimbusds:oauth2-oidc-sdk", "com.sun.istack:istack-commons-runtime", "com.zaxxer:HikariCP", "io.micrometer:micrometer-commons", "io.micrometer:micrometer-core", "io.micrometer:micrometer-jakarta9", "io.micrometer:micrometer-observation", "io.netty:netty-buffer", "io.netty:netty-codec", "io.netty:netty-codec-dns", "io.netty:netty-codec-http", "io.netty:netty-codec-http2", "io.netty:netty-codec-socks", "io.netty:netty-common", "io.netty:netty-handler", "io.netty:netty-handler-proxy", "io.netty:netty-resolver", "io.netty:netty-resolver-dns", "io.netty:netty-resolver-dns-classes-macos", "io.netty:netty-resolver-dns-native-macos:jar:osx-x86_64", "io.netty:netty-transport", "io.netty:netty-transport-classes-epoll", "io.netty:netty-transport-native-epoll:jar:linux-x86_64", "io.netty:netty-transport-native-unix-common", "io.projectreactor.netty:reactor-netty-core", "io.projectreactor.netty:reactor-netty-http", "io.projectreactor:reactor-core", "io.smallrye:jandex", "jakarta.activation:jakarta.activation-api", "jakarta.annotation:jakarta.annotation-api", "jakarta.inject:jakarta.inject-api", "jakarta.persistence:jakarta.persistence-api", "jakarta.servlet.jsp:jakarta.servlet.jsp-api", "jakarta.transaction:jakarta.transaction-api", "jakarta.xml.bind:jakarta.xml.bind-api", "junit:junit", "net.bytebuddy:byte-buddy", "net.minidev:accessors-smart", "net.minidev:json-smart", "org.antlr:antlr4-runtime", "org.apache.logging.log4j:log4j-api", "org.apache.logging.log4j:log4j-to-slf4j", "org.aspectj:aspectjweaver", "org.assertj:assertj-core", "org.eclipse.angus:angus-activation", "org.glassfish.jaxb:jaxb-core", "org.glassfish.jaxb:jaxb-runtime", "org.glassfish.jaxb:txw2", "org.hamcrest:hamcrest-core", "org.hdrhistogram:HdrHistogram", "org.hibernate.common:hibernate-commons-annotations", "org.hibernate.orm:hibernate-core", "org.jboss.logging:jboss-logging", "org.latencyutils:LatencyUtils", "org.ow2.asm:asm", "org.reactivestreams:reactive-streams", "org.slf4j:jul-to-slf4j", "org.springframework.boot:spring-boot", "org.springframework.boot:spring-boot-actuator", "org.springframework.boot:spring-boot-actuator-autoconfigure", "org.springframework.boot:spring-boot-autoconfigure", "org.springframework.boot:spring-boot-starter", "org.springframework.boot:spring-boot-starter-actuator", "org.springframework.boot:spring-boot-starter-aop", "org.springframework.boot:spring-boot-starter-data-jpa", "org.springframework.boot:spring-boot-starter-jdbc", "org.springframework.boot:spring-boot-starter-json", "org.springframework.boot:spring-boot-starter-logging", "org.springframework.boot:spring-boot-starter-oauth2-client", "org.springframework.boot:spring-boot-starter-reactor-netty", "org.springframework.boot:spring-boot-starter-security", "org.springframework.boot:spring-boot-starter-webflux", "org.springframework.data:spring-data-commons", "org.springframework.data:spring-data-jpa", "org.springframework.security:spring-security-config", "org.springframework.security:spring-security-core", "org.springframework.security:spring-security-crypto", "org.springframework.security:spring-security-oauth2-client", "org.springframework.security:spring-security-oauth2-core", "org.springframework.security:spring-security-oauth2-jose", "org.springframework.security:spring-security-web", "org.springframework:spring-aop", "org.springframework:spring-aspects", "org.springframework:spring-beans", "org.springframework:spring-context", "org.springframework:spring-core", "org.springframework:spring-expression", "org.springframework:spring-jcl", "org.springframework:spring-jdbc", "org.springframework:spring-orm", "org.springframework:spring-tx", "org.springframework:spring-web", "org.springframework:spring-webflux" ] }, "services": { "ch.qos.logback:logback-classic": { "jakarta.servlet.ServletContainerInitializer": [ "ch.qos.logback.classic.servlet.LogbackServletContainerInitializer" ], "org.slf4j.spi.SLF4JServiceProvider": [ "ch.qos.logback.classic.spi.LogbackServiceProvider" ] }, "com.fasterxml.jackson.core:jackson-core": { "com.fasterxml.jackson.core.JsonFactory": [ "com.fasterxml.jackson.core.JsonFactory" ] }, "com.fasterxml.jackson.core:jackson-databind": { "com.fasterxml.jackson.core.ObjectCodec": [ "com.fasterxml.jackson.databind.ObjectMapper" ] }, "com.fasterxml.jackson.datatype:jackson-datatype-jdk8": { "com.fasterxml.jackson.databind.Module": [ "com.fasterxml.jackson.datatype.jdk8.Jdk8Module" ] }, "com.fasterxml.jackson.datatype:jackson-datatype-jsr310": { "com.fasterxml.jackson.databind.Module": [ "com.fasterxml.jackson.datatype.jsr310.JavaTimeModule" ] }, "com.fasterxml.jackson.module:jackson-module-parameter-names": { "com.fasterxml.jackson.databind.Module": [ "com.fasterxml.jackson.module.paramnames.ParameterNamesModule" ] }, "io.micrometer:micrometer-observation": { "io.micrometer.context.ThreadLocalAccessor": [ "io.micrometer.observation.contextpropagation.ObservationThreadLocalAccessor" ] }, "io.netty:netty-common": { "reactor.blockhound.integration.BlockHoundIntegration": [ "io.netty.util.internal.Hidden$NettyBlockHoundIntegration" ] }, "io.projectreactor.netty:reactor-netty-core": { "io.micrometer.context.ContextAccessor": [ "reactor.netty.contextpropagation.ChannelContextAccessor" ] }, "io.projectreactor:reactor-core": { "io.micrometer.context.ContextAccessor": [ "reactor.util.context.ReactorContextAccessor" ], "reactor.blockhound.integration.BlockHoundIntegration": [ "reactor.core.scheduler.ReactorBlockHoundIntegration" ] }, "org.apache.logging.log4j:log4j-api": { "org.apache.logging.log4j.util.PropertySource": [ "org.apache.logging.log4j.util.EnvironmentPropertySource", "org.apache.logging.log4j.util.SystemPropertiesPropertySource" ] }, "org.apache.logging.log4j:log4j-to-slf4j": { "org.apache.logging.log4j.spi.Provider": [ "org.apache.logging.slf4j.SLF4JProvider" ] }, "org.eclipse.angus:angus-activation": { "jakarta.activation.spi.MailcapRegistryProvider": [ "org.eclipse.angus.activation.MailcapRegistryProviderImpl" ], "jakarta.activation.spi.MimeTypeRegistryProvider": [ "org.eclipse.angus.activation.MimeTypeRegistryProviderImpl" ] }, "org.glassfish.jaxb:jaxb-runtime": { "jakarta.xml.bind.JAXBContextFactory": [ "org.glassfish.jaxb.runtime.v2.JAXBContextFactory" ] }, "org.hibernate.orm:hibernate-core": { "jakarta.persistence.spi.PersistenceProvider": [ "org.hibernate.jpa.HibernatePersistenceProvider" ], "org.hibernate.bytecode.spi.BytecodeProvider": [ "org.hibernate.bytecode.internal.bytebuddy.BytecodeProviderImpl" ] }, "org.springframework.boot:spring-boot": { "ch.qos.logback.classic.spi.Configurator": [ "org.springframework.boot.logging.logback.RootLogLevelConfigurator" ], "org.apache.logging.log4j.util.PropertySource": [ "org.springframework.boot.logging.log4j2.SpringBootPropertySource" ] }, "org.springframework.data:spring-data-jpa": { "jakarta.enterprise.inject.spi.Extension": [ "org.springframework.data.jpa.repository.cdi.JpaRepositoryExtension" ] }, "org.springframework:spring-core": { "reactor.blockhound.integration.BlockHoundIntegration": [ "org.springframework.core.ReactiveAdapterRegistry$SpringCoreBlockHoundIntegration" ] }, "org.springframework:spring-jcl": { "org.apache.commons.logging.LogFactory": [ "org.apache.commons.logging.LogFactoryService" ] }, "org.springframework:spring-web": { "jakarta.servlet.ServletContainerInitializer": [ "org.springframework.web.SpringServletContainerInitializer" ], "reactor.blockhound.integration.BlockHoundIntegration": [ "org.springframework.web.server.adapter.WebHttpHandlerBuilder$SpringWebBlockHoundIntegration" ] } }, "version": "2" } ================================================ FILE: springboot/deps_filter_rules/tests/internal_dependencies_testing.md ================================================ # Internal Dependencies Testing `internal_dependencies` under both `depsfilter` and `dependencyset` contain comprehensive tests for the `deps_filter` rule and `dependencyset` macro, which filters compile-time and runtime dependencies in Java projects. The tests cover various dependency scenarios and filtering mechanisms to ensure the rule works correctly across different use cases. ## Directory Structure ``` tests/ ├── depsfilter/ │ └── internal_dependencies/ │ ├── compile_time_only/ │ ├── runtime_only/ │ ├── compile_and_runtime_1/ │ └── compile_and_runtime_2/ └── dependencyset/ └── internal_dependencies/ ├── compile_time_only/ ├── runtime_only/ ├── compile_and_runtime_1/ └── compile_and_runtime_2/ ``` ## Testing Approach Similar testing scenarios are implemented using two different approaches: ### 1. Deps Filter Rule Testing **Pattern**: `base_lib -> deps_filter() -> bazel starlark/java tests` **Example from compile_and_runtime_1**: ```bazel # Base library with dependencies java_library( name = "base_lib", srcs = ["src/main/java/com/depsfilter/H.java"], deps = [":lib_a"], runtime_deps = [":lib_g"], ) # Apply filtering deps_filter( name = "filtered_deps_exclude_b_g", deps = [":base_lib"], deps_exclude_labels = [":lib_b", ":lib_g"], ) # Test the filtered result filtered_deps_test( name = "deps_filter_exclude_b_g_test", filtered = ":filtered_deps_exclude_b_g", ) ``` **Exception in compile_and_runtime_2**: No base_lib, direct `deps` and `runtime_deps` specified in `deps_filter` rule: ```bazel deps_filter( name = "filtered_deps_exclude_b_g", deps = [":lib_a", ":lib_i"], runtime_deps = [":lib_h", ":lib_j"], deps_exclude_labels = [":lib_b", ":lib_g"], ) filtered_deps_test( name = "deps_filter_exclude_b_g_test", filtered = ":filtered_deps_exclude_b_g", ) ``` ### 2. Dependencyset Macro Testing **Pattern**: `dependencyset("deps), dependencyset("runtime_deps") -> java_library -> bazel starlark/java tests` **Consistent approach across all test categories**: ```bazel # Create filtered dependency sets dependencyset( name = "deps_exclude_b_g", items = [":lib_a", ":lib_i"], deps_exclude_labels = [":lib_b", ":lib_g"], ) dependencyset( name = "runtime_deps_exclude_b_g", items = [":lib_h", ":lib_j"], deps_exclude_labels = [":lib_b", ":lib_g"], ) # Create test library using filtered sets java_library( name = "exclude_b_g_test_lib", srcs = ["src/main/java/com/depsfilter/H.java"], deps = [":deps_exclude_b_g"], runtime_deps = [":runtime_deps_exclude_b_g"], ) # Test the filtered result filtered_deps_test( name = "deps_filter_exclude_b_g_test", test_lib = ":exclude_b_g_test_lib", ) # Java test for runtime verification java_test( name = "DepsFilterFilteredDepsTest", size = "small", srcs = [ "src/test/java/com/depsfilter/DepsFilterTestHelper.java", "src/test/java/com/depsfilter/DepsFilterFilteredDepsTest.java" ], deps = [":exclude_b_g_test_lib"] + test_deps, ) ``` ## Test Structure The testing is organized into four main categories, each focusing on different aspects of dependency filtering: ### 1. `compile_time_only/` **Purpose**: Tests dependency filtering when only compile-time dependencies are present. **Key Characteristics**: - All dependencies are compile-time (`deps` attribute) - No runtime dependencies (`runtime_deps` attribute) - Tests both interface JARs (`-hjar`) and implementation JARs **Test Scenarios**: - **No Filtering**: Verifies that `deps_filter`/`dependencyset` preserves all dependencies when no exclusions are applied - **Basic Filtering**: Tests label-based exclusions with `exclude_transitives=False` - **Transitive Exclusions**: Tests label-based exclusions with `exclude_transitives=True` - **Path-based Exclusions**: Tests filtering based on path patterns **Dependency Graph for depsfilter**: ``` base_lib / \ A G / \ / B E / | | / | F \ / C | D ``` **Dependency Graph for dependencyset**: ``` base_lib | dependencyset() / \ A I / \ / B E G | | / | F \ / C | D ``` ### 2. `runtime_only/` **Purpose**: Tests dependency filtering when only runtime dependencies are present. **Key Characteristics**: - All dependencies are runtime (`runtime_deps` attribute) - No compile-time dependencies (`deps` attribute) - Focuses on runtime JARs only **Test Scenarios**: - **No Filtering**: Verifies preservation of all runtime dependencies - **Basic Filtering**: Tests label-based exclusions for runtime deps - **Transitive Exclusions**: Tests transitive exclusion behavior for runtime deps - **Path-based Exclusions**: Tests path pattern filtering for runtime deps **Dependency Graph**: Same as compile_time_only, but all edges represent runtime dependencies. ### 3. `compile_and_runtime_1/` **Purpose**: Tests mixed compile-time and runtime dependencies with a single direct dep. **Key Characteristics**: - Mixed compile-time and runtime dependencies - Single root dependency (`base_lib`) - Tests interface vs implementation JAR distinction **Test Scenarios**: - **No Filtering**: Verifies preservation of both compile and runtime JARs - **Basic Filtering**: Tests label-based exclusions preserving transitives - **Transitive Exclusions**: Tests label-based exclusions with transitives removal - **Path-based Exclusions**: Tests path pattern filtering **Dependency Graph for depsfilter**: ``` base_lib / \ A (c) G (r) / \ | / \ | / \ | B (c) E (r) / | | / | | / | F (c) \ / C (c) | D (r) ``` **Dependency Graph for dependencyset**: ``` base_lib | dependencyset() / \ A (c) I (r) / \ | / \ G (r) / \ | B (c) E (r) / | | / | | / | F (c) \ / C (c) | D (r) ``` **Legend**: (c) = compile-time dependency, (r) = runtime dependency ### 4. `compile_and_runtime_2/` **Purpose**: Tests complex mixed dependencies with multiple deps and runtime deps, and cross-branch connections. **Key Characteristics**: - More than one deps and runtime deps (A, I for compile; H, J for runtime) - Cross-branch dependencies - More complex dependency graph - Tests interface/implementation JAR handling **Test Scenarios**: - **Filtered Dependencies**: Basic label-based exclusions - **Transitive Exclusions**: Label-based exclusions with transitives removal - **Path-based Exclusions**: Path pattern filtering - **Interface/Implementation JARs**: Tests proper handling of -hjar vs full JARs - **Multiple Exclusions**: Combined label and path exclusions - **Empty Exclusions**: Behavior with no exclusions - **Multiple Paths**: Handling of multiple paths to same dependency **Dependency Graph for depsfilter**: ``` J(r) A (c) H (r) I (c) \ / \ | | \ / \ G (r) | \ / \ | / B (c) E (r) / / | | / / | | / / | | / / | | / / | F (c) \ / C (c) | D (r) ``` **Dependency Graph for dependencyset**: ``` test_lib | dependencyset / \ ("deps") ("runtime_deps") / \ / \ J(r) A (c) H (r) I (c) \ / \ | | \ / \ G (r) | \ / \ | / B (c) E (r) / / | | / / | | / / | | / / | | / / | F (c) \ / C (c) | D (r) ``` ## Test Verification Each test verifies the following JAR fields: - **`compile_jars`**: Interface JARs (e.g., `liblib_a-hjar.jar`) - **`full_compile_jars`**: Implementation JARs (e.g., `liblib_a.jar`) - **`transitive_compile_time_jars`**: Transitive interface JARs - **`transitive_runtime_jars`**: Transitive implementation JARs ## Java Test Files Each test scenario includes corresponding Java test files that: - Verify the jars available at runtime - Use centralized test helper (`DepsFilterTestHelper`) ## Key Testing Concepts ### 1. Label-based Exclusions - Excludes dependencies by their Bazel label - Can optionally exclude transitive dependencies - More precise than path-based exclusions ### 2. Path-based Exclusions - Excludes dependencies matching path patterns - Less precise but more flexible - Does not exclude transitives (exclude_transitives = true doesn't work) ### 3. Transitive Exclusion Behavior - `exclude_transitives=False`: Only excludes direct dependencies, preserves transitives - `exclude_transitives=True`: Excludes both direct and transitive dependencies ### 4. Interface vs Implementation JARs - Interface JARs (`-hjar`) contain only public APIs - Implementation JARs contain full class implementations - Both are verified in tests to ensure proper filtering ### 5. Compile-time vs Runtime Dependencies - Compile-time dependencies are needed during compilation - Runtime dependencies are needed during execution - Tests verify proper handling of both types ### 6. Rule vs Macro Testing - **deps_filter rule**: Tests direct rule usage with synthetic dependency graphs - **dependencyset macro**: Tests macro-level dependency management - Both approaches should produce equivalent results for the same filtering criteria ## Test Coverage The test suite covers: - Basic dependency filtering functionality - Label-based exclusion mechanisms - Path-based exclusion mechanisms - Transitive dependency handling - Interface vs implementation JAR distinction - Mixed compile-time and runtime dependencies - Multiple deps and runtime deps - Cross-branch dependency relationships - Empty exclusion list behavior - Multiple path handling to same dependency - Complex dependency graph scenarios ## Running Tests ```bash # Run all internal dependency tests bazel test //springboot/deps_filter_rules/tests/depsfilter/internal_dependencies/... bazel test //springboot/deps_filter_rules/tests/dependencyset/internal_dependencies/... ``` This comprehensive test suite ensures the `deps_filter` rule and `dependencyset` macro work correctly across all expected use cases and edge cases. ================================================ FILE: springboot/deps_filter_rules/tests/test_utils/BUILD ================================================ package(default_visibility = ["//visibility:public"]) java_library( name = "test_utils", srcs = glob(["src/test/java/**/*.java"]), data = [":dependency_graph.txt"], deps = [], ) # Export the dependency graph file for tests exports_files(["dependency_graph.txt"]) ================================================ FILE: springboot/deps_filter_rules/tests/test_utils/dependency_graph.txt ================================================ digraph mygraph { node [shape=box]; "//springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime:no_filtering" "//springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime:no_filtering" -> "//:license" "//springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime:no_filtering" -> "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa" "//springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime:no_filtering" -> "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core" "//springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime:no_filtering" -> "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security" "//springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime:no_filtering" -> "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind" "//springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime:no_filtering" -> "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client" "//springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime:no_filtering" -> "@unmanaged_deps_filter//:jakarta_servlet_jsp_jakarta_servlet_jsp_api" "//springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime:no_filtering" -> "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux" "//springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime:no_filtering" -> "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator" "//springboot/deps_filter_rules/tests/depsfilter/external_dependencies/compile_and_runtime:no_filtering" -> "@bazel_tools//tools/jdk:current_java_toolchain" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator" -> "@unmanaged_deps_filter//:org/springframework/boot/spring-boot-starter-actuator/3.3.11/spring-boot-starter-actuator-3.3.11.jar" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator" -> "@unmanaged_deps_filter//:io_micrometer_micrometer_jakarta9" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator" -> "@unmanaged_deps_filter//:io_micrometer_micrometer_observation" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator" -> "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_actuator_autoconfigure" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator" -> "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:jakarta_servlet_jsp_jakarta_servlet_jsp_api" "@unmanaged_deps_filter//:jakarta_servlet_jsp_jakarta_servlet_jsp_api" -> "@unmanaged_deps_filter//:jakarta/servlet/jsp/jakarta.servlet.jsp-api/3.1.1/jakarta.servlet.jsp-api-3.1.1.jar" "@unmanaged_deps_filter//:jakarta_servlet_jsp_jakarta_servlet_jsp_api" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:jakarta_servlet_jsp_jakarta_servlet_jsp_api" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client" -> "@unmanaged_deps_filter//:org/springframework/boot/spring-boot-starter-oauth2-client/3.3.11/spring-boot-starter-oauth2-client-3.3.11.jar" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client" -> "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client" -> "@unmanaged_deps_filter//:org_springframework_security_spring_security_config" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client" -> "@unmanaged_deps_filter//:org_springframework_security_spring_security_core" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client" -> "@unmanaged_deps_filter//:org_springframework_security_spring_security_oauth2_client" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client" -> "@unmanaged_deps_filter//:org_springframework_security_spring_security_oauth2_jose" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "//:license" "//:license" -> "//:LICENSE.txt\n@rules_license//licenses/spdx:Apache-2.0" "@unmanaged_deps_filter//:org_springframework_security_spring_security_oauth2_client" "@unmanaged_deps_filter//:org_springframework_security_spring_security_oauth2_client" -> "@unmanaged_deps_filter//:org/springframework/security/spring-security-oauth2-client/6.3.9/spring-security-oauth2-client-6.3.9.jar" "@unmanaged_deps_filter//:org_springframework_security_spring_security_oauth2_client" -> "@unmanaged_deps_filter//:com_nimbusds_oauth2_oidc_sdk" "@unmanaged_deps_filter//:org_springframework_security_spring_security_oauth2_client" -> "@unmanaged_deps_filter//:org_springframework_security_spring_security_core" "@unmanaged_deps_filter//:org_springframework_security_spring_security_oauth2_client" -> "@unmanaged_deps_filter//:org_springframework_security_spring_security_oauth2_core" "@unmanaged_deps_filter//:org_springframework_security_spring_security_oauth2_client" -> "@unmanaged_deps_filter//:org_springframework_security_spring_security_web" "@unmanaged_deps_filter//:org_springframework_security_spring_security_oauth2_client" -> "@unmanaged_deps_filter//:org_springframework_spring_core" "@unmanaged_deps_filter//:org_springframework_security_spring_security_oauth2_client" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:org_springframework_security_spring_security_oauth2_client" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:org/springframework/security/spring-security-oauth2-client/6.3.9/spring-security-oauth2-client-6.3.9.jar" "@unmanaged_deps_filter//:org/springframework/security/spring-security-oauth2-client/6.3.9/spring-security-oauth2-client-6.3.9.jar" -> "@unmanaged_deps_filter//:org_springframework_security_spring_security_oauth2_client_6_3_9_extension" "@unmanaged_deps_filter//:org_springframework_security_spring_security_oauth2_client_6_3_9_extension" "@unmanaged_deps_filter//:org_springframework_security_spring_security_oauth2_client_6_3_9_extension" -> "@@rules_jvm_external~~maven~org_springframework_security_spring_security_oauth2_client_6_3_9//file:file" "@unmanaged_deps_filter//:org_springframework_security_spring_security_oauth2_client_6_3_9_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@unmanaged_deps_filter//:org/springframework/boot/spring-boot-starter-oauth2-client/3.3.11/spring-boot-starter-oauth2-client-3.3.11.jar" "@unmanaged_deps_filter//:org/springframework/boot/spring-boot-starter-oauth2-client/3.3.11/spring-boot-starter-oauth2-client-3.3.11.jar" -> "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client_3_3_11_extension" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa" -> "@unmanaged_deps_filter//:org/springframework/boot/spring-boot-starter-data-jpa/3.3.11/spring-boot-starter-data-jpa-3.3.11.jar" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa" -> "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa" -> "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_aop" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa" -> "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_jdbc" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa" -> "@unmanaged_deps_filter//:org_springframework_data_spring_data_jpa" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa" -> "@unmanaged_deps_filter//:org_springframework_spring_aspects" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client_3_3_11_extension" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client_3_3_11_extension" -> "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_oauth2_client_3_3_11//file:file" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client_3_3_11_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core" "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core" -> "@unmanaged_deps_filter//:org/hibernate/orm/hibernate-core/6.5.3.Final/hibernate-core-6.5.3.Final.jar" "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core" -> "@unmanaged_deps_filter//:com_fasterxml_classmate" "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core" -> "@unmanaged_deps_filter//:io_smallrye_jandex" "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core" -> "@unmanaged_deps_filter//:jakarta_inject_jakarta_inject_api" "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core" -> "@unmanaged_deps_filter//:jakarta_persistence_jakarta_persistence_api" "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core" -> "@unmanaged_deps_filter//:jakarta_transaction_jakarta_transaction_api" "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core" -> "@unmanaged_deps_filter//:jakarta_xml_bind_jakarta_xml_bind_api" "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core" -> "@unmanaged_deps_filter//:net_bytebuddy_byte_buddy" "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core" -> "@unmanaged_deps_filter//:org_antlr_antlr4_runtime" "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core" -> "@unmanaged_deps_filter//:org_glassfish_jaxb_jaxb_runtime" "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core" -> "@unmanaged_deps_filter//:org_hibernate_common_hibernate_commons_annotations" "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core" -> "@unmanaged_deps_filter//:org_jboss_logging_jboss_logging" "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:org_jboss_logging_jboss_logging" "@unmanaged_deps_filter//:org_jboss_logging_jboss_logging" -> "@unmanaged_deps_filter//:org/jboss/logging/jboss-logging/3.5.0.Final/jboss-logging-3.5.0.Final.jar" "@unmanaged_deps_filter//:org_jboss_logging_jboss_logging" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:org_jboss_logging_jboss_logging" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:org_glassfish_jaxb_jaxb_runtime" "@unmanaged_deps_filter//:org_glassfish_jaxb_jaxb_runtime" -> "@unmanaged_deps_filter//:org/glassfish/jaxb/jaxb-runtime/4.0.2/jaxb-runtime-4.0.2.jar" "@unmanaged_deps_filter//:org_glassfish_jaxb_jaxb_runtime" -> "@unmanaged_deps_filter//:org_glassfish_jaxb_jaxb_core" "@unmanaged_deps_filter//:org_glassfish_jaxb_jaxb_runtime" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:org_glassfish_jaxb_jaxb_runtime" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:org_glassfish_jaxb_jaxb_core" "@unmanaged_deps_filter//:org_glassfish_jaxb_jaxb_core" -> "@unmanaged_deps_filter//:org/glassfish/jaxb/jaxb-core/4.0.2/jaxb-core-4.0.2.jar" "@unmanaged_deps_filter//:org_glassfish_jaxb_jaxb_core" -> "@unmanaged_deps_filter//:com_sun_istack_istack_commons_runtime" "@unmanaged_deps_filter//:org_glassfish_jaxb_jaxb_core" -> "@unmanaged_deps_filter//:jakarta_activation_jakarta_activation_api" "@unmanaged_deps_filter//:org_glassfish_jaxb_jaxb_core" -> "@unmanaged_deps_filter//:jakarta_xml_bind_jakarta_xml_bind_api" "@unmanaged_deps_filter//:org_glassfish_jaxb_jaxb_core" -> "@unmanaged_deps_filter//:org_eclipse_angus_angus_activation" "@unmanaged_deps_filter//:org_glassfish_jaxb_jaxb_core" -> "@unmanaged_deps_filter//:org_glassfish_jaxb_txw2" "@unmanaged_deps_filter//:org_glassfish_jaxb_jaxb_core" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:org_glassfish_jaxb_jaxb_core" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:org_eclipse_angus_angus_activation" "@unmanaged_deps_filter//:org_eclipse_angus_angus_activation" -> "@unmanaged_deps_filter//:org/eclipse/angus/angus-activation/2.0.0/angus-activation-2.0.0.jar" "@unmanaged_deps_filter//:org_eclipse_angus_angus_activation" -> "@unmanaged_deps_filter//:jakarta_activation_jakarta_activation_api" "@unmanaged_deps_filter//:org_eclipse_angus_angus_activation" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:org_eclipse_angus_angus_activation" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:org/eclipse/angus/angus-activation/2.0.0/angus-activation-2.0.0.jar" "@unmanaged_deps_filter//:org/eclipse/angus/angus-activation/2.0.0/angus-activation-2.0.0.jar" -> "@unmanaged_deps_filter//:org_eclipse_angus_angus_activation_2_0_0_extension" "@unmanaged_deps_filter//:org_eclipse_angus_angus_activation_2_0_0_extension" "@unmanaged_deps_filter//:org_eclipse_angus_angus_activation_2_0_0_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@unmanaged_deps_filter//:org_eclipse_angus_angus_activation_2_0_0_extension" -> "@@rules_jvm_external~~maven~org_eclipse_angus_angus_activation_2_0_0//file:file" "@unmanaged_deps_filter//:org/glassfish/jaxb/jaxb-core/4.0.2/jaxb-core-4.0.2.jar" "@unmanaged_deps_filter//:org/glassfish/jaxb/jaxb-core/4.0.2/jaxb-core-4.0.2.jar" -> "@unmanaged_deps_filter//:org_glassfish_jaxb_jaxb_core_4_0_2_extension" "@unmanaged_deps_filter//:org/glassfish/jaxb/jaxb-runtime/4.0.2/jaxb-runtime-4.0.2.jar" "@unmanaged_deps_filter//:org/glassfish/jaxb/jaxb-runtime/4.0.2/jaxb-runtime-4.0.2.jar" -> "@unmanaged_deps_filter//:org_glassfish_jaxb_jaxb_runtime_4_0_2_extension" "@unmanaged_deps_filter//:jakarta_xml_bind_jakarta_xml_bind_api" "@unmanaged_deps_filter//:jakarta_xml_bind_jakarta_xml_bind_api" -> "@unmanaged_deps_filter//:jakarta/xml/bind/jakarta.xml.bind-api/4.0.0/jakarta.xml.bind-api-4.0.0.jar" "@unmanaged_deps_filter//:jakarta_xml_bind_jakarta_xml_bind_api" -> "@unmanaged_deps_filter//:jakarta_activation_jakarta_activation_api" "@unmanaged_deps_filter//:jakarta_xml_bind_jakarta_xml_bind_api" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:jakarta_xml_bind_jakarta_xml_bind_api" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:jakarta_transaction_jakarta_transaction_api" "@unmanaged_deps_filter//:jakarta_transaction_jakarta_transaction_api" -> "@unmanaged_deps_filter//:jakarta/transaction/jakarta.transaction-api/2.0.1/jakarta.transaction-api-2.0.1.jar" "@unmanaged_deps_filter//:jakarta_transaction_jakarta_transaction_api" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:jakarta_transaction_jakarta_transaction_api" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:jakarta_inject_jakarta_inject_api" "@unmanaged_deps_filter//:jakarta_inject_jakarta_inject_api" -> "@unmanaged_deps_filter//:jakarta/inject/jakarta.inject-api/2.0.1/jakarta.inject-api-2.0.1.jar" "@unmanaged_deps_filter//:jakarta_inject_jakarta_inject_api" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:jakarta_inject_jakarta_inject_api" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:com_fasterxml_classmate" "@unmanaged_deps_filter//:com_fasterxml_classmate" -> "@unmanaged_deps_filter//:com/fasterxml/classmate/1.5.1/classmate-1.5.1.jar" "@unmanaged_deps_filter//:com_fasterxml_classmate" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:com_fasterxml_classmate" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:org/jboss/logging/jboss-logging/3.5.0.Final/jboss-logging-3.5.0.Final.jar" "@unmanaged_deps_filter//:org/jboss/logging/jboss-logging/3.5.0.Final/jboss-logging-3.5.0.Final.jar" -> "@unmanaged_deps_filter//:org_jboss_logging_jboss_logging_3_5_0_Final_extension" "@unmanaged_deps_filter//:org_jboss_logging_jboss_logging_3_5_0_Final_extension" "@unmanaged_deps_filter//:org_jboss_logging_jboss_logging_3_5_0_Final_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@unmanaged_deps_filter//:org_jboss_logging_jboss_logging_3_5_0_Final_extension" -> "@@rules_jvm_external~~maven~org_jboss_logging_jboss_logging_3_5_0_Final//file:file" "@@rules_jvm_external~~maven~org_jboss_logging_jboss_logging_3_5_0_Final//file:file" "@@rules_jvm_external~~maven~org_jboss_logging_jboss_logging_3_5_0_Final//file:file" -> "@@rules_jvm_external~~maven~org_jboss_logging_jboss_logging_3_5_0_Final//file:v1/org/jboss/logging/jboss-logging/3.5.0.Final/jboss-logging-3.5.0.Final.jar" "@unmanaged_deps_filter//:org_springframework_data_spring_data_jpa" "@unmanaged_deps_filter//:org_springframework_data_spring_data_jpa" -> "@unmanaged_deps_filter//:org/springframework/data/spring-data-jpa/3.3.11/spring-data-jpa-3.3.11.jar" "@unmanaged_deps_filter//:org_springframework_data_spring_data_jpa" -> "@unmanaged_deps_filter//:jakarta_annotation_jakarta_annotation_api" "@unmanaged_deps_filter//:org_springframework_data_spring_data_jpa" -> "@unmanaged_deps_filter//:org_antlr_antlr4_runtime" "@unmanaged_deps_filter//:org_springframework_data_spring_data_jpa" -> "@unmanaged_deps_filter//:org_springframework_data_spring_data_commons" "@unmanaged_deps_filter//:org_springframework_data_spring_data_jpa" -> "@unmanaged_deps_filter//:org_springframework_spring_aop" "@unmanaged_deps_filter//:org_springframework_data_spring_data_jpa" -> "@unmanaged_deps_filter//:org_springframework_spring_beans" "@unmanaged_deps_filter//:org_springframework_data_spring_data_jpa" -> "@unmanaged_deps_filter//:org_springframework_spring_context" "@unmanaged_deps_filter//:org_springframework_data_spring_data_jpa" -> "@unmanaged_deps_filter//:org_springframework_spring_core" "@unmanaged_deps_filter//:org_springframework_data_spring_data_jpa" -> "@unmanaged_deps_filter//:org_springframework_spring_orm" "@unmanaged_deps_filter//:org_springframework_data_spring_data_jpa" -> "@unmanaged_deps_filter//:org_springframework_spring_tx" "@unmanaged_deps_filter//:org_springframework_data_spring_data_jpa" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:org_springframework_data_spring_data_jpa" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:org/springframework/data/spring-data-jpa/3.3.11/spring-data-jpa-3.3.11.jar" "@unmanaged_deps_filter//:org/springframework/data/spring-data-jpa/3.3.11/spring-data-jpa-3.3.11.jar" -> "@unmanaged_deps_filter//:org_springframework_data_spring_data_jpa_3_3_11_extension" "@@rules_jvm_external~~maven~org_springframework_security_spring_security_oauth2_client_6_3_9//file:file" "@@rules_jvm_external~~maven~org_springframework_security_spring_security_oauth2_client_6_3_9//file:file" -> "@@rules_jvm_external~~maven~org_springframework_security_spring_security_oauth2_client_6_3_9//file:v1/org/springframework/security/spring-security-oauth2-client/6.3.9/spring-security-oauth2-client-6.3.9.jar" "@@rules_jvm_external~~maven~org_springframework_security_spring_security_oauth2_client_6_3_9//file:v1/org/springframework/security/spring-security-oauth2-client/6.3.9/spring-security-oauth2-client-6.3.9.jar" "@unmanaged_deps_filter//:org_hibernate_common_hibernate_commons_annotations" "@unmanaged_deps_filter//:org_hibernate_common_hibernate_commons_annotations" -> "@unmanaged_deps_filter//:org/hibernate/common/hibernate-commons-annotations/6.0.6.Final/hibernate-commons-annotations-6.0.6.Final.jar" "@unmanaged_deps_filter//:org_hibernate_common_hibernate_commons_annotations" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:org_hibernate_common_hibernate_commons_annotations" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security" -> "@unmanaged_deps_filter//:org/springframework/boot/spring-boot-starter-security/3.3.11/spring-boot-starter-security-3.3.11.jar" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security" -> "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security" -> "@unmanaged_deps_filter//:org_springframework_security_spring_security_config" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security" -> "@unmanaged_deps_filter//:org_springframework_security_spring_security_web" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security" -> "@unmanaged_deps_filter//:org_springframework_spring_aop" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:org_springframework_security_spring_security_web" "@unmanaged_deps_filter//:org_springframework_security_spring_security_web" -> "@unmanaged_deps_filter//:org/springframework/security/spring-security-web/6.3.9/spring-security-web-6.3.9.jar" "@unmanaged_deps_filter//:org_springframework_security_spring_security_web" -> "@unmanaged_deps_filter//:org_springframework_security_spring_security_core" "@unmanaged_deps_filter//:org_springframework_security_spring_security_web" -> "@unmanaged_deps_filter//:org_springframework_spring_aop" "@unmanaged_deps_filter//:org_springframework_security_spring_security_web" -> "@unmanaged_deps_filter//:org_springframework_spring_beans" "@unmanaged_deps_filter//:org_springframework_security_spring_security_web" -> "@unmanaged_deps_filter//:org_springframework_spring_context" "@unmanaged_deps_filter//:org_springframework_security_spring_security_web" -> "@unmanaged_deps_filter//:org_springframework_spring_core" "@unmanaged_deps_filter//:org_springframework_security_spring_security_web" -> "@unmanaged_deps_filter//:org_springframework_spring_expression" "@unmanaged_deps_filter//:org_springframework_security_spring_security_web" -> "@unmanaged_deps_filter//:org_springframework_spring_web" "@unmanaged_deps_filter//:org_springframework_security_spring_security_web" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:org_springframework_security_spring_security_web" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:org_springframework_security_spring_security_config" "@unmanaged_deps_filter//:org_springframework_security_spring_security_config" -> "@unmanaged_deps_filter//:org/springframework/security/spring-security-config/6.3.9/spring-security-config-6.3.9.jar" "@unmanaged_deps_filter//:org_springframework_security_spring_security_config" -> "@unmanaged_deps_filter//:org_springframework_security_spring_security_core" "@unmanaged_deps_filter//:org_springframework_security_spring_security_config" -> "@unmanaged_deps_filter//:org_springframework_spring_aop" "@unmanaged_deps_filter//:org_springframework_security_spring_security_config" -> "@unmanaged_deps_filter//:org_springframework_spring_beans" "@unmanaged_deps_filter//:org_springframework_security_spring_security_config" -> "@unmanaged_deps_filter//:org_springframework_spring_context" "@unmanaged_deps_filter//:org_springframework_security_spring_security_config" -> "@unmanaged_deps_filter//:org_springframework_spring_core" "@unmanaged_deps_filter//:org_springframework_security_spring_security_config" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:org_springframework_security_spring_security_config" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:org/springframework/security/spring-security-config/6.3.9/spring-security-config-6.3.9.jar" "@unmanaged_deps_filter//:org/springframework/security/spring-security-config/6.3.9/spring-security-config-6.3.9.jar" -> "@unmanaged_deps_filter//:org_springframework_security_spring_security_config_6_3_9_extension" "@@rules_jvm_external~~maven~org_eclipse_angus_angus_activation_2_0_0//file:file" "@@rules_jvm_external~~maven~org_eclipse_angus_angus_activation_2_0_0//file:file" -> "@@rules_jvm_external~~maven~org_eclipse_angus_angus_activation_2_0_0//file:v1/org/eclipse/angus/angus-activation/2.0.0/angus-activation-2.0.0.jar" "@unmanaged_deps_filter//:org_springframework_security_spring_security_oauth2_jose" "@unmanaged_deps_filter//:org_springframework_security_spring_security_oauth2_jose" -> "@unmanaged_deps_filter//:org/springframework/security/spring-security-oauth2-jose/6.3.9/spring-security-oauth2-jose-6.3.9.jar" "@unmanaged_deps_filter//:org_springframework_security_spring_security_oauth2_jose" -> "@unmanaged_deps_filter//:com_nimbusds_nimbus_jose_jwt" "@unmanaged_deps_filter//:org_springframework_security_spring_security_oauth2_jose" -> "@unmanaged_deps_filter//:org_springframework_security_spring_security_core" "@unmanaged_deps_filter//:org_springframework_security_spring_security_oauth2_jose" -> "@unmanaged_deps_filter//:org_springframework_security_spring_security_oauth2_core" "@unmanaged_deps_filter//:org_springframework_security_spring_security_oauth2_jose" -> "@unmanaged_deps_filter//:org_springframework_spring_core" "@unmanaged_deps_filter//:org_springframework_security_spring_security_oauth2_jose" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:org_springframework_security_spring_security_oauth2_jose" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:org_springframework_security_spring_security_oauth2_core" "@unmanaged_deps_filter//:org_springframework_security_spring_security_oauth2_core" -> "@unmanaged_deps_filter//:org/springframework/security/spring-security-oauth2-core/6.3.9/spring-security-oauth2-core-6.3.9.jar" "@unmanaged_deps_filter//:org_springframework_security_spring_security_oauth2_core" -> "@unmanaged_deps_filter//:org_springframework_security_spring_security_core" "@unmanaged_deps_filter//:org_springframework_security_spring_security_oauth2_core" -> "@unmanaged_deps_filter//:org_springframework_spring_core" "@unmanaged_deps_filter//:org_springframework_security_spring_security_oauth2_core" -> "@unmanaged_deps_filter//:org_springframework_spring_web" "@unmanaged_deps_filter//:org_springframework_security_spring_security_oauth2_core" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:org_springframework_security_spring_security_oauth2_core" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:org/springframework/security/spring-security-oauth2-core/6.3.9/spring-security-oauth2-core-6.3.9.jar" "@unmanaged_deps_filter//:org/springframework/security/spring-security-oauth2-core/6.3.9/spring-security-oauth2-core-6.3.9.jar" -> "@unmanaged_deps_filter//:org_springframework_security_spring_security_oauth2_core_6_3_9_extension" "@unmanaged_deps_filter//:org_springframework_security_spring_security_oauth2_core_6_3_9_extension" "@unmanaged_deps_filter//:org_springframework_security_spring_security_oauth2_core_6_3_9_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@unmanaged_deps_filter//:org_springframework_security_spring_security_oauth2_core_6_3_9_extension" -> "@@rules_jvm_external~~maven~org_springframework_security_spring_security_oauth2_core_6_3_9//file:file" "@@rules_jvm_external~~maven~org_springframework_security_spring_security_oauth2_core_6_3_9//file:file" "@@rules_jvm_external~~maven~org_springframework_security_spring_security_oauth2_core_6_3_9//file:file" -> "@@rules_jvm_external~~maven~org_springframework_security_spring_security_oauth2_core_6_3_9//file:v1/org/springframework/security/spring-security-oauth2-core/6.3.9/spring-security-oauth2-core-6.3.9.jar" "@@rules_jvm_external~~maven~org_springframework_security_spring_security_oauth2_core_6_3_9//file:v1/org/springframework/security/spring-security-oauth2-core/6.3.9/spring-security-oauth2-core-6.3.9.jar" "@unmanaged_deps_filter//:org_springframework_security_spring_security_config_6_3_9_extension" "@unmanaged_deps_filter//:org_springframework_security_spring_security_config_6_3_9_extension" -> "@@rules_jvm_external~~maven~org_springframework_security_spring_security_config_6_3_9//file:file" "@unmanaged_deps_filter//:org_springframework_security_spring_security_config_6_3_9_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~org_springframework_security_spring_security_config_6_3_9//file:file" "@@rules_jvm_external~~maven~org_springframework_security_spring_security_config_6_3_9//file:file" -> "@@rules_jvm_external~~maven~org_springframework_security_spring_security_config_6_3_9//file:v1/org/springframework/security/spring-security-config/6.3.9/spring-security-config-6.3.9.jar" "@@rules_jvm_external~~maven~org_springframework_security_spring_security_config_6_3_9//file:v1/org/springframework/security/spring-security-config/6.3.9/spring-security-config-6.3.9.jar" "@unmanaged_deps_filter//:io_micrometer_micrometer_jakarta9" "@unmanaged_deps_filter//:io_micrometer_micrometer_jakarta9" -> "@unmanaged_deps_filter//:io/micrometer/micrometer-jakarta9/1.13.13/micrometer-jakarta9-1.13.13.jar" "@unmanaged_deps_filter//:io_micrometer_micrometer_jakarta9" -> "@unmanaged_deps_filter//:io_micrometer_micrometer_commons" "@unmanaged_deps_filter//:io_micrometer_micrometer_jakarta9" -> "@unmanaged_deps_filter//:io_micrometer_micrometer_core" "@unmanaged_deps_filter//:io_micrometer_micrometer_jakarta9" -> "@unmanaged_deps_filter//:io_micrometer_micrometer_observation" "@unmanaged_deps_filter//:io_micrometer_micrometer_jakarta9" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:io_micrometer_micrometer_jakarta9" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:io/micrometer/micrometer-jakarta9/1.13.13/micrometer-jakarta9-1.13.13.jar" "@unmanaged_deps_filter//:io/micrometer/micrometer-jakarta9/1.13.13/micrometer-jakarta9-1.13.13.jar" -> "@unmanaged_deps_filter//:io_micrometer_micrometer_jakarta9_1_13_13_extension" "@unmanaged_deps_filter//:io_micrometer_micrometer_jakarta9_1_13_13_extension" "@unmanaged_deps_filter//:io_micrometer_micrometer_jakarta9_1_13_13_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@unmanaged_deps_filter//:io_micrometer_micrometer_jakarta9_1_13_13_extension" -> "@@rules_jvm_external~~maven~io_micrometer_micrometer_jakarta9_1_13_13//file:file" "@unmanaged_deps_filter//:com_nimbusds_oauth2_oidc_sdk" "@unmanaged_deps_filter//:com_nimbusds_oauth2_oidc_sdk" -> "@unmanaged_deps_filter//:com/nimbusds/oauth2-oidc-sdk/9.43.6/oauth2-oidc-sdk-9.43.6.jar" "@unmanaged_deps_filter//:com_nimbusds_oauth2_oidc_sdk" -> "@unmanaged_deps_filter//:com_github_stephenc_jcip_jcip_annotations" "@unmanaged_deps_filter//:com_nimbusds_oauth2_oidc_sdk" -> "@unmanaged_deps_filter//:com_nimbusds_content_type" "@unmanaged_deps_filter//:com_nimbusds_oauth2_oidc_sdk" -> "@unmanaged_deps_filter//:com_nimbusds_lang_tag" "@unmanaged_deps_filter//:com_nimbusds_oauth2_oidc_sdk" -> "@unmanaged_deps_filter//:com_nimbusds_nimbus_jose_jwt" "@unmanaged_deps_filter//:com_nimbusds_oauth2_oidc_sdk" -> "@unmanaged_deps_filter//:net_minidev_json_smart" "@unmanaged_deps_filter//:com_nimbusds_oauth2_oidc_sdk" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:com_nimbusds_oauth2_oidc_sdk" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:net_minidev_json_smart" "@unmanaged_deps_filter//:net_minidev_json_smart" -> "@unmanaged_deps_filter//:net/minidev/json-smart/2.5.2/json-smart-2.5.2.jar" "@unmanaged_deps_filter//:net_minidev_json_smart" -> "@unmanaged_deps_filter//:net_minidev_accessors_smart" "@unmanaged_deps_filter//:net_minidev_json_smart" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:net_minidev_json_smart" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:net_minidev_accessors_smart" "@unmanaged_deps_filter//:net_minidev_accessors_smart" -> "@unmanaged_deps_filter//:net/minidev/accessors-smart/2.5.2/accessors-smart-2.5.2.jar" "@unmanaged_deps_filter//:net_minidev_accessors_smart" -> "@unmanaged_deps_filter//:org_ow2_asm_asm" "@unmanaged_deps_filter//:net_minidev_accessors_smart" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:net_minidev_accessors_smart" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:net/minidev/accessors-smart/2.5.2/accessors-smart-2.5.2.jar" "@unmanaged_deps_filter//:net/minidev/accessors-smart/2.5.2/accessors-smart-2.5.2.jar" -> "@unmanaged_deps_filter//:net_minidev_accessors_smart_2_5_2_extension" "@unmanaged_deps_filter//:net_minidev_accessors_smart_2_5_2_extension" "@unmanaged_deps_filter//:net_minidev_accessors_smart_2_5_2_extension" -> "@@rules_jvm_external~~maven~net_minidev_accessors_smart_2_5_2//file:file" "@unmanaged_deps_filter//:net_minidev_accessors_smart_2_5_2_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~net_minidev_accessors_smart_2_5_2//file:file" "@@rules_jvm_external~~maven~net_minidev_accessors_smart_2_5_2//file:file" -> "@@rules_jvm_external~~maven~net_minidev_accessors_smart_2_5_2//file:v1/net/minidev/accessors-smart/2.5.2/accessors-smart-2.5.2.jar" "@unmanaged_deps_filter//:net/minidev/json-smart/2.5.2/json-smart-2.5.2.jar" "@unmanaged_deps_filter//:net/minidev/json-smart/2.5.2/json-smart-2.5.2.jar" -> "@unmanaged_deps_filter//:net_minidev_json_smart_2_5_2_extension" "@unmanaged_deps_filter//:com_nimbusds_lang_tag" "@unmanaged_deps_filter//:com_nimbusds_lang_tag" -> "@unmanaged_deps_filter//:com/nimbusds/lang-tag/1.7/lang-tag-1.7.jar" "@unmanaged_deps_filter//:com_nimbusds_lang_tag" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:com_nimbusds_lang_tag" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:com/nimbusds/lang-tag/1.7/lang-tag-1.7.jar" "@unmanaged_deps_filter//:com/nimbusds/lang-tag/1.7/lang-tag-1.7.jar" -> "@unmanaged_deps_filter//:com_nimbusds_lang_tag_1_7_extension" "@unmanaged_deps_filter//:com/nimbusds/oauth2-oidc-sdk/9.43.6/oauth2-oidc-sdk-9.43.6.jar" "@unmanaged_deps_filter//:com/nimbusds/oauth2-oidc-sdk/9.43.6/oauth2-oidc-sdk-9.43.6.jar" -> "@unmanaged_deps_filter//:com_nimbusds_oauth2_oidc_sdk_9_43_6_extension" "@unmanaged_deps_filter//:com_nimbusds_oauth2_oidc_sdk_9_43_6_extension" "@unmanaged_deps_filter//:com_nimbusds_oauth2_oidc_sdk_9_43_6_extension" -> "@@rules_jvm_external~~maven~com_nimbusds_oauth2_oidc_sdk_9_43_6//file:file" "@unmanaged_deps_filter//:com_nimbusds_oauth2_oidc_sdk_9_43_6_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@unmanaged_deps_filter//:jakarta_activation_jakarta_activation_api" "@unmanaged_deps_filter//:jakarta_activation_jakarta_activation_api" -> "@unmanaged_deps_filter//:jakarta/activation/jakarta.activation-api/2.1.1/jakarta.activation-api-2.1.1.jar" "@unmanaged_deps_filter//:jakarta_activation_jakarta_activation_api" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:jakarta_activation_jakarta_activation_api" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:jakarta/activation/jakarta.activation-api/2.1.1/jakarta.activation-api-2.1.1.jar" "@unmanaged_deps_filter//:jakarta/activation/jakarta.activation-api/2.1.1/jakarta.activation-api-2.1.1.jar" -> "@unmanaged_deps_filter//:jakarta_activation_jakarta_activation_api_2_1_1_extension" "@unmanaged_deps_filter//:jakarta_activation_jakarta_activation_api_2_1_1_extension" "@unmanaged_deps_filter//:jakarta_activation_jakarta_activation_api_2_1_1_extension" -> "@@rules_jvm_external~~maven~jakarta_activation_jakarta_activation_api_2_1_1//file:file" "@unmanaged_deps_filter//:jakarta_activation_jakarta_activation_api_2_1_1_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~jakarta_activation_jakarta_activation_api_2_1_1//file:file" "@@rules_jvm_external~~maven~jakarta_activation_jakarta_activation_api_2_1_1//file:file" -> "@@rules_jvm_external~~maven~jakarta_activation_jakarta_activation_api_2_1_1//file:v1/jakarta/activation/jakarta.activation-api/2.1.1/jakarta.activation-api-2.1.1.jar" "@@rules_jvm_external~~maven~jakarta_activation_jakarta_activation_api_2_1_1//file:v1/jakarta/activation/jakarta.activation-api/2.1.1/jakarta.activation-api-2.1.1.jar" "@unmanaged_deps_filter//:org_glassfish_jaxb_jaxb_core_4_0_2_extension" "@unmanaged_deps_filter//:org_glassfish_jaxb_jaxb_core_4_0_2_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@unmanaged_deps_filter//:org_glassfish_jaxb_jaxb_core_4_0_2_extension" -> "@@rules_jvm_external~~maven~org_glassfish_jaxb_jaxb_core_4_0_2//file:file" "@@rules_jvm_external~~maven~org_glassfish_jaxb_jaxb_core_4_0_2//file:file" "@@rules_jvm_external~~maven~org_glassfish_jaxb_jaxb_core_4_0_2//file:file" -> "@@rules_jvm_external~~maven~org_glassfish_jaxb_jaxb_core_4_0_2//file:v1/org/glassfish/jaxb/jaxb-core/4.0.2/jaxb-core-4.0.2.jar" "@@rules_jvm_external~~maven~org_glassfish_jaxb_jaxb_core_4_0_2//file:v1/org/glassfish/jaxb/jaxb-core/4.0.2/jaxb-core-4.0.2.jar" "@unmanaged_deps_filter//:net_minidev_json_smart_2_5_2_extension" "@unmanaged_deps_filter//:net_minidev_json_smart_2_5_2_extension" -> "@@rules_jvm_external~~maven~net_minidev_json_smart_2_5_2//file:file" "@unmanaged_deps_filter//:net_minidev_json_smart_2_5_2_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~net_minidev_json_smart_2_5_2//file:file" "@@rules_jvm_external~~maven~net_minidev_json_smart_2_5_2//file:file" -> "@@rules_jvm_external~~maven~net_minidev_json_smart_2_5_2//file:v1/net/minidev/json-smart/2.5.2/json-smart-2.5.2.jar" "@@rules_jvm_external~~maven~net_minidev_json_smart_2_5_2//file:v1/net/minidev/json-smart/2.5.2/json-smart-2.5.2.jar" "@unmanaged_deps_filter//:org_antlr_antlr4_runtime" "@unmanaged_deps_filter//:org_antlr_antlr4_runtime" -> "@unmanaged_deps_filter//:org/antlr/antlr4-runtime/4.13.0/antlr4-runtime-4.13.0.jar" "@unmanaged_deps_filter//:org_antlr_antlr4_runtime" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:org_antlr_antlr4_runtime" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:org/antlr/antlr4-runtime/4.13.0/antlr4-runtime-4.13.0.jar" "@unmanaged_deps_filter//:org/antlr/antlr4-runtime/4.13.0/antlr4-runtime-4.13.0.jar" -> "@unmanaged_deps_filter//:org_antlr_antlr4_runtime_4_13_0_extension" "@unmanaged_deps_filter//:org_antlr_antlr4_runtime_4_13_0_extension" "@unmanaged_deps_filter//:org_antlr_antlr4_runtime_4_13_0_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@unmanaged_deps_filter//:org_antlr_antlr4_runtime_4_13_0_extension" -> "@@rules_jvm_external~~maven~org_antlr_antlr4_runtime_4_13_0//file:file" "@@rules_jvm_external~~maven~org_antlr_antlr4_runtime_4_13_0//file:file" "@@rules_jvm_external~~maven~org_antlr_antlr4_runtime_4_13_0//file:file" -> "@@rules_jvm_external~~maven~org_antlr_antlr4_runtime_4_13_0//file:v1/org/antlr/antlr4-runtime/4.13.0/antlr4-runtime-4.13.0.jar" "@unmanaged_deps_filter//:org/springframework/boot/spring-boot-starter-security/3.3.11/spring-boot-starter-security-3.3.11.jar" "@unmanaged_deps_filter//:org/springframework/boot/spring-boot-starter-security/3.3.11/spring-boot-starter-security-3.3.11.jar" -> "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security_3_3_11_extension" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security_3_3_11_extension" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security_3_3_11_extension" -> "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_security_3_3_11//file:file" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security_3_3_11_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_security_3_3_11//file:file" "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_security_3_3_11//file:file" -> "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_security_3_3_11//file:v1/org/springframework/boot/spring-boot-starter-security/3.3.11/spring-boot-starter-security-3.3.11.jar" "@unmanaged_deps_filter//:jakarta/xml/bind/jakarta.xml.bind-api/4.0.0/jakarta.xml.bind-api-4.0.0.jar" "@unmanaged_deps_filter//:jakarta/xml/bind/jakarta.xml.bind-api/4.0.0/jakarta.xml.bind-api-4.0.0.jar" -> "@unmanaged_deps_filter//:jakarta_xml_bind_jakarta_xml_bind_api_4_0_0_extension" "@unmanaged_deps_filter//:jakarta_xml_bind_jakarta_xml_bind_api_4_0_0_extension" "@unmanaged_deps_filter//:jakarta_xml_bind_jakarta_xml_bind_api_4_0_0_extension" -> "@@rules_jvm_external~~maven~jakarta_xml_bind_jakarta_xml_bind_api_4_0_0//file:file" "@unmanaged_deps_filter//:jakarta_xml_bind_jakarta_xml_bind_api_4_0_0_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~org_eclipse_angus_angus_activation_2_0_0//file:v1/org/eclipse/angus/angus-activation/2.0.0/angus-activation-2.0.0.jar" "@unmanaged_deps_filter//:org_springframework_spring_aspects" "@unmanaged_deps_filter//:org_springframework_spring_aspects" -> "@unmanaged_deps_filter//:org/springframework/spring-aspects/6.1.19/spring-aspects-6.1.19.jar" "@unmanaged_deps_filter//:org_springframework_spring_aspects" -> "@unmanaged_deps_filter//:org_aspectj_aspectjweaver" "@unmanaged_deps_filter//:org_springframework_spring_aspects" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:org_springframework_spring_aspects" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:org/springframework/spring-aspects/6.1.19/spring-aspects-6.1.19.jar" "@unmanaged_deps_filter//:org/springframework/spring-aspects/6.1.19/spring-aspects-6.1.19.jar" -> "@unmanaged_deps_filter//:org_springframework_spring_aspects_6_1_19_extension" "@unmanaged_deps_filter//:org_springframework_spring_aspects_6_1_19_extension" "@unmanaged_deps_filter//:org_springframework_spring_aspects_6_1_19_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@unmanaged_deps_filter//:org_springframework_spring_aspects_6_1_19_extension" -> "@@rules_jvm_external~~maven~org_springframework_spring_aspects_6_1_19//file:file" "@@rules_jvm_external~~maven~org_springframework_spring_aspects_6_1_19//file:file" "@@rules_jvm_external~~maven~org_springframework_spring_aspects_6_1_19//file:file" -> "@@rules_jvm_external~~maven~org_springframework_spring_aspects_6_1_19//file:v1/org/springframework/spring-aspects/6.1.19/spring-aspects-6.1.19.jar" "@@rules_jvm_external~~maven~org_springframework_spring_aspects_6_1_19//file:v1/org/springframework/spring-aspects/6.1.19/spring-aspects-6.1.19.jar" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_jdbc" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_jdbc" -> "@unmanaged_deps_filter//:org/springframework/boot/spring-boot-starter-jdbc/3.3.11/spring-boot-starter-jdbc-3.3.11.jar" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_jdbc" -> "@unmanaged_deps_filter//:com_zaxxer_HikariCP" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_jdbc" -> "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_jdbc" -> "@unmanaged_deps_filter//:org_springframework_spring_jdbc" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_jdbc" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_jdbc" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:com_zaxxer_HikariCP" "@unmanaged_deps_filter//:com_zaxxer_HikariCP" -> "@unmanaged_deps_filter//:com/zaxxer/HikariCP/5.1.0/HikariCP-5.1.0.jar" "@unmanaged_deps_filter//:com_zaxxer_HikariCP" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:com_zaxxer_HikariCP" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:com/zaxxer/HikariCP/5.1.0/HikariCP-5.1.0.jar" "@unmanaged_deps_filter//:com/zaxxer/HikariCP/5.1.0/HikariCP-5.1.0.jar" -> "@unmanaged_deps_filter//:com_zaxxer_HikariCP_5_1_0_extension" "@@rules_jvm_external~~maven~com_nimbusds_oauth2_oidc_sdk_9_43_6//file:file" "@@rules_jvm_external~~maven~com_nimbusds_oauth2_oidc_sdk_9_43_6//file:file" -> "@@rules_jvm_external~~maven~com_nimbusds_oauth2_oidc_sdk_9_43_6//file:v1/com/nimbusds/oauth2-oidc-sdk/9.43.6/oauth2-oidc-sdk-9.43.6.jar" "@@rules_jvm_external~~maven~org_jboss_logging_jboss_logging_3_5_0_Final//file:v1/org/jboss/logging/jboss-logging/3.5.0.Final/jboss-logging-3.5.0.Final.jar" "@unmanaged_deps_filter//:org_springframework_data_spring_data_jpa_3_3_11_extension" "@unmanaged_deps_filter//:org_springframework_data_spring_data_jpa_3_3_11_extension" -> "@@rules_jvm_external~~maven~org_springframework_data_spring_data_jpa_3_3_11//file:file" "@unmanaged_deps_filter//:org_springframework_data_spring_data_jpa_3_3_11_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~org_springframework_data_spring_data_jpa_3_3_11//file:file" "@@rules_jvm_external~~maven~org_springframework_data_spring_data_jpa_3_3_11//file:file" -> "@@rules_jvm_external~~maven~org_springframework_data_spring_data_jpa_3_3_11//file:v1/org/springframework/data/spring-data-jpa/3.3.11/spring-data-jpa-3.3.11.jar" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_actuator_autoconfigure" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_actuator_autoconfigure" -> "@unmanaged_deps_filter//:org/springframework/boot/spring-boot-actuator-autoconfigure/3.3.11/spring-boot-actuator-autoconfigure-3.3.11.jar" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_actuator_autoconfigure" -> "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_actuator_autoconfigure" -> "@unmanaged_deps_filter//:com_fasterxml_jackson_datatype_jackson_datatype_jsr310" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_actuator_autoconfigure" -> "@unmanaged_deps_filter//:org_springframework_boot_spring_boot" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_actuator_autoconfigure" -> "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_actuator" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_actuator_autoconfigure" -> "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_autoconfigure" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_actuator_autoconfigure" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_actuator_autoconfigure" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_actuator" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_actuator" -> "@unmanaged_deps_filter//:org/springframework/boot/spring-boot-actuator/3.3.11/spring-boot-actuator-3.3.11.jar" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_actuator" -> "@unmanaged_deps_filter//:org_springframework_boot_spring_boot" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_actuator" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_actuator" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:org/springframework/boot/spring-boot-actuator/3.3.11/spring-boot-actuator-3.3.11.jar" "@unmanaged_deps_filter//:org/springframework/boot/spring-boot-actuator/3.3.11/spring-boot-actuator-3.3.11.jar" -> "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_actuator_3_3_11_extension" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux" -> "@unmanaged_deps_filter//:org/springframework/boot/spring-boot-starter-webflux/3.3.11/spring-boot-starter-webflux-3.3.11.jar" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux" -> "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux" -> "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_json" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux" -> "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_reactor_netty" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux" -> "@unmanaged_deps_filter//:org_springframework_spring_web" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux" -> "@unmanaged_deps_filter//:org_springframework_spring_webflux" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:org_springframework_spring_webflux" "@unmanaged_deps_filter//:org_springframework_spring_webflux" -> "@unmanaged_deps_filter//:org/springframework/spring-webflux/6.1.19/spring-webflux-6.1.19.jar" "@unmanaged_deps_filter//:org_springframework_spring_webflux" -> "@unmanaged_deps_filter//:io_projectreactor_reactor_core" "@unmanaged_deps_filter//:org_springframework_spring_webflux" -> "@unmanaged_deps_filter//:org_springframework_spring_beans" "@unmanaged_deps_filter//:org_springframework_spring_webflux" -> "@unmanaged_deps_filter//:org_springframework_spring_core" "@unmanaged_deps_filter//:org_springframework_spring_webflux" -> "@unmanaged_deps_filter//:org_springframework_spring_web" "@unmanaged_deps_filter//:org_springframework_spring_webflux" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:org_springframework_spring_webflux" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:org/springframework/spring-webflux/6.1.19/spring-webflux-6.1.19.jar" "@unmanaged_deps_filter//:org/springframework/spring-webflux/6.1.19/spring-webflux-6.1.19.jar" -> "@unmanaged_deps_filter//:org_springframework_spring_webflux_6_1_19_extension" "@unmanaged_deps_filter//:org_springframework_spring_webflux_6_1_19_extension" "@unmanaged_deps_filter//:org_springframework_spring_webflux_6_1_19_extension" -> "@@rules_jvm_external~~maven~org_springframework_spring_webflux_6_1_19//file:file" "@unmanaged_deps_filter//:org_springframework_spring_webflux_6_1_19_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~org_springframework_spring_webflux_6_1_19//file:file" "@@rules_jvm_external~~maven~org_springframework_spring_webflux_6_1_19//file:file" -> "@@rules_jvm_external~~maven~org_springframework_spring_webflux_6_1_19//file:v1/org/springframework/spring-webflux/6.1.19/spring-webflux-6.1.19.jar" "@@rules_jvm_external~~maven~org_springframework_spring_webflux_6_1_19//file:v1/org/springframework/spring-webflux/6.1.19/spring-webflux-6.1.19.jar" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_reactor_netty" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_reactor_netty" -> "@unmanaged_deps_filter//:org/springframework/boot/spring-boot-starter-reactor-netty/3.3.11/spring-boot-starter-reactor-netty-3.3.11.jar" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_reactor_netty" -> "@unmanaged_deps_filter//:io_projectreactor_netty_reactor_netty_http" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_reactor_netty" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_reactor_netty" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:io_projectreactor_netty_reactor_netty_http" "@unmanaged_deps_filter//:io_projectreactor_netty_reactor_netty_http" -> "@unmanaged_deps_filter//:io/projectreactor/netty/reactor-netty-http/1.1.29/reactor-netty-http-1.1.29.jar" "@unmanaged_deps_filter//:io_projectreactor_netty_reactor_netty_http" -> "@unmanaged_deps_filter//:io_netty_netty_codec_http" "@unmanaged_deps_filter//:io_projectreactor_netty_reactor_netty_http" -> "@unmanaged_deps_filter//:io_netty_netty_codec_http2" "@unmanaged_deps_filter//:io_projectreactor_netty_reactor_netty_http" -> "@unmanaged_deps_filter//:io_netty_netty_resolver_dns" "@unmanaged_deps_filter//:io_projectreactor_netty_reactor_netty_http" -> "@unmanaged_deps_filter//:io_netty_netty_resolver_dns_native_macos_osx_x86_64" "@unmanaged_deps_filter//:io_projectreactor_netty_reactor_netty_http" -> "@unmanaged_deps_filter//:io_netty_netty_transport_native_epoll_linux_x86_64" "@unmanaged_deps_filter//:io_projectreactor_netty_reactor_netty_http" -> "@unmanaged_deps_filter//:io_projectreactor_netty_reactor_netty_core" "@unmanaged_deps_filter//:io_projectreactor_netty_reactor_netty_http" -> "@unmanaged_deps_filter//:io_projectreactor_reactor_core" "@unmanaged_deps_filter//:io_projectreactor_netty_reactor_netty_http" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:io_projectreactor_netty_reactor_netty_http" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:io_netty_netty_codec_http2" "@unmanaged_deps_filter//:io_netty_netty_codec_http2" -> "@unmanaged_deps_filter//:io/netty/netty-codec-http2/4.1.119.Final/netty-codec-http2-4.1.119.Final.jar" "@unmanaged_deps_filter//:io_netty_netty_codec_http2" -> "@unmanaged_deps_filter//:io_netty_netty_buffer" "@unmanaged_deps_filter//:io_netty_netty_codec_http2" -> "@unmanaged_deps_filter//:io_netty_netty_codec" "@unmanaged_deps_filter//:io_netty_netty_codec_http2" -> "@unmanaged_deps_filter//:io_netty_netty_codec_http" "@unmanaged_deps_filter//:io_netty_netty_codec_http2" -> "@unmanaged_deps_filter//:io_netty_netty_common" "@unmanaged_deps_filter//:io_netty_netty_codec_http2" -> "@unmanaged_deps_filter//:io_netty_netty_handler" "@unmanaged_deps_filter//:io_netty_netty_codec_http2" -> "@unmanaged_deps_filter//:io_netty_netty_transport" "@unmanaged_deps_filter//:io_netty_netty_codec_http2" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:io_netty_netty_codec_http2" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:io/projectreactor/netty/reactor-netty-http/1.1.29/reactor-netty-http-1.1.29.jar" "@unmanaged_deps_filter//:io/projectreactor/netty/reactor-netty-http/1.1.29/reactor-netty-http-1.1.29.jar" -> "@unmanaged_deps_filter//:io_projectreactor_netty_reactor_netty_http_1_1_29_extension" "@unmanaged_deps_filter//:io_projectreactor_netty_reactor_netty_http_1_1_29_extension" "@unmanaged_deps_filter//:io_projectreactor_netty_reactor_netty_http_1_1_29_extension" -> "@@rules_jvm_external~~maven~io_projectreactor_netty_reactor_netty_http_1_1_29//file:file" "@unmanaged_deps_filter//:io_projectreactor_netty_reactor_netty_http_1_1_29_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~io_projectreactor_netty_reactor_netty_http_1_1_29//file:file" "@@rules_jvm_external~~maven~io_projectreactor_netty_reactor_netty_http_1_1_29//file:file" -> "@@rules_jvm_external~~maven~io_projectreactor_netty_reactor_netty_http_1_1_29//file:v1/io/projectreactor/netty/reactor-netty-http/1.1.29/reactor-netty-http-1.1.29.jar" "@@rules_jvm_external~~maven~io_projectreactor_netty_reactor_netty_http_1_1_29//file:v1/io/projectreactor/netty/reactor-netty-http/1.1.29/reactor-netty-http-1.1.29.jar" "@unmanaged_deps_filter//:org/springframework/boot/spring-boot-starter-reactor-netty/3.3.11/spring-boot-starter-reactor-netty-3.3.11.jar" "@unmanaged_deps_filter//:org/springframework/boot/spring-boot-starter-reactor-netty/3.3.11/spring-boot-starter-reactor-netty-3.3.11.jar" -> "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_reactor_netty_3_3_11_extension" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_reactor_netty_3_3_11_extension" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_reactor_netty_3_3_11_extension" -> "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_reactor_netty_3_3_11//file:file" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_reactor_netty_3_3_11_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_reactor_netty_3_3_11//file:file" "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_reactor_netty_3_3_11//file:file" -> "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_reactor_netty_3_3_11//file:v1/org/springframework/boot/spring-boot-starter-reactor-netty/3.3.11/spring-boot-starter-reactor-netty-3.3.11.jar" "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_reactor_netty_3_3_11//file:v1/org/springframework/boot/spring-boot-starter-reactor-netty/3.3.11/spring-boot-starter-reactor-netty-3.3.11.jar" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_json" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_json" -> "@unmanaged_deps_filter//:org/springframework/boot/spring-boot-starter-json/3.3.11/spring-boot-starter-json-3.3.11.jar" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_json" -> "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_json" -> "@unmanaged_deps_filter//:com_fasterxml_jackson_datatype_jackson_datatype_jdk8" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_json" -> "@unmanaged_deps_filter//:com_fasterxml_jackson_datatype_jackson_datatype_jsr310" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_json" -> "@unmanaged_deps_filter//:com_fasterxml_jackson_module_jackson_module_parameter_names" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_json" -> "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_json" -> "@unmanaged_deps_filter//:org_springframework_spring_web" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_json" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_json" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:org_springframework_spring_web" "@unmanaged_deps_filter//:org_springframework_spring_web" -> "@unmanaged_deps_filter//:org/springframework/spring-web/6.1.19/spring-web-6.1.19.jar" "@unmanaged_deps_filter//:org_springframework_spring_web" -> "@unmanaged_deps_filter//:io_micrometer_micrometer_observation" "@unmanaged_deps_filter//:org_springframework_spring_web" -> "@unmanaged_deps_filter//:org_springframework_spring_beans" "@unmanaged_deps_filter//:org_springframework_spring_web" -> "@unmanaged_deps_filter//:org_springframework_spring_core" "@unmanaged_deps_filter//:org_springframework_spring_web" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:org_springframework_spring_web" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:org/springframework/spring-web/6.1.19/spring-web-6.1.19.jar" "@unmanaged_deps_filter//:org/springframework/spring-web/6.1.19/spring-web-6.1.19.jar" -> "@unmanaged_deps_filter//:org_springframework_spring_web_6_1_19_extension" "@unmanaged_deps_filter//:org_springframework_spring_web_6_1_19_extension" "@unmanaged_deps_filter//:org_springframework_spring_web_6_1_19_extension" -> "@@rules_jvm_external~~maven~org_springframework_spring_web_6_1_19//file:file" "@unmanaged_deps_filter//:org_springframework_spring_web_6_1_19_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~org_springframework_spring_web_6_1_19//file:file" "@@rules_jvm_external~~maven~org_springframework_spring_web_6_1_19//file:file" -> "@@rules_jvm_external~~maven~org_springframework_spring_web_6_1_19//file:v1/org/springframework/spring-web/6.1.19/spring-web-6.1.19.jar" "@@rules_jvm_external~~maven~org_springframework_spring_web_6_1_19//file:v1/org/springframework/spring-web/6.1.19/spring-web-6.1.19.jar" "@unmanaged_deps_filter//:com_fasterxml_jackson_module_jackson_module_parameter_names" "@unmanaged_deps_filter//:com_fasterxml_jackson_module_jackson_module_parameter_names" -> "@unmanaged_deps_filter//:com/fasterxml/jackson/module/jackson-module-parameter-names/2.17.3/jackson-module-parameter-names-2.17.3.jar" "@unmanaged_deps_filter//:com_fasterxml_jackson_module_jackson_module_parameter_names" -> "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_core" "@unmanaged_deps_filter//:com_fasterxml_jackson_module_jackson_module_parameter_names" -> "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind" "@unmanaged_deps_filter//:com_fasterxml_jackson_module_jackson_module_parameter_names" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:com_fasterxml_jackson_module_jackson_module_parameter_names" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:com/fasterxml/jackson/module/jackson-module-parameter-names/2.17.3/jackson-module-parameter-names-2.17.3.jar" "@unmanaged_deps_filter//:com/fasterxml/jackson/module/jackson-module-parameter-names/2.17.3/jackson-module-parameter-names-2.17.3.jar" -> "@unmanaged_deps_filter//:com_fasterxml_jackson_module_jackson_module_parameter_names_2_17_3_extension" "@unmanaged_deps_filter//:com_fasterxml_jackson_datatype_jackson_datatype_jsr310" "@unmanaged_deps_filter//:com_fasterxml_jackson_datatype_jackson_datatype_jsr310" -> "@unmanaged_deps_filter//:com/fasterxml/jackson/datatype/jackson-datatype-jsr310/2.17.3/jackson-datatype-jsr310-2.17.3.jar" "@unmanaged_deps_filter//:com_fasterxml_jackson_datatype_jackson_datatype_jsr310" -> "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_annotations" "@unmanaged_deps_filter//:com_fasterxml_jackson_datatype_jackson_datatype_jsr310" -> "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_core" "@unmanaged_deps_filter//:com_fasterxml_jackson_datatype_jackson_datatype_jsr310" -> "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind" "@unmanaged_deps_filter//:com_fasterxml_jackson_datatype_jackson_datatype_jsr310" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:com_fasterxml_jackson_datatype_jackson_datatype_jsr310" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:com/fasterxml/jackson/datatype/jackson-datatype-jsr310/2.17.3/jackson-datatype-jsr310-2.17.3.jar" "@unmanaged_deps_filter//:com/fasterxml/jackson/datatype/jackson-datatype-jsr310/2.17.3/jackson-datatype-jsr310-2.17.3.jar" -> "@unmanaged_deps_filter//:com_fasterxml_jackson_datatype_jackson_datatype_jsr310_2_17_3_extension" "@unmanaged_deps_filter//:com_fasterxml_jackson_datatype_jackson_datatype_jdk8" "@unmanaged_deps_filter//:com_fasterxml_jackson_datatype_jackson_datatype_jdk8" -> "@unmanaged_deps_filter//:com/fasterxml/jackson/datatype/jackson-datatype-jdk8/2.17.3/jackson-datatype-jdk8-2.17.3.jar" "@unmanaged_deps_filter//:com_fasterxml_jackson_datatype_jackson_datatype_jdk8" -> "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_core" "@unmanaged_deps_filter//:com_fasterxml_jackson_datatype_jackson_datatype_jdk8" -> "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind" "@unmanaged_deps_filter//:com_fasterxml_jackson_datatype_jackson_datatype_jdk8" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:com_fasterxml_jackson_datatype_jackson_datatype_jdk8" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:com/fasterxml/jackson/datatype/jackson-datatype-jdk8/2.17.3/jackson-datatype-jdk8-2.17.3.jar" "@unmanaged_deps_filter//:com/fasterxml/jackson/datatype/jackson-datatype-jdk8/2.17.3/jackson-datatype-jdk8-2.17.3.jar" -> "@unmanaged_deps_filter//:com_fasterxml_jackson_datatype_jackson_datatype_jdk8_2_17_3_extension" "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind" "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind" -> "@unmanaged_deps_filter//:com/fasterxml/jackson/core/jackson-databind/2.17.3/jackson-databind-2.17.3.jar" "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind" -> "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_annotations" "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind" -> "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_core" "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_core" "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_core" -> "@unmanaged_deps_filter//:com/fasterxml/jackson/core/jackson-core/2.17.3/jackson-core-2.17.3.jar" "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_core" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_core" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:com/fasterxml/jackson/core/jackson-core/2.17.3/jackson-core-2.17.3.jar" "@unmanaged_deps_filter//:com/fasterxml/jackson/core/jackson-core/2.17.3/jackson-core-2.17.3.jar" -> "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_core_2_17_3_extension" "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_core_2_17_3_extension" "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_core_2_17_3_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_core_2_17_3_extension" -> "@@rules_jvm_external~~maven~com_fasterxml_jackson_core_jackson_core_2_17_3//file:file" "@@rules_jvm_external~~maven~com_fasterxml_jackson_core_jackson_core_2_17_3//file:file" "@@rules_jvm_external~~maven~com_fasterxml_jackson_core_jackson_core_2_17_3//file:file" -> "@@rules_jvm_external~~maven~com_fasterxml_jackson_core_jackson_core_2_17_3//file:v1/com/fasterxml/jackson/core/jackson-core/2.17.3/jackson-core-2.17.3.jar" "@@rules_jvm_external~~maven~com_fasterxml_jackson_core_jackson_core_2_17_3//file:v1/com/fasterxml/jackson/core/jackson-core/2.17.3/jackson-core-2.17.3.jar" "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_annotations" "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_annotations" -> "@unmanaged_deps_filter//:com/fasterxml/jackson/core/jackson-annotations/2.17.3/jackson-annotations-2.17.3.jar" "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_annotations" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_annotations" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:com/fasterxml/jackson/core/jackson-annotations/2.17.3/jackson-annotations-2.17.3.jar" "@unmanaged_deps_filter//:com/fasterxml/jackson/core/jackson-annotations/2.17.3/jackson-annotations-2.17.3.jar" -> "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_annotations_2_17_3_extension" "@unmanaged_deps_filter//:org/springframework/boot/spring-boot-starter-json/3.3.11/spring-boot-starter-json-3.3.11.jar" "@unmanaged_deps_filter//:org/springframework/boot/spring-boot-starter-json/3.3.11/spring-boot-starter-json-3.3.11.jar" -> "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_json_3_3_11_extension" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_json_3_3_11_extension" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_json_3_3_11_extension" -> "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_json_3_3_11//file:file" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_json_3_3_11_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_json_3_3_11//file:file" "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_json_3_3_11//file:file" -> "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_json_3_3_11//file:v1/org/springframework/boot/spring-boot-starter-json/3.3.11/spring-boot-starter-json-3.3.11.jar" "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_json_3_3_11//file:v1/org/springframework/boot/spring-boot-starter-json/3.3.11/spring-boot-starter-json-3.3.11.jar" "@unmanaged_deps_filter//:org/springframework/boot/spring-boot-starter-webflux/3.3.11/spring-boot-starter-webflux-3.3.11.jar" "@unmanaged_deps_filter//:org/springframework/boot/spring-boot-starter-webflux/3.3.11/spring-boot-starter-webflux-3.3.11.jar" -> "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux_3_3_11_extension" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux_3_3_11_extension" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux_3_3_11_extension" -> "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_webflux_3_3_11//file:file" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux_3_3_11_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_aop" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_aop" -> "@unmanaged_deps_filter//:org/springframework/boot/spring-boot-starter-aop/3.3.11/spring-boot-starter-aop-3.3.11.jar" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_aop" -> "@unmanaged_deps_filter//:org_aspectj_aspectjweaver" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_aop" -> "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_aop" -> "@unmanaged_deps_filter//:org_springframework_spring_aop" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_aop" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_aop" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:org_aspectj_aspectjweaver" "@unmanaged_deps_filter//:org_aspectj_aspectjweaver" -> "@unmanaged_deps_filter//:org/aspectj/aspectjweaver/1.9.24/aspectjweaver-1.9.24.jar" "@unmanaged_deps_filter//:org_aspectj_aspectjweaver" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:org_aspectj_aspectjweaver" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:org/springframework/boot/spring-boot-starter-aop/3.3.11/spring-boot-starter-aop-3.3.11.jar" "@unmanaged_deps_filter//:org/springframework/boot/spring-boot-starter-aop/3.3.11/spring-boot-starter-aop-3.3.11.jar" -> "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_aop_3_3_11_extension" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_aop_3_3_11_extension" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_aop_3_3_11_extension" -> "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_aop_3_3_11//file:file" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_aop_3_3_11_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_aop_3_3_11//file:file" "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_aop_3_3_11//file:file" -> "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_aop_3_3_11//file:v1/org/springframework/boot/spring-boot-starter-aop/3.3.11/spring-boot-starter-aop-3.3.11.jar" "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_aop_3_3_11//file:v1/org/springframework/boot/spring-boot-starter-aop/3.3.11/spring-boot-starter-aop-3.3.11.jar" "@unmanaged_deps_filter//:com_fasterxml_jackson_datatype_jackson_datatype_jsr310_2_17_3_extension" "@unmanaged_deps_filter//:com_fasterxml_jackson_datatype_jackson_datatype_jsr310_2_17_3_extension" -> "@@rules_jvm_external~~maven~com_fasterxml_jackson_datatype_jackson_datatype_jsr310_2_17_3//file:file" "@unmanaged_deps_filter//:com_fasterxml_jackson_datatype_jackson_datatype_jsr310_2_17_3_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@unmanaged_deps_filter//:org/springframework/boot/spring-boot-starter-actuator/3.3.11/spring-boot-starter-actuator-3.3.11.jar" "@unmanaged_deps_filter//:org/springframework/boot/spring-boot-starter-actuator/3.3.11/spring-boot-starter-actuator-3.3.11.jar" -> "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator_3_3_11_extension" "@@rules_jvm_external~~maven~jakarta_xml_bind_jakarta_xml_bind_api_4_0_0//file:file" "@@rules_jvm_external~~maven~jakarta_xml_bind_jakarta_xml_bind_api_4_0_0//file:file" -> "@@rules_jvm_external~~maven~jakarta_xml_bind_jakarta_xml_bind_api_4_0_0//file:v1/jakarta/xml/bind/jakarta.xml.bind-api/4.0.0/jakarta.xml.bind-api-4.0.0.jar" "@@rules_jvm_external~~maven~jakarta_xml_bind_jakarta_xml_bind_api_4_0_0//file:v1/jakarta/xml/bind/jakarta.xml.bind-api/4.0.0/jakarta.xml.bind-api-4.0.0.jar" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_actuator_3_3_11_extension" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_actuator_3_3_11_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_actuator_3_3_11_extension" -> "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_actuator_3_3_11//file:file" "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_actuator_3_3_11//file:file" "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_actuator_3_3_11//file:file" -> "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_actuator_3_3_11//file:v1/org/springframework/boot/spring-boot-actuator/3.3.11/spring-boot-actuator-3.3.11.jar" "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_actuator_3_3_11//file:v1/org/springframework/boot/spring-boot-actuator/3.3.11/spring-boot-actuator-3.3.11.jar" "@unmanaged_deps_filter//:org/springframework/security/spring-security-oauth2-jose/6.3.9/spring-security-oauth2-jose-6.3.9.jar" "@unmanaged_deps_filter//:org/springframework/security/spring-security-oauth2-jose/6.3.9/spring-security-oauth2-jose-6.3.9.jar" -> "@unmanaged_deps_filter//:org_springframework_security_spring_security_oauth2_jose_6_3_9_extension" "@unmanaged_deps_filter//:org_springframework_security_spring_security_oauth2_jose_6_3_9_extension" "@unmanaged_deps_filter//:org_springframework_security_spring_security_oauth2_jose_6_3_9_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@unmanaged_deps_filter//:org_springframework_security_spring_security_oauth2_jose_6_3_9_extension" -> "@@rules_jvm_external~~maven~org_springframework_security_spring_security_oauth2_jose_6_3_9//file:file" "@@rules_jvm_external~~maven~org_antlr_antlr4_runtime_4_13_0//file:v1/org/antlr/antlr4-runtime/4.13.0/antlr4-runtime-4.13.0.jar" "@unmanaged_deps_filter//:org_glassfish_jaxb_txw2" "@unmanaged_deps_filter//:org_glassfish_jaxb_txw2" -> "@unmanaged_deps_filter//:org/glassfish/jaxb/txw2/4.0.2/txw2-4.0.2.jar" "@unmanaged_deps_filter//:org_glassfish_jaxb_txw2" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:org_glassfish_jaxb_txw2" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:org/glassfish/jaxb/txw2/4.0.2/txw2-4.0.2.jar" "@unmanaged_deps_filter//:org/glassfish/jaxb/txw2/4.0.2/txw2-4.0.2.jar" -> "@unmanaged_deps_filter//:org_glassfish_jaxb_txw2_4_0_2_extension" "@unmanaged_deps_filter//:org_glassfish_jaxb_txw2_4_0_2_extension" "@unmanaged_deps_filter//:org_glassfish_jaxb_txw2_4_0_2_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@unmanaged_deps_filter//:org_glassfish_jaxb_txw2_4_0_2_extension" -> "@@rules_jvm_external~~maven~org_glassfish_jaxb_txw2_4_0_2//file:file" "@@rules_jvm_external~~maven~org_glassfish_jaxb_txw2_4_0_2//file:file" "@@rules_jvm_external~~maven~org_glassfish_jaxb_txw2_4_0_2//file:file" -> "@@rules_jvm_external~~maven~org_glassfish_jaxb_txw2_4_0_2//file:v1/org/glassfish/jaxb/txw2/4.0.2/txw2-4.0.2.jar" "@unmanaged_deps_filter//:com_fasterxml_jackson_datatype_jackson_datatype_jdk8_2_17_3_extension" "@unmanaged_deps_filter//:com_fasterxml_jackson_datatype_jackson_datatype_jdk8_2_17_3_extension" -> "@@rules_jvm_external~~maven~com_fasterxml_jackson_datatype_jackson_datatype_jdk8_2_17_3//file:file" "@unmanaged_deps_filter//:com_fasterxml_jackson_datatype_jackson_datatype_jdk8_2_17_3_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~com_fasterxml_jackson_datatype_jackson_datatype_jdk8_2_17_3//file:file" "@@rules_jvm_external~~maven~com_fasterxml_jackson_datatype_jackson_datatype_jdk8_2_17_3//file:file" -> "@@rules_jvm_external~~maven~com_fasterxml_jackson_datatype_jackson_datatype_jdk8_2_17_3//file:v1/com/fasterxml/jackson/datatype/jackson-datatype-jdk8/2.17.3/jackson-datatype-jdk8-2.17.3.jar" "@@rules_jvm_external~~maven~com_fasterxml_jackson_datatype_jackson_datatype_jdk8_2_17_3//file:v1/com/fasterxml/jackson/datatype/jackson-datatype-jdk8/2.17.3/jackson-datatype-jdk8-2.17.3.jar" "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_security_3_3_11//file:v1/org/springframework/boot/spring-boot-starter-security/3.3.11/spring-boot-starter-security-3.3.11.jar" "@unmanaged_deps_filter//:org/springframework/security/spring-security-web/6.3.9/spring-security-web-6.3.9.jar" "@unmanaged_deps_filter//:org/springframework/security/spring-security-web/6.3.9/spring-security-web-6.3.9.jar" -> "@unmanaged_deps_filter//:org_springframework_security_spring_security_web_6_3_9_extension" "@unmanaged_deps_filter//:org_springframework_security_spring_security_web_6_3_9_extension" "@unmanaged_deps_filter//:org_springframework_security_spring_security_web_6_3_9_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@unmanaged_deps_filter//:org_springframework_security_spring_security_web_6_3_9_extension" -> "@@rules_jvm_external~~maven~org_springframework_security_spring_security_web_6_3_9//file:file" "@@rules_jvm_external~~maven~org_springframework_security_spring_security_web_6_3_9//file:file" "@@rules_jvm_external~~maven~org_springframework_security_spring_security_web_6_3_9//file:file" -> "@@rules_jvm_external~~maven~org_springframework_security_spring_security_web_6_3_9//file:v1/org/springframework/security/spring-security-web/6.3.9/spring-security-web-6.3.9.jar" "@@rules_jvm_external~~maven~org_springframework_security_spring_security_web_6_3_9//file:v1/org/springframework/security/spring-security-web/6.3.9/spring-security-web-6.3.9.jar" "@unmanaged_deps_filter//:com_nimbusds_nimbus_jose_jwt" "@unmanaged_deps_filter//:com_nimbusds_nimbus_jose_jwt" -> "@unmanaged_deps_filter//:com/nimbusds/nimbus-jose-jwt/9.37.3/nimbus-jose-jwt-9.37.3.jar" "@unmanaged_deps_filter//:com_nimbusds_nimbus_jose_jwt" -> "@unmanaged_deps_filter//:com_github_stephenc_jcip_jcip_annotations" "@unmanaged_deps_filter//:com_nimbusds_nimbus_jose_jwt" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:com_nimbusds_nimbus_jose_jwt" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:com_github_stephenc_jcip_jcip_annotations" "@unmanaged_deps_filter//:com_github_stephenc_jcip_jcip_annotations" -> "@unmanaged_deps_filter//:com/github/stephenc/jcip/jcip-annotations/1.0-1/jcip-annotations-1.0-1.jar" "@unmanaged_deps_filter//:com_github_stephenc_jcip_jcip_annotations" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:com_github_stephenc_jcip_jcip_annotations" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:com/github/stephenc/jcip/jcip-annotations/1.0-1/jcip-annotations-1.0-1.jar" "@unmanaged_deps_filter//:com/github/stephenc/jcip/jcip-annotations/1.0-1/jcip-annotations-1.0-1.jar" -> "@unmanaged_deps_filter//:com_github_stephenc_jcip_jcip_annotations_1_0_1_extension" "@unmanaged_deps_filter//:com/nimbusds/nimbus-jose-jwt/9.37.3/nimbus-jose-jwt-9.37.3.jar" "@unmanaged_deps_filter//:com/nimbusds/nimbus-jose-jwt/9.37.3/nimbus-jose-jwt-9.37.3.jar" -> "@unmanaged_deps_filter//:com_nimbusds_nimbus_jose_jwt_9_37_3_extension" "@unmanaged_deps_filter//:com_nimbusds_nimbus_jose_jwt_9_37_3_extension" "@unmanaged_deps_filter//:com_nimbusds_nimbus_jose_jwt_9_37_3_extension" -> "@@rules_jvm_external~~maven~com_nimbusds_nimbus_jose_jwt_9_37_3//file:file" "@unmanaged_deps_filter//:com_nimbusds_nimbus_jose_jwt_9_37_3_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@unmanaged_deps_filter//:org_ow2_asm_asm" "@unmanaged_deps_filter//:org_ow2_asm_asm" -> "@unmanaged_deps_filter//:org/ow2/asm/asm/9.7.1/asm-9.7.1.jar" "@unmanaged_deps_filter//:org_ow2_asm_asm" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:org_ow2_asm_asm" -> "@rules_jvm_external//settings:stamp_manifest" "@@rules_jvm_external~~maven~com_nimbusds_nimbus_jose_jwt_9_37_3//file:file" "@@rules_jvm_external~~maven~com_nimbusds_nimbus_jose_jwt_9_37_3//file:file" -> "@@rules_jvm_external~~maven~com_nimbusds_nimbus_jose_jwt_9_37_3//file:v1/com/nimbusds/nimbus-jose-jwt/9.37.3/nimbus-jose-jwt-9.37.3.jar" "@@rules_jvm_external~~maven~com_nimbusds_nimbus_jose_jwt_9_37_3//file:v1/com/nimbusds/nimbus-jose-jwt/9.37.3/nimbus-jose-jwt-9.37.3.jar" "@unmanaged_deps_filter//:jakarta/inject/jakarta.inject-api/2.0.1/jakarta.inject-api-2.0.1.jar" "@unmanaged_deps_filter//:jakarta/inject/jakarta.inject-api/2.0.1/jakarta.inject-api-2.0.1.jar" -> "@unmanaged_deps_filter//:jakarta_inject_jakarta_inject_api_2_0_1_extension" "@unmanaged_deps_filter//:jakarta_inject_jakarta_inject_api_2_0_1_extension" "@unmanaged_deps_filter//:jakarta_inject_jakarta_inject_api_2_0_1_extension" -> "@@rules_jvm_external~~maven~jakarta_inject_jakarta_inject_api_2_0_1//file:file" "@unmanaged_deps_filter//:jakarta_inject_jakarta_inject_api_2_0_1_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@unmanaged_deps_filter//:org_springframework_data_spring_data_commons" "@unmanaged_deps_filter//:org_springframework_data_spring_data_commons" -> "@unmanaged_deps_filter//:org/springframework/data/spring-data-commons/3.3.11/spring-data-commons-3.3.11.jar" "@unmanaged_deps_filter//:org_springframework_data_spring_data_commons" -> "@unmanaged_deps_filter//:org_springframework_spring_beans" "@unmanaged_deps_filter//:org_springframework_data_spring_data_commons" -> "@unmanaged_deps_filter//:org_springframework_spring_core" "@unmanaged_deps_filter//:org_springframework_data_spring_data_commons" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:org_springframework_data_spring_data_commons" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:org/springframework/data/spring-data-commons/3.3.11/spring-data-commons-3.3.11.jar" "@unmanaged_deps_filter//:org/springframework/data/spring-data-commons/3.3.11/spring-data-commons-3.3.11.jar" -> "@unmanaged_deps_filter//:org_springframework_data_spring_data_commons_3_3_11_extension" "@unmanaged_deps_filter//:org_springframework_data_spring_data_commons_3_3_11_extension" "@unmanaged_deps_filter//:org_springframework_data_spring_data_commons_3_3_11_extension" -> "@@rules_jvm_external~~maven~org_springframework_data_spring_data_commons_3_3_11//file:file" "@unmanaged_deps_filter//:org_springframework_data_spring_data_commons_3_3_11_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~org_springframework_data_spring_data_commons_3_3_11//file:file" "@@rules_jvm_external~~maven~org_springframework_data_spring_data_commons_3_3_11//file:file" -> "@@rules_jvm_external~~maven~org_springframework_data_spring_data_commons_3_3_11//file:v1/org/springframework/data/spring-data-commons/3.3.11/spring-data-commons-3.3.11.jar" "@@rules_jvm_external~~maven~org_springframework_data_spring_data_commons_3_3_11//file:v1/org/springframework/data/spring-data-commons/3.3.11/spring-data-commons-3.3.11.jar" "@@rules_jvm_external~~maven~net_minidev_accessors_smart_2_5_2//file:v1/net/minidev/accessors-smart/2.5.2/accessors-smart-2.5.2.jar" "@@rules_jvm_external~~maven~org_glassfish_jaxb_txw2_4_0_2//file:v1/org/glassfish/jaxb/txw2/4.0.2/txw2-4.0.2.jar" "@unmanaged_deps_filter//:org/hibernate/orm/hibernate-core/6.5.3.Final/hibernate-core-6.5.3.Final.jar" "@unmanaged_deps_filter//:org/hibernate/orm/hibernate-core/6.5.3.Final/hibernate-core-6.5.3.Final.jar" -> "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core_6_5_3_Final_extension" "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core_6_5_3_Final_extension" "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core_6_5_3_Final_extension" -> "@@rules_jvm_external~~maven~org_hibernate_orm_hibernate_core_6_5_3_Final//file:file" "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core_6_5_3_Final_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~org_hibernate_orm_hibernate_core_6_5_3_Final//file:file" "@@rules_jvm_external~~maven~org_hibernate_orm_hibernate_core_6_5_3_Final//file:file" -> "@@rules_jvm_external~~maven~org_hibernate_orm_hibernate_core_6_5_3_Final//file:v1/org/hibernate/orm/hibernate-core/6.5.3.Final/hibernate-core-6.5.3.Final.jar" "@@rules_jvm_external~~maven~org_hibernate_orm_hibernate_core_6_5_3_Final//file:v1/org/hibernate/orm/hibernate-core/6.5.3.Final/hibernate-core-6.5.3.Final.jar" "@unmanaged_deps_filter//:org_springframework_spring_orm" "@unmanaged_deps_filter//:org_springframework_spring_orm" -> "@unmanaged_deps_filter//:org/springframework/spring-orm/6.1.19/spring-orm-6.1.19.jar" "@unmanaged_deps_filter//:org_springframework_spring_orm" -> "@unmanaged_deps_filter//:org_springframework_spring_beans" "@unmanaged_deps_filter//:org_springframework_spring_orm" -> "@unmanaged_deps_filter//:org_springframework_spring_core" "@unmanaged_deps_filter//:org_springframework_spring_orm" -> "@unmanaged_deps_filter//:org_springframework_spring_jdbc" "@unmanaged_deps_filter//:org_springframework_spring_orm" -> "@unmanaged_deps_filter//:org_springframework_spring_tx" "@unmanaged_deps_filter//:org_springframework_spring_orm" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:org_springframework_spring_orm" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:org_springframework_spring_jdbc" "@unmanaged_deps_filter//:org_springframework_spring_jdbc" -> "@unmanaged_deps_filter//:org/springframework/spring-jdbc/6.1.19/spring-jdbc-6.1.19.jar" "@unmanaged_deps_filter//:org_springframework_spring_jdbc" -> "@unmanaged_deps_filter//:org_springframework_spring_beans" "@unmanaged_deps_filter//:org_springframework_spring_jdbc" -> "@unmanaged_deps_filter//:org_springframework_spring_core" "@unmanaged_deps_filter//:org_springframework_spring_jdbc" -> "@unmanaged_deps_filter//:org_springframework_spring_tx" "@unmanaged_deps_filter//:org_springframework_spring_jdbc" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:org_springframework_spring_jdbc" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:org_springframework_spring_tx" "@unmanaged_deps_filter//:org_springframework_spring_tx" -> "@unmanaged_deps_filter//:org/springframework/spring-tx/6.1.19/spring-tx-6.1.19.jar" "@unmanaged_deps_filter//:org_springframework_spring_tx" -> "@unmanaged_deps_filter//:org_springframework_spring_beans" "@unmanaged_deps_filter//:org_springframework_spring_tx" -> "@unmanaged_deps_filter//:org_springframework_spring_core" "@unmanaged_deps_filter//:org_springframework_spring_tx" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:org_springframework_spring_tx" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:org/springframework/spring-tx/6.1.19/spring-tx-6.1.19.jar" "@unmanaged_deps_filter//:org/springframework/spring-tx/6.1.19/spring-tx-6.1.19.jar" -> "@unmanaged_deps_filter//:org_springframework_spring_tx_6_1_19_extension" "@unmanaged_deps_filter//:org_springframework_spring_tx_6_1_19_extension" "@unmanaged_deps_filter//:org_springframework_spring_tx_6_1_19_extension" -> "@@rules_jvm_external~~maven~org_springframework_spring_tx_6_1_19//file:file" "@unmanaged_deps_filter//:org_springframework_spring_tx_6_1_19_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@unmanaged_deps_filter//:org/springframework/spring-jdbc/6.1.19/spring-jdbc-6.1.19.jar" "@unmanaged_deps_filter//:org/springframework/spring-jdbc/6.1.19/spring-jdbc-6.1.19.jar" -> "@unmanaged_deps_filter//:org_springframework_spring_jdbc_6_1_19_extension" "@unmanaged_deps_filter//:org_springframework_spring_jdbc_6_1_19_extension" "@unmanaged_deps_filter//:org_springframework_spring_jdbc_6_1_19_extension" -> "@@rules_jvm_external~~maven~org_springframework_spring_jdbc_6_1_19//file:file" "@unmanaged_deps_filter//:org_springframework_spring_jdbc_6_1_19_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~org_springframework_spring_jdbc_6_1_19//file:file" "@@rules_jvm_external~~maven~org_springframework_spring_jdbc_6_1_19//file:file" -> "@@rules_jvm_external~~maven~org_springframework_spring_jdbc_6_1_19//file:v1/org/springframework/spring-jdbc/6.1.19/spring-jdbc-6.1.19.jar" "@@rules_jvm_external~~maven~org_springframework_spring_jdbc_6_1_19//file:v1/org/springframework/spring-jdbc/6.1.19/spring-jdbc-6.1.19.jar" "@unmanaged_deps_filter//:jakarta/transaction/jakarta.transaction-api/2.0.1/jakarta.transaction-api-2.0.1.jar" "@unmanaged_deps_filter//:jakarta/transaction/jakarta.transaction-api/2.0.1/jakarta.transaction-api-2.0.1.jar" -> "@unmanaged_deps_filter//:jakarta_transaction_jakarta_transaction_api_2_0_1_extension" "@unmanaged_deps_filter//:jakarta_transaction_jakarta_transaction_api_2_0_1_extension" "@unmanaged_deps_filter//:jakarta_transaction_jakarta_transaction_api_2_0_1_extension" -> "@@rules_jvm_external~~maven~jakarta_transaction_jakarta_transaction_api_2_0_1//file:file" "@unmanaged_deps_filter//:jakarta_transaction_jakarta_transaction_api_2_0_1_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~jakarta_transaction_jakarta_transaction_api_2_0_1//file:file" "@@rules_jvm_external~~maven~jakarta_transaction_jakarta_transaction_api_2_0_1//file:file" -> "@@rules_jvm_external~~maven~jakarta_transaction_jakarta_transaction_api_2_0_1//file:v1/jakarta/transaction/jakarta.transaction-api/2.0.1/jakarta.transaction-api-2.0.1.jar" "@@rules_jvm_external~~maven~jakarta_transaction_jakarta_transaction_api_2_0_1//file:v1/jakarta/transaction/jakarta.transaction-api/2.0.1/jakarta.transaction-api-2.0.1.jar" "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_oauth2_client_3_3_11//file:file" "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_oauth2_client_3_3_11//file:file" -> "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_oauth2_client_3_3_11//file:v1/org/springframework/boot/spring-boot-starter-oauth2-client/3.3.11/spring-boot-starter-oauth2-client-3.3.11.jar" "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_oauth2_client_3_3_11//file:v1/org/springframework/boot/spring-boot-starter-oauth2-client/3.3.11/spring-boot-starter-oauth2-client-3.3.11.jar" "@unmanaged_deps_filter//:org/aspectj/aspectjweaver/1.9.24/aspectjweaver-1.9.24.jar" "@unmanaged_deps_filter//:org/aspectj/aspectjweaver/1.9.24/aspectjweaver-1.9.24.jar" -> "@unmanaged_deps_filter//:org_aspectj_aspectjweaver_1_9_24_extension" "@unmanaged_deps_filter//:org_aspectj_aspectjweaver_1_9_24_extension" "@unmanaged_deps_filter//:org_aspectj_aspectjweaver_1_9_24_extension" -> "@@rules_jvm_external~~maven~org_aspectj_aspectjweaver_1_9_24//file:file" "@unmanaged_deps_filter//:org_aspectj_aspectjweaver_1_9_24_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~org_aspectj_aspectjweaver_1_9_24//file:file" "@@rules_jvm_external~~maven~org_aspectj_aspectjweaver_1_9_24//file:file" -> "@@rules_jvm_external~~maven~org_aspectj_aspectjweaver_1_9_24//file:v1/org/aspectj/aspectjweaver/1.9.24/aspectjweaver-1.9.24.jar" "@@rules_jvm_external~~maven~org_aspectj_aspectjweaver_1_9_24//file:v1/org/aspectj/aspectjweaver/1.9.24/aspectjweaver-1.9.24.jar" "@unmanaged_deps_filter//:com_fasterxml_jackson_module_jackson_module_parameter_names_2_17_3_extension" "@unmanaged_deps_filter//:com_fasterxml_jackson_module_jackson_module_parameter_names_2_17_3_extension" -> "@@rules_jvm_external~~maven~com_fasterxml_jackson_module_jackson_module_parameter_names_2_17_3//file:file" "@unmanaged_deps_filter//:com_fasterxml_jackson_module_jackson_module_parameter_names_2_17_3_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~com_fasterxml_jackson_module_jackson_module_parameter_names_2_17_3//file:file" "@@rules_jvm_external~~maven~com_fasterxml_jackson_module_jackson_module_parameter_names_2_17_3//file:file" -> "@@rules_jvm_external~~maven~com_fasterxml_jackson_module_jackson_module_parameter_names_2_17_3//file:v1/com/fasterxml/jackson/module/jackson-module-parameter-names/2.17.3/jackson-module-parameter-names-2.17.3.jar" "@@rules_jvm_external~~maven~com_fasterxml_jackson_module_jackson_module_parameter_names_2_17_3//file:v1/com/fasterxml/jackson/module/jackson-module-parameter-names/2.17.3/jackson-module-parameter-names-2.17.3.jar" "@unmanaged_deps_filter//:io_projectreactor_netty_reactor_netty_core" "@unmanaged_deps_filter//:io_projectreactor_netty_reactor_netty_core" -> "@unmanaged_deps_filter//:io/projectreactor/netty/reactor-netty-core/1.1.29/reactor-netty-core-1.1.29.jar" "@unmanaged_deps_filter//:io_projectreactor_netty_reactor_netty_core" -> "@unmanaged_deps_filter//:io_netty_netty_handler" "@unmanaged_deps_filter//:io_projectreactor_netty_reactor_netty_core" -> "@unmanaged_deps_filter//:io_netty_netty_handler_proxy" "@unmanaged_deps_filter//:io_projectreactor_netty_reactor_netty_core" -> "@unmanaged_deps_filter//:io_netty_netty_resolver_dns" "@unmanaged_deps_filter//:io_projectreactor_netty_reactor_netty_core" -> "@unmanaged_deps_filter//:io_netty_netty_resolver_dns_native_macos_osx_x86_64" "@unmanaged_deps_filter//:io_projectreactor_netty_reactor_netty_core" -> "@unmanaged_deps_filter//:io_netty_netty_transport_native_epoll_linux_x86_64" "@unmanaged_deps_filter//:io_projectreactor_netty_reactor_netty_core" -> "@unmanaged_deps_filter//:io_projectreactor_reactor_core" "@unmanaged_deps_filter//:io_projectreactor_netty_reactor_netty_core" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:io_projectreactor_netty_reactor_netty_core" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:io_projectreactor_reactor_core" "@unmanaged_deps_filter//:io_projectreactor_reactor_core" -> "@unmanaged_deps_filter//:io/projectreactor/reactor-core/3.6.15/reactor-core-3.6.15.jar" "@unmanaged_deps_filter//:io_projectreactor_reactor_core" -> "@unmanaged_deps_filter//:org_reactivestreams_reactive_streams" "@unmanaged_deps_filter//:io_projectreactor_reactor_core" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:io_projectreactor_reactor_core" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:org_reactivestreams_reactive_streams" "@unmanaged_deps_filter//:org_reactivestreams_reactive_streams" -> "@unmanaged_deps_filter//:org/reactivestreams/reactive-streams/1.0.4/reactive-streams-1.0.4.jar" "@unmanaged_deps_filter//:org_reactivestreams_reactive_streams" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:org_reactivestreams_reactive_streams" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:org/reactivestreams/reactive-streams/1.0.4/reactive-streams-1.0.4.jar" "@unmanaged_deps_filter//:org/reactivestreams/reactive-streams/1.0.4/reactive-streams-1.0.4.jar" -> "@unmanaged_deps_filter//:org_reactivestreams_reactive_streams_1_0_4_extension" "@unmanaged_deps_filter//:io_netty_netty_transport_native_epoll_linux_x86_64" "@unmanaged_deps_filter//:io_netty_netty_transport_native_epoll_linux_x86_64" -> "@unmanaged_deps_filter//:io/netty/netty-transport-native-epoll/4.1.119.Final/netty-transport-native-epoll-4.1.119.Final-linux-x86_64.jar" "@unmanaged_deps_filter//:io_netty_netty_transport_native_epoll_linux_x86_64" -> "@unmanaged_deps_filter//:io_netty_netty_buffer" "@unmanaged_deps_filter//:io_netty_netty_transport_native_epoll_linux_x86_64" -> "@unmanaged_deps_filter//:io_netty_netty_common" "@unmanaged_deps_filter//:io_netty_netty_transport_native_epoll_linux_x86_64" -> "@unmanaged_deps_filter//:io_netty_netty_transport" "@unmanaged_deps_filter//:io_netty_netty_transport_native_epoll_linux_x86_64" -> "@unmanaged_deps_filter//:io_netty_netty_transport_classes_epoll" "@unmanaged_deps_filter//:io_netty_netty_transport_native_epoll_linux_x86_64" -> "@unmanaged_deps_filter//:io_netty_netty_transport_native_unix_common" "@unmanaged_deps_filter//:io_netty_netty_transport_native_epoll_linux_x86_64" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:io_netty_netty_transport_native_epoll_linux_x86_64" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:io_netty_netty_transport_classes_epoll" "@unmanaged_deps_filter//:io_netty_netty_transport_classes_epoll" -> "@unmanaged_deps_filter//:io/netty/netty-transport-classes-epoll/4.1.119.Final/netty-transport-classes-epoll-4.1.119.Final.jar" "@unmanaged_deps_filter//:io_netty_netty_transport_classes_epoll" -> "@unmanaged_deps_filter//:io_netty_netty_buffer" "@unmanaged_deps_filter//:io_netty_netty_transport_classes_epoll" -> "@unmanaged_deps_filter//:io_netty_netty_common" "@unmanaged_deps_filter//:io_netty_netty_transport_classes_epoll" -> "@unmanaged_deps_filter//:io_netty_netty_transport" "@unmanaged_deps_filter//:io_netty_netty_transport_classes_epoll" -> "@unmanaged_deps_filter//:io_netty_netty_transport_native_unix_common" "@unmanaged_deps_filter//:io_netty_netty_transport_classes_epoll" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:io_netty_netty_transport_classes_epoll" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:io/netty/netty-transport-classes-epoll/4.1.119.Final/netty-transport-classes-epoll-4.1.119.Final.jar" "@unmanaged_deps_filter//:io/netty/netty-transport-classes-epoll/4.1.119.Final/netty-transport-classes-epoll-4.1.119.Final.jar" -> "@unmanaged_deps_filter//:io_netty_netty_transport_classes_epoll_4_1_119_Final_extension" "@unmanaged_deps_filter//:io_netty_netty_transport_classes_epoll_4_1_119_Final_extension" "@unmanaged_deps_filter//:io_netty_netty_transport_classes_epoll_4_1_119_Final_extension" -> "@@rules_jvm_external~~maven~io_netty_netty_transport_classes_epoll_4_1_119_Final//file:file" "@unmanaged_deps_filter//:io_netty_netty_transport_classes_epoll_4_1_119_Final_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~io_netty_netty_transport_classes_epoll_4_1_119_Final//file:file" "@@rules_jvm_external~~maven~io_netty_netty_transport_classes_epoll_4_1_119_Final//file:file" -> "@@rules_jvm_external~~maven~io_netty_netty_transport_classes_epoll_4_1_119_Final//file:v1/io/netty/netty-transport-classes-epoll/4.1.119.Final/netty-transport-classes-epoll-4.1.119.Final.jar" "@@rules_jvm_external~~maven~io_netty_netty_transport_classes_epoll_4_1_119_Final//file:v1/io/netty/netty-transport-classes-epoll/4.1.119.Final/netty-transport-classes-epoll-4.1.119.Final.jar" "@unmanaged_deps_filter//:io/netty/netty-transport-native-epoll/4.1.119.Final/netty-transport-native-epoll-4.1.119.Final-linux-x86_64.jar" "@unmanaged_deps_filter//:io/netty/netty-transport-native-epoll/4.1.119.Final/netty-transport-native-epoll-4.1.119.Final-linux-x86_64.jar" -> "@unmanaged_deps_filter//:io_netty_netty_transport_native_epoll_jar_linux_x86_64_4_1_119_Final_extension" "@unmanaged_deps_filter//:io_netty_netty_transport_native_epoll_jar_linux_x86_64_4_1_119_Final_extension" "@unmanaged_deps_filter//:io_netty_netty_transport_native_epoll_jar_linux_x86_64_4_1_119_Final_extension" -> "@@rules_jvm_external~~maven~io_netty_netty_transport_native_epoll_jar_linux_x86_64_4_1_119_Final//file:file" "@unmanaged_deps_filter//:io_netty_netty_transport_native_epoll_jar_linux_x86_64_4_1_119_Final_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~io_netty_netty_transport_native_epoll_jar_linux_x86_64_4_1_119_Final//file:file" "@@rules_jvm_external~~maven~io_netty_netty_transport_native_epoll_jar_linux_x86_64_4_1_119_Final//file:file" -> "@@rules_jvm_external~~maven~io_netty_netty_transport_native_epoll_jar_linux_x86_64_4_1_119_Final//file:v1/io/netty/netty-transport-native-epoll/4.1.119.Final/netty-transport-native-epoll-4.1.119.Final-linux-x86_64.jar" "@@rules_jvm_external~~maven~io_netty_netty_transport_native_epoll_jar_linux_x86_64_4_1_119_Final//file:v1/io/netty/netty-transport-native-epoll/4.1.119.Final/netty-transport-native-epoll-4.1.119.Final-linux-x86_64.jar" "@unmanaged_deps_filter//:io_netty_netty_resolver_dns_native_macos_osx_x86_64" "@unmanaged_deps_filter//:io_netty_netty_resolver_dns_native_macos_osx_x86_64" -> "@unmanaged_deps_filter//:io/netty/netty-resolver-dns-native-macos/4.1.119.Final/netty-resolver-dns-native-macos-4.1.119.Final-osx-x86_64.jar" "@unmanaged_deps_filter//:io_netty_netty_resolver_dns_native_macos_osx_x86_64" -> "@unmanaged_deps_filter//:io_netty_netty_resolver_dns_classes_macos" "@unmanaged_deps_filter//:io_netty_netty_resolver_dns_native_macos_osx_x86_64" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:io_netty_netty_resolver_dns_native_macos_osx_x86_64" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:io_netty_netty_resolver_dns_classes_macos" "@unmanaged_deps_filter//:io_netty_netty_resolver_dns_classes_macos" -> "@unmanaged_deps_filter//:io/netty/netty-resolver-dns-classes-macos/4.1.119.Final/netty-resolver-dns-classes-macos-4.1.119.Final.jar" "@unmanaged_deps_filter//:io_netty_netty_resolver_dns_classes_macos" -> "@unmanaged_deps_filter//:io_netty_netty_common" "@unmanaged_deps_filter//:io_netty_netty_resolver_dns_classes_macos" -> "@unmanaged_deps_filter//:io_netty_netty_resolver_dns" "@unmanaged_deps_filter//:io_netty_netty_resolver_dns_classes_macos" -> "@unmanaged_deps_filter//:io_netty_netty_transport_native_unix_common" "@unmanaged_deps_filter//:io_netty_netty_resolver_dns_classes_macos" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:io_netty_netty_resolver_dns_classes_macos" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:io/netty/netty-resolver-dns-classes-macos/4.1.119.Final/netty-resolver-dns-classes-macos-4.1.119.Final.jar" "@unmanaged_deps_filter//:io/netty/netty-resolver-dns-classes-macos/4.1.119.Final/netty-resolver-dns-classes-macos-4.1.119.Final.jar" -> "@unmanaged_deps_filter//:io_netty_netty_resolver_dns_classes_macos_4_1_119_Final_extension" "@unmanaged_deps_filter//:io_netty_netty_resolver_dns_classes_macos_4_1_119_Final_extension" "@unmanaged_deps_filter//:io_netty_netty_resolver_dns_classes_macos_4_1_119_Final_extension" -> "@@rules_jvm_external~~maven~io_netty_netty_resolver_dns_classes_macos_4_1_119_Final//file:file" "@unmanaged_deps_filter//:io_netty_netty_resolver_dns_classes_macos_4_1_119_Final_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~io_netty_netty_resolver_dns_classes_macos_4_1_119_Final//file:file" "@@rules_jvm_external~~maven~io_netty_netty_resolver_dns_classes_macos_4_1_119_Final//file:file" -> "@@rules_jvm_external~~maven~io_netty_netty_resolver_dns_classes_macos_4_1_119_Final//file:v1/io/netty/netty-resolver-dns-classes-macos/4.1.119.Final/netty-resolver-dns-classes-macos-4.1.119.Final.jar" "@@rules_jvm_external~~maven~io_netty_netty_resolver_dns_classes_macos_4_1_119_Final//file:v1/io/netty/netty-resolver-dns-classes-macos/4.1.119.Final/netty-resolver-dns-classes-macos-4.1.119.Final.jar" "@unmanaged_deps_filter//:io/netty/netty-resolver-dns-native-macos/4.1.119.Final/netty-resolver-dns-native-macos-4.1.119.Final-osx-x86_64.jar" "@unmanaged_deps_filter//:io/netty/netty-resolver-dns-native-macos/4.1.119.Final/netty-resolver-dns-native-macos-4.1.119.Final-osx-x86_64.jar" -> "@unmanaged_deps_filter//:io_netty_netty_resolver_dns_native_macos_jar_osx_x86_64_4_1_119_Final_extension" "@unmanaged_deps_filter//:io_netty_netty_resolver_dns_native_macos_jar_osx_x86_64_4_1_119_Final_extension" "@unmanaged_deps_filter//:io_netty_netty_resolver_dns_native_macos_jar_osx_x86_64_4_1_119_Final_extension" -> "@@rules_jvm_external~~maven~io_netty_netty_resolver_dns_native_macos_jar_osx_x86_64_4_1_119_Final//file:file" "@unmanaged_deps_filter//:io_netty_netty_resolver_dns_native_macos_jar_osx_x86_64_4_1_119_Final_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~io_netty_netty_resolver_dns_native_macos_jar_osx_x86_64_4_1_119_Final//file:file" "@@rules_jvm_external~~maven~io_netty_netty_resolver_dns_native_macos_jar_osx_x86_64_4_1_119_Final//file:file" -> "@@rules_jvm_external~~maven~io_netty_netty_resolver_dns_native_macos_jar_osx_x86_64_4_1_119_Final//file:v1/io/netty/netty-resolver-dns-native-macos/4.1.119.Final/netty-resolver-dns-native-macos-4.1.119.Final-osx-x86_64.jar" "@@rules_jvm_external~~maven~io_netty_netty_resolver_dns_native_macos_jar_osx_x86_64_4_1_119_Final//file:v1/io/netty/netty-resolver-dns-native-macos/4.1.119.Final/netty-resolver-dns-native-macos-4.1.119.Final-osx-x86_64.jar" "@unmanaged_deps_filter//:io_netty_netty_resolver_dns" "@unmanaged_deps_filter//:io_netty_netty_resolver_dns" -> "@unmanaged_deps_filter//:io/netty/netty-resolver-dns/4.1.119.Final/netty-resolver-dns-4.1.119.Final.jar" "@unmanaged_deps_filter//:io_netty_netty_resolver_dns" -> "@unmanaged_deps_filter//:io_netty_netty_buffer" "@unmanaged_deps_filter//:io_netty_netty_resolver_dns" -> "@unmanaged_deps_filter//:io_netty_netty_codec" "@unmanaged_deps_filter//:io_netty_netty_resolver_dns" -> "@unmanaged_deps_filter//:io_netty_netty_codec_dns" "@unmanaged_deps_filter//:io_netty_netty_resolver_dns" -> "@unmanaged_deps_filter//:io_netty_netty_common" "@unmanaged_deps_filter//:io_netty_netty_resolver_dns" -> "@unmanaged_deps_filter//:io_netty_netty_handler" "@unmanaged_deps_filter//:io_netty_netty_resolver_dns" -> "@unmanaged_deps_filter//:io_netty_netty_resolver" "@unmanaged_deps_filter//:io_netty_netty_resolver_dns" -> "@unmanaged_deps_filter//:io_netty_netty_transport" "@unmanaged_deps_filter//:io_netty_netty_resolver_dns" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:io_netty_netty_resolver_dns" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:io_netty_netty_codec_dns" "@unmanaged_deps_filter//:io_netty_netty_codec_dns" -> "@unmanaged_deps_filter//:io/netty/netty-codec-dns/4.1.119.Final/netty-codec-dns-4.1.119.Final.jar" "@unmanaged_deps_filter//:io_netty_netty_codec_dns" -> "@unmanaged_deps_filter//:io_netty_netty_buffer" "@unmanaged_deps_filter//:io_netty_netty_codec_dns" -> "@unmanaged_deps_filter//:io_netty_netty_codec" "@unmanaged_deps_filter//:io_netty_netty_codec_dns" -> "@unmanaged_deps_filter//:io_netty_netty_common" "@unmanaged_deps_filter//:io_netty_netty_codec_dns" -> "@unmanaged_deps_filter//:io_netty_netty_transport" "@unmanaged_deps_filter//:io_netty_netty_codec_dns" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:io_netty_netty_codec_dns" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:io/netty/netty-codec-dns/4.1.119.Final/netty-codec-dns-4.1.119.Final.jar" "@unmanaged_deps_filter//:io/netty/netty-codec-dns/4.1.119.Final/netty-codec-dns-4.1.119.Final.jar" -> "@unmanaged_deps_filter//:io_netty_netty_codec_dns_4_1_119_Final_extension" "@unmanaged_deps_filter//:io_netty_netty_codec_dns_4_1_119_Final_extension" "@unmanaged_deps_filter//:io_netty_netty_codec_dns_4_1_119_Final_extension" -> "@@rules_jvm_external~~maven~io_netty_netty_codec_dns_4_1_119_Final//file:file" "@unmanaged_deps_filter//:io_netty_netty_codec_dns_4_1_119_Final_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~io_netty_netty_codec_dns_4_1_119_Final//file:file" "@@rules_jvm_external~~maven~io_netty_netty_codec_dns_4_1_119_Final//file:file" -> "@@rules_jvm_external~~maven~io_netty_netty_codec_dns_4_1_119_Final//file:v1/io/netty/netty-codec-dns/4.1.119.Final/netty-codec-dns-4.1.119.Final.jar" "@@rules_jvm_external~~maven~io_netty_netty_codec_dns_4_1_119_Final//file:v1/io/netty/netty-codec-dns/4.1.119.Final/netty-codec-dns-4.1.119.Final.jar" "@unmanaged_deps_filter//:io/netty/netty-resolver-dns/4.1.119.Final/netty-resolver-dns-4.1.119.Final.jar" "@unmanaged_deps_filter//:io/netty/netty-resolver-dns/4.1.119.Final/netty-resolver-dns-4.1.119.Final.jar" -> "@unmanaged_deps_filter//:io_netty_netty_resolver_dns_4_1_119_Final_extension" "@unmanaged_deps_filter//:io_netty_netty_resolver_dns_4_1_119_Final_extension" "@unmanaged_deps_filter//:io_netty_netty_resolver_dns_4_1_119_Final_extension" -> "@@rules_jvm_external~~maven~io_netty_netty_resolver_dns_4_1_119_Final//file:file" "@unmanaged_deps_filter//:io_netty_netty_resolver_dns_4_1_119_Final_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@unmanaged_deps_filter//:io/projectreactor/netty/reactor-netty-core/1.1.29/reactor-netty-core-1.1.29.jar" "@unmanaged_deps_filter//:io/projectreactor/netty/reactor-netty-core/1.1.29/reactor-netty-core-1.1.29.jar" -> "@unmanaged_deps_filter//:io_projectreactor_netty_reactor_netty_core_1_1_29_extension" "@unmanaged_deps_filter//:io_projectreactor_netty_reactor_netty_core_1_1_29_extension" "@unmanaged_deps_filter//:io_projectreactor_netty_reactor_netty_core_1_1_29_extension" -> "@@rules_jvm_external~~maven~io_projectreactor_netty_reactor_netty_core_1_1_29//file:file" "@unmanaged_deps_filter//:io_projectreactor_netty_reactor_netty_core_1_1_29_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~io_projectreactor_netty_reactor_netty_core_1_1_29//file:file" "@@rules_jvm_external~~maven~io_projectreactor_netty_reactor_netty_core_1_1_29//file:file" -> "@@rules_jvm_external~~maven~io_projectreactor_netty_reactor_netty_core_1_1_29//file:v1/io/projectreactor/netty/reactor-netty-core/1.1.29/reactor-netty-core-1.1.29.jar" "@@rules_jvm_external~~maven~io_projectreactor_netty_reactor_netty_core_1_1_29//file:v1/io/projectreactor/netty/reactor-netty-core/1.1.29/reactor-netty-core-1.1.29.jar" "@unmanaged_deps_filter//:io/netty/netty-codec-http2/4.1.119.Final/netty-codec-http2-4.1.119.Final.jar" "@unmanaged_deps_filter//:io/netty/netty-codec-http2/4.1.119.Final/netty-codec-http2-4.1.119.Final.jar" -> "@unmanaged_deps_filter//:io_netty_netty_codec_http2_4_1_119_Final_extension" "@unmanaged_deps_filter//:io_netty_netty_codec_http2_4_1_119_Final_extension" "@unmanaged_deps_filter//:io_netty_netty_codec_http2_4_1_119_Final_extension" -> "@@rules_jvm_external~~maven~io_netty_netty_codec_http2_4_1_119_Final//file:file" "@unmanaged_deps_filter//:io_netty_netty_codec_http2_4_1_119_Final_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~io_netty_netty_codec_http2_4_1_119_Final//file:file" "@@rules_jvm_external~~maven~io_netty_netty_codec_http2_4_1_119_Final//file:file" -> "@@rules_jvm_external~~maven~io_netty_netty_codec_http2_4_1_119_Final//file:v1/io/netty/netty-codec-http2/4.1.119.Final/netty-codec-http2-4.1.119.Final.jar" "@@rules_jvm_external~~maven~io_netty_netty_codec_http2_4_1_119_Final//file:v1/io/netty/netty-codec-http2/4.1.119.Final/netty-codec-http2-4.1.119.Final.jar" "@@rules_jvm_external~~maven~com_fasterxml_jackson_datatype_jackson_datatype_jsr310_2_17_3//file:file" "@@rules_jvm_external~~maven~com_fasterxml_jackson_datatype_jackson_datatype_jsr310_2_17_3//file:file" -> "@@rules_jvm_external~~maven~com_fasterxml_jackson_datatype_jackson_datatype_jsr310_2_17_3//file:v1/com/fasterxml/jackson/datatype/jackson-datatype-jsr310/2.17.3/jackson-datatype-jsr310-2.17.3.jar" "@@rules_jvm_external~~maven~com_fasterxml_jackson_datatype_jackson_datatype_jsr310_2_17_3//file:v1/com/fasterxml/jackson/datatype/jackson-datatype-jsr310/2.17.3/jackson-datatype-jsr310-2.17.3.jar" "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_annotations_2_17_3_extension" "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_annotations_2_17_3_extension" -> "@@rules_jvm_external~~maven~com_fasterxml_jackson_core_jackson_annotations_2_17_3//file:file" "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_annotations_2_17_3_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~com_fasterxml_jackson_core_jackson_annotations_2_17_3//file:file" "@@rules_jvm_external~~maven~com_fasterxml_jackson_core_jackson_annotations_2_17_3//file:file" -> "@@rules_jvm_external~~maven~com_fasterxml_jackson_core_jackson_annotations_2_17_3//file:v1/com/fasterxml/jackson/core/jackson-annotations/2.17.3/jackson-annotations-2.17.3.jar" "@@rules_jvm_external~~maven~com_fasterxml_jackson_core_jackson_annotations_2_17_3//file:v1/com/fasterxml/jackson/core/jackson-annotations/2.17.3/jackson-annotations-2.17.3.jar" "@unmanaged_deps_filter//:org/hibernate/common/hibernate-commons-annotations/6.0.6.Final/hibernate-commons-annotations-6.0.6.Final.jar" "@unmanaged_deps_filter//:org/hibernate/common/hibernate-commons-annotations/6.0.6.Final/hibernate-commons-annotations-6.0.6.Final.jar" -> "@unmanaged_deps_filter//:org_hibernate_common_hibernate_commons_annotations_6_0_6_Final_extension" "@unmanaged_deps_filter//:org_hibernate_common_hibernate_commons_annotations_6_0_6_Final_extension" "@unmanaged_deps_filter//:org_hibernate_common_hibernate_commons_annotations_6_0_6_Final_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@unmanaged_deps_filter//:org_hibernate_common_hibernate_commons_annotations_6_0_6_Final_extension" -> "@@rules_jvm_external~~maven~org_hibernate_common_hibernate_commons_annotations_6_0_6_Final//file:file" "@@rules_jvm_external~~maven~org_hibernate_common_hibernate_commons_annotations_6_0_6_Final//file:file" "@@rules_jvm_external~~maven~org_hibernate_common_hibernate_commons_annotations_6_0_6_Final//file:file" -> "@@rules_jvm_external~~maven~org_hibernate_common_hibernate_commons_annotations_6_0_6_Final//file:v1/org/hibernate/common/hibernate-commons-annotations/6.0.6.Final/hibernate-commons-annotations-6.0.6.Final.jar" "@@rules_jvm_external~~maven~org_hibernate_common_hibernate_commons_annotations_6_0_6_Final//file:v1/org/hibernate/common/hibernate-commons-annotations/6.0.6.Final/hibernate-commons-annotations-6.0.6.Final.jar" "@unmanaged_deps_filter//:org_springframework_security_spring_security_core" "@unmanaged_deps_filter//:org_springframework_security_spring_security_core" -> "@unmanaged_deps_filter//:org/springframework/security/spring-security-core/6.3.9/spring-security-core-6.3.9.jar" "@unmanaged_deps_filter//:org_springframework_security_spring_security_core" -> "@unmanaged_deps_filter//:io_micrometer_micrometer_observation" "@unmanaged_deps_filter//:org_springframework_security_spring_security_core" -> "@unmanaged_deps_filter//:org_springframework_security_spring_security_crypto" "@unmanaged_deps_filter//:org_springframework_security_spring_security_core" -> "@unmanaged_deps_filter//:org_springframework_spring_aop" "@unmanaged_deps_filter//:org_springframework_security_spring_security_core" -> "@unmanaged_deps_filter//:org_springframework_spring_beans" "@unmanaged_deps_filter//:org_springframework_security_spring_security_core" -> "@unmanaged_deps_filter//:org_springframework_spring_context" "@unmanaged_deps_filter//:org_springframework_security_spring_security_core" -> "@unmanaged_deps_filter//:org_springframework_spring_core" "@unmanaged_deps_filter//:org_springframework_security_spring_security_core" -> "@unmanaged_deps_filter//:org_springframework_spring_expression" "@unmanaged_deps_filter//:org_springframework_security_spring_security_core" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:org_springframework_security_spring_security_core" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:org_springframework_security_spring_security_crypto" "@unmanaged_deps_filter//:org_springframework_security_spring_security_crypto" -> "@unmanaged_deps_filter//:org/springframework/security/spring-security-crypto/6.3.9/spring-security-crypto-6.3.9.jar" "@unmanaged_deps_filter//:org_springframework_security_spring_security_crypto" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:org_springframework_security_spring_security_crypto" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:org/springframework/security/spring-security-core/6.3.9/spring-security-core-6.3.9.jar" "@unmanaged_deps_filter//:org/springframework/security/spring-security-core/6.3.9/spring-security-core-6.3.9.jar" -> "@unmanaged_deps_filter//:org_springframework_security_spring_security_core_6_3_9_extension" "@unmanaged_deps_filter//:org_springframework_security_spring_security_core_6_3_9_extension" "@unmanaged_deps_filter//:org_springframework_security_spring_security_core_6_3_9_extension" -> "@@rules_jvm_external~~maven~org_springframework_security_spring_security_core_6_3_9//file:file" "@unmanaged_deps_filter//:org_springframework_security_spring_security_core_6_3_9_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~org_springframework_security_spring_security_core_6_3_9//file:file" "@@rules_jvm_external~~maven~org_springframework_security_spring_security_core_6_3_9//file:file" -> "@@rules_jvm_external~~maven~org_springframework_security_spring_security_core_6_3_9//file:v1/org/springframework/security/spring-security-core/6.3.9/spring-security-core-6.3.9.jar" "@@rules_jvm_external~~maven~org_springframework_security_spring_security_core_6_3_9//file:v1/org/springframework/security/spring-security-core/6.3.9/spring-security-core-6.3.9.jar" "@@rules_jvm_external~~maven~com_nimbusds_oauth2_oidc_sdk_9_43_6//file:v1/com/nimbusds/oauth2-oidc-sdk/9.43.6/oauth2-oidc-sdk-9.43.6.jar" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator_3_3_11_extension" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator_3_3_11_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator_3_3_11_extension" -> "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_actuator_3_3_11//file:file" "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_actuator_3_3_11//file:file" "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_actuator_3_3_11//file:file" -> "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_actuator_3_3_11//file:v1/org/springframework/boot/spring-boot-starter-actuator/3.3.11/spring-boot-starter-actuator-3.3.11.jar" "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_actuator_3_3_11//file:v1/org/springframework/boot/spring-boot-starter-actuator/3.3.11/spring-boot-starter-actuator-3.3.11.jar" "@unmanaged_deps_filter//:org_reactivestreams_reactive_streams_1_0_4_extension" "@unmanaged_deps_filter//:org_reactivestreams_reactive_streams_1_0_4_extension" -> "@@rules_jvm_external~~maven~org_reactivestreams_reactive_streams_1_0_4//file:file" "@unmanaged_deps_filter//:org_reactivestreams_reactive_streams_1_0_4_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@unmanaged_deps_filter//:org/springframework/boot/spring-boot-starter-jdbc/3.3.11/spring-boot-starter-jdbc-3.3.11.jar" "@unmanaged_deps_filter//:org/springframework/boot/spring-boot-starter-jdbc/3.3.11/spring-boot-starter-jdbc-3.3.11.jar" -> "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_jdbc_3_3_11_extension" "@unmanaged_deps_filter//:io_smallrye_jandex" "@unmanaged_deps_filter//:io_smallrye_jandex" -> "@unmanaged_deps_filter//:io/smallrye/jandex/3.1.2/jandex-3.1.2.jar" "@unmanaged_deps_filter//:io_smallrye_jandex" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:io_smallrye_jandex" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:io/smallrye/jandex/3.1.2/jandex-3.1.2.jar" "@unmanaged_deps_filter//:io/smallrye/jandex/3.1.2/jandex-3.1.2.jar" -> "@unmanaged_deps_filter//:io_smallrye_jandex_3_1_2_extension" "@unmanaged_deps_filter//:io_smallrye_jandex_3_1_2_extension" "@unmanaged_deps_filter//:io_smallrye_jandex_3_1_2_extension" -> "@@rules_jvm_external~~maven~io_smallrye_jandex_3_1_2//file:file" "@unmanaged_deps_filter//:io_smallrye_jandex_3_1_2_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~io_smallrye_jandex_3_1_2//file:file" "@@rules_jvm_external~~maven~io_smallrye_jandex_3_1_2//file:file" -> "@@rules_jvm_external~~maven~io_smallrye_jandex_3_1_2//file:v1/io/smallrye/jandex/3.1.2/jandex-3.1.2.jar" "@@rules_jvm_external~~maven~io_smallrye_jandex_3_1_2//file:v1/io/smallrye/jandex/3.1.2/jandex-3.1.2.jar" "@@rules_jvm_external~~maven~org_springframework_security_spring_security_oauth2_jose_6_3_9//file:file" "@@rules_jvm_external~~maven~org_springframework_security_spring_security_oauth2_jose_6_3_9//file:file" -> "@@rules_jvm_external~~maven~org_springframework_security_spring_security_oauth2_jose_6_3_9//file:v1/org/springframework/security/spring-security-oauth2-jose/6.3.9/spring-security-oauth2-jose-6.3.9.jar" "@@rules_jvm_external~~maven~org_springframework_security_spring_security_oauth2_jose_6_3_9//file:v1/org/springframework/security/spring-security-oauth2-jose/6.3.9/spring-security-oauth2-jose-6.3.9.jar" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_jdbc_3_3_11_extension" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_jdbc_3_3_11_extension" -> "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_jdbc_3_3_11//file:file" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_jdbc_3_3_11_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_jdbc_3_3_11//file:file" "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_jdbc_3_3_11//file:file" -> "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_jdbc_3_3_11//file:v1/org/springframework/boot/spring-boot-starter-jdbc/3.3.11/spring-boot-starter-jdbc-3.3.11.jar" "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_jdbc_3_3_11//file:v1/org/springframework/boot/spring-boot-starter-jdbc/3.3.11/spring-boot-starter-jdbc-3.3.11.jar" "@unmanaged_deps_filter//:io_micrometer_micrometer_core" "@unmanaged_deps_filter//:io_micrometer_micrometer_core" -> "@unmanaged_deps_filter//:io/micrometer/micrometer-core/1.13.13/micrometer-core-1.13.13.jar" "@unmanaged_deps_filter//:io_micrometer_micrometer_core" -> "@unmanaged_deps_filter//:io_micrometer_micrometer_commons" "@unmanaged_deps_filter//:io_micrometer_micrometer_core" -> "@unmanaged_deps_filter//:io_micrometer_micrometer_observation" "@unmanaged_deps_filter//:io_micrometer_micrometer_core" -> "@unmanaged_deps_filter//:org_hdrhistogram_HdrHistogram" "@unmanaged_deps_filter//:io_micrometer_micrometer_core" -> "@unmanaged_deps_filter//:org_latencyutils_LatencyUtils" "@unmanaged_deps_filter//:io_micrometer_micrometer_core" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:io_micrometer_micrometer_core" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:org_latencyutils_LatencyUtils" "@unmanaged_deps_filter//:org_latencyutils_LatencyUtils" -> "@unmanaged_deps_filter//:org/latencyutils/LatencyUtils/2.0.3/LatencyUtils-2.0.3.jar" "@unmanaged_deps_filter//:org_latencyutils_LatencyUtils" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:org_latencyutils_LatencyUtils" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:org/latencyutils/LatencyUtils/2.0.3/LatencyUtils-2.0.3.jar" "@unmanaged_deps_filter//:org/latencyutils/LatencyUtils/2.0.3/LatencyUtils-2.0.3.jar" -> "@unmanaged_deps_filter//:org_latencyutils_LatencyUtils_2_0_3_extension" "@unmanaged_deps_filter//:org_latencyutils_LatencyUtils_2_0_3_extension" "@unmanaged_deps_filter//:org_latencyutils_LatencyUtils_2_0_3_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@unmanaged_deps_filter//:org_latencyutils_LatencyUtils_2_0_3_extension" -> "@@rules_jvm_external~~maven~org_latencyutils_LatencyUtils_2_0_3//file:file" "@@rules_jvm_external~~maven~org_latencyutils_LatencyUtils_2_0_3//file:file" "@@rules_jvm_external~~maven~org_latencyutils_LatencyUtils_2_0_3//file:file" -> "@@rules_jvm_external~~maven~org_latencyutils_LatencyUtils_2_0_3//file:v1/org/latencyutils/LatencyUtils/2.0.3/LatencyUtils-2.0.3.jar" "@@rules_jvm_external~~maven~org_latencyutils_LatencyUtils_2_0_3//file:v1/org/latencyutils/LatencyUtils/2.0.3/LatencyUtils-2.0.3.jar" "@unmanaged_deps_filter//:org_hdrhistogram_HdrHistogram" "@unmanaged_deps_filter//:org_hdrhistogram_HdrHistogram" -> "@unmanaged_deps_filter//:org/hdrhistogram/HdrHistogram/2.2.2/HdrHistogram-2.2.2.jar" "@unmanaged_deps_filter//:org_hdrhistogram_HdrHistogram" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:org_hdrhistogram_HdrHistogram" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:org/hdrhistogram/HdrHistogram/2.2.2/HdrHistogram-2.2.2.jar" "@unmanaged_deps_filter//:org/hdrhistogram/HdrHistogram/2.2.2/HdrHistogram-2.2.2.jar" -> "@unmanaged_deps_filter//:org_hdrhistogram_HdrHistogram_2_2_2_extension" "@unmanaged_deps_filter//:org_hdrhistogram_HdrHistogram_2_2_2_extension" "@unmanaged_deps_filter//:org_hdrhistogram_HdrHistogram_2_2_2_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@unmanaged_deps_filter//:org_hdrhistogram_HdrHistogram_2_2_2_extension" -> "@@rules_jvm_external~~maven~org_hdrhistogram_HdrHistogram_2_2_2//file:file" "@@rules_jvm_external~~maven~org_hdrhistogram_HdrHistogram_2_2_2//file:file" "@@rules_jvm_external~~maven~org_hdrhistogram_HdrHistogram_2_2_2//file:file" -> "@@rules_jvm_external~~maven~org_hdrhistogram_HdrHistogram_2_2_2//file:v1/org/hdrhistogram/HdrHistogram/2.2.2/HdrHistogram-2.2.2.jar" "@@rules_jvm_external~~maven~org_hdrhistogram_HdrHistogram_2_2_2//file:v1/org/hdrhistogram/HdrHistogram/2.2.2/HdrHistogram-2.2.2.jar" "@unmanaged_deps_filter//:io/micrometer/micrometer-core/1.13.13/micrometer-core-1.13.13.jar" "@unmanaged_deps_filter//:io/micrometer/micrometer-core/1.13.13/micrometer-core-1.13.13.jar" -> "@unmanaged_deps_filter//:io_micrometer_micrometer_core_1_13_13_extension" "@unmanaged_deps_filter//:io_micrometer_micrometer_core_1_13_13_extension" "@unmanaged_deps_filter//:io_micrometer_micrometer_core_1_13_13_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@unmanaged_deps_filter//:io_micrometer_micrometer_core_1_13_13_extension" -> "@@rules_jvm_external~~maven~io_micrometer_micrometer_core_1_13_13//file:file" "@@rules_jvm_external~~maven~io_netty_netty_resolver_dns_4_1_119_Final//file:file" "@@rules_jvm_external~~maven~io_netty_netty_resolver_dns_4_1_119_Final//file:file" -> "@@rules_jvm_external~~maven~io_netty_netty_resolver_dns_4_1_119_Final//file:v1/io/netty/netty-resolver-dns/4.1.119.Final/netty-resolver-dns-4.1.119.Final.jar" "@@rules_jvm_external~~maven~io_netty_netty_resolver_dns_4_1_119_Final//file:v1/io/netty/netty-resolver-dns/4.1.119.Final/netty-resolver-dns-4.1.119.Final.jar" "@unmanaged_deps_filter//:com_sun_istack_istack_commons_runtime" "@unmanaged_deps_filter//:com_sun_istack_istack_commons_runtime" -> "@unmanaged_deps_filter//:com/sun/istack/istack-commons-runtime/4.1.1/istack-commons-runtime-4.1.1.jar" "@unmanaged_deps_filter//:com_sun_istack_istack_commons_runtime" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:com_sun_istack_istack_commons_runtime" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:com/sun/istack/istack-commons-runtime/4.1.1/istack-commons-runtime-4.1.1.jar" "@unmanaged_deps_filter//:com/sun/istack/istack-commons-runtime/4.1.1/istack-commons-runtime-4.1.1.jar" -> "@unmanaged_deps_filter//:com_sun_istack_istack_commons_runtime_4_1_1_extension" "@unmanaged_deps_filter//:com_sun_istack_istack_commons_runtime_4_1_1_extension" "@unmanaged_deps_filter//:com_sun_istack_istack_commons_runtime_4_1_1_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@unmanaged_deps_filter//:com_sun_istack_istack_commons_runtime_4_1_1_extension" -> "@@rules_jvm_external~~maven~com_sun_istack_istack_commons_runtime_4_1_1//file:file" "@@rules_jvm_external~~maven~com_sun_istack_istack_commons_runtime_4_1_1//file:file" "@@rules_jvm_external~~maven~com_sun_istack_istack_commons_runtime_4_1_1//file:file" -> "@@rules_jvm_external~~maven~com_sun_istack_istack_commons_runtime_4_1_1//file:v1/com/sun/istack/istack-commons-runtime/4.1.1/istack-commons-runtime-4.1.1.jar" "@@rules_jvm_external~~maven~com_sun_istack_istack_commons_runtime_4_1_1//file:v1/com/sun/istack/istack-commons-runtime/4.1.1/istack-commons-runtime-4.1.1.jar" "@@rules_jvm_external~~maven~org_springframework_data_spring_data_jpa_3_3_11//file:v1/org/springframework/data/spring-data-jpa/3.3.11/spring-data-jpa-3.3.11.jar" "@@rules_jvm_external~~maven~org_reactivestreams_reactive_streams_1_0_4//file:file" "@@rules_jvm_external~~maven~org_reactivestreams_reactive_streams_1_0_4//file:file" -> "@@rules_jvm_external~~maven~org_reactivestreams_reactive_streams_1_0_4//file:v1/org/reactivestreams/reactive-streams/1.0.4/reactive-streams-1.0.4.jar" "@@rules_jvm_external~~maven~org_reactivestreams_reactive_streams_1_0_4//file:v1/org/reactivestreams/reactive-streams/1.0.4/reactive-streams-1.0.4.jar" "@unmanaged_deps_filter//:com/fasterxml/jackson/core/jackson-databind/2.17.3/jackson-databind-2.17.3.jar" "@unmanaged_deps_filter//:com/fasterxml/jackson/core/jackson-databind/2.17.3/jackson-databind-2.17.3.jar" -> "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind_2_17_3_extension" "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind_2_17_3_extension" "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind_2_17_3_extension" -> "@@rules_jvm_external~~maven~com_fasterxml_jackson_core_jackson_databind_2_17_3//file:file" "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind_2_17_3_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~com_fasterxml_jackson_core_jackson_databind_2_17_3//file:file" "@@rules_jvm_external~~maven~com_fasterxml_jackson_core_jackson_databind_2_17_3//file:file" -> "@@rules_jvm_external~~maven~com_fasterxml_jackson_core_jackson_databind_2_17_3//file:v1/com/fasterxml/jackson/core/jackson-databind/2.17.3/jackson-databind-2.17.3.jar" "@@rules_jvm_external~~maven~com_fasterxml_jackson_core_jackson_databind_2_17_3//file:v1/com/fasterxml/jackson/core/jackson-databind/2.17.3/jackson-databind-2.17.3.jar" "@unmanaged_deps_filter//:io_netty_netty_handler_proxy" "@unmanaged_deps_filter//:io_netty_netty_handler_proxy" -> "@unmanaged_deps_filter//:io/netty/netty-handler-proxy/4.1.119.Final/netty-handler-proxy-4.1.119.Final.jar" "@unmanaged_deps_filter//:io_netty_netty_handler_proxy" -> "@unmanaged_deps_filter//:io_netty_netty_buffer" "@unmanaged_deps_filter//:io_netty_netty_handler_proxy" -> "@unmanaged_deps_filter//:io_netty_netty_codec" "@unmanaged_deps_filter//:io_netty_netty_handler_proxy" -> "@unmanaged_deps_filter//:io_netty_netty_codec_http" "@unmanaged_deps_filter//:io_netty_netty_handler_proxy" -> "@unmanaged_deps_filter//:io_netty_netty_codec_socks" "@unmanaged_deps_filter//:io_netty_netty_handler_proxy" -> "@unmanaged_deps_filter//:io_netty_netty_common" "@unmanaged_deps_filter//:io_netty_netty_handler_proxy" -> "@unmanaged_deps_filter//:io_netty_netty_transport" "@unmanaged_deps_filter//:io_netty_netty_handler_proxy" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:io_netty_netty_handler_proxy" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:io_netty_netty_codec_socks" "@unmanaged_deps_filter//:io_netty_netty_codec_socks" -> "@unmanaged_deps_filter//:io/netty/netty-codec-socks/4.1.119.Final/netty-codec-socks-4.1.119.Final.jar" "@unmanaged_deps_filter//:io_netty_netty_codec_socks" -> "@unmanaged_deps_filter//:io_netty_netty_buffer" "@unmanaged_deps_filter//:io_netty_netty_codec_socks" -> "@unmanaged_deps_filter//:io_netty_netty_codec" "@unmanaged_deps_filter//:io_netty_netty_codec_socks" -> "@unmanaged_deps_filter//:io_netty_netty_common" "@unmanaged_deps_filter//:io_netty_netty_codec_socks" -> "@unmanaged_deps_filter//:io_netty_netty_transport" "@unmanaged_deps_filter//:io_netty_netty_codec_socks" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:io_netty_netty_codec_socks" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:io/netty/netty-codec-socks/4.1.119.Final/netty-codec-socks-4.1.119.Final.jar" "@unmanaged_deps_filter//:io/netty/netty-codec-socks/4.1.119.Final/netty-codec-socks-4.1.119.Final.jar" -> "@unmanaged_deps_filter//:io_netty_netty_codec_socks_4_1_119_Final_extension" "@unmanaged_deps_filter//:io_netty_netty_codec_socks_4_1_119_Final_extension" "@unmanaged_deps_filter//:io_netty_netty_codec_socks_4_1_119_Final_extension" -> "@@rules_jvm_external~~maven~io_netty_netty_codec_socks_4_1_119_Final//file:file" "@unmanaged_deps_filter//:io_netty_netty_codec_socks_4_1_119_Final_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~io_netty_netty_codec_socks_4_1_119_Final//file:file" "@@rules_jvm_external~~maven~io_netty_netty_codec_socks_4_1_119_Final//file:file" -> "@@rules_jvm_external~~maven~io_netty_netty_codec_socks_4_1_119_Final//file:v1/io/netty/netty-codec-socks/4.1.119.Final/netty-codec-socks-4.1.119.Final.jar" "@@rules_jvm_external~~maven~io_netty_netty_codec_socks_4_1_119_Final//file:v1/io/netty/netty-codec-socks/4.1.119.Final/netty-codec-socks-4.1.119.Final.jar" "@unmanaged_deps_filter//:io_netty_netty_codec_http" "@unmanaged_deps_filter//:io_netty_netty_codec_http" -> "@unmanaged_deps_filter//:io/netty/netty-codec-http/4.1.119.Final/netty-codec-http-4.1.119.Final.jar" "@unmanaged_deps_filter//:io_netty_netty_codec_http" -> "@unmanaged_deps_filter//:io_netty_netty_buffer" "@unmanaged_deps_filter//:io_netty_netty_codec_http" -> "@unmanaged_deps_filter//:io_netty_netty_codec" "@unmanaged_deps_filter//:io_netty_netty_codec_http" -> "@unmanaged_deps_filter//:io_netty_netty_common" "@unmanaged_deps_filter//:io_netty_netty_codec_http" -> "@unmanaged_deps_filter//:io_netty_netty_handler" "@unmanaged_deps_filter//:io_netty_netty_codec_http" -> "@unmanaged_deps_filter//:io_netty_netty_transport" "@unmanaged_deps_filter//:io_netty_netty_codec_http" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:io_netty_netty_codec_http" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:io_netty_netty_handler" "@unmanaged_deps_filter//:io_netty_netty_handler" -> "@unmanaged_deps_filter//:io/netty/netty-handler/4.1.119.Final/netty-handler-4.1.119.Final.jar" "@unmanaged_deps_filter//:io_netty_netty_handler" -> "@unmanaged_deps_filter//:io_netty_netty_buffer" "@unmanaged_deps_filter//:io_netty_netty_handler" -> "@unmanaged_deps_filter//:io_netty_netty_codec" "@unmanaged_deps_filter//:io_netty_netty_handler" -> "@unmanaged_deps_filter//:io_netty_netty_common" "@unmanaged_deps_filter//:io_netty_netty_handler" -> "@unmanaged_deps_filter//:io_netty_netty_resolver" "@unmanaged_deps_filter//:io_netty_netty_handler" -> "@unmanaged_deps_filter//:io_netty_netty_transport" "@unmanaged_deps_filter//:io_netty_netty_handler" -> "@unmanaged_deps_filter//:io_netty_netty_transport_native_unix_common" "@unmanaged_deps_filter//:io_netty_netty_handler" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:io_netty_netty_handler" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:io_netty_netty_transport_native_unix_common" "@unmanaged_deps_filter//:io_netty_netty_transport_native_unix_common" -> "@unmanaged_deps_filter//:io/netty/netty-transport-native-unix-common/4.1.119.Final/netty-transport-native-unix-common-4.1.119.Final.jar" "@unmanaged_deps_filter//:io_netty_netty_transport_native_unix_common" -> "@unmanaged_deps_filter//:io_netty_netty_buffer" "@unmanaged_deps_filter//:io_netty_netty_transport_native_unix_common" -> "@unmanaged_deps_filter//:io_netty_netty_common" "@unmanaged_deps_filter//:io_netty_netty_transport_native_unix_common" -> "@unmanaged_deps_filter//:io_netty_netty_transport" "@unmanaged_deps_filter//:io_netty_netty_transport_native_unix_common" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:io_netty_netty_transport_native_unix_common" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:io/netty/netty-transport-native-unix-common/4.1.119.Final/netty-transport-native-unix-common-4.1.119.Final.jar" "@unmanaged_deps_filter//:io/netty/netty-transport-native-unix-common/4.1.119.Final/netty-transport-native-unix-common-4.1.119.Final.jar" -> "@unmanaged_deps_filter//:io_netty_netty_transport_native_unix_common_4_1_119_Final_extension" "@unmanaged_deps_filter//:io_netty_netty_transport_native_unix_common_4_1_119_Final_extension" "@unmanaged_deps_filter//:io_netty_netty_transport_native_unix_common_4_1_119_Final_extension" -> "@@rules_jvm_external~~maven~io_netty_netty_transport_native_unix_common_4_1_119_Final//file:file" "@unmanaged_deps_filter//:io_netty_netty_transport_native_unix_common_4_1_119_Final_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~io_netty_netty_transport_native_unix_common_4_1_119_Final//file:file" "@@rules_jvm_external~~maven~io_netty_netty_transport_native_unix_common_4_1_119_Final//file:file" -> "@@rules_jvm_external~~maven~io_netty_netty_transport_native_unix_common_4_1_119_Final//file:v1/io/netty/netty-transport-native-unix-common/4.1.119.Final/netty-transport-native-unix-common-4.1.119.Final.jar" "@@rules_jvm_external~~maven~io_netty_netty_transport_native_unix_common_4_1_119_Final//file:v1/io/netty/netty-transport-native-unix-common/4.1.119.Final/netty-transport-native-unix-common-4.1.119.Final.jar" "@unmanaged_deps_filter//:io/netty/netty-handler/4.1.119.Final/netty-handler-4.1.119.Final.jar" "@unmanaged_deps_filter//:io/netty/netty-handler/4.1.119.Final/netty-handler-4.1.119.Final.jar" -> "@unmanaged_deps_filter//:io_netty_netty_handler_4_1_119_Final_extension" "@unmanaged_deps_filter//:io_netty_netty_handler_4_1_119_Final_extension" "@unmanaged_deps_filter//:io_netty_netty_handler_4_1_119_Final_extension" -> "@@rules_jvm_external~~maven~io_netty_netty_handler_4_1_119_Final//file:file" "@unmanaged_deps_filter//:io_netty_netty_handler_4_1_119_Final_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@unmanaged_deps_filter//:io/netty/netty-codec-http/4.1.119.Final/netty-codec-http-4.1.119.Final.jar" "@unmanaged_deps_filter//:io/netty/netty-codec-http/4.1.119.Final/netty-codec-http-4.1.119.Final.jar" -> "@unmanaged_deps_filter//:io_netty_netty_codec_http_4_1_119_Final_extension" "@unmanaged_deps_filter//:io_netty_netty_codec" "@unmanaged_deps_filter//:io_netty_netty_codec" -> "@unmanaged_deps_filter//:io/netty/netty-codec/4.1.119.Final/netty-codec-4.1.119.Final.jar" "@unmanaged_deps_filter//:io_netty_netty_codec" -> "@unmanaged_deps_filter//:io_netty_netty_buffer" "@unmanaged_deps_filter//:io_netty_netty_codec" -> "@unmanaged_deps_filter//:io_netty_netty_common" "@unmanaged_deps_filter//:io_netty_netty_codec" -> "@unmanaged_deps_filter//:io_netty_netty_transport" "@unmanaged_deps_filter//:io_netty_netty_codec" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:io_netty_netty_codec" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:io_netty_netty_transport" "@unmanaged_deps_filter//:io_netty_netty_transport" -> "@unmanaged_deps_filter//:io/netty/netty-transport/4.1.119.Final/netty-transport-4.1.119.Final.jar" "@unmanaged_deps_filter//:io_netty_netty_transport" -> "@unmanaged_deps_filter//:io_netty_netty_buffer" "@unmanaged_deps_filter//:io_netty_netty_transport" -> "@unmanaged_deps_filter//:io_netty_netty_common" "@unmanaged_deps_filter//:io_netty_netty_transport" -> "@unmanaged_deps_filter//:io_netty_netty_resolver" "@unmanaged_deps_filter//:io_netty_netty_transport" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:io_netty_netty_transport" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:io_netty_netty_resolver" "@unmanaged_deps_filter//:io_netty_netty_resolver" -> "@unmanaged_deps_filter//:io/netty/netty-resolver/4.1.119.Final/netty-resolver-4.1.119.Final.jar" "@unmanaged_deps_filter//:io_netty_netty_resolver" -> "@unmanaged_deps_filter//:io_netty_netty_common" "@unmanaged_deps_filter//:io_netty_netty_resolver" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:io_netty_netty_resolver" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:io/netty/netty-resolver/4.1.119.Final/netty-resolver-4.1.119.Final.jar" "@unmanaged_deps_filter//:io/netty/netty-resolver/4.1.119.Final/netty-resolver-4.1.119.Final.jar" -> "@unmanaged_deps_filter//:io_netty_netty_resolver_4_1_119_Final_extension" "@unmanaged_deps_filter//:io_netty_netty_resolver_4_1_119_Final_extension" "@unmanaged_deps_filter//:io_netty_netty_resolver_4_1_119_Final_extension" -> "@@rules_jvm_external~~maven~io_netty_netty_resolver_4_1_119_Final//file:file" "@unmanaged_deps_filter//:io_netty_netty_resolver_4_1_119_Final_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~io_netty_netty_resolver_4_1_119_Final//file:file" "@@rules_jvm_external~~maven~io_netty_netty_resolver_4_1_119_Final//file:file" -> "@@rules_jvm_external~~maven~io_netty_netty_resolver_4_1_119_Final//file:v1/io/netty/netty-resolver/4.1.119.Final/netty-resolver-4.1.119.Final.jar" "@@rules_jvm_external~~maven~io_netty_netty_resolver_4_1_119_Final//file:v1/io/netty/netty-resolver/4.1.119.Final/netty-resolver-4.1.119.Final.jar" "@unmanaged_deps_filter//:io/netty/netty-transport/4.1.119.Final/netty-transport-4.1.119.Final.jar" "@unmanaged_deps_filter//:io/netty/netty-transport/4.1.119.Final/netty-transport-4.1.119.Final.jar" -> "@unmanaged_deps_filter//:io_netty_netty_transport_4_1_119_Final_extension" "@unmanaged_deps_filter//:io_netty_netty_transport_4_1_119_Final_extension" "@unmanaged_deps_filter//:io_netty_netty_transport_4_1_119_Final_extension" -> "@@rules_jvm_external~~maven~io_netty_netty_transport_4_1_119_Final//file:file" "@unmanaged_deps_filter//:io_netty_netty_transport_4_1_119_Final_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~io_netty_netty_transport_4_1_119_Final//file:file" "@@rules_jvm_external~~maven~io_netty_netty_transport_4_1_119_Final//file:file" -> "@@rules_jvm_external~~maven~io_netty_netty_transport_4_1_119_Final//file:v1/io/netty/netty-transport/4.1.119.Final/netty-transport-4.1.119.Final.jar" "@@rules_jvm_external~~maven~io_netty_netty_transport_4_1_119_Final//file:v1/io/netty/netty-transport/4.1.119.Final/netty-transport-4.1.119.Final.jar" "@unmanaged_deps_filter//:io/netty/netty-codec/4.1.119.Final/netty-codec-4.1.119.Final.jar" "@unmanaged_deps_filter//:io/netty/netty-codec/4.1.119.Final/netty-codec-4.1.119.Final.jar" -> "@unmanaged_deps_filter//:io_netty_netty_codec_4_1_119_Final_extension" "@unmanaged_deps_filter//:io_netty_netty_codec_4_1_119_Final_extension" "@unmanaged_deps_filter//:io_netty_netty_codec_4_1_119_Final_extension" -> "@@rules_jvm_external~~maven~io_netty_netty_codec_4_1_119_Final//file:file" "@unmanaged_deps_filter//:io_netty_netty_codec_4_1_119_Final_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~io_netty_netty_codec_4_1_119_Final//file:file" "@@rules_jvm_external~~maven~io_netty_netty_codec_4_1_119_Final//file:file" -> "@@rules_jvm_external~~maven~io_netty_netty_codec_4_1_119_Final//file:v1/io/netty/netty-codec/4.1.119.Final/netty-codec-4.1.119.Final.jar" "@@rules_jvm_external~~maven~io_netty_netty_codec_4_1_119_Final//file:v1/io/netty/netty-codec/4.1.119.Final/netty-codec-4.1.119.Final.jar" "@unmanaged_deps_filter//:io_netty_netty_buffer" "@unmanaged_deps_filter//:io_netty_netty_buffer" -> "@unmanaged_deps_filter//:io/netty/netty-buffer/4.1.119.Final/netty-buffer-4.1.119.Final.jar" "@unmanaged_deps_filter//:io_netty_netty_buffer" -> "@unmanaged_deps_filter//:io_netty_netty_common" "@unmanaged_deps_filter//:io_netty_netty_buffer" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:io_netty_netty_buffer" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:io_netty_netty_common" "@unmanaged_deps_filter//:io_netty_netty_common" -> "@unmanaged_deps_filter//:io/netty/netty-common/4.1.119.Final/netty-common-4.1.119.Final.jar" "@unmanaged_deps_filter//:io_netty_netty_common" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:io_netty_netty_common" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:io/netty/netty-common/4.1.119.Final/netty-common-4.1.119.Final.jar" "@unmanaged_deps_filter//:io/netty/netty-common/4.1.119.Final/netty-common-4.1.119.Final.jar" -> "@unmanaged_deps_filter//:io_netty_netty_common_4_1_119_Final_extension" "@unmanaged_deps_filter//:io_netty_netty_common_4_1_119_Final_extension" "@unmanaged_deps_filter//:io_netty_netty_common_4_1_119_Final_extension" -> "@@rules_jvm_external~~maven~io_netty_netty_common_4_1_119_Final//file:file" "@unmanaged_deps_filter//:io_netty_netty_common_4_1_119_Final_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~io_netty_netty_common_4_1_119_Final//file:file" "@@rules_jvm_external~~maven~io_netty_netty_common_4_1_119_Final//file:file" -> "@@rules_jvm_external~~maven~io_netty_netty_common_4_1_119_Final//file:v1/io/netty/netty-common/4.1.119.Final/netty-common-4.1.119.Final.jar" "@@rules_jvm_external~~maven~io_netty_netty_common_4_1_119_Final//file:v1/io/netty/netty-common/4.1.119.Final/netty-common-4.1.119.Final.jar" "@unmanaged_deps_filter//:io/netty/netty-buffer/4.1.119.Final/netty-buffer-4.1.119.Final.jar" "@unmanaged_deps_filter//:io/netty/netty-buffer/4.1.119.Final/netty-buffer-4.1.119.Final.jar" -> "@unmanaged_deps_filter//:io_netty_netty_buffer_4_1_119_Final_extension" "@unmanaged_deps_filter//:io_netty_netty_buffer_4_1_119_Final_extension" "@unmanaged_deps_filter//:io_netty_netty_buffer_4_1_119_Final_extension" -> "@@rules_jvm_external~~maven~io_netty_netty_buffer_4_1_119_Final//file:file" "@unmanaged_deps_filter//:io_netty_netty_buffer_4_1_119_Final_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~io_netty_netty_buffer_4_1_119_Final//file:file" "@@rules_jvm_external~~maven~io_netty_netty_buffer_4_1_119_Final//file:file" -> "@@rules_jvm_external~~maven~io_netty_netty_buffer_4_1_119_Final//file:v1/io/netty/netty-buffer/4.1.119.Final/netty-buffer-4.1.119.Final.jar" "@@rules_jvm_external~~maven~io_netty_netty_buffer_4_1_119_Final//file:v1/io/netty/netty-buffer/4.1.119.Final/netty-buffer-4.1.119.Final.jar" "@unmanaged_deps_filter//:io/netty/netty-handler-proxy/4.1.119.Final/netty-handler-proxy-4.1.119.Final.jar" "@unmanaged_deps_filter//:io/netty/netty-handler-proxy/4.1.119.Final/netty-handler-proxy-4.1.119.Final.jar" -> "@unmanaged_deps_filter//:io_netty_netty_handler_proxy_4_1_119_Final_extension" "@unmanaged_deps_filter//:io_netty_netty_handler_proxy_4_1_119_Final_extension" "@unmanaged_deps_filter//:io_netty_netty_handler_proxy_4_1_119_Final_extension" -> "@@rules_jvm_external~~maven~io_netty_netty_handler_proxy_4_1_119_Final//file:file" "@unmanaged_deps_filter//:io_netty_netty_handler_proxy_4_1_119_Final_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~io_netty_netty_handler_proxy_4_1_119_Final//file:file" "@@rules_jvm_external~~maven~io_netty_netty_handler_proxy_4_1_119_Final//file:file" -> "@@rules_jvm_external~~maven~io_netty_netty_handler_proxy_4_1_119_Final//file:v1/io/netty/netty-handler-proxy/4.1.119.Final/netty-handler-proxy-4.1.119.Final.jar" "@@rules_jvm_external~~maven~io_netty_netty_handler_proxy_4_1_119_Final//file:v1/io/netty/netty-handler-proxy/4.1.119.Final/netty-handler-proxy-4.1.119.Final.jar" "@unmanaged_deps_filter//:com_nimbusds_content_type" "@unmanaged_deps_filter//:com_nimbusds_content_type" -> "@unmanaged_deps_filter//:com/nimbusds/content-type/2.2/content-type-2.2.jar" "@unmanaged_deps_filter//:com_nimbusds_content_type" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:com_nimbusds_content_type" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:com/nimbusds/content-type/2.2/content-type-2.2.jar" "@unmanaged_deps_filter//:com/nimbusds/content-type/2.2/content-type-2.2.jar" -> "@unmanaged_deps_filter//:com_nimbusds_content_type_2_2_extension" "@unmanaged_deps_filter//:com_nimbusds_content_type_2_2_extension" "@unmanaged_deps_filter//:com_nimbusds_content_type_2_2_extension" -> "@@rules_jvm_external~~maven~com_nimbusds_content_type_2_2//file:file" "@unmanaged_deps_filter//:com_nimbusds_content_type_2_2_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~com_nimbusds_content_type_2_2//file:file" "@@rules_jvm_external~~maven~com_nimbusds_content_type_2_2//file:file" -> "@@rules_jvm_external~~maven~com_nimbusds_content_type_2_2//file:v1/com/nimbusds/content-type/2.2/content-type-2.2.jar" "@@rules_jvm_external~~maven~com_nimbusds_content_type_2_2//file:v1/com/nimbusds/content-type/2.2/content-type-2.2.jar" "@unmanaged_deps_filter//:org_glassfish_jaxb_jaxb_runtime_4_0_2_extension" "@unmanaged_deps_filter//:org_glassfish_jaxb_jaxb_runtime_4_0_2_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@unmanaged_deps_filter//:org_glassfish_jaxb_jaxb_runtime_4_0_2_extension" -> "@@rules_jvm_external~~maven~org_glassfish_jaxb_jaxb_runtime_4_0_2//file:file" "@@rules_jvm_external~~maven~org_glassfish_jaxb_jaxb_runtime_4_0_2//file:file" "@@rules_jvm_external~~maven~org_glassfish_jaxb_jaxb_runtime_4_0_2//file:file" -> "@@rules_jvm_external~~maven~org_glassfish_jaxb_jaxb_runtime_4_0_2//file:v1/org/glassfish/jaxb/jaxb-runtime/4.0.2/jaxb-runtime-4.0.2.jar" "@@rules_jvm_external~~maven~org_glassfish_jaxb_jaxb_runtime_4_0_2//file:v1/org/glassfish/jaxb/jaxb-runtime/4.0.2/jaxb-runtime-4.0.2.jar" "@unmanaged_deps_filter//:org/springframework/security/spring-security-crypto/6.3.9/spring-security-crypto-6.3.9.jar" "@unmanaged_deps_filter//:org/springframework/security/spring-security-crypto/6.3.9/spring-security-crypto-6.3.9.jar" -> "@unmanaged_deps_filter//:org_springframework_security_spring_security_crypto_6_3_9_extension" "@unmanaged_deps_filter//:org_springframework_security_spring_security_crypto_6_3_9_extension" "@unmanaged_deps_filter//:org_springframework_security_spring_security_crypto_6_3_9_extension" -> "@@rules_jvm_external~~maven~org_springframework_security_spring_security_crypto_6_3_9//file:file" "@unmanaged_deps_filter//:org_springframework_security_spring_security_crypto_6_3_9_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~org_springframework_security_spring_security_crypto_6_3_9//file:file" "@@rules_jvm_external~~maven~org_springframework_security_spring_security_crypto_6_3_9//file:file" -> "@@rules_jvm_external~~maven~org_springframework_security_spring_security_crypto_6_3_9//file:v1/org/springframework/security/spring-security-crypto/6.3.9/spring-security-crypto-6.3.9.jar" "@@rules_jvm_external~~maven~org_springframework_security_spring_security_crypto_6_3_9//file:v1/org/springframework/security/spring-security-crypto/6.3.9/spring-security-crypto-6.3.9.jar" "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_webflux_3_3_11//file:file" "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_webflux_3_3_11//file:file" -> "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_webflux_3_3_11//file:v1/org/springframework/boot/spring-boot-starter-webflux/3.3.11/spring-boot-starter-webflux-3.3.11.jar" "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_webflux_3_3_11//file:v1/org/springframework/boot/spring-boot-starter-webflux/3.3.11/spring-boot-starter-webflux-3.3.11.jar" "@unmanaged_deps_filter//:io_netty_netty_codec_http_4_1_119_Final_extension" "@unmanaged_deps_filter//:io_netty_netty_codec_http_4_1_119_Final_extension" -> "@@rules_jvm_external~~maven~io_netty_netty_codec_http_4_1_119_Final//file:file" "@unmanaged_deps_filter//:io_netty_netty_codec_http_4_1_119_Final_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~io_netty_netty_codec_http_4_1_119_Final//file:file" "@@rules_jvm_external~~maven~io_netty_netty_codec_http_4_1_119_Final//file:file" -> "@@rules_jvm_external~~maven~io_netty_netty_codec_http_4_1_119_Final//file:v1/io/netty/netty-codec-http/4.1.119.Final/netty-codec-http-4.1.119.Final.jar" "@@rules_jvm_external~~maven~io_netty_netty_codec_http_4_1_119_Final//file:v1/io/netty/netty-codec-http/4.1.119.Final/netty-codec-http-4.1.119.Final.jar" "@unmanaged_deps_filter//:jakarta_persistence_jakarta_persistence_api" "@unmanaged_deps_filter//:jakarta_persistence_jakarta_persistence_api" -> "@unmanaged_deps_filter//:jakarta/persistence/jakarta.persistence-api/3.1.0/jakarta.persistence-api-3.1.0.jar" "@unmanaged_deps_filter//:jakarta_persistence_jakarta_persistence_api" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:jakarta_persistence_jakarta_persistence_api" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:jakarta/persistence/jakarta.persistence-api/3.1.0/jakarta.persistence-api-3.1.0.jar" "@unmanaged_deps_filter//:jakarta/persistence/jakarta.persistence-api/3.1.0/jakarta.persistence-api-3.1.0.jar" -> "@unmanaged_deps_filter//:jakarta_persistence_jakarta_persistence_api_3_1_0_extension" "@unmanaged_deps_filter//:jakarta_persistence_jakarta_persistence_api_3_1_0_extension" "@unmanaged_deps_filter//:jakarta_persistence_jakarta_persistence_api_3_1_0_extension" -> "@@rules_jvm_external~~maven~jakarta_persistence_jakarta_persistence_api_3_1_0//file:file" "@unmanaged_deps_filter//:jakarta_persistence_jakarta_persistence_api_3_1_0_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~jakarta_persistence_jakarta_persistence_api_3_1_0//file:file" "@@rules_jvm_external~~maven~jakarta_persistence_jakarta_persistence_api_3_1_0//file:file" -> "@@rules_jvm_external~~maven~jakarta_persistence_jakarta_persistence_api_3_1_0//file:v1/jakarta/persistence/jakarta.persistence-api/3.1.0/jakarta.persistence-api-3.1.0.jar" "@@rules_jvm_external~~maven~io_netty_netty_handler_4_1_119_Final//file:file" "@@rules_jvm_external~~maven~io_netty_netty_handler_4_1_119_Final//file:file" -> "@@rules_jvm_external~~maven~io_netty_netty_handler_4_1_119_Final//file:v1/io/netty/netty-handler/4.1.119.Final/netty-handler-4.1.119.Final.jar" "@@rules_jvm_external~~maven~io_netty_netty_handler_4_1_119_Final//file:v1/io/netty/netty-handler/4.1.119.Final/netty-handler-4.1.119.Final.jar" "@@rules_jvm_external~~maven~jakarta_inject_jakarta_inject_api_2_0_1//file:file" "@@rules_jvm_external~~maven~jakarta_inject_jakarta_inject_api_2_0_1//file:file" -> "@@rules_jvm_external~~maven~jakarta_inject_jakarta_inject_api_2_0_1//file:v1/jakarta/inject/jakarta.inject-api/2.0.1/jakarta.inject-api-2.0.1.jar" "@@rules_jvm_external~~maven~jakarta_inject_jakarta_inject_api_2_0_1//file:v1/jakarta/inject/jakarta.inject-api/2.0.1/jakarta.inject-api-2.0.1.jar" "@unmanaged_deps_filter//:com_zaxxer_HikariCP_5_1_0_extension" "@unmanaged_deps_filter//:com_zaxxer_HikariCP_5_1_0_extension" -> "@@rules_jvm_external~~maven~com_zaxxer_HikariCP_5_1_0//file:file" "@unmanaged_deps_filter//:com_zaxxer_HikariCP_5_1_0_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@unmanaged_deps_filter//:com_nimbusds_lang_tag_1_7_extension" "@unmanaged_deps_filter//:com_nimbusds_lang_tag_1_7_extension" -> "@@rules_jvm_external~~maven~com_nimbusds_lang_tag_1_7//file:file" "@unmanaged_deps_filter//:com_nimbusds_lang_tag_1_7_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~com_nimbusds_lang_tag_1_7//file:file" "@@rules_jvm_external~~maven~com_nimbusds_lang_tag_1_7//file:file" -> "@@rules_jvm_external~~maven~com_nimbusds_lang_tag_1_7//file:v1/com/nimbusds/lang-tag/1.7/lang-tag-1.7.jar" "@@rules_jvm_external~~maven~com_nimbusds_lang_tag_1_7//file:v1/com/nimbusds/lang-tag/1.7/lang-tag-1.7.jar" "@@rules_jvm_external~~maven~jakarta_persistence_jakarta_persistence_api_3_1_0//file:v1/jakarta/persistence/jakarta.persistence-api/3.1.0/jakarta.persistence-api-3.1.0.jar" "@unmanaged_deps_filter//:org/ow2/asm/asm/9.7.1/asm-9.7.1.jar" "@unmanaged_deps_filter//:org/ow2/asm/asm/9.7.1/asm-9.7.1.jar" -> "@unmanaged_deps_filter//:org_ow2_asm_asm_9_7_1_extension" "@unmanaged_deps_filter//:org_ow2_asm_asm_9_7_1_extension" "@unmanaged_deps_filter//:org_ow2_asm_asm_9_7_1_extension" -> "@@rules_jvm_external~~maven~org_ow2_asm_asm_9_7_1//file:file" "@unmanaged_deps_filter//:org_ow2_asm_asm_9_7_1_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~org_ow2_asm_asm_9_7_1//file:file" "@@rules_jvm_external~~maven~org_ow2_asm_asm_9_7_1//file:file" -> "@@rules_jvm_external~~maven~org_ow2_asm_asm_9_7_1//file:v1/org/ow2/asm/asm/9.7.1/asm-9.7.1.jar" "@@rules_jvm_external~~maven~org_ow2_asm_asm_9_7_1//file:v1/org/ow2/asm/asm/9.7.1/asm-9.7.1.jar" "@unmanaged_deps_filter//:org/springframework/boot/spring-boot-starter-data-jpa/3.3.11/spring-boot-starter-data-jpa-3.3.11.jar" "@unmanaged_deps_filter//:org/springframework/boot/spring-boot-starter-data-jpa/3.3.11/spring-boot-starter-data-jpa-3.3.11.jar" -> "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa_3_3_11_extension" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa_3_3_11_extension" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa_3_3_11_extension" -> "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_data_jpa_3_3_11//file:file" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa_3_3_11_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_data_jpa_3_3_11//file:file" "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_data_jpa_3_3_11//file:file" -> "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_data_jpa_3_3_11//file:v1/org/springframework/boot/spring-boot-starter-data-jpa/3.3.11/spring-boot-starter-data-jpa-3.3.11.jar" "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_data_jpa_3_3_11//file:v1/org/springframework/boot/spring-boot-starter-data-jpa/3.3.11/spring-boot-starter-data-jpa-3.3.11.jar" "@@rules_jvm_external~~maven~io_micrometer_micrometer_jakarta9_1_13_13//file:file" "@@rules_jvm_external~~maven~io_micrometer_micrometer_jakarta9_1_13_13//file:file" -> "@@rules_jvm_external~~maven~io_micrometer_micrometer_jakarta9_1_13_13//file:v1/io/micrometer/micrometer-jakarta9/1.13.13/micrometer-jakarta9-1.13.13.jar" "@@rules_jvm_external~~maven~io_micrometer_micrometer_jakarta9_1_13_13//file:v1/io/micrometer/micrometer-jakarta9/1.13.13/micrometer-jakarta9-1.13.13.jar" "@unmanaged_deps_filter//:com_github_stephenc_jcip_jcip_annotations_1_0_1_extension" "@unmanaged_deps_filter//:com_github_stephenc_jcip_jcip_annotations_1_0_1_extension" -> "@@rules_jvm_external~~maven~com_github_stephenc_jcip_jcip_annotations_1_0_1//file:file" "@unmanaged_deps_filter//:com_github_stephenc_jcip_jcip_annotations_1_0_1_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~com_github_stephenc_jcip_jcip_annotations_1_0_1//file:file" "@@rules_jvm_external~~maven~com_github_stephenc_jcip_jcip_annotations_1_0_1//file:file" -> "@@rules_jvm_external~~maven~com_github_stephenc_jcip_jcip_annotations_1_0_1//file:v1/com/github/stephenc/jcip/jcip-annotations/1.0-1/jcip-annotations-1.0-1.jar" "@@rules_jvm_external~~maven~com_github_stephenc_jcip_jcip_annotations_1_0_1//file:v1/com/github/stephenc/jcip/jcip-annotations/1.0-1/jcip-annotations-1.0-1.jar" "@@rules_jvm_external~~maven~org_springframework_spring_tx_6_1_19//file:file" "@@rules_jvm_external~~maven~org_springframework_spring_tx_6_1_19//file:file" -> "@@rules_jvm_external~~maven~org_springframework_spring_tx_6_1_19//file:v1/org/springframework/spring-tx/6.1.19/spring-tx-6.1.19.jar" "@@rules_jvm_external~~maven~org_springframework_spring_tx_6_1_19//file:v1/org/springframework/spring-tx/6.1.19/spring-tx-6.1.19.jar" "@unmanaged_deps_filter//:io/projectreactor/reactor-core/3.6.15/reactor-core-3.6.15.jar" "@unmanaged_deps_filter//:io/projectreactor/reactor-core/3.6.15/reactor-core-3.6.15.jar" -> "@unmanaged_deps_filter//:io_projectreactor_reactor_core_3_6_15_extension" "@unmanaged_deps_filter//:io_projectreactor_reactor_core_3_6_15_extension" "@unmanaged_deps_filter//:io_projectreactor_reactor_core_3_6_15_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@unmanaged_deps_filter//:io_projectreactor_reactor_core_3_6_15_extension" -> "@@rules_jvm_external~~maven~io_projectreactor_reactor_core_3_6_15//file:file" "@@rules_jvm_external~~maven~io_projectreactor_reactor_core_3_6_15//file:file" "@@rules_jvm_external~~maven~io_projectreactor_reactor_core_3_6_15//file:file" -> "@@rules_jvm_external~~maven~io_projectreactor_reactor_core_3_6_15//file:v1/io/projectreactor/reactor-core/3.6.15/reactor-core-3.6.15.jar" "@@rules_jvm_external~~maven~io_projectreactor_reactor_core_3_6_15//file:v1/io/projectreactor/reactor-core/3.6.15/reactor-core-3.6.15.jar" "@unmanaged_deps_filter//:org/springframework/boot/spring-boot-actuator-autoconfigure/3.3.11/spring-boot-actuator-autoconfigure-3.3.11.jar" "@unmanaged_deps_filter//:org/springframework/boot/spring-boot-actuator-autoconfigure/3.3.11/spring-boot-actuator-autoconfigure-3.3.11.jar" -> "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_actuator_autoconfigure_3_3_11_extension" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_actuator_autoconfigure_3_3_11_extension" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_actuator_autoconfigure_3_3_11_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_actuator_autoconfigure_3_3_11_extension" -> "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_actuator_autoconfigure_3_3_11//file:file" "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_actuator_autoconfigure_3_3_11//file:file" "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_actuator_autoconfigure_3_3_11//file:file" -> "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_actuator_autoconfigure_3_3_11//file:v1/org/springframework/boot/spring-boot-actuator-autoconfigure/3.3.11/spring-boot-actuator-autoconfigure-3.3.11.jar" "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_actuator_autoconfigure_3_3_11//file:v1/org/springframework/boot/spring-boot-actuator-autoconfigure/3.3.11/spring-boot-actuator-autoconfigure-3.3.11.jar" "@unmanaged_deps_filter//:jakarta/servlet/jsp/jakarta.servlet.jsp-api/3.1.1/jakarta.servlet.jsp-api-3.1.1.jar" "@unmanaged_deps_filter//:jakarta/servlet/jsp/jakarta.servlet.jsp-api/3.1.1/jakarta.servlet.jsp-api-3.1.1.jar" -> "@unmanaged_deps_filter//:jakarta_servlet_jsp_jakarta_servlet_jsp_api_3_1_1_extension" "@unmanaged_deps_filter//:jakarta_servlet_jsp_jakarta_servlet_jsp_api_3_1_1_extension" "@unmanaged_deps_filter//:jakarta_servlet_jsp_jakarta_servlet_jsp_api_3_1_1_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@unmanaged_deps_filter//:jakarta_servlet_jsp_jakarta_servlet_jsp_api_3_1_1_extension" -> "@@rules_jvm_external~~maven~jakarta_servlet_jsp_jakarta_servlet_jsp_api_3_1_1//file:file" "@@rules_jvm_external~~maven~jakarta_servlet_jsp_jakarta_servlet_jsp_api_3_1_1//file:file" "@@rules_jvm_external~~maven~jakarta_servlet_jsp_jakarta_servlet_jsp_api_3_1_1//file:file" -> "@@rules_jvm_external~~maven~jakarta_servlet_jsp_jakarta_servlet_jsp_api_3_1_1//file:v1/jakarta/servlet/jsp/jakarta.servlet.jsp-api/3.1.1/jakarta.servlet.jsp-api-3.1.1.jar" "@@rules_jvm_external~~maven~jakarta_servlet_jsp_jakarta_servlet_jsp_api_3_1_1//file:v1/jakarta/servlet/jsp/jakarta.servlet.jsp-api/3.1.1/jakarta.servlet.jsp-api-3.1.1.jar" "@unmanaged_deps_filter//:com/fasterxml/classmate/1.5.1/classmate-1.5.1.jar" "@unmanaged_deps_filter//:com/fasterxml/classmate/1.5.1/classmate-1.5.1.jar" -> "@unmanaged_deps_filter//:com_fasterxml_classmate_1_5_1_extension" "@unmanaged_deps_filter//:com_fasterxml_classmate_1_5_1_extension" "@unmanaged_deps_filter//:com_fasterxml_classmate_1_5_1_extension" -> "@@rules_jvm_external~~maven~com_fasterxml_classmate_1_5_1//file:file" "@unmanaged_deps_filter//:com_fasterxml_classmate_1_5_1_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~com_fasterxml_classmate_1_5_1//file:file" "@@rules_jvm_external~~maven~com_fasterxml_classmate_1_5_1//file:file" -> "@@rules_jvm_external~~maven~com_fasterxml_classmate_1_5_1//file:v1/com/fasterxml/classmate/1.5.1/classmate-1.5.1.jar" "@@rules_jvm_external~~maven~com_fasterxml_classmate_1_5_1//file:v1/com/fasterxml/classmate/1.5.1/classmate-1.5.1.jar" "@@rules_jvm_external~~maven~io_micrometer_micrometer_core_1_13_13//file:file" "@@rules_jvm_external~~maven~io_micrometer_micrometer_core_1_13_13//file:file" -> "@@rules_jvm_external~~maven~io_micrometer_micrometer_core_1_13_13//file:v1/io/micrometer/micrometer-core/1.13.13/micrometer-core-1.13.13.jar" "@@rules_jvm_external~~maven~io_micrometer_micrometer_core_1_13_13//file:v1/io/micrometer/micrometer-core/1.13.13/micrometer-core-1.13.13.jar" "@unmanaged_deps_filter//:org/springframework/spring-orm/6.1.19/spring-orm-6.1.19.jar" "@unmanaged_deps_filter//:org/springframework/spring-orm/6.1.19/spring-orm-6.1.19.jar" -> "@unmanaged_deps_filter//:org_springframework_spring_orm_6_1_19_extension" "@unmanaged_deps_filter//:org_springframework_spring_orm_6_1_19_extension" "@unmanaged_deps_filter//:org_springframework_spring_orm_6_1_19_extension" -> "@@rules_jvm_external~~maven~org_springframework_spring_orm_6_1_19//file:file" "@unmanaged_deps_filter//:org_springframework_spring_orm_6_1_19_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~org_springframework_spring_orm_6_1_19//file:file" "@@rules_jvm_external~~maven~org_springframework_spring_orm_6_1_19//file:file" -> "@@rules_jvm_external~~maven~org_springframework_spring_orm_6_1_19//file:v1/org/springframework/spring-orm/6.1.19/spring-orm-6.1.19.jar" "@@rules_jvm_external~~maven~org_springframework_spring_orm_6_1_19//file:v1/org/springframework/spring-orm/6.1.19/spring-orm-6.1.19.jar" "//:LICENSE.txt\n@rules_license//licenses/spdx:Apache-2.0" "@unmanaged_deps_filter//:net_bytebuddy_byte_buddy" "@unmanaged_deps_filter//:net_bytebuddy_byte_buddy" -> "@unmanaged_deps_filter//:net/bytebuddy/byte-buddy/1.14.16/byte-buddy-1.14.16.jar" "@unmanaged_deps_filter//:net_bytebuddy_byte_buddy" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:net_bytebuddy_byte_buddy" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:net/bytebuddy/byte-buddy/1.14.16/byte-buddy-1.14.16.jar" "@unmanaged_deps_filter//:net/bytebuddy/byte-buddy/1.14.16/byte-buddy-1.14.16.jar" -> "@unmanaged_deps_filter//:net_bytebuddy_byte_buddy_1_14_16_extension" "@unmanaged_deps_filter//:net_bytebuddy_byte_buddy_1_14_16_extension" "@unmanaged_deps_filter//:net_bytebuddy_byte_buddy_1_14_16_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@unmanaged_deps_filter//:net_bytebuddy_byte_buddy_1_14_16_extension" -> "@@rules_jvm_external~~maven~net_bytebuddy_byte_buddy_1_14_16//file:file" "@@rules_jvm_external~~maven~net_bytebuddy_byte_buddy_1_14_16//file:file" "@@rules_jvm_external~~maven~net_bytebuddy_byte_buddy_1_14_16//file:file" -> "@@rules_jvm_external~~maven~net_bytebuddy_byte_buddy_1_14_16//file:v1/net/bytebuddy/byte-buddy/1.14.16/byte-buddy-1.14.16.jar" "@@rules_jvm_external~~maven~net_bytebuddy_byte_buddy_1_14_16//file:v1/net/bytebuddy/byte-buddy/1.14.16/byte-buddy-1.14.16.jar" "@@rules_jvm_external~~maven~com_zaxxer_HikariCP_5_1_0//file:file" "@@rules_jvm_external~~maven~com_zaxxer_HikariCP_5_1_0//file:file" -> "@@rules_jvm_external~~maven~com_zaxxer_HikariCP_5_1_0//file:v1/com/zaxxer/HikariCP/5.1.0/HikariCP-5.1.0.jar" "@@rules_jvm_external~~maven~com_zaxxer_HikariCP_5_1_0//file:v1/com/zaxxer/HikariCP/5.1.0/HikariCP-5.1.0.jar" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter" -> "@unmanaged_deps_filter//:org/springframework/boot/spring-boot-starter/3.3.11/spring-boot-starter-3.3.11.jar" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter" -> "@unmanaged_deps_filter//:jakarta_annotation_jakarta_annotation_api" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter" -> "@unmanaged_deps_filter//:org_springframework_boot_spring_boot" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter" -> "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_autoconfigure" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter" -> "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_logging" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter" -> "@unmanaged_deps_filter//:org_springframework_spring_core" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_logging" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_logging" -> "@unmanaged_deps_filter//:org/springframework/boot/spring-boot-starter-logging/3.3.11/spring-boot-starter-logging-3.3.11.jar" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_logging" -> "@unmanaged_deps_filter//:ch_qos_logback_logback_classic" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_logging" -> "@unmanaged_deps_filter//:org_apache_logging_log4j_log4j_to_slf4j" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_logging" -> "@unmanaged_deps_filter//:org_slf4j_jul_to_slf4j" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_logging" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_logging" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:org_slf4j_jul_to_slf4j" "@unmanaged_deps_filter//:org_slf4j_jul_to_slf4j" -> "@unmanaged_deps_filter//:org/slf4j/jul-to-slf4j/2.0.17/jul-to-slf4j-2.0.17.jar" "@unmanaged_deps_filter//:org_slf4j_jul_to_slf4j" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:org_slf4j_jul_to_slf4j" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:org/slf4j/jul-to-slf4j/2.0.17/jul-to-slf4j-2.0.17.jar" "@unmanaged_deps_filter//:org/slf4j/jul-to-slf4j/2.0.17/jul-to-slf4j-2.0.17.jar" -> "@unmanaged_deps_filter//:org_slf4j_jul_to_slf4j_2_0_17_extension" "@unmanaged_deps_filter//:org_slf4j_jul_to_slf4j_2_0_17_extension" "@unmanaged_deps_filter//:org_slf4j_jul_to_slf4j_2_0_17_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@unmanaged_deps_filter//:org_slf4j_jul_to_slf4j_2_0_17_extension" -> "@@rules_jvm_external~~maven~org_slf4j_jul_to_slf4j_2_0_17//file:file" "@@rules_jvm_external~~maven~org_slf4j_jul_to_slf4j_2_0_17//file:file" "@@rules_jvm_external~~maven~org_slf4j_jul_to_slf4j_2_0_17//file:file" -> "@@rules_jvm_external~~maven~org_slf4j_jul_to_slf4j_2_0_17//file:v1/org/slf4j/jul-to-slf4j/2.0.17/jul-to-slf4j-2.0.17.jar" "@@rules_jvm_external~~maven~org_slf4j_jul_to_slf4j_2_0_17//file:v1/org/slf4j/jul-to-slf4j/2.0.17/jul-to-slf4j-2.0.17.jar" "@unmanaged_deps_filter//:org_apache_logging_log4j_log4j_to_slf4j" "@unmanaged_deps_filter//:org_apache_logging_log4j_log4j_to_slf4j" -> "@unmanaged_deps_filter//:org/apache/logging/log4j/log4j-to-slf4j/2.23.1/log4j-to-slf4j-2.23.1.jar" "@unmanaged_deps_filter//:org_apache_logging_log4j_log4j_to_slf4j" -> "@unmanaged_deps_filter//:org_apache_logging_log4j_log4j_api" "@unmanaged_deps_filter//:org_apache_logging_log4j_log4j_to_slf4j" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:org_apache_logging_log4j_log4j_to_slf4j" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:org_apache_logging_log4j_log4j_api" "@unmanaged_deps_filter//:org_apache_logging_log4j_log4j_api" -> "@unmanaged_deps_filter//:org/apache/logging/log4j/log4j-api/2.23.1/log4j-api-2.23.1.jar" "@unmanaged_deps_filter//:org_apache_logging_log4j_log4j_api" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:org_apache_logging_log4j_log4j_api" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:org/apache/logging/log4j/log4j-api/2.23.1/log4j-api-2.23.1.jar" "@unmanaged_deps_filter//:org/apache/logging/log4j/log4j-api/2.23.1/log4j-api-2.23.1.jar" -> "@unmanaged_deps_filter//:org_apache_logging_log4j_log4j_api_2_23_1_extension" "@unmanaged_deps_filter//:org_apache_logging_log4j_log4j_api_2_23_1_extension" "@unmanaged_deps_filter//:org_apache_logging_log4j_log4j_api_2_23_1_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@unmanaged_deps_filter//:org_apache_logging_log4j_log4j_api_2_23_1_extension" -> "@@rules_jvm_external~~maven~org_apache_logging_log4j_log4j_api_2_23_1//file:file" "@@rules_jvm_external~~maven~org_apache_logging_log4j_log4j_api_2_23_1//file:file" "@@rules_jvm_external~~maven~org_apache_logging_log4j_log4j_api_2_23_1//file:file" -> "@@rules_jvm_external~~maven~org_apache_logging_log4j_log4j_api_2_23_1//file:v1/org/apache/logging/log4j/log4j-api/2.23.1/log4j-api-2.23.1.jar" "@@rules_jvm_external~~maven~org_apache_logging_log4j_log4j_api_2_23_1//file:v1/org/apache/logging/log4j/log4j-api/2.23.1/log4j-api-2.23.1.jar" "@unmanaged_deps_filter//:org/apache/logging/log4j/log4j-to-slf4j/2.23.1/log4j-to-slf4j-2.23.1.jar" "@unmanaged_deps_filter//:org/apache/logging/log4j/log4j-to-slf4j/2.23.1/log4j-to-slf4j-2.23.1.jar" -> "@unmanaged_deps_filter//:org_apache_logging_log4j_log4j_to_slf4j_2_23_1_extension" "@unmanaged_deps_filter//:org_apache_logging_log4j_log4j_to_slf4j_2_23_1_extension" "@unmanaged_deps_filter//:org_apache_logging_log4j_log4j_to_slf4j_2_23_1_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@unmanaged_deps_filter//:org_apache_logging_log4j_log4j_to_slf4j_2_23_1_extension" -> "@@rules_jvm_external~~maven~org_apache_logging_log4j_log4j_to_slf4j_2_23_1//file:file" "@@rules_jvm_external~~maven~org_apache_logging_log4j_log4j_to_slf4j_2_23_1//file:file" "@@rules_jvm_external~~maven~org_apache_logging_log4j_log4j_to_slf4j_2_23_1//file:file" -> "@@rules_jvm_external~~maven~org_apache_logging_log4j_log4j_to_slf4j_2_23_1//file:v1/org/apache/logging/log4j/log4j-to-slf4j/2.23.1/log4j-to-slf4j-2.23.1.jar" "@@rules_jvm_external~~maven~org_apache_logging_log4j_log4j_to_slf4j_2_23_1//file:v1/org/apache/logging/log4j/log4j-to-slf4j/2.23.1/log4j-to-slf4j-2.23.1.jar" "@unmanaged_deps_filter//:ch_qos_logback_logback_classic" "@unmanaged_deps_filter//:ch_qos_logback_logback_classic" -> "@unmanaged_deps_filter//:ch/qos/logback/logback-classic/1.5.18/logback-classic-1.5.18.jar" "@unmanaged_deps_filter//:ch_qos_logback_logback_classic" -> "@unmanaged_deps_filter//:ch_qos_logback_logback_core" "@unmanaged_deps_filter//:ch_qos_logback_logback_classic" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:ch_qos_logback_logback_classic" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:ch_qos_logback_logback_core" "@unmanaged_deps_filter//:ch_qos_logback_logback_core" -> "@unmanaged_deps_filter//:ch/qos/logback/logback-core/1.5.18/logback-core-1.5.18.jar" "@unmanaged_deps_filter//:ch_qos_logback_logback_core" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:ch_qos_logback_logback_core" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:ch/qos/logback/logback-core/1.5.18/logback-core-1.5.18.jar" "@unmanaged_deps_filter//:ch/qos/logback/logback-core/1.5.18/logback-core-1.5.18.jar" -> "@unmanaged_deps_filter//:ch_qos_logback_logback_core_1_5_18_extension" "@unmanaged_deps_filter//:ch_qos_logback_logback_core_1_5_18_extension" "@unmanaged_deps_filter//:ch_qos_logback_logback_core_1_5_18_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@unmanaged_deps_filter//:ch_qos_logback_logback_core_1_5_18_extension" -> "@@rules_jvm_external~~maven~ch_qos_logback_logback_core_1_5_18//file:file" "@@rules_jvm_external~~maven~ch_qos_logback_logback_core_1_5_18//file:file" "@@rules_jvm_external~~maven~ch_qos_logback_logback_core_1_5_18//file:file" -> "@@rules_jvm_external~~maven~ch_qos_logback_logback_core_1_5_18//file:v1/ch/qos/logback/logback-core/1.5.18/logback-core-1.5.18.jar" "@@rules_jvm_external~~maven~ch_qos_logback_logback_core_1_5_18//file:v1/ch/qos/logback/logback-core/1.5.18/logback-core-1.5.18.jar" "@unmanaged_deps_filter//:ch/qos/logback/logback-classic/1.5.18/logback-classic-1.5.18.jar" "@unmanaged_deps_filter//:ch/qos/logback/logback-classic/1.5.18/logback-classic-1.5.18.jar" -> "@unmanaged_deps_filter//:ch_qos_logback_logback_classic_1_5_18_extension" "@unmanaged_deps_filter//:ch_qos_logback_logback_classic_1_5_18_extension" "@unmanaged_deps_filter//:ch_qos_logback_logback_classic_1_5_18_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@unmanaged_deps_filter//:ch_qos_logback_logback_classic_1_5_18_extension" -> "@@rules_jvm_external~~maven~ch_qos_logback_logback_classic_1_5_18//file:file" "@@rules_jvm_external~~maven~ch_qos_logback_logback_classic_1_5_18//file:file" "@@rules_jvm_external~~maven~ch_qos_logback_logback_classic_1_5_18//file:file" -> "@@rules_jvm_external~~maven~ch_qos_logback_logback_classic_1_5_18//file:v1/ch/qos/logback/logback-classic/1.5.18/logback-classic-1.5.18.jar" "@@rules_jvm_external~~maven~ch_qos_logback_logback_classic_1_5_18//file:v1/ch/qos/logback/logback-classic/1.5.18/logback-classic-1.5.18.jar" "@unmanaged_deps_filter//:org/springframework/boot/spring-boot-starter-logging/3.3.11/spring-boot-starter-logging-3.3.11.jar" "@unmanaged_deps_filter//:org/springframework/boot/spring-boot-starter-logging/3.3.11/spring-boot-starter-logging-3.3.11.jar" -> "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_logging_3_3_11_extension" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_logging_3_3_11_extension" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_logging_3_3_11_extension" -> "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_logging_3_3_11//file:file" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_logging_3_3_11_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_logging_3_3_11//file:file" "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_logging_3_3_11//file:file" -> "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_logging_3_3_11//file:v1/org/springframework/boot/spring-boot-starter-logging/3.3.11/spring-boot-starter-logging-3.3.11.jar" "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_logging_3_3_11//file:v1/org/springframework/boot/spring-boot-starter-logging/3.3.11/spring-boot-starter-logging-3.3.11.jar" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_autoconfigure" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_autoconfigure" -> "@unmanaged_deps_filter//:org/springframework/boot/spring-boot-autoconfigure/3.3.11/spring-boot-autoconfigure-3.3.11.jar" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_autoconfigure" -> "@unmanaged_deps_filter//:org_springframework_boot_spring_boot" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_autoconfigure" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_autoconfigure" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:org/springframework/boot/spring-boot-autoconfigure/3.3.11/spring-boot-autoconfigure-3.3.11.jar" "@unmanaged_deps_filter//:org/springframework/boot/spring-boot-autoconfigure/3.3.11/spring-boot-autoconfigure-3.3.11.jar" -> "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_autoconfigure_3_3_11_extension" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_autoconfigure_3_3_11_extension" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_autoconfigure_3_3_11_extension" -> "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_autoconfigure_3_3_11//file:file" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_autoconfigure_3_3_11_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_autoconfigure_3_3_11//file:file" "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_autoconfigure_3_3_11//file:file" -> "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_autoconfigure_3_3_11//file:v1/org/springframework/boot/spring-boot-autoconfigure/3.3.11/spring-boot-autoconfigure-3.3.11.jar" "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_autoconfigure_3_3_11//file:v1/org/springframework/boot/spring-boot-autoconfigure/3.3.11/spring-boot-autoconfigure-3.3.11.jar" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot" -> "@unmanaged_deps_filter//:org/springframework/boot/spring-boot/3.3.11/spring-boot-3.3.11.jar" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot" -> "@unmanaged_deps_filter//:org_springframework_spring_context" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot" -> "@unmanaged_deps_filter//:org_springframework_spring_core" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:org_springframework_spring_context" "@unmanaged_deps_filter//:org_springframework_spring_context" -> "@unmanaged_deps_filter//:org/springframework/spring-context/6.1.19/spring-context-6.1.19.jar" "@unmanaged_deps_filter//:org_springframework_spring_context" -> "@unmanaged_deps_filter//:io_micrometer_micrometer_observation" "@unmanaged_deps_filter//:org_springframework_spring_context" -> "@unmanaged_deps_filter//:org_springframework_spring_aop" "@unmanaged_deps_filter//:org_springframework_spring_context" -> "@unmanaged_deps_filter//:org_springframework_spring_beans" "@unmanaged_deps_filter//:org_springframework_spring_context" -> "@unmanaged_deps_filter//:org_springframework_spring_core" "@unmanaged_deps_filter//:org_springframework_spring_context" -> "@unmanaged_deps_filter//:org_springframework_spring_expression" "@unmanaged_deps_filter//:org_springframework_spring_context" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:org_springframework_spring_context" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:org_springframework_spring_expression" "@unmanaged_deps_filter//:org_springframework_spring_expression" -> "@unmanaged_deps_filter//:org/springframework/spring-expression/6.1.19/spring-expression-6.1.19.jar" "@unmanaged_deps_filter//:org_springframework_spring_expression" -> "@unmanaged_deps_filter//:org_springframework_spring_core" "@unmanaged_deps_filter//:org_springframework_spring_expression" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:org_springframework_spring_expression" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:org/springframework/spring-expression/6.1.19/spring-expression-6.1.19.jar" "@unmanaged_deps_filter//:org/springframework/spring-expression/6.1.19/spring-expression-6.1.19.jar" -> "@unmanaged_deps_filter//:org_springframework_spring_expression_6_1_19_extension" "@unmanaged_deps_filter//:org_springframework_spring_expression_6_1_19_extension" "@unmanaged_deps_filter//:org_springframework_spring_expression_6_1_19_extension" -> "@@rules_jvm_external~~maven~org_springframework_spring_expression_6_1_19//file:file" "@unmanaged_deps_filter//:org_springframework_spring_expression_6_1_19_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~org_springframework_spring_expression_6_1_19//file:file" "@@rules_jvm_external~~maven~org_springframework_spring_expression_6_1_19//file:file" -> "@@rules_jvm_external~~maven~org_springframework_spring_expression_6_1_19//file:v1/org/springframework/spring-expression/6.1.19/spring-expression-6.1.19.jar" "@@rules_jvm_external~~maven~org_springframework_spring_expression_6_1_19//file:v1/org/springframework/spring-expression/6.1.19/spring-expression-6.1.19.jar" "@unmanaged_deps_filter//:org_springframework_spring_aop" "@unmanaged_deps_filter//:org_springframework_spring_aop" -> "@unmanaged_deps_filter//:org/springframework/spring-aop/6.1.19/spring-aop-6.1.19.jar" "@unmanaged_deps_filter//:org_springframework_spring_aop" -> "@unmanaged_deps_filter//:org_springframework_spring_beans" "@unmanaged_deps_filter//:org_springframework_spring_aop" -> "@unmanaged_deps_filter//:org_springframework_spring_core" "@unmanaged_deps_filter//:org_springframework_spring_aop" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:org_springframework_spring_aop" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:org_springframework_spring_beans" "@unmanaged_deps_filter//:org_springframework_spring_beans" -> "@unmanaged_deps_filter//:org/springframework/spring-beans/6.1.19/spring-beans-6.1.19.jar" "@unmanaged_deps_filter//:org_springframework_spring_beans" -> "@unmanaged_deps_filter//:org_springframework_spring_core" "@unmanaged_deps_filter//:org_springframework_spring_beans" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:org_springframework_spring_beans" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:org_springframework_spring_core" "@unmanaged_deps_filter//:org_springframework_spring_core" -> "@unmanaged_deps_filter//:org/springframework/spring-core/6.1.19/spring-core-6.1.19.jar" "@unmanaged_deps_filter//:org_springframework_spring_core" -> "@unmanaged_deps_filter//:org_springframework_spring_jcl" "@unmanaged_deps_filter//:org_springframework_spring_core" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:org_springframework_spring_core" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:org_springframework_spring_jcl" "@unmanaged_deps_filter//:org_springframework_spring_jcl" -> "@unmanaged_deps_filter//:org/springframework/spring-jcl/6.1.19/spring-jcl-6.1.19.jar" "@unmanaged_deps_filter//:org_springframework_spring_jcl" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:org_springframework_spring_jcl" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:org/springframework/spring-jcl/6.1.19/spring-jcl-6.1.19.jar" "@unmanaged_deps_filter//:org/springframework/spring-jcl/6.1.19/spring-jcl-6.1.19.jar" -> "@unmanaged_deps_filter//:org_springframework_spring_jcl_6_1_19_extension" "@unmanaged_deps_filter//:org_springframework_spring_jcl_6_1_19_extension" "@unmanaged_deps_filter//:org_springframework_spring_jcl_6_1_19_extension" -> "@@rules_jvm_external~~maven~org_springframework_spring_jcl_6_1_19//file:file" "@unmanaged_deps_filter//:org_springframework_spring_jcl_6_1_19_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~org_springframework_spring_jcl_6_1_19//file:file" "@@rules_jvm_external~~maven~org_springframework_spring_jcl_6_1_19//file:file" -> "@@rules_jvm_external~~maven~org_springframework_spring_jcl_6_1_19//file:v1/org/springframework/spring-jcl/6.1.19/spring-jcl-6.1.19.jar" "@@rules_jvm_external~~maven~org_springframework_spring_jcl_6_1_19//file:v1/org/springframework/spring-jcl/6.1.19/spring-jcl-6.1.19.jar" "@unmanaged_deps_filter//:org/springframework/spring-core/6.1.19/spring-core-6.1.19.jar" "@unmanaged_deps_filter//:org/springframework/spring-core/6.1.19/spring-core-6.1.19.jar" -> "@unmanaged_deps_filter//:org_springframework_spring_core_6_1_19_extension" "@unmanaged_deps_filter//:org_springframework_spring_core_6_1_19_extension" "@unmanaged_deps_filter//:org_springframework_spring_core_6_1_19_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@unmanaged_deps_filter//:org_springframework_spring_core_6_1_19_extension" -> "@@rules_jvm_external~~maven~org_springframework_spring_core_6_1_19//file:file" "@@rules_jvm_external~~maven~org_springframework_spring_core_6_1_19//file:file" "@@rules_jvm_external~~maven~org_springframework_spring_core_6_1_19//file:file" -> "@@rules_jvm_external~~maven~org_springframework_spring_core_6_1_19//file:v1/org/springframework/spring-core/6.1.19/spring-core-6.1.19.jar" "@@rules_jvm_external~~maven~org_springframework_spring_core_6_1_19//file:v1/org/springframework/spring-core/6.1.19/spring-core-6.1.19.jar" "@unmanaged_deps_filter//:org/springframework/spring-beans/6.1.19/spring-beans-6.1.19.jar" "@unmanaged_deps_filter//:org/springframework/spring-beans/6.1.19/spring-beans-6.1.19.jar" -> "@unmanaged_deps_filter//:org_springframework_spring_beans_6_1_19_extension" "@unmanaged_deps_filter//:org_springframework_spring_beans_6_1_19_extension" "@unmanaged_deps_filter//:org_springframework_spring_beans_6_1_19_extension" -> "@@rules_jvm_external~~maven~org_springframework_spring_beans_6_1_19//file:file" "@unmanaged_deps_filter//:org_springframework_spring_beans_6_1_19_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~org_springframework_spring_beans_6_1_19//file:file" "@@rules_jvm_external~~maven~org_springframework_spring_beans_6_1_19//file:file" -> "@@rules_jvm_external~~maven~org_springframework_spring_beans_6_1_19//file:v1/org/springframework/spring-beans/6.1.19/spring-beans-6.1.19.jar" "@@rules_jvm_external~~maven~org_springframework_spring_beans_6_1_19//file:v1/org/springframework/spring-beans/6.1.19/spring-beans-6.1.19.jar" "@unmanaged_deps_filter//:org/springframework/spring-aop/6.1.19/spring-aop-6.1.19.jar" "@unmanaged_deps_filter//:org/springframework/spring-aop/6.1.19/spring-aop-6.1.19.jar" -> "@unmanaged_deps_filter//:org_springframework_spring_aop_6_1_19_extension" "@unmanaged_deps_filter//:org_springframework_spring_aop_6_1_19_extension" "@unmanaged_deps_filter//:org_springframework_spring_aop_6_1_19_extension" -> "@@rules_jvm_external~~maven~org_springframework_spring_aop_6_1_19//file:file" "@unmanaged_deps_filter//:org_springframework_spring_aop_6_1_19_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~org_springframework_spring_aop_6_1_19//file:file" "@@rules_jvm_external~~maven~org_springframework_spring_aop_6_1_19//file:file" -> "@@rules_jvm_external~~maven~org_springframework_spring_aop_6_1_19//file:v1/org/springframework/spring-aop/6.1.19/spring-aop-6.1.19.jar" "@@rules_jvm_external~~maven~org_springframework_spring_aop_6_1_19//file:v1/org/springframework/spring-aop/6.1.19/spring-aop-6.1.19.jar" "@unmanaged_deps_filter//:io_micrometer_micrometer_observation" "@unmanaged_deps_filter//:io_micrometer_micrometer_observation" -> "@unmanaged_deps_filter//:io/micrometer/micrometer-observation/1.13.13/micrometer-observation-1.13.13.jar" "@unmanaged_deps_filter//:io_micrometer_micrometer_observation" -> "@unmanaged_deps_filter//:io_micrometer_micrometer_commons" "@unmanaged_deps_filter//:io_micrometer_micrometer_observation" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:io_micrometer_micrometer_observation" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:io_micrometer_micrometer_commons" "@unmanaged_deps_filter//:io_micrometer_micrometer_commons" -> "@unmanaged_deps_filter//:io/micrometer/micrometer-commons/1.13.13/micrometer-commons-1.13.13.jar" "@unmanaged_deps_filter//:io_micrometer_micrometer_commons" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:io_micrometer_micrometer_commons" -> "@rules_jvm_external//settings:stamp_manifest" "@unmanaged_deps_filter//:io/micrometer/micrometer-commons/1.13.13/micrometer-commons-1.13.13.jar" "@unmanaged_deps_filter//:io/micrometer/micrometer-commons/1.13.13/micrometer-commons-1.13.13.jar" -> "@unmanaged_deps_filter//:io_micrometer_micrometer_commons_1_13_13_extension" "@unmanaged_deps_filter//:io_micrometer_micrometer_commons_1_13_13_extension" "@unmanaged_deps_filter//:io_micrometer_micrometer_commons_1_13_13_extension" -> "@@rules_jvm_external~~maven~io_micrometer_micrometer_commons_1_13_13//file:file" "@unmanaged_deps_filter//:io_micrometer_micrometer_commons_1_13_13_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~io_micrometer_micrometer_commons_1_13_13//file:file" "@@rules_jvm_external~~maven~io_micrometer_micrometer_commons_1_13_13//file:file" -> "@@rules_jvm_external~~maven~io_micrometer_micrometer_commons_1_13_13//file:v1/io/micrometer/micrometer-commons/1.13.13/micrometer-commons-1.13.13.jar" "@@rules_jvm_external~~maven~io_micrometer_micrometer_commons_1_13_13//file:v1/io/micrometer/micrometer-commons/1.13.13/micrometer-commons-1.13.13.jar" "@unmanaged_deps_filter//:io/micrometer/micrometer-observation/1.13.13/micrometer-observation-1.13.13.jar" "@unmanaged_deps_filter//:io/micrometer/micrometer-observation/1.13.13/micrometer-observation-1.13.13.jar" -> "@unmanaged_deps_filter//:io_micrometer_micrometer_observation_1_13_13_extension" "@unmanaged_deps_filter//:io_micrometer_micrometer_observation_1_13_13_extension" "@unmanaged_deps_filter//:io_micrometer_micrometer_observation_1_13_13_extension" -> "@@rules_jvm_external~~maven~io_micrometer_micrometer_observation_1_13_13//file:file" "@unmanaged_deps_filter//:io_micrometer_micrometer_observation_1_13_13_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~io_micrometer_micrometer_observation_1_13_13//file:file" "@@rules_jvm_external~~maven~io_micrometer_micrometer_observation_1_13_13//file:file" -> "@@rules_jvm_external~~maven~io_micrometer_micrometer_observation_1_13_13//file:v1/io/micrometer/micrometer-observation/1.13.13/micrometer-observation-1.13.13.jar" "@@rules_jvm_external~~maven~io_micrometer_micrometer_observation_1_13_13//file:v1/io/micrometer/micrometer-observation/1.13.13/micrometer-observation-1.13.13.jar" "@unmanaged_deps_filter//:org/springframework/spring-context/6.1.19/spring-context-6.1.19.jar" "@unmanaged_deps_filter//:org/springframework/spring-context/6.1.19/spring-context-6.1.19.jar" -> "@unmanaged_deps_filter//:org_springframework_spring_context_6_1_19_extension" "@unmanaged_deps_filter//:org_springframework_spring_context_6_1_19_extension" "@unmanaged_deps_filter//:org_springframework_spring_context_6_1_19_extension" -> "@@rules_jvm_external~~maven~org_springframework_spring_context_6_1_19//file:file" "@unmanaged_deps_filter//:org_springframework_spring_context_6_1_19_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~org_springframework_spring_context_6_1_19//file:file" "@@rules_jvm_external~~maven~org_springframework_spring_context_6_1_19//file:file" -> "@@rules_jvm_external~~maven~org_springframework_spring_context_6_1_19//file:v1/org/springframework/spring-context/6.1.19/spring-context-6.1.19.jar" "@@rules_jvm_external~~maven~org_springframework_spring_context_6_1_19//file:v1/org/springframework/spring-context/6.1.19/spring-context-6.1.19.jar" "@unmanaged_deps_filter//:org/springframework/boot/spring-boot/3.3.11/spring-boot-3.3.11.jar" "@unmanaged_deps_filter//:org/springframework/boot/spring-boot/3.3.11/spring-boot-3.3.11.jar" -> "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_3_3_11_extension" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_3_3_11_extension" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_3_3_11_extension" -> "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_3_3_11//file:file" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_3_3_11_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_3_3_11//file:file" "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_3_3_11//file:file" -> "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_3_3_11//file:v1/org/springframework/boot/spring-boot/3.3.11/spring-boot-3.3.11.jar" "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_3_3_11//file:v1/org/springframework/boot/spring-boot/3.3.11/spring-boot-3.3.11.jar" "@unmanaged_deps_filter//:jakarta_annotation_jakarta_annotation_api" "@unmanaged_deps_filter//:jakarta_annotation_jakarta_annotation_api" -> "@unmanaged_deps_filter//:jakarta/annotation/jakarta.annotation-api/2.1.1/jakarta.annotation-api-2.1.1.jar" "@unmanaged_deps_filter//:jakarta_annotation_jakarta_annotation_api" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@unmanaged_deps_filter//:jakarta_annotation_jakarta_annotation_api" -> "@rules_jvm_external//settings:stamp_manifest" "@rules_jvm_external//settings:stamp_manifest" "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry.java\n@bazel_tools//tools/jdk:launcher_flag_alias\n@bazel_tools//tools/jdk:java_stub_template.txt" "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" -> "@bazel_tools//tools/cpp:optional_current_cc_toolchain" "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" -> "@bazel_tools//tools/launcher:launcher_maker" "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" -> "@bazel_tools//tools/jdk:toolchain_type\n@bazel_tools//tools/jdk:java_plugins_flag_alias" "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" -> "@bazel_tools//tools/jdk:current_java_toolchain" "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external:rules_jvm_external" "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/zip:zip" "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry" -> "@bazel_tools//tools/launcher:launcher" "@bazel_tools//tools/launcher:launcher" "@bazel_tools//tools/launcher:launcher" -> "@bazel_tools//tools/launcher:launcher_windows" [label="@@bazel_tools//src/conditions:host_windows"]; "@bazel_tools//tools/launcher:launcher" -> "@bazel_tools//src/tools/launcher:launcher" [label="//conditions:default"]; "@bazel_tools//tools/launcher:launcher" -> "@bazel_tools//src/conditions:host_windows" "@bazel_tools//tools/launcher:launcher_windows" "@bazel_tools//tools/launcher:launcher_windows" -> "@bazel_tools//tools/launcher:launcher.exe" [label="//conditions:default"]; "@bazel_tools//tools/launcher:launcher_windows" -> "@bazel_tools//src/tools/launcher:launcher" [label="@@bazel_tools//src/conditions:remote"]; "@bazel_tools//tools/launcher:launcher_windows" -> "@bazel_tools//src/conditions:remote" "@bazel_tools//src/tools/launcher:launcher" "@bazel_tools//src/tools/launcher:launcher" -> "@bazel_tools//src/tools/launcher:dummy.cc" [label="//conditions:default"]; "@bazel_tools//src/tools/launcher:launcher" -> "@bazel_tools//src/tools/launcher:launcher_main.cc" [label="@@bazel_tools//src/conditions:windows"]; "@bazel_tools//src/tools/launcher:launcher" -> "@bazel_tools//src/tools/launcher:bash_launcher" [label="@@bazel_tools//src/conditions:windows"]; "@bazel_tools//src/tools/launcher:launcher" -> "@bazel_tools//src/tools/launcher:java_launcher" [label="@@bazel_tools//src/conditions:windows"]; "@bazel_tools//src/tools/launcher:launcher" -> "@bazel_tools//src/tools/launcher:launcher_base" [label="@@bazel_tools//src/conditions:windows"]; "@bazel_tools//src/tools/launcher:launcher" -> "@bazel_tools//src/tools/launcher:python_launcher" [label="@@bazel_tools//src/conditions:windows"]; "@bazel_tools//src/tools/launcher:launcher" -> "@bazel_tools//tools/def_parser:def_parser" "@bazel_tools//src/tools/launcher:launcher" -> "@bazel_tools//tools/cpp:toolchain_type" "@bazel_tools//src/tools/launcher:launcher" -> "@bazel_tools//tools/cpp:current_cc_toolchain" "@bazel_tools//src/tools/launcher:launcher" -> "@bazel_tools//tools/cpp:link_extra_lib" "@bazel_tools//src/tools/launcher:launcher" -> "@bazel_tools//tools/cpp:malloc" "@bazel_tools//src/tools/launcher:launcher" -> "@bazel_tools//src/tools/launcher/util:data_parser" [label="@@bazel_tools//src/conditions:windows"]; "@bazel_tools//src/tools/launcher:launcher" -> "@bazel_tools//src/tools/launcher/util:util" [label="@@bazel_tools//src/conditions:windows"]; "@bazel_tools//src/tools/launcher:launcher" -> "@bazel_tools//src/conditions:windows" "@bazel_tools//src/tools/launcher:python_launcher" "@bazel_tools//src/tools/launcher:python_launcher" -> "@bazel_tools//src/tools/launcher:dummy.cc" [label="//conditions:default"]; "@bazel_tools//src/tools/launcher:python_launcher" -> "@bazel_tools//src/tools/launcher:python_launcher.h\n@bazel_tools//src/tools/launcher:python_launcher.cc" [label="@@bazel_tools//src/conditions:windows"]; "@bazel_tools//src/tools/launcher:python_launcher" -> "@bazel_tools//src/tools/launcher:launcher_base" [label="@@bazel_tools//src/conditions:windows"]; "@bazel_tools//src/tools/launcher:python_launcher" -> "@bazel_tools//tools/cpp:current_cc_toolchain" "@bazel_tools//src/tools/launcher:python_launcher" -> "@bazel_tools//tools/def_parser:def_parser" "@bazel_tools//src/tools/launcher:python_launcher" -> "@bazel_tools//src/main/native/windows:lib-process" [label="@@bazel_tools//src/conditions:windows"]; "@bazel_tools//src/tools/launcher:python_launcher" -> "@bazel_tools//src/conditions:windows" "@bazel_tools//src/tools/launcher:python_launcher.h\n@bazel_tools//src/tools/launcher:python_launcher.cc" "@bazel_tools//src/tools/launcher:java_launcher" "@bazel_tools//src/tools/launcher:java_launcher" -> "@bazel_tools//src/tools/launcher:dummy.cc" [label="//conditions:default"]; "@bazel_tools//src/tools/launcher:java_launcher" -> "@bazel_tools//src/tools/launcher:java_launcher.cc\n@bazel_tools//src/tools/launcher:java_launcher.h" [label="@@bazel_tools//src/conditions:windows"]; "@bazel_tools//src/tools/launcher:java_launcher" -> "@bazel_tools//src/tools/launcher:launcher_base" [label="@@bazel_tools//src/conditions:windows"]; "@bazel_tools//src/tools/launcher:java_launcher" -> "@bazel_tools//tools/cpp:current_cc_toolchain" "@bazel_tools//src/tools/launcher:java_launcher" -> "@bazel_tools//tools/def_parser:def_parser" "@bazel_tools//src/tools/launcher:java_launcher" -> "@bazel_tools//src/main/native/windows:lib-process" [label="@@bazel_tools//src/conditions:windows"]; "@bazel_tools//src/tools/launcher:java_launcher" -> "@bazel_tools//src/conditions:windows" "@bazel_tools//src/main/native/windows:lib-process" "@bazel_tools//src/main/native/windows:lib-process" -> "@bazel_tools//src/main/native/windows:process.h\n@bazel_tools//src/main/native/windows:process.cc" "@bazel_tools//src/main/native/windows:lib-process" -> "@bazel_tools//src/main/native/windows:lib-file" "@bazel_tools//src/main/native/windows:lib-process" -> "@bazel_tools//tools/cpp:current_cc_toolchain" "@bazel_tools//src/main/native/windows:lib-process" -> "@bazel_tools//tools/def_parser:def_parser" "@bazel_tools//src/main/native/windows:process.h\n@bazel_tools//src/main/native/windows:process.cc" "@bazel_tools//src/tools/launcher:java_launcher.cc\n@bazel_tools//src/tools/launcher:java_launcher.h" "@bazel_tools//src/tools/launcher:bash_launcher" "@bazel_tools//src/tools/launcher:bash_launcher" -> "@bazel_tools//src/tools/launcher:dummy.cc" [label="//conditions:default"]; "@bazel_tools//src/tools/launcher:bash_launcher" -> "@bazel_tools//src/tools/launcher:bash_launcher.h\n@bazel_tools//src/tools/launcher:bash_launcher.cc" [label="@@bazel_tools//src/conditions:windows"]; "@bazel_tools//src/tools/launcher:bash_launcher" -> "@bazel_tools//src/tools/launcher:launcher_base" [label="@@bazel_tools//src/conditions:windows"]; "@bazel_tools//src/tools/launcher:bash_launcher" -> "@bazel_tools//tools/cpp:current_cc_toolchain" "@bazel_tools//src/tools/launcher:bash_launcher" -> "@bazel_tools//tools/def_parser:def_parser" "@bazel_tools//src/tools/launcher:bash_launcher" -> "@bazel_tools//src/conditions:windows" "@bazel_tools//src/tools/launcher:launcher_base" "@bazel_tools//src/tools/launcher:launcher_base" -> "@bazel_tools//src/tools/launcher:dummy.cc" [label="//conditions:default"]; "@bazel_tools//src/tools/launcher:launcher_base" -> "@bazel_tools//src/tools/launcher:launcher.h\n@bazel_tools//src/tools/launcher:launcher.cc" [label="@@bazel_tools//src/conditions:windows"]; "@bazel_tools//src/tools/launcher:launcher_base" -> "@bazel_tools//tools/cpp:current_cc_toolchain" "@bazel_tools//src/tools/launcher:launcher_base" -> "@bazel_tools//tools/def_parser:def_parser" "@bazel_tools//src/tools/launcher:launcher_base" -> "@bazel_tools//src/tools/launcher/util:data_parser" [label="@@bazel_tools//src/conditions:windows"]; "@bazel_tools//src/tools/launcher:launcher_base" -> "@bazel_tools//src/tools/launcher/util:util" [label="@@bazel_tools//src/conditions:windows"]; "@bazel_tools//src/tools/launcher:launcher_base" -> "@bazel_tools//src/main/cpp/util:filesystem" [label="@@bazel_tools//src/conditions:windows"]; "@bazel_tools//src/tools/launcher:launcher_base" -> "@bazel_tools//src/conditions:windows" "@bazel_tools//src/tools/launcher/util:data_parser" "@bazel_tools//src/tools/launcher/util:data_parser" -> "@bazel_tools//src/tools/launcher/util:dummy.cc" [label="//conditions:default"]; "@bazel_tools//src/tools/launcher/util:data_parser" -> "@bazel_tools//src/tools/launcher/util:data_parser.h\n@bazel_tools//src/tools/launcher/util:data_parser.cc" [label="@@bazel_tools//src/conditions:windows"]; "@bazel_tools//src/tools/launcher/util:data_parser" -> "@bazel_tools//src/tools/launcher/util:util" [label="@@bazel_tools//src/conditions:windows"]; "@bazel_tools//src/tools/launcher/util:data_parser" -> "@bazel_tools//tools/cpp:current_cc_toolchain" "@bazel_tools//src/tools/launcher/util:data_parser" -> "@bazel_tools//tools/def_parser:def_parser" "@bazel_tools//src/tools/launcher/util:data_parser" -> "@bazel_tools//src/conditions:windows" "@bazel_tools//src/tools/launcher/util:util" "@bazel_tools//src/tools/launcher/util:util" -> "@bazel_tools//src/tools/launcher/util:dummy.cc" [label="//conditions:default"]; "@bazel_tools//src/tools/launcher/util:util" -> "@bazel_tools//src/tools/launcher/util:launcher_util.cc\n@bazel_tools//src/tools/launcher/util:launcher_util.h" [label="@@bazel_tools//src/conditions:windows"]; "@bazel_tools//src/tools/launcher/util:util" -> "@bazel_tools//tools/cpp:current_cc_toolchain" "@bazel_tools//src/tools/launcher/util:util" -> "@bazel_tools//tools/def_parser:def_parser" "@bazel_tools//src/tools/launcher/util:util" -> "@bazel_tools//src/main/cpp/util:filesystem" [label="@@bazel_tools//src/conditions:windows"]; "@bazel_tools//src/tools/launcher/util:util" -> "@bazel_tools//src/conditions:windows" "@bazel_tools//src/tools/launcher/util:launcher_util.cc\n@bazel_tools//src/tools/launcher/util:launcher_util.h" "@bazel_tools//src/tools/launcher/util:data_parser.h\n@bazel_tools//src/tools/launcher/util:data_parser.cc" "@bazel_tools//src/tools/launcher/util:dummy.cc" "@bazel_tools//src/tools/launcher:launcher.h\n@bazel_tools//src/tools/launcher:launcher.cc" "@bazel_tools//src/tools/launcher:bash_launcher.h\n@bazel_tools//src/tools/launcher:bash_launcher.cc" "@bazel_tools//src/tools/launcher:launcher_main.cc" "@bazel_tools//src/tools/launcher:dummy.cc" "@bazel_tools//tools/launcher:launcher.exe" "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/zip:zip" "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/zip:zip" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/zip:StableZipEntry.java" "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/zip:zip" -> "@bazel_tools//tools/jdk:toolchain_type\n@bazel_tools//tools/jdk:java_plugins_flag_alias" "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/zip:zip" -> "@bazel_tools//tools/jdk:current_java_toolchain" "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/zip:StableZipEntry.java" "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external:rules_jvm_external" "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external:rules_jvm_external" -> "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external:ByteStreams.java\n@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external:Coordinates.java\n@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external:Hasher.java" "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external:rules_jvm_external" -> "@bazel_tools//tools/jdk:toolchain_type\n@bazel_tools//tools/jdk:java_plugins_flag_alias" "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external:rules_jvm_external" -> "@bazel_tools//tools/jdk:current_java_toolchain" "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external:ByteStreams.java\n@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external:Coordinates.java\n@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external:Hasher.java" "@bazel_tools//tools/jdk:current_java_toolchain" "@bazel_tools//tools/jdk:current_java_toolchain" -> "@@rules_java~//toolchains:current_java_toolchain" "@@rules_java~//toolchains:current_java_toolchain" "@bazel_tools//tools/jdk:toolchain_type\n@bazel_tools//tools/jdk:java_plugins_flag_alias" "@bazel_tools//tools/launcher:launcher_maker" "@bazel_tools//tools/launcher:launcher_maker" -> "@bazel_tools//tools/launcher:launcher_maker_windows" [label="@@bazel_tools//src/conditions:host_windows"]; "@bazel_tools//tools/launcher:launcher_maker" -> "@bazel_tools//src/tools/launcher:launcher_maker" [label="//conditions:default"]; "@bazel_tools//tools/launcher:launcher_maker" -> "@bazel_tools//src/conditions:host_windows" "@bazel_tools//tools/launcher:launcher_maker_windows" "@bazel_tools//tools/launcher:launcher_maker_windows" -> "@bazel_tools//tools/launcher:launcher_maker.exe" [label="//conditions:default"]; "@bazel_tools//tools/launcher:launcher_maker_windows" -> "@bazel_tools//src/conditions:remote" "@bazel_tools//tools/launcher:launcher_maker_windows" -> "@bazel_tools//src/tools/launcher:launcher_maker" [label="@@bazel_tools//src/conditions:remote"]; "@bazel_tools//src/tools/launcher:launcher_maker" "@bazel_tools//src/tools/launcher:launcher_maker" -> "@bazel_tools//src/tools/launcher:launcher_maker.cc" "@bazel_tools//src/tools/launcher:launcher_maker" -> "@bazel_tools//tools/def_parser:def_parser" "@bazel_tools//src/tools/launcher:launcher_maker" -> "@bazel_tools//tools/cpp:toolchain_type" "@bazel_tools//src/tools/launcher:launcher_maker" -> "@bazel_tools//tools/cpp:current_cc_toolchain" "@bazel_tools//src/tools/launcher:launcher_maker" -> "@bazel_tools//tools/cpp:link_extra_lib" "@bazel_tools//src/tools/launcher:launcher_maker" -> "@bazel_tools//tools/cpp:malloc" "@bazel_tools//src/tools/launcher:launcher_maker" -> "@bazel_tools//src/main/cpp/util:filesystem" [label="@@platforms//os:windows"]; "@bazel_tools//src/tools/launcher:launcher_maker" -> "@platforms//os:windows" "@bazel_tools//src/main/cpp/util:filesystem" "@bazel_tools//src/main/cpp/util:filesystem" -> "@bazel_tools//src/main/cpp/util:ijar" "@bazel_tools//src/main/cpp/util:filesystem" -> "@bazel_tools//src/main/cpp/util:file.cc\n@bazel_tools//src/main/cpp/util:path.cc\n@bazel_tools//src/main/cpp/util:path_windows.cc\n@bazel_tools//src/main/cpp/util:path_posix.cc\n@bazel_tools//src/main/cpp/util:file.h\n@bazel_tools//src/main/cpp/util:file_windows.cc\n@bazel_tools//src/main/cpp/util:file_posix.cc\n@bazel_tools//src/main/cpp/util:path.h\n@bazel_tools//src/main/cpp/util:path_platform.h\n@bazel_tools//src/main/cpp/util:file_platform.h" [label="@@bazel_tools//src/conditions:windows//conditions:default"]; "@bazel_tools//src/main/cpp/util:filesystem" -> "@bazel_tools//src/main/cpp/util:blaze_exit_code" "@bazel_tools//src/main/cpp/util:filesystem" -> "@bazel_tools//src/main/cpp/util:errors" "@bazel_tools//src/main/cpp/util:filesystem" -> "@bazel_tools//src/main/cpp/util:logging" "@bazel_tools//src/main/cpp/util:filesystem" -> "@bazel_tools//src/main/cpp/util:strings" "@bazel_tools//src/main/cpp/util:filesystem" -> "@bazel_tools//tools/cpp:current_cc_toolchain" "@bazel_tools//src/main/cpp/util:filesystem" -> "@bazel_tools//tools/def_parser:def_parser" "@bazel_tools//src/main/cpp/util:filesystem" -> "@bazel_tools//src/main/native/windows:lib-file" [label="@@bazel_tools//src/conditions:windows"]; "@bazel_tools//src/main/cpp/util:filesystem" -> "@bazel_tools//src/conditions:windows" "@bazel_tools//src/main/native/windows:lib-file" "@bazel_tools//src/main/native/windows:lib-file" -> "@bazel_tools//src/main/native/windows:util.cc\n@bazel_tools//src/main/native/windows:util.h\n@bazel_tools//src/main/native/windows:file.cc\n@bazel_tools//src/main/native/windows:file.h" "@bazel_tools//src/main/native/windows:lib-file" -> "@bazel_tools//tools/cpp:current_cc_toolchain" "@bazel_tools//src/main/native/windows:lib-file" -> "@bazel_tools//tools/def_parser:def_parser" "@bazel_tools//src/main/native/windows:util.cc\n@bazel_tools//src/main/native/windows:util.h\n@bazel_tools//src/main/native/windows:file.cc\n@bazel_tools//src/main/native/windows:file.h" "@bazel_tools//src/main/cpp/util:errors" "@bazel_tools//src/main/cpp/util:errors" -> "@bazel_tools//src/main/cpp/util:ijar" "@bazel_tools//src/main/cpp/util:errors" -> "@bazel_tools//src/main/cpp/util:errors_posix.cc\n@bazel_tools//src/main/cpp/util:errors_windows.cc\n@bazel_tools//src/main/cpp/util:errors.h" [label="//conditions:default@@bazel_tools//src/conditions:windows"]; "@bazel_tools//src/main/cpp/util:errors" -> "@bazel_tools//src/main/cpp/util:logging" "@bazel_tools//src/main/cpp/util:errors" -> "@bazel_tools//src/main/cpp/util:port" "@bazel_tools//src/main/cpp/util:errors" -> "@bazel_tools//src/main/cpp/util:strings" "@bazel_tools//src/main/cpp/util:errors" -> "@bazel_tools//tools/cpp:current_cc_toolchain" "@bazel_tools//src/main/cpp/util:errors" -> "@bazel_tools//tools/def_parser:def_parser" "@bazel_tools//src/main/cpp/util:errors" -> "@bazel_tools//src/conditions:windows" "@bazel_tools//src/conditions:windows" "@bazel_tools//src/conditions:windows" -> "@platforms//os:windows" "@platforms//os:windows" "@platforms//os:windows" -> "@platforms//os:os" "@platforms//os:os" "@bazel_tools//src/main/cpp/util:port" "@bazel_tools//src/main/cpp/util:port" -> "@bazel_tools//src/main/cpp/util:port.cc\n@bazel_tools//src/main/cpp/util:port.h" "@bazel_tools//src/main/cpp/util:port" -> "@bazel_tools//tools/cpp:current_cc_toolchain" "@bazel_tools//src/main/cpp/util:port" -> "@bazel_tools//tools/def_parser:def_parser" "@bazel_tools//src/main/cpp/util:port.cc\n@bazel_tools//src/main/cpp/util:port.h" "@bazel_tools//src/main/cpp/util:logging" "@bazel_tools//src/main/cpp/util:logging" -> "@bazel_tools//src/main/cpp/util:logging.h\n@bazel_tools//src/main/cpp/util:logging.cc" "@bazel_tools//src/main/cpp/util:logging" -> "@bazel_tools//src/main/cpp/util:blaze_exit_code" "@bazel_tools//src/main/cpp/util:logging" -> "@bazel_tools//src/main/cpp/util:strings" "@bazel_tools//src/main/cpp/util:logging" -> "@bazel_tools//tools/cpp:current_cc_toolchain" "@bazel_tools//src/main/cpp/util:logging" -> "@bazel_tools//tools/def_parser:def_parser" "@bazel_tools//src/main/cpp/util:strings" "@bazel_tools//src/main/cpp/util:strings" -> "@bazel_tools//src/main/cpp/util:strings.cc\n@bazel_tools//src/main/cpp/util:strings.h" "@bazel_tools//src/main/cpp/util:strings" -> "@bazel_tools//src/main/cpp/util:blaze_exit_code" "@bazel_tools//src/main/cpp/util:strings" -> "@bazel_tools//tools/cpp:current_cc_toolchain" "@bazel_tools//src/main/cpp/util:strings" -> "@bazel_tools//tools/def_parser:def_parser" "@bazel_tools//src/main/cpp/util:strings.cc\n@bazel_tools//src/main/cpp/util:strings.h" "@bazel_tools//src/main/cpp/util:logging.h\n@bazel_tools//src/main/cpp/util:logging.cc" "@bazel_tools//src/main/cpp/util:errors_posix.cc\n@bazel_tools//src/main/cpp/util:errors_windows.cc\n@bazel_tools//src/main/cpp/util:errors.h" "@bazel_tools//src/main/cpp/util:blaze_exit_code" "@bazel_tools//src/main/cpp/util:blaze_exit_code" -> "@bazel_tools//src/main/cpp/util:exit_code.h" "@bazel_tools//src/main/cpp/util:blaze_exit_code" -> "@bazel_tools//tools/def_parser:def_parser" "@bazel_tools//src/main/cpp/util:blaze_exit_code" -> "@bazel_tools//tools/cpp:current_cc_toolchain" "@bazel_tools//src/main/cpp/util:exit_code.h" "@bazel_tools//src/main/cpp/util:file.cc\n@bazel_tools//src/main/cpp/util:path.cc\n@bazel_tools//src/main/cpp/util:path_windows.cc\n@bazel_tools//src/main/cpp/util:path_posix.cc\n@bazel_tools//src/main/cpp/util:file.h\n@bazel_tools//src/main/cpp/util:file_windows.cc\n@bazel_tools//src/main/cpp/util:file_posix.cc\n@bazel_tools//src/main/cpp/util:path.h\n@bazel_tools//src/main/cpp/util:path_platform.h\n@bazel_tools//src/main/cpp/util:file_platform.h" "@bazel_tools//src/main/cpp/util:ijar" "@bazel_tools//tools/def_parser:def_parser" "@bazel_tools//tools/def_parser:def_parser" -> "@bazel_tools//tools/def_parser:def_parser_windows" [label="@@bazel_tools//src/conditions:host_windows"]; "@bazel_tools//tools/def_parser:def_parser" -> "@bazel_tools//tools/def_parser:no_op.bat" [label="//conditions:default"]; "@bazel_tools//tools/def_parser:def_parser" -> "@bazel_tools//src/conditions:host_windows" "@bazel_tools//src/conditions:host_windows" "@bazel_tools//src/conditions:host_windows" -> "@bazel_tools//src/conditions:host_windows_x64_constraint\n@bazel_tools//src/conditions:host_windows_arm64_constraint" [label="//conditions:default@@bazel_tools//src/conditions:host_windows_arm64_constraint"]; "@bazel_tools//src/conditions:host_windows_x64_constraint\n@bazel_tools//src/conditions:host_windows_arm64_constraint" "@bazel_tools//tools/def_parser:no_op.bat" "@bazel_tools//tools/def_parser:def_parser_windows" "@bazel_tools//tools/def_parser:def_parser_windows" -> "@bazel_tools//tools/def_parser:def_parser.exe" [label="//conditions:default"]; "@bazel_tools//tools/def_parser:def_parser_windows" -> "@bazel_tools//third_party/def_parser:def_parser" [label="@@bazel_tools//src/conditions:remote"]; "@bazel_tools//tools/def_parser:def_parser_windows" -> "@bazel_tools//src/conditions:remote" "@bazel_tools//third_party/def_parser:def_parser" "@bazel_tools//third_party/def_parser:def_parser" -> "@bazel_tools//third_party/def_parser:def_parser_main.cc" "@bazel_tools//third_party/def_parser:def_parser" -> "@bazel_tools//third_party/def_parser:def_parser_lib" "@bazel_tools//third_party/def_parser:def_parser" -> "@bazel_tools//tools/cpp:toolchain_type" "@bazel_tools//third_party/def_parser:def_parser" -> "@bazel_tools//tools/cpp:current_cc_toolchain" "@bazel_tools//third_party/def_parser:def_parser" -> "@bazel_tools//tools/cpp:link_extra_lib" "@bazel_tools//third_party/def_parser:def_parser" -> "@bazel_tools//tools/cpp:malloc" "@bazel_tools//tools/cpp:malloc" "@bazel_tools//tools/cpp:malloc" -> "@bazel_tools//tools/cpp:current_cc_toolchain" "@bazel_tools//tools/cpp:link_extra_lib" "@bazel_tools//tools/cpp:link_extra_lib" -> "@bazel_tools//tools/cpp:link_extra_libs" "@bazel_tools//tools/cpp:link_extra_lib" -> "@bazel_tools//tools/cpp:current_cc_toolchain" "@bazel_tools//tools/cpp:link_extra_libs" "@bazel_tools//tools/cpp:link_extra_libs" -> "@bazel_tools//tools/cpp:empty_lib" "@bazel_tools//tools/cpp:empty_lib" "@bazel_tools//tools/cpp:empty_lib" -> "@bazel_tools//tools/cpp:current_cc_toolchain" "@bazel_tools//third_party/def_parser:def_parser_lib" "@bazel_tools//third_party/def_parser:def_parser_lib" -> "@bazel_tools//third_party/def_parser:def_parser.h\n@bazel_tools//third_party/def_parser:def_parser.cc" "@bazel_tools//third_party/def_parser:def_parser_lib" -> "@bazel_tools//tools/cpp:current_cc_toolchain" "@bazel_tools//tools/cpp:current_cc_toolchain" "@bazel_tools//tools/cpp:current_cc_toolchain" -> "@bazel_tools//tools/cpp:toolchain" "@bazel_tools//tools/cpp:current_cc_toolchain" -> "@bazel_tools//tools/cpp:toolchain_type" "@bazel_tools//third_party/def_parser:def_parser.h\n@bazel_tools//third_party/def_parser:def_parser.cc" "@bazel_tools//third_party/def_parser:def_parser_main.cc" "@bazel_tools//tools/def_parser:def_parser.exe" "@bazel_tools//src/tools/launcher:launcher_maker.cc" "@bazel_tools//src/conditions:remote" "@bazel_tools//tools/launcher:launcher_maker.exe" "@bazel_tools//tools/cpp:optional_current_cc_toolchain" "@bazel_tools//tools/cpp:optional_current_cc_toolchain" -> "@bazel_tools//tools/cpp:toolchain" "@bazel_tools//tools/cpp:optional_current_cc_toolchain" -> "@bazel_tools//tools/cpp:toolchain_type" "@bazel_tools//tools/cpp:toolchain" "@bazel_tools//tools/cpp:toolchain" -> "@@bazel_tools~cc_configure_extension~local_config_cc//:toolchain" "@@bazel_tools~cc_configure_extension~local_config_cc//:toolchain" "@@bazel_tools~cc_configure_extension~local_config_cc//:toolchain" -> "@@bazel_tools~cc_configure_extension~local_config_cc//:cc-compiler-darwin_arm64" "@@bazel_tools~cc_configure_extension~local_config_cc//:toolchain" -> "@@bazel_tools~cc_configure_extension~local_config_cc//:cc-compiler-armeabi-v7a" "@@bazel_tools~cc_configure_extension~local_config_cc//:cc-compiler-armeabi-v7a" "@@bazel_tools~cc_configure_extension~local_config_cc//:cc-compiler-armeabi-v7a" -> "@@bazel_tools~cc_configure_extension~local_config_cc//:empty\n@bazel_tools//tools/build_defs/cc/whitelists/parse_headers_and_layering_check:disabling_parse_headers_and_layering_check_allowed" "@@bazel_tools~cc_configure_extension~local_config_cc//:cc-compiler-armeabi-v7a" -> "@@bazel_tools~cc_configure_extension~local_config_cc//:stub_armeabi-v7a" "@@bazel_tools~cc_configure_extension~local_config_cc//:cc-compiler-armeabi-v7a" -> "@bazel_tools//tools/build_defs/build_info:cc_build_info" "@@bazel_tools~cc_configure_extension~local_config_cc//:cc-compiler-armeabi-v7a" -> "@bazel_tools//tools/cpp:toolchain_type" "@@bazel_tools~cc_configure_extension~local_config_cc//:cc-compiler-armeabi-v7a" -> "@bazel_tools//tools/cpp:link_dynamic_library" "@@bazel_tools~cc_configure_extension~local_config_cc//:cc-compiler-armeabi-v7a" -> "@bazel_tools//tools/cpp:interface_library_builder" "@@bazel_tools~cc_configure_extension~local_config_cc//:stub_armeabi-v7a" "@@bazel_tools~cc_configure_extension~local_config_cc//:cc-compiler-darwin_arm64" "@@bazel_tools~cc_configure_extension~local_config_cc//:cc-compiler-darwin_arm64" -> "@@bazel_tools~cc_configure_extension~local_config_cc//:compiler_deps" "@@bazel_tools~cc_configure_extension~local_config_cc//:cc-compiler-darwin_arm64" -> "@@bazel_tools~cc_configure_extension~local_config_cc//:empty\n@bazel_tools//tools/build_defs/cc/whitelists/parse_headers_and_layering_check:disabling_parse_headers_and_layering_check_allowed" "@@bazel_tools~cc_configure_extension~local_config_cc//:cc-compiler-darwin_arm64" -> "@@bazel_tools~cc_configure_extension~local_config_cc//:module.modulemap" "@@bazel_tools~cc_configure_extension~local_config_cc//:cc-compiler-darwin_arm64" -> "@@bazel_tools~cc_configure_extension~local_config_cc//:local" "@@bazel_tools~cc_configure_extension~local_config_cc//:cc-compiler-darwin_arm64" -> "@bazel_tools//tools/build_defs/build_info:cc_build_info" "@@bazel_tools~cc_configure_extension~local_config_cc//:cc-compiler-darwin_arm64" -> "@bazel_tools//tools/cpp:toolchain_type" "@@bazel_tools~cc_configure_extension~local_config_cc//:cc-compiler-darwin_arm64" -> "@bazel_tools//tools/cpp:link_dynamic_library" "@@bazel_tools~cc_configure_extension~local_config_cc//:cc-compiler-darwin_arm64" -> "@bazel_tools//tools/cpp:interface_library_builder" "@bazel_tools//tools/cpp:interface_library_builder" "@bazel_tools//tools/cpp:interface_library_builder" -> "@bazel_tools//tools/cpp:build_interface_so" "@bazel_tools//tools/cpp:build_interface_so" "@bazel_tools//tools/cpp:link_dynamic_library" "@bazel_tools//tools/cpp:link_dynamic_library" -> "@bazel_tools//tools/cpp:link_dynamic_library.sh" "@bazel_tools//tools/cpp:link_dynamic_library.sh" "@bazel_tools//tools/cpp:toolchain_type" "@bazel_tools//tools/build_defs/build_info:cc_build_info" "@bazel_tools//tools/build_defs/build_info:cc_build_info" -> "@bazel_tools//tools/build_defs/build_info/templates:volatile_file.h.template\n@bazel_tools//tools/build_defs/build_info/templates:non_volatile_file.h.template\n@bazel_tools//tools/build_defs/build_info/templates:redacted_file.h.template" "@bazel_tools//tools/build_defs/build_info/templates:volatile_file.h.template\n@bazel_tools//tools/build_defs/build_info/templates:non_volatile_file.h.template\n@bazel_tools//tools/build_defs/build_info/templates:redacted_file.h.template" "@@bazel_tools~cc_configure_extension~local_config_cc//:local" "@@bazel_tools~cc_configure_extension~local_config_cc//:local" -> "@bazel_tools//tools/objc:host_xcodes" "@bazel_tools//tools/objc:host_xcodes" "@@bazel_tools~cc_configure_extension~local_config_cc//:module.modulemap" "@@bazel_tools~cc_configure_extension~local_config_cc//:empty\n@bazel_tools//tools/build_defs/cc/whitelists/parse_headers_and_layering_check:disabling_parse_headers_and_layering_check_allowed" "@@bazel_tools~cc_configure_extension~local_config_cc//:compiler_deps" "@@bazel_tools~cc_configure_extension~local_config_cc//:compiler_deps" -> "@@bazel_tools~cc_configure_extension~local_config_cc//:builtin_include_directory_paths" "@@bazel_tools~cc_configure_extension~local_config_cc//:compiler_deps" -> "@@bazel_tools~cc_configure_extension~local_config_cc//:cc_wrapper" "@@bazel_tools~cc_configure_extension~local_config_cc//:compiler_deps" -> "@@bazel_tools~cc_configure_extension~local_config_cc//:validate_static_library" "@@bazel_tools~cc_configure_extension~local_config_cc//:validate_static_library" "@@bazel_tools~cc_configure_extension~local_config_cc//:validate_static_library" -> "@@bazel_tools~cc_configure_extension~local_config_cc//:validate_static_library.sh" "@@bazel_tools~cc_configure_extension~local_config_cc//:validate_static_library.sh" "@@bazel_tools~cc_configure_extension~local_config_cc//:cc_wrapper" "@@bazel_tools~cc_configure_extension~local_config_cc//:cc_wrapper" -> "@@bazel_tools~cc_configure_extension~local_config_cc//:cc_wrapper.sh" "@@bazel_tools~cc_configure_extension~local_config_cc//:cc_wrapper.sh" "@@bazel_tools~cc_configure_extension~local_config_cc//:builtin_include_directory_paths" "@rules_jvm_external//private/tools/java/com/github/bazelbuild/rules_jvm_external/jar:AddJarManifestEntry.java\n@bazel_tools//tools/jdk:launcher_flag_alias\n@bazel_tools//tools/jdk:java_stub_template.txt" "@unmanaged_deps_filter//:jakarta/annotation/jakarta.annotation-api/2.1.1/jakarta.annotation-api-2.1.1.jar" "@unmanaged_deps_filter//:jakarta/annotation/jakarta.annotation-api/2.1.1/jakarta.annotation-api-2.1.1.jar" -> "@unmanaged_deps_filter//:jakarta_annotation_jakarta_annotation_api_2_1_1_extension" "@unmanaged_deps_filter//:jakarta_annotation_jakarta_annotation_api_2_1_1_extension" "@unmanaged_deps_filter//:jakarta_annotation_jakarta_annotation_api_2_1_1_extension" -> "@@rules_jvm_external~~maven~jakarta_annotation_jakarta_annotation_api_2_1_1//file:file" "@unmanaged_deps_filter//:jakarta_annotation_jakarta_annotation_api_2_1_1_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~jakarta_annotation_jakarta_annotation_api_2_1_1//file:file" "@@rules_jvm_external~~maven~jakarta_annotation_jakarta_annotation_api_2_1_1//file:file" -> "@@rules_jvm_external~~maven~jakarta_annotation_jakarta_annotation_api_2_1_1//file:v1/jakarta/annotation/jakarta.annotation-api/2.1.1/jakarta.annotation-api-2.1.1.jar" "@@rules_jvm_external~~maven~jakarta_annotation_jakarta_annotation_api_2_1_1//file:v1/jakarta/annotation/jakarta.annotation-api/2.1.1/jakarta.annotation-api-2.1.1.jar" "@unmanaged_deps_filter//:org/springframework/boot/spring-boot-starter/3.3.11/spring-boot-starter-3.3.11.jar" "@unmanaged_deps_filter//:org/springframework/boot/spring-boot-starter/3.3.11/spring-boot-starter-3.3.11.jar" -> "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_3_3_11_extension" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_3_3_11_extension" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_3_3_11_extension" -> "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_3_3_11//file:file" "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_3_3_11_extension" -> "@bazel_tools//tools/genrule:genrule-setup.sh" "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_3_3_11//file:file" "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_3_3_11//file:file" -> "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_3_3_11//file:v1/org/springframework/boot/spring-boot-starter/3.3.11/spring-boot-starter-3.3.11.jar" "@@rules_jvm_external~~maven~org_springframework_boot_spring_boot_starter_3_3_11//file:v1/org/springframework/boot/spring-boot-starter/3.3.11/spring-boot-starter-3.3.11.jar" "@bazel_tools//tools/genrule:genrule-setup.sh" } ================================================ FILE: springboot/deps_filter_rules/tests/test_utils/src/test/java/com/depsfilter/DependencyGraphAnalyzer.java ================================================ package com.depsfilter; import java.util.*; import java.util.regex.Matcher; import java.util.regex.Pattern; public class DependencyGraphAnalyzer { private final Map> dependencyGraph = new HashMap<>(); private final Map labelToRuntimeMapping = new HashMap<>(); private final Set allJarLabels = new HashSet<>(); public void parseDependencyGraph(String graphOutput) { String[] lines = graphOutput.split("\n"); for (String line : lines) { if (line.trim().isEmpty() || !line.contains("->")) { continue; } Pattern edgePattern = Pattern.compile("\"([^\"]+)\"\\s*->\\s*\"([^\"]+)\""); Matcher matcher = edgePattern.matcher(line); if (matcher.find()) { String from = matcher.group(1); String to = matcher.group(2); // Build complete graph - don't filter here dependencyGraph.computeIfAbsent(from, k -> new HashSet<>()).add(to); // Track JAR labels for mapping if (isJarLabel(from)) { allJarLabels.add(from); } if (isJarLabel(to)) { allJarLabels.add(to); } } } buildLabelToRuntimeMapping(); } private boolean isJarLabel(String label) { return label.startsWith("@") && label.contains("//:") && label.endsWith(".jar"); } private boolean isTargetLabel(String label) { return (label.startsWith("@spring//") || label.startsWith("@jakarta//")) && !label.contains(".jar"); } private void buildLabelToRuntimeMapping() { for (String label : allJarLabels) { String runtimeName = convertLabelToRuntimeName(label); if (runtimeName != null) { labelToRuntimeMapping.put(label, runtimeName); } } } private String convertLabelToRuntimeName(String label) { if (!isJarLabel(label)) { return null; } String runtimePath = label.substring(1).replace("//:", "/"); // Replace unmanaged_deps_filter/ with rules_jvm_external~~maven~unmanaged_deps_filter/ runtimePath = runtimePath.replace("unmanaged_deps_filter/", "rules_jvm_external~~maven~unmanaged_deps_filter/"); int lastSlash = runtimePath.lastIndexOf('/'); if (lastSlash != -1) { String directory = runtimePath.substring(0, lastSlash + 1); String filename = runtimePath.substring(lastSlash + 1); return directory + "processed_" + filename; } return null; } public Set computeExpectedRuntimeJars( List depsLabels, List runtimeDepsLabels, Set excludedLabels, Set excludedPatterns, boolean excludeTransitives) { Set expectedJars = new HashSet<>(); Set excludedNodes = new HashSet<>(); if (excludeTransitives) { // When excludeTransitives=true, exclude the labels and all their transitives for (String excludedLabel : excludedLabels) { excludedNodes.add(excludedLabel); excludedNodes.addAll(getTransitiveDependencies(excludedLabel)); } } else { // When excludeTransitives=false, only exclude the specific labels, not their transitives excludedNodes.addAll(excludedLabels); } // Process compile dependencies for (String depLabel : depsLabels) { if (!excludedNodes.contains(depLabel)) { addDependencyAndTransitives(depLabel, expectedJars, excludedNodes, excludedPatterns, excludeTransitives); } } // Process runtime dependencies for (String runtimeDepLabel : runtimeDepsLabels) { if (!excludedNodes.contains(runtimeDepLabel)) { addDependencyAndTransitives(runtimeDepLabel, expectedJars, excludedNodes, excludedPatterns, excludeTransitives); } } // Final filtering: remove any excluded labels from the result Set finalResult = new HashSet<>(); // Build a set of JAR labels that should be excluded Set excludedJarLabels = new HashSet<>(); for (String excludedLabel : excludedLabels) { if (isJarLabel(excludedLabel)) { // Direct JAR label exclusion excludedJarLabels.add(excludedLabel); } else { // Target label exclusion - find all JAR labels reachable from this target Set reachableJars = new HashSet<>(); Set visited = new HashSet<>(); findReachableJarLabels(excludedLabel, reachableJars, visited); excludedJarLabels.addAll(reachableJars); } } for (String jar : expectedJars) { // Check if this JAR corresponds to an excluded JAR label boolean isExcluded = false; for (String excludedJarLabel : excludedJarLabels) { String runtimeName = labelToRuntimeMapping.get(excludedJarLabel); if (runtimeName != null && runtimeName.equals(jar)) { isExcluded = true; break; } } if (!isExcluded) { finalResult.add(jar); } } return finalResult; } private void addDependencyAndTransitives( String depLabel, Set expectedJars, Set excludedNodes, Set excludedPatterns, boolean excludeTransitives) { // Add the direct dependency if it's not excluded if (!excludedNodes.contains(depLabel) && !isExcludedByPattern(depLabel, excludedPatterns)) { String runtimeName = labelToRuntimeMapping.get(depLabel); if (runtimeName != null) { expectedJars.add(runtimeName); } } // Add transitives, but respect exclusions Set transitives = getTransitiveDependencies(depLabel); for (String transitive : transitives) { if (!excludedNodes.contains(transitive) && !isExcludedByPattern(transitive, excludedPatterns)) { String runtimeName = labelToRuntimeMapping.get(transitive); if (runtimeName != null) { expectedJars.add(runtimeName); } } } } private Set getTransitiveDependencies(String label) { Set transitives = new HashSet<>(); Set visited = new HashSet<>(); dfs(label, visited, transitives); return transitives; } private void dfs(String node, Set transitives, Set visited) { if (visited.contains(node)) { return; } visited.add(node); Set neighbors = dependencyGraph.get(node); if (neighbors != null) { for (String neighbor : neighbors) { // Only add JAR labels to transitives, but traverse all paths if (isJarLabel(neighbor)) { transitives.add(neighbor); } // Continue traversal regardless of node type dfs(neighbor, transitives, visited); } } } private boolean isExcludedByPattern(String label, Set patterns) { String runtimeName = labelToRuntimeMapping.get(label); if (runtimeName == null) { return false; } for (String pattern : patterns) { if (runtimeName.contains(pattern)) { return true; } } return false; } public Map getLabelToRuntimeMapping() { return new HashMap<>(labelToRuntimeMapping); } public Map> getDependencyGraph() { return new HashMap<>(dependencyGraph); } private void findReachableJarLabels(String node, Set jarLabels, Set visited) { if (visited.contains(node)) { return; } visited.add(node); // If this is a JAR label, add it to the result if (isJarLabel(node)) { jarLabels.add(node); } // Continue traversing to find all reachable JAR labels Set neighbors = dependencyGraph.get(node); if (neighbors != null) { for (String neighbor : neighbors) { findReachableJarLabels(neighbor, jarLabels, visited); } } } } ================================================ FILE: springboot/deps_filter_rules/tests/test_utils/src/test/java/com/depsfilter/DependencyGraphTestConfig.java ================================================ package com.depsfilter; import java.io.IOException; import java.nio.file.Files; import java.nio.file.Paths; import java.util.*; public class DependencyGraphTestConfig { private static DependencyGraphAnalyzer analyzer; private static boolean initialized = false; private static final List STANDARD_DEPS = Arrays.asList( "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_data_jpa", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_security", "@unmanaged_deps_filter//:com_fasterxml_jackson_core_jackson_databind", "@unmanaged_deps_filter//:org_hibernate_orm_hibernate_core", "@unmanaged_deps_filter//:jakarta_servlet_jsp_jakarta_servlet_jsp_api" ); private static final List STANDARD_RUNTIME_DEPS = Arrays.asList( "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_oauth2_client", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_webflux", "@unmanaged_deps_filter//:org_springframework_boot_spring_boot_starter_actuator" ); public static void initialize() { if (initialized) { return; } try { String graphOutput = Files.readString(Paths.get("springboot/deps_filter_rules/tests/test_utils/dependency_graph.txt")); analyzer = new DependencyGraphAnalyzer(); analyzer.parseDependencyGraph(graphOutput); initialized = true; } catch (IOException e) { throw new RuntimeException("Failed to load dependency graph", e); } } public static DependencyGraphAnalyzer getAnalyzer() { if (!initialized) { initialize(); } return analyzer; } public static Set getExpectedJarsForNoFiltering() { return getAnalyzer().computeExpectedRuntimeJars( STANDARD_DEPS, STANDARD_RUNTIME_DEPS, Collections.emptySet(), Collections.emptySet(), false ); } public static Set getExpectedJarsForNoFilteringFiltered() { Set all = getExpectedJarsForNoFiltering(); Set filtered = new HashSet<>(); for (String jar : all) { if (!jar.endsWith("-sources.jar")) { filtered.add(jar); } } return filtered; } public static Set getExpectedJarsForLabelExclusions(Set excludedLabels, boolean excludeTransitives) { return getAnalyzer().computeExpectedRuntimeJars( STANDARD_DEPS, STANDARD_RUNTIME_DEPS, excludedLabels, Collections.emptySet(), excludeTransitives ); } public static Set getExpectedJarsForLabelExclusionsFiltered(Set excludedLabels, boolean excludeTransitives) { Set all = getExpectedJarsForLabelExclusions(excludedLabels, excludeTransitives); Set filtered = new HashSet<>(); for (String jar : all) { if (!jar.endsWith("-sources.jar")) { filtered.add(jar); } } return filtered; } public static Set getExpectedJarsForPathExclusions(Set excludedPatterns, boolean excludeTransitives) { return getAnalyzer().computeExpectedRuntimeJars( STANDARD_DEPS, STANDARD_RUNTIME_DEPS, Collections.emptySet(), excludedPatterns, excludeTransitives ); } public static Set getExpectedJarsForPathExclusionsFiltered(Set excludedPatterns, boolean excludeTransitives) { Set all = getExpectedJarsForPathExclusions(excludedPatterns, excludeTransitives); Set filtered = new HashSet<>(); for (String jar : all) { if (!jar.endsWith("-sources.jar")) { filtered.add(jar); } } return filtered; } public static Set getExpectedJarsForMultipleExclusions( Set excludedLabels, Set excludedPatterns, boolean excludeTransitives) { return getAnalyzer().computeExpectedRuntimeJars( STANDARD_DEPS, STANDARD_RUNTIME_DEPS, excludedLabels, excludedPatterns, excludeTransitives ); } public static Set getExpectedJarsForMultipleExclusionsFiltered( Set excludedLabels, Set excludedPatterns, boolean excludeTransitives) { Set all = getExpectedJarsForMultipleExclusions(excludedLabels, excludedPatterns, excludeTransitives); Set filtered = new HashSet<>(); for (String jar : all) { if (!jar.endsWith("-sources.jar")) { filtered.add(jar); } } return filtered; } public static List getStandardDeps() { return new ArrayList<>(STANDARD_DEPS); } public static List getStandardRuntimeDeps() { return new ArrayList<>(STANDARD_RUNTIME_DEPS); } public static Set getExpectedJarsForCustomDeps( List depsLabels, List runtimeDepsLabels, Set excludedLabels, Set excludedPatterns, boolean excludeTransitives) { return getAnalyzer().computeExpectedRuntimeJars( depsLabels, runtimeDepsLabels, excludedLabels, excludedPatterns, excludeTransitives ); } public static Set getExpectedJarsForCustomDepsFiltered( Set depsLabels, Set runtimeDepsLabels, Set excludedLabels, Set excludedPatterns, boolean excludeTransitives) { Set all = getAnalyzer().computeExpectedRuntimeJars( new ArrayList<>(depsLabels), new ArrayList<>(runtimeDepsLabels), excludedLabels, excludedPatterns, excludeTransitives ); Set filtered = new HashSet<>(); for (String jar : all) { if (!jar.endsWith("-sources.jar")) { filtered.add(jar); } } return filtered; } } ================================================ FILE: springboot/deps_filter_rules/tests/test_utils/src/test/java/com/depsfilter/DepsFilterTestHelper.java ================================================ package com.depsfilter; import java.util.ArrayList; import java.util.List; public class DepsFilterTestHelper { public static List computeClasspathDependencies() { String classpath = System.getProperty("java.class.path"); String[] classpathEntries = classpath.split(System.getProperty("path.separator")); List availableDeps = new ArrayList<>(); for (String entry : classpathEntries) { availableDeps.add(entry.replace("../", "")); } return availableDeps; } public static List getTestDeps() { return List.of( "rules_jvm_external~~maven~unmanaged_deps_filter/junit/junit/4.13.2/processed_junit-4.13.2.jar", "rules_jvm_external~~maven~unmanaged_deps_filter/org/hamcrest/hamcrest-core/1.3/processed_hamcrest-core-1.3.jar", "rules_jvm_external~~maven~unmanaged_deps_filter/org/assertj/assertj-core/3.26.0/processed_assertj-core-3.26.0.jar", "rules_jvm_external~~maven~unmanaged_deps_filter/net/bytebuddy/byte-buddy/1.14.16/processed_byte-buddy-1.14.16.jar", "rules_java~~toolchains~remote_java_tools/java_tools/Runner_deploy.jar", "springboot/deps_filter_rules/tests/test_utils/libtest_utils.jar" ); } } ================================================ FILE: springboot/deps_filter_rules/tests/test_utils/verification_utils.bzl ================================================ load("@bazel_skylib//lib:unittest.bzl", "asserts") def verify_jars(env, actual_jars, expected_jars, jar_field): expected_jars = sorted(expected_jars) actual_jars = sorted(actual_jars) asserts.equals(env, type(expected_jars), type(actual_jars), "JAR type mismatch: {}".format(jar_field)) asserts.equals(env, expected_jars, actual_jars, "JAR contents mismatch: {}".format(jar_field)) def verify_runtime_and_compile_jars(ctx, env, javainfo, expected_compile_jars = None, expected_full_compile_jars = None, expected_transitive_compile_jars = None, expected_transitive_runtime_jars = None): """Helper function to verify runtime and compile time JARs.""" transitive_runtime_jars = [jar.basename for jar in javainfo.transitive_runtime_jars.to_list()] verify_jars(env, transitive_runtime_jars, expected_transitive_runtime_jars, "transitive_runtime_jars") transitive_compile_jars = [jar.basename for jar in javainfo.transitive_compile_time_jars.to_list()] verify_jars(env, transitive_compile_jars, expected_transitive_compile_jars, "transitive_compile_jars") compile_jars = [jar.basename for jar in javainfo.compile_jars.to_list()] verify_jars(env, compile_jars, expected_compile_jars, "compile_jars") full_compile_jars = [jar.basename for jar in javainfo.full_compile_jars.to_list()] verify_jars(env, full_compile_jars, expected_full_compile_jars, "full_compile_jars") def verify_jars_and_dropped_counts(env, expected, expected_compile_dropped = "0", expected_full_compile_dropped = "0", expected_transitive_compile_dropped = "0", expected_transitive_runtime_dropped = "0"): dropped_counts = { "compile_jars_dropped": expected["compile_jars_dropped"], "full_compile_jars_dropped": expected["full_compile_jars_dropped"], "transitive_compile_jars_dropped": expected["transitive_compile_jars_dropped"], "transitive_runtime_jars_dropped": expected["transitive_runtime_jars_dropped"], } verify_dropped_counts(env, dropped_counts, expected_compile_dropped, expected_full_compile_dropped, expected_transitive_compile_dropped, expected_transitive_runtime_dropped) def verify_dropped_counts(env, dropped_counts, expected_compile_dropped = "0", expected_full_compile_dropped = "0", expected_transitive_compile_dropped = "0", expected_transitive_runtime_dropped = "0"): """ Verifies that the correct number of JARs were dropped for each type. """ if expected_compile_dropped == "0": asserts.equals(env, dropped_counts["compile_jars_dropped"], 0, "Expected no compile JARs to be dropped, but {} were dropped".format(dropped_counts["compile_jars_dropped"])) elif expected_compile_dropped == ">0": asserts.true(env, dropped_counts["compile_jars_dropped"] > 0, "Expected some compile JARs to be dropped, but {} were dropped".format(dropped_counts["compile_jars_dropped"])) if expected_full_compile_dropped == "0": asserts.equals(env, dropped_counts["full_compile_jars_dropped"], 0, "Expected no full compile JARs to be dropped, but {} were dropped".format(dropped_counts["full_compile_jars_dropped"])) elif expected_full_compile_dropped == ">0": asserts.true(env, dropped_counts["full_compile_jars_dropped"] > 0, "Expected some full compile JARs to be dropped, but {} were dropped".format(dropped_counts["full_compile_jars_dropped"])) if expected_transitive_compile_dropped == "0": asserts.equals(env, dropped_counts["transitive_compile_jars_dropped"], 0, "Expected no transitive compile JARs to be dropped, but {} were dropped".format(dropped_counts["transitive_compile_jars_dropped"])) elif expected_transitive_compile_dropped == ">0": asserts.true(env, dropped_counts["transitive_compile_jars_dropped"] > 0, "Expected some transitive compile JARs to be dropped, but {} were dropped".format(dropped_counts["transitive_compile_jars_dropped"])) if expected_transitive_runtime_dropped == "0": asserts.equals(env, dropped_counts["transitive_runtime_jars_dropped"], 0, "Expected no transitive runtime JARs to be dropped, but {} were dropped".format(dropped_counts["transitive_runtime_jars_dropped"])) elif expected_transitive_runtime_dropped == ">0": asserts.true(env, dropped_counts["transitive_runtime_jars_dropped"] > 0, "Expected some transitive runtime JARs to be dropped, but {} were dropped".format(dropped_counts["transitive_runtime_jars_dropped"])) def update_jar_name(jar_name, new_jar_name, jar_list): for i, jar in enumerate(jar_list): if jar_name in jar: jar_list[i] = jar.replace(jar_name, new_jar_name) return jar_list def _collect_filtered_jars(existing_jars, jar_list, excluded_jars = [], exclusion_patterns = []): dropped_count = 0 for jar in jar_list: jar_name = jar.basename if jar_name not in existing_jars and jar_name not in excluded_jars: should_include = True for pattern in exclusion_patterns: if pattern in jar_name: should_include = False dropped_count += 1 break if should_include: existing_jars.append(jar_name) else: dropped_count += 1 elif jar_name in excluded_jars: dropped_count += 1 return existing_jars, dropped_count def _compute_excluded_jars_from_labels(ctx): excluded_compile_jars = [] excluded_full_compile_jars = [] excluded_transitive_compile_jars = [] excluded_transitive_runtime_jars = [] if not ctx.attr.deps_exclude_labels: return { "compile_jars": excluded_compile_jars, "full_compile_jars": excluded_full_compile_jars, "transitive_compile_jars": excluded_transitive_compile_jars, "transitive_runtime_jars": excluded_transitive_runtime_jars, } for excluded_label in ctx.attr.deps_exclude_labels: java_info = excluded_label[JavaInfo] if ctx.attr.exclude_transitives: # Exclude the dep and its transitives excluded_compile_jars, _ = _collect_filtered_jars(excluded_compile_jars, java_info.compile_jars.to_list()) excluded_full_compile_jars, _ = _collect_filtered_jars(excluded_full_compile_jars, java_info.full_compile_jars.to_list()) excluded_transitive_compile_jars, _ = _collect_filtered_jars(excluded_transitive_compile_jars, java_info.transitive_compile_time_jars.to_list()) excluded_transitive_runtime_jars, _ = _collect_filtered_jars(excluded_transitive_runtime_jars, java_info.transitive_runtime_jars.to_list()) else: # Only exclude the direct dep JARs excluded_compile_jars, _ = _collect_filtered_jars(excluded_compile_jars, java_info.compile_jars.to_list()) excluded_full_compile_jars, _ = _collect_filtered_jars(excluded_full_compile_jars, java_info.full_compile_jars.to_list()) excluded_transitive_compile_jars, _ = _collect_filtered_jars(excluded_transitive_compile_jars, java_info.compile_jars.to_list()) excluded_transitive_runtime_jars, _ = _collect_filtered_jars(excluded_transitive_runtime_jars, java_info.full_compile_jars.to_list()) return { "compile_jars": excluded_compile_jars, "full_compile_jars": excluded_full_compile_jars, "transitive_compile_jars": excluded_transitive_compile_jars, "transitive_runtime_jars": excluded_transitive_runtime_jars, } def compute_expected_jars(ctx, test_lib_name = None): """ Computes expected JARs after applying all exclusions (labels and patterns). """ excluded_jars = _compute_excluded_jars_from_labels(ctx) exclusion_patterns = ctx.attr.deps_exclude_paths or [] if test_lib_name == None: expected_compile_jars = [] expected_full_compile_jars = [] expected_transitive_compile_jars = [] expected_transitive_runtime_jars = [] else: test_lib_compile_jar = "lib" + test_lib_name + "-hjar.jar" test_lib_full_compile_jar = "lib" + test_lib_name + ".jar" expected_compile_jars = [test_lib_compile_jar] expected_full_compile_jars = [test_lib_full_compile_jar] expected_transitive_compile_jars = [test_lib_compile_jar] expected_transitive_runtime_jars = [test_lib_full_compile_jar] compile_jars_dropped = 0 full_compile_jars_dropped = 0 transitive_compile_jars_dropped = 0 transitive_runtime_jars_dropped = 0 # Process compile-time deps for dep in ctx.attr.deps_labels: java_info = dep[JavaInfo] if test_lib_name == None: expected_compile_jars, dropped = _collect_filtered_jars(expected_compile_jars, java_info.compile_jars.to_list(), excluded_jars["compile_jars"], exclusion_patterns) compile_jars_dropped += dropped expected_full_compile_jars, dropped = _collect_filtered_jars(expected_full_compile_jars, java_info.full_compile_jars.to_list(), excluded_jars["full_compile_jars"], exclusion_patterns) full_compile_jars_dropped += dropped else: _, dropped = _collect_filtered_jars([], java_info.compile_jars.to_list(), excluded_jars["compile_jars"], exclusion_patterns) compile_jars_dropped += dropped _, dropped = _collect_filtered_jars([], java_info.full_compile_jars.to_list(), excluded_jars["full_compile_jars"], exclusion_patterns) full_compile_jars_dropped += dropped expected_transitive_compile_jars, dropped = _collect_filtered_jars(expected_transitive_compile_jars, java_info.transitive_compile_time_jars.to_list(), excluded_jars["transitive_compile_jars"], exclusion_patterns) transitive_compile_jars_dropped += dropped expected_transitive_runtime_jars, dropped = _collect_filtered_jars(expected_transitive_runtime_jars, java_info.transitive_runtime_jars.to_list(), excluded_jars["transitive_runtime_jars"], exclusion_patterns) transitive_runtime_jars_dropped += dropped # Process runtime deps for runtime_dep in ctx.attr.runtime_deps_labels: java_info = runtime_dep[JavaInfo] expected_transitive_runtime_jars, dropped = _collect_filtered_jars(expected_transitive_runtime_jars, java_info.transitive_runtime_jars.to_list(), excluded_jars["transitive_runtime_jars"], exclusion_patterns) transitive_runtime_jars_dropped += dropped # Note: Runtime deps typically don't contribute to compile-time transitives return { "compile_jars": expected_compile_jars, "full_compile_jars": expected_full_compile_jars, "transitive_compile_jars": expected_transitive_compile_jars, "transitive_runtime_jars": expected_transitive_runtime_jars, "compile_jars_dropped": compile_jars_dropped, "full_compile_jars_dropped": full_compile_jars_dropped, "transitive_compile_jars_dropped": transitive_compile_jars_dropped, "transitive_runtime_jars_dropped": transitive_runtime_jars_dropped, } ================================================ FILE: springboot/deps_filter_rules_legacy/BUILD ================================================ load("//springboot/deps_filter_rules_legacy:deps_filter.bzl", "deps_filter") load("//springboot/deps_filter_rules_legacy:deps_filter_disable_transitives.bzl", "deps_filter_disable_transitives") deps = [ "@maven//:org_springframework_spring_jdbc", "@maven//:org_springframework_spring_web", ] test_deps = [ "@maven//:junit_junit", "@maven//:org_assertj_assertj_core", ] deps_filter( name = "filtered_test_deps_with_transitives_excluded", deps = [ "@maven//:org_springframework_spring_jdbc", "@maven//:org_springframework_spring_web", ], deps_exclude_labels = [ "@maven//:org_springframework_spring_web", # share transitives with spring-jdbc ], exclude_transitives = True, testonly = True, ) deps_filter( name = "filtered_test_deps_without_transitives_excluded", deps = [ "@maven//:org_springframework_spring_jdbc", "@maven//:org_springframework_spring_web", ], deps_exclude_labels = [ "@maven//:org_springframework_spring_web", # share transitives with spring-jdbc ], exclude_transitives = False, testonly = True, ) deps_filter_disable_transitives( name = "filtered_deps_disable_transitives_case_A", deps = [ "@maven//:org_springframework_spring_jdbc", "@maven//:org_springframework_spring_web", ], deps_to_exclude_transitives = [ "@maven//:org_springframework_spring_jdbc", "@maven//:org_springframework_spring_web", ], testonly = True, ) deps_filter_disable_transitives( name = "filtered_deps_disable_transitives_case_B", deps = [ "@maven//:org_springframework_spring_jdbc", "@maven//:org_springframework_spring_web", ], deps_to_exclude_transitives = [ # "@maven//:org_springframework_spring_jdbc", "@maven//:org_springframework_spring_web", ], testonly = True, ) deps_filter_disable_transitives( name = "filtered_deps_disable_transitives_case_C", deps = [ "@maven//:org_springframework_spring_jdbc", "@maven//:org_springframework_spring_web", ], deps_to_exclude_transitives = [ "@maven//:org_springframework_spring_jdbc", # "@maven//:org_springframework_spring_web", ], testonly = True, ) deps_filter_disable_transitives( name = "filtered_deps_disable_transitives_case_D", deps = [ "@maven//:org_springframework_spring_jdbc", "@maven//:org_springframework_spring_web", ], testonly = True, ) java_test( name = "TransitiveDepsFilterCaseA", size = "small", srcs = ["src/test/java/com/depsfilter/TransitiveDepsFilterCaseA.java"], deps = [":filtered_deps_disable_transitives_case_A"] + test_deps, ) java_test( name = "TransitiveDepsFilterCaseB", size = "small", srcs = ["src/test/java/com/depsfilter/TransitiveDepsFilterCaseB.java"], deps = [":filtered_deps_disable_transitives_case_B"] + test_deps, ) java_test( name = "TransitiveDepsFilterCaseC", size = "small", srcs = ["src/test/java/com/depsfilter/TransitiveDepsFilterCaseC.java"], deps = [":filtered_deps_disable_transitives_case_C"] + test_deps, ) java_test( name = "TransitiveDepsFilterCaseD", size = "small", srcs = ["src/test/java/com/depsfilter/TransitiveDepsFilterCaseD.java"], deps = [":filtered_deps_disable_transitives_case_D"] + test_deps, ) java_test( name = "DepsFilterWithTransitivesExclusionTest", size = "small", srcs = ["src/test/java/com/depsfilter/DepsFilterWithTransitivesExclusionTest.java"], deps = [":filtered_test_deps_with_transitives_excluded"] + test_deps, ) java_test( name = "DepsFilterWithoutTransitivesExclusionTest", size = "small", srcs = ["src/test/java/com/depsfilter/DepsFilterWithoutTransitivesExclusionTest.java"], deps = [":filtered_test_deps_without_transitives_excluded"] + test_deps, ) ================================================ FILE: springboot/deps_filter_rules_legacy/README.md ================================================ ## SpringBoot Deps Filters > **⚠️ Recommendation: Use `@deps_filter_rules/` instead of this legacy rule.** This rule is maintained for backward compatibility only. > > The legacy `deps_filter` rule has a drawback: it resolves transitive dependencies in the filtered output, which contrasts the Bazel’s standard model, where transitive dependencies are not automatically available for direct use. If a target uses a transitive dependency at compile time without explicitly declaring it, Bazel will throw an "indirect dependency" error and will recommend that as a direct dependency. > > The new `@deps_filter_rules/` filters out unwanted Java dependency JARs (by label or path pattern) while preserving the correct JavaInfo structure for Bazel builds, ensuring proper dependency declarations and avoiding indirect dependency issues. This directory contains implementations of deps filters. Deps filters are used to remove unwanted dependencies from the dependency graph of your springboot application. The topic of unwanted classes and dependencies is explained in detail on this document: - [Unwanted Classes and Dependencies](../unwanted_classes.md) ### deps_filter This is the standard filter to use for excluding dependencies. For each listed dependency, the dependency is excluded. Optionally, the transitives of each excluded dependency is also excluded. See the full docs for more information: - [deps_filter documentation](deps_filter.md) ### deps_filter_disable_transitives This filter is similar to *deps_filter*, but does not exclude the listed dependencies. It excludes the transitives of the listed dependencies. See the full docs for more information: - [deps_filter_disable_transitives documentation](deps_filter_disable_transitives.md) ================================================ FILE: springboot/deps_filter_rules_legacy/deps_filter.bzl ================================================ def _depaggregator_rule_impl(merged, ctx): """ This method processes declared deps and their transitive closures to assemble a cohesive set of jars essential for the build process. During this process, it excludes deps specified in 'deps_exclude_labels', which lists jar labels to be omitted from packaging due to issues that cannot be resolved upstream. If 'exclude_transitives' is set to 'true' (default: 'false'), any transitive deps that are only required by excluded deps are also omitted, ensuring that only necessary transitives are included in the final package. It uses 'deps_exclude_paths' to exclude deps based on partial filename matches, ensuring problematic files are also excluded from the build. This method ensures that only necessary deps are included for the build process. """ exclude_transitives = ctx.attr.exclude_transitives # list to store jars to be included and a dictionary to track excluded jars jars = [] excludes = {} if exclude_transitives: # Dictionary to track transitive dependency paths that should be excluded transitives_excludes = {} # List to store deps info for deps present in 'deps_exclude_labels' direct_excludes = [] # Iterate through the deps specified in 'deps_exclude_labels' to collect # jars that should be excluded from the final set. for exclusion_info in ctx.attr.deps_exclude_labels: # For each excluded dependency, add its compile-time JARs to the exclusion list for compile_jar in exclusion_info[JavaInfo].full_compile_jars.to_list(): excludes[compile_jar.path] = True if exclude_transitives: # Mark all transitives of the current dependency as excluded # This list will be updated later based on transitives of non-excluded deps direct_excludes.append(str(exclusion_info)) for transitive_jar in exclusion_info[JavaInfo].transitive_runtime_jars.to_list(): transitives_excludes[transitive_jar.path] = True if exclude_transitives: # Iterate over all deps, for non-excluded deps, mark their transitives as included. for deps_info in ctx.attr.deps: # skip the current dependency if it is listed in 'deps_exclude_labels'. if str(deps_info) in direct_excludes: continue # For non-excluded deps, mark them and their transitive deps as included (not to be excluded) # (transitive_runtime_jars includes both the primary JAR and its transitive deps) for transitive_jar in deps_info[JavaInfo].transitive_runtime_jars.to_list(): if transitive_jar.path in transitives_excludes: transitives_excludes[transitive_jar.path] = False # update the excludes list for dep_path in transitives_excludes: # print("Transitive:", str(dep_path), "is excluded", transitives_excludes[dep_path]) if transitives_excludes[dep_path]: excludes[dep_path] = True # compute the final set of jars for dep in merged.transitive_runtime_jars.to_list(): # If the current JAR is in the exclusion list, skip it (do not include it) if excludes.get(dep.path, None) != None: pass else: # Default to including the JAR unless a pattern match excludes it include = True for pattern in ctx.attr.deps_exclude_paths: if dep.path.find(pattern) > -1: include = False break if include: jars.append(dep) return jars def _deps_filter_impl(ctx): """ This rule filters out specified deps and JARs from the compile-time and runtime deps. It utilizes the 'deps_exclude_labels' attribute to omit specific JAR labels and the 'deps_exclude_paths' attribute to exclude deps based on partial paths in their filenames. If 'exclude_transitives' is set to `True` (default: `False`), any transitive deps solely required by the deps in 'deps_exclude_labels' are also excluded. These exclusions ensure the final collection includes only the necessary elements for the build process, eliminating problematic deps. """ if len(ctx.attr.deps) == 0: fail("Error: 'deps' cannot be an empty list") # magical incantation for getting upstream transitive closure of java deps merged = java_common.merge([dep[java_common.provider] for dep in ctx.attr.deps]) runtime_dep_merged = java_common.merge([runtime_dep[java_common.provider] for runtime_dep in ctx.attr.runtime_deps]) compile_time_jars = _depaggregator_rule_impl(merged, ctx) runtime_jars = _depaggregator_rule_impl(runtime_dep_merged, ctx) if len(compile_time_jars) == 0: fail("Error: The rule must return at least one compile-time JAR. Excluding all compile-time dependencies is not allowed.") return [ DefaultInfo(files = depset(compile_time_jars,)), JavaInfo( compile_jar = None, output_jar = compile_time_jars[0], # output jar must be non-empty, adding a dummy value to it exports = [JavaInfo(source_jar = jar, compile_jar = jar, output_jar = jar) for jar in compile_time_jars], runtime_deps = [JavaInfo(source_jar = jar, compile_jar = jar, output_jar = jar) for jar in runtime_jars], deps = [JavaInfo(source_jar = jar, compile_jar = jar, output_jar = jar) for jar in compile_time_jars], ), ] deps_filter = rule( implementation = _deps_filter_impl, attrs = { "deps": attr.label_list(providers = [java_common.provider]), "runtime_deps": attr.label_list(providers = [java_common.provider], allow_empty = True), "deps_exclude_labels": attr.label_list(providers = [java_common.provider], allow_empty = True), "deps_exclude_paths": attr.string_list(), "exclude_transitives": attr.bool(default = False), }, ) ================================================ FILE: springboot/deps_filter_rules_legacy/deps_filter.md ================================================ # `deps_filter` Rule ## Overview The `deps_filter` rule provides a way to filter java dependencies in Bazel projects, ensuring only the necessary ones are included in the build. This rule can be referenced by other java targets, such as `java_library` and helps to remove problematic or unwanted dependencies, offering better control over dependency graphs. It removes Java dependencies from your dependency graph. This is done when you have knowledge that Bazel does not, specifically that your application does not need a dependency at runtime. This is useful in cases where: - You want to exclude a dependency for a specific reason (it has a vulnerability) - There are multiple versions of a dependency on the classpath (dupe classes) and you want to exclude the unfavored one. ## Rule Definition The rule is defined as `dep_filter` in `deps_filter.bzl`. It filters out specified deps and JARs from the compile-time and runtime deps. It utilizes the `deps_exclude_labels` attribute to omit specific JAR labels and the `deps_exclude_paths` attribute to exclude dependencies based on partial paths in their filenames. If `exclude_transitives` is set to `True` (default: `False`), any transitive dependencies solely required by the dependencies in `deps_exclude_labels` are also excluded. These exclusions ensure the final collection includes only the necessary elements for the build process, eliminating problematic dependencies. ``` deps_filter( name = , deps = , runtime_deps = , deps_exclude_labels = , deps_exclude_paths = , exclude_transitives = , testonly = , ) ``` ### Attributes: - `name` (Required): Name of the target. - `deps` (Required): List of dependencies to include. - `runtime_deps` (Optional): List of runtime dependencies to include. - `deps_exclude_labels` (Optional): Dependencies to exclude from the build. - `deps_exclude_paths` (Optional): Filename patterns for excluding dependencies. - `exclude_transitives` (Optional, Default: `False`): If `True`, transitive dependencies of excluded dependencies are also removed, unless needed by other included dependencies. - `testonly` (Optional, Default: `False`): Restricts usage to test environments. ### Behavior 1. **Excludes Specific Dependencies**: - Removes any dependencies listed in `deps_exclude_labels`. 2. **Handles Transitive Dependencies**: - If `exclude_transitives` is `True`, transitive dependencies that are only required by excluded dependencies are removed. - If `False`, transitive dependencies remain in the build. 3. **Filename-Based Exclusions**: - Dependencies matching patterns in `deps_exclude_paths` are excluded. ## Adding to Your Project ### Step 1: Add `rules_spring` to your workspace: Follow the steps mentioned [here](../../README.md#loading-the-spring-rules-in-your-workspace). ### Step 2: Load the `deps_filter` rule in your BUILD file: ``` load("@rules_spring//springboot/deps_filter_rules_legacy:deps_filter.bzl", "deps_filter") ``` ### Step 3: Define and reference the `deps_filter` rule in other targets (e.g., `java_library`) to manage their dependencies: ``` load("@rules_spring//springboot/deps_filter_rules_legacy:deps_filter.bzl", "deps_filter") deps = [ ... ] runtime_deps = [ ... ] deps_filter( name = "filtered_deps", deps = deps, runtime_deps = runtime_deps, deps_exclude_labels = [ "@maven//:some_dep_you_dont_want", ], deps_exclude_paths = [ "javax-servlet", ], exclude_transitives = True, ) java_library( name = "my_library", deps = [":filtered_deps"], # <--- KEY LINE: USE YOUR FILTERED DEPS HERE! ... ) # the filter is not specific to springboot apps, but is often used for springboot # due to the complexity of classpaths in springboot apps salesforce_springboot( name = "myspringboot_app", java_library = ":my_library", ) ``` ## Example Usage ### Example 1: Without Excluding Transitives ``` deps_filter( name = "filtered_deps", deps = [ "@maven//:org_springframework_spring_jdbc", "@maven//:org_springframework_spring_web", ], deps_exclude_labels = [ "@maven//:org_springframework_spring_web", ], exclude_transitives = False, testonly = True, ) ``` #### Behavior: `org_springframework_spring_web` is excluded, but its transitive dependencies remain. ### Example 2: With Excluding Transitives ``` deps_filter( name = "filtered_deps", deps = [ "@maven//:org_springframework_spring_jdbc", "@maven//:org_springframework_spring_web", ], deps_exclude_labels = [ "@maven//:org_springframework_spring_web", ], exclude_transitives = True, testonly = True, ) ``` #### Behavior: Both `org_springframework_spring_web` and its transitive dependencies are excluded, except those required by `org_springframework_spring_jdbc`. ================================================ FILE: springboot/deps_filter_rules_legacy/deps_filter_disable_transitives.bzl ================================================ def _depaggregator_rule_impl(merged, deps, ctx): """ This method processes declared dependencies and their transitive closures to assemble a cohesive set of jars essential for the build process. During this process, it excludes all the transitives of dependencies specified in 'deps_to_exclude_transitives'. """ jars = [] excludes = {} # exclude transitives of the specified deps deps_info_to_exclude_transitives = [] for dep_info in ctx.attr.deps_to_exclude_transitives: deps_info_to_exclude_transitives.append(str(dep_info)) for transitive_jar in dep_info[JavaInfo].transitive_runtime_jars.to_list(): excludes[transitive_jar.path] = True # process the deps whose transitives are to be kept for dep_info in deps: # always keep the specified deps for compile_jar in dep_info[JavaInfo].full_compile_jars.to_list(): if compile_jar.path in excludes: excludes[compile_jar.path] = False if str(dep_info) not in deps_info_to_exclude_transitives: for transitive_jar in dep_info[JavaInfo].transitive_runtime_jars.to_list(): if transitive_jar.path in excludes: excludes[transitive_jar.path] = False for dep in merged.transitive_runtime_jars.to_list(): if excludes.get(dep.path, None) != None and excludes[dep.path]: pass else: jars.append(dep) return jars def _deps_filter_disable_transitives_impl(ctx): """ This rule filters out transitives of the specified dependencies and JARs from the compile-time and runtime dependencies. """ if len(ctx.attr.deps) == 0: fail("Error: 'deps' cannot be an empty list") # deps whose transitives are to be excluded must be a subset of deps + runtime_deps deps_info_list = [] for dep_info in ctx.attr.deps: deps_info_list.append(str(dep_info)) for dep_info in ctx.attr.runtime_deps: deps_info_list.append(str(dep_info)) for dep_info in ctx.attr.deps_to_exclude_transitives: if str(dep_info) not in deps_info_list: fail("Error: 'deps' specified in deps_to_exclude_transitives must be subset of deps + runtime_deps") # magical incantation for getting upstream transitive closure of java deps merged = java_common.merge([dep[java_common.provider] for dep in ctx.attr.deps]) runtime_dep_merged = java_common.merge([runtime_dep[java_common.provider] for runtime_dep in ctx.attr.runtime_deps]) compile_time_jars = _depaggregator_rule_impl(merged, ctx.attr.deps, ctx) runtime_jars = _depaggregator_rule_impl(runtime_dep_merged, ctx.attr.runtime_deps, ctx) if len(compile_time_jars) == 0: fail("Error: The rule must return at least one compile-time JAR. Excluding all compile-time dependencies is not allowed.") return [ DefaultInfo(files = depset(compile_time_jars,)), JavaInfo( compile_jar = None, output_jar = compile_time_jars[0], # output jar must be non-empty, adding a dummy value to it exports = [JavaInfo(source_jar = jar, compile_jar = jar, output_jar = jar) for jar in compile_time_jars], runtime_deps = [JavaInfo(source_jar = jar, compile_jar = jar, output_jar = jar) for jar in runtime_jars], deps = [JavaInfo(source_jar = jar, compile_jar = jar, output_jar = jar) for jar in compile_time_jars], ), ] deps_filter_disable_transitives = rule( implementation = _deps_filter_disable_transitives_impl, attrs = { "deps": attr.label_list(providers = [java_common.provider]), "runtime_deps": attr.label_list(providers = [java_common.provider], allow_empty = True), "deps_to_exclude_transitives": attr.label_list(providers = [java_common.provider], allow_empty = True), }, ) ================================================ FILE: springboot/deps_filter_rules_legacy/deps_filter_disable_transitives.md ================================================ # `deps_filter_disable_transitives` Rule ## Overview The `deps_filter_disable_transitives` rule gives you control over transitive dependencies by disabling their resolution for specific dependencies. Inspired by [Gradle's transitive dependency resolution rule](https://docs.gradle.org/current/userguide/resolution_rules.html#sec:disabling-resolution-transitive-dependencies), it’s useful for excluding problematic dependencies from your project. ## Rule Definition This rule filters out transitives of the specified dependencies and JARs from the compile-time and runtime dependencies. ``` deps_filter_disable_transitives( name = , deps = , runtime_deps = , deps_to_exclude_transitives = , testonly = , ) ``` ### Attributes: - `name` (Required): Name of the target. - `deps` (Required): List of dependencies to include. - `runtime_deps` (Optional): List of runtime dependencies to include. - `deps_to_exclude_transitives` (Optional): List of dependencies for which transitive dependencies should be excluded. (must be a subset of `deps` + `runtime_deps`) - `testonly` (Optional, Default: False): Restricts usage to test environments. ## Adding to Your Project ### Step 1: Add `rules_spring` to your workspace: Follow the steps mentioned [here](../../README.md#loading-the-spring-rules-in-your-workspace). ### Step 2: Load the `deps_filter_disable_transitives` rule in your BUILD file: ``` load("@rules_spring//springboot/deps_filter_rules_legacy:deps_filter_disable_transitives.bzl", "deps_filter_disable_transitives") ``` ### Step 3: Define and reference the `deps_filter_disable_transitives` in other targets (e.g., `java_library`) to manage their dependencies: ``` load("@rules_spring//springboot/deps_filter_rules_legacy:deps_filter_disable_transitives.bzl", "deps_filter_disable_transitives") deps = [ ... ] runtime_deps = [ ... ] deps_filter_disable_transitives( name = "filtered_deps", deps = deps, runtime_deps = runtime_deps, deps_to_exclude_transitives = ["@maven//:some_dep_whose_transitives_you_dont_want",] ) java_library( name = "my_library", deps = [":filtered_deps"], # <--- KEY LINE: USE YOUR FILTERED DEPS HERE! ... ) # the filter is not specific to springboot apps, but is often used for springboot # due to the complexity of classpaths in springboot apps salesforce_springboot( name = "myspringboot_app", java_library = ":my_library", ) ``` ## Example Usage ### Example 1 ``` deps_filter_disable_transitives( name = "filtered_deps_disable_transitives_case_A", deps = [ "@maven//:org_springframework_spring_jdbc", "@maven//:org_springframework_spring_web", ], deps_to_exclude_transitives = [ "@maven//:org_springframework_spring_jdbc", "@maven//:org_springframework_spring_web", ], ) ``` #### Behavior: The build includes `@maven//:org_springframework_spring_jdbc` and `@maven//:org_springframework_spring_web`, but all transitive dependencies of both are excluded. ### Example 2 ``` deps_filter_disable_transitives( name = "filtered_deps_disable_transitives_case_A", deps = [ "@maven//:org_springframework_spring_jdbc", "@maven//:org_springframework_spring_web", ], deps_to_exclude_transitives = [ "@maven//:org_springframework_spring_web", ], ) ``` #### Behavior: - The build includes `@maven//:org_springframework_spring_jdbc` and its transitive dependencies, as well as `@maven//:org_springframework_spring_web`. - Transitive dependencies of `@maven//:org_springframework_spring_web` are excluded, but transitive dependencies of `@maven//:org_springframework_spring_jdbc` are included. ### Example 3 ``` deps_filter_disable_transitives( name = "filtered_deps_disable_transitives_case_A", deps = [ "@maven//:org_springframework_spring_jdbc", "@maven//:org_springframework_spring_web", ], ) ``` #### Behavior: - The build includes `@maven//:org_springframework_spring_jdbc` and `@maven//:org_springframework_spring_web`, along with their respective transitive dependencies. - No dependencies are excluded. ================================================ FILE: springboot/deps_filter_rules_legacy/src/test/java/com/depsfilter/DepsFilterWithTransitivesExclusionTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.ArrayList; import java.util.List; import org.junit.Test; public class DepsFilterWithTransitivesExclusionTest { private List testDeps; private List depsList; private List excludedDirectDeps; private List nonexcludedDirectDeps; private List transitivesOfExcludedDirectDeps; private List transitivesOfNonExcludedDirectDeps; @Test public void testTransitivesExclusion() { /* Tests the 'deps_filter' rule with its 'exclude_transitives' attribute set to True. Corresponds to the 'filtered_test_deps_with_transitives_excluded' rule in the BUILD file: deps_filter( name = "filtered_test_deps_with_transitives_excluded", deps = [ "@maven//:org_springframework_spring_jdbc", "@maven//:org_springframework_spring_web", ], deps_exclude_labels = [ "@maven//:org_springframework_spring_web", # share transitives with spring-jdbc ], exclude_transitives = True, testonly = True, ) This test verifies: - Build-time deps include "@maven//:org_springframework_spring_jdbc" and its transitive deps - Excluded deps include "@maven//:org_springframework_spring_web" and its transitive deps, except those that are also transitive deps of "@maven//:org_springframework_spring_jdbc" This is validated by checking the available deps in the code. */ initialTestSetup(); List expectedExcludedTransitives = getExcludedTransitives(); List expectedNonExcludedTransitives = getNonExcludedTransitives(); List availableDeps = computeClasspathDependencies(); // Ensure that excluded direct deps and their transitive deps (if not required by other non-excluded deps) // are not present in the available dependencies. for (String excludedDep : excludedDirectDeps) { assertThat(availableDeps).doesNotContain(excludedDep); } for (String excludedTransitive : expectedExcludedTransitives) { assertThat(availableDeps).doesNotContain(excludedTransitive); } // Ensure that non-excluded direct deps and their transitive deps are present in the available deps. for (String nonExcludedDep : nonexcludedDirectDeps) { assertThat(availableDeps).contains(nonExcludedDep); } for (String nonExcludedTransitive : expectedNonExcludedTransitives) { assertThat(availableDeps).contains(nonExcludedTransitive); } // Ensure that combined list of testDeps, depsList, expectedExcludedTransitives, and // expectedNonExcludedTransitives is equal to the combined list of availableDeps, // excludedDirectDeps, and expectedExcludedTransitives. List expectedCombinedDepsList = new ArrayList<>(); List actualCombinedDepsList = new ArrayList<>(); expectedCombinedDepsList.addAll(testDeps); expectedCombinedDepsList.addAll(depsList); expectedCombinedDepsList.addAll(expectedNonExcludedTransitives); expectedCombinedDepsList.addAll(expectedExcludedTransitives); actualCombinedDepsList.addAll(availableDeps); actualCombinedDepsList.addAll(excludedDirectDeps); actualCombinedDepsList.addAll(expectedExcludedTransitives); assertThat(actualCombinedDepsList).containsExactlyInAnyOrderElementsOf(expectedCombinedDepsList); } private List getExcludedTransitives() { // Exclude transitive deps of excluded deps, except those of non-excluded deps or non-excluded deps themselves List expectedExcludedTransitives = new ArrayList<>(); for (String transitive : transitivesOfExcludedDirectDeps) { if ((!transitivesOfNonExcludedDirectDeps.contains(transitive)) && (!nonexcludedDirectDeps.contains( transitive))) { expectedExcludedTransitives.add(transitive); } } return expectedExcludedTransitives; } private List getNonExcludedTransitives() { // Transitive deps of non-excluded deps List expectedNonExcludedTransitives = new ArrayList<>(); for (String transitive : transitivesOfNonExcludedDirectDeps) { expectedNonExcludedTransitives.add(transitive); } return expectedNonExcludedTransitives; } private List computeClasspathDependencies() { String classpath = System.getProperty("java.class.path"); String[] classpathEntries = classpath.split(System.getProperty("path.separator")); List availableDeps = new ArrayList<>(); for (String entry : classpathEntries) { availableDeps.add(entry.replace("../", "")); } return availableDeps; } private void initialTestSetup() { // required to run the test - specified in the test target testDeps = List.of("springboot/deps_filter_rules_legacy/DepsFilterWithTransitivesExclusionTest.jar", "rules_jvm_external~~maven~maven/junit/junit/4.13.2/processed_junit-4.13.2.jar", "rules_jvm_external~~maven~maven/org/hamcrest/hamcrest-core/2.2/processed_hamcrest-core-2.2.jar", "rules_jvm_external~~maven~maven/org/hamcrest/hamcrest/2.2/processed_hamcrest-2.2.jar", "rules_jvm_external~~maven~maven/org/assertj/assertj-core/3.25.3/processed_assertj-core-3.25.3.jar", "rules_jvm_external~~maven~maven/net/bytebuddy/byte-buddy/1.14.12/processed_byte-buddy-1.14.12.jar", "rules_java~~toolchains~remote_java_tools/java_tools/Runner_deploy.jar" ); // specified in the 'deps' attribute of 'deps_filter' depsList = List.of( "rules_jvm_external~~maven~maven/org/springframework/spring-jdbc/6.1.14/processed_spring-jdbc-6.1.14.jar", "rules_jvm_external~~maven~maven/org/springframework/spring-web/6.1.14/processed_spring-web-6.1.14.jar" ); // specified in the 'deps_exclude_labels' attribute of 'deps_filter' excludedDirectDeps = List.of( "rules_jvm_external~~maven~maven/org/springframework/spring-web/6.1.14/processed_spring-web-6.1.14.jar" ); // deps that are not excluded = depsList - excludedDirectDeps nonexcludedDirectDeps = List.of( "rules_jvm_external~~maven~maven/org/springframework/spring-jdbc/6.1.14/processed_spring-jdbc-6.1.14.jar" ); transitivesOfExcludedDirectDeps = List.of( "rules_jvm_external~~maven~maven/io/micrometer/micrometer-observation/1.13" + ".6/processed_micrometer-observation-1.13.6.jar", "rules_jvm_external~~maven~maven/io/micrometer/micrometer-commons/1.13.6/processed_micrometer-commons-1" + ".13.6.jar", "rules_jvm_external~~maven~maven/org/springframework/spring-beans/6.1.14/processed_spring-beans-6.1.14.jar", "rules_jvm_external~~maven~maven/org/springframework/spring-core/6.1.14/processed_spring-core-6.1.14.jar", "rules_jvm_external~~maven~maven/org/springframework/spring-jcl/6.1.14/processed_spring-jcl-6.1.14.jar" ); transitivesOfNonExcludedDirectDeps = List.of( "rules_jvm_external~~maven~maven/org/springframework/spring-beans/6.1.14/processed_spring-beans-6.1.14.jar", "rules_jvm_external~~maven~maven/org/springframework/spring-core/6.1.14/processed_spring-core-6.1.14.jar", "rules_jvm_external~~maven~maven/org/springframework/spring-jcl/6.1.14/processed_spring-jcl-6.1.14.jar", "rules_jvm_external~~maven~maven/org/springframework/spring-tx/6.1.14/processed_spring-tx-6.1.14.jar" ); } } ================================================ FILE: springboot/deps_filter_rules_legacy/src/test/java/com/depsfilter/DepsFilterWithoutTransitivesExclusionTest.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.ArrayList; import java.util.HashSet; import java.util.List; import java.util.Set; import org.junit.Test; public class DepsFilterWithoutTransitivesExclusionTest { private List testDeps; private List depsList; private List excludedDirectDeps; private List nonexcludedDirectDeps; private List transitivesOfExcludedDirectDeps; private List transitivesOfNonExcludedDirectDeps; @Test public void testTransitivesExclusion() { /* Tests the 'deps_filter' rule with its 'exclude_transitives' attribute set to False. Corresponds to the 'filtered_test_deps_with_transitives_excluded' rule in the BUILD file: deps_filter( name = "filtered_test_deps_without_transitives_excluded", deps = [ "@maven//:org_springframework_spring_jdbc", "@maven//:org_springframework_spring_web", ], deps_exclude_labels = [ "@maven//:org_springframework_spring_web", # share transitives with spring-jdbc ], exclude_transitives = False, testonly = True, ) This test verifies: - Excluded deps include "@maven//:org_springframework_spring_web" - Build-time deps include "@maven//:org_springframework_spring_jdbc" and its transitive deps Build-time deps also include transitive deps of "@maven//:org_springframework_spring_web" This is validated by checking the available deps in the code. */ initialTestSetup(); List allTransitivesDeps = getTransitiveDeps(); List availableDeps = computeClasspathDependencies(); // Ensure that direct deps listed for exclusion are not present in the available deps. for (String excludedDep : excludedDirectDeps) { assertThat(availableDeps).doesNotContain(excludedDep); } // Ensure that non-excluded direct deps, their transitive deps, and the transitive deps of excluded deps are // present in the available deps. for (String nonExcludedDep : nonexcludedDirectDeps) { assertThat(availableDeps).contains(nonExcludedDep); } for (String transitive : transitivesOfExcludedDirectDeps) { assertThat(availableDeps).contains(transitive); } for (String transitive : transitivesOfNonExcludedDirectDeps) { assertThat(availableDeps).contains(transitive); } // Ensure that the combined list of testDeps, depsList, and allTransitivesDeps // is equal to the combined list of availableDeps, and excludedDirectDeps. List expectedCombinedDepsList = new ArrayList<>(); List actualCombinedDepsList = new ArrayList<>(); expectedCombinedDepsList.addAll(testDeps); expectedCombinedDepsList.addAll(depsList); expectedCombinedDepsList.addAll(allTransitivesDeps); actualCombinedDepsList.addAll(availableDeps); actualCombinedDepsList.addAll(excludedDirectDeps); assertThat(actualCombinedDepsList).containsExactlyInAnyOrderElementsOf(expectedCombinedDepsList); } private List getTransitiveDeps() { // Compute transitive deps of both excluded and non-excluded deps Set uniqueTransitivesSet = new HashSet<>(); uniqueTransitivesSet.addAll(transitivesOfExcludedDirectDeps); uniqueTransitivesSet.addAll(transitivesOfNonExcludedDirectDeps); for (String directDependency : depsList) { uniqueTransitivesSet.remove(directDependency); } List allTransitivesDeps = List.copyOf(uniqueTransitivesSet); return allTransitivesDeps; } private List computeClasspathDependencies() { String classpath = System.getProperty("java.class.path"); String[] classpathEntries = classpath.split(System.getProperty("path.separator")); List availableDeps = new ArrayList<>(); for (String entry : classpathEntries) { availableDeps.add(entry.replace("../", "")); } return availableDeps; } private void initialTestSetup() { // required to run the test - specified in the test target testDeps = List.of("springboot/deps_filter_rules_legacy/DepsFilterWithoutTransitivesExclusionTest.jar", "rules_jvm_external~~maven~maven/junit/junit/4.13.2/processed_junit-4.13.2.jar", "rules_jvm_external~~maven~maven/org/hamcrest/hamcrest-core/2.2/processed_hamcrest-core-2.2.jar", "rules_jvm_external~~maven~maven/org/hamcrest/hamcrest/2.2/processed_hamcrest-2.2.jar", "rules_jvm_external~~maven~maven/org/assertj/assertj-core/3.25.3/processed_assertj-core-3.25.3.jar", "rules_jvm_external~~maven~maven/net/bytebuddy/byte-buddy/1.14.12/processed_byte-buddy-1.14.12.jar", "rules_java~~toolchains~remote_java_tools/java_tools/Runner_deploy.jar" ); // specified in the 'deps' attribute of 'deps_filter' depsList = List.of( "rules_jvm_external~~maven~maven/org/springframework/spring-jdbc/6.1.14/processed_spring-jdbc-6.1.14.jar", "rules_jvm_external~~maven~maven/org/springframework/spring-web/6.1.14/processed_spring-web-6.1.14.jar" ); // specified in the 'deps_exclude_labels' attribute of 'deps_filter' excludedDirectDeps = List.of( "rules_jvm_external~~maven~maven/org/springframework/spring-web/6.1.14/processed_spring-web-6.1.14.jar" ); // deps that are not excluded = depsList - excludedDirectDeps nonexcludedDirectDeps = List.of( "rules_jvm_external~~maven~maven/org/springframework/spring-jdbc/6.1.14/processed_spring-jdbc-6.1.14.jar" ); transitivesOfExcludedDirectDeps = List.of( "rules_jvm_external~~maven~maven/io/micrometer/micrometer-observation/1.13" + ".6/processed_micrometer-observation-1.13.6.jar", "rules_jvm_external~~maven~maven/io/micrometer/micrometer-commons/1.13.6/processed_micrometer-commons-1" + ".13.6.jar", "rules_jvm_external~~maven~maven/org/springframework/spring-beans/6.1.14/processed_spring-beans-6.1.14.jar", "rules_jvm_external~~maven~maven/org/springframework/spring-core/6.1.14/processed_spring-core-6.1.14.jar", "rules_jvm_external~~maven~maven/org/springframework/spring-jcl/6.1.14/processed_spring-jcl-6.1.14.jar" ); transitivesOfNonExcludedDirectDeps = List.of( "rules_jvm_external~~maven~maven/org/springframework/spring-beans/6.1.14/processed_spring-beans-6.1.14.jar", "rules_jvm_external~~maven~maven/org/springframework/spring-core/6.1.14/processed_spring-core-6.1.14.jar", "rules_jvm_external~~maven~maven/org/springframework/spring-jcl/6.1.14/processed_spring-jcl-6.1.14.jar", "rules_jvm_external~~maven~maven/org/springframework/spring-tx/6.1.14/processed_spring-tx-6.1.14.jar" ); } } ================================================ FILE: springboot/deps_filter_rules_legacy/src/test/java/com/depsfilter/TransitiveDepsFilterCaseA.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.ArrayList; import java.util.HashSet; import java.util.List; import java.util.Set; import org.junit.Test; public class TransitiveDepsFilterCaseA { private List testDeps; private List depsList; private List transitivesOfFirstDep; private List transitivesOfSecondDep; @Test public void testTransitivesExclusion() { /* This test is for the 'deps_filter_disable_transitives' rule Corresponds to the 'filtered_deps_disable_transitives_case_A' rule in the BUILD file: deps_filter_disable_transitives( name = "filtered_deps_disable_transitives_case_A", deps = [ "@maven//:org_springframework_spring_jdbc", "@maven//:org_springframework_spring_web", ], deps_to_exclude_transitives = [ "@maven//:org_springframework_spring_jdbc", "@maven//:org_springframework_spring_web", ], testonly = True, ) It verifies: - Build-time deps include "@maven//:org_springframework_spring_jdbc" and "@maven//:org_springframework_spring_web" - Excluded deps include transitive deps of "@maven//:org_springframework_spring_jdbc" and "@maven//:org_springframework_spring_web" i.e exclude all the transitive deps. This is validated by checking the available deps in the code. */ initialTestSetup(); List allTransitivesDeps = getTransitiveDeps(); List availableDeps = computeClasspathDependencies(); // Ensure that all transitive deps are not present in available deps. for (String transitive : allTransitivesDeps) { assertThat(availableDeps).doesNotContain(transitive); } // Ensure that all direct deps are present in available deps. for (String dep : depsList) { assertThat(availableDeps).contains(dep); } // Ensure that combined list of testDeps, and depsList is equal to combined list of available deps. List expectedCombinedDepsList = new ArrayList<>(); List actualCombinedDepsList = new ArrayList<>(); expectedCombinedDepsList.addAll(testDeps); expectedCombinedDepsList.addAll(depsList); actualCombinedDepsList.addAll(availableDeps); assertThat(actualCombinedDepsList).containsExactlyInAnyOrderElementsOf(expectedCombinedDepsList); } private List getTransitiveDeps() { Set uniqueTransitivesSet = new HashSet<>(); uniqueTransitivesSet.addAll(transitivesOfFirstDep); uniqueTransitivesSet.addAll(transitivesOfSecondDep); for (String directDependency : depsList) { uniqueTransitivesSet.remove(directDependency); } List allTransitivesDeps = List.copyOf(uniqueTransitivesSet); return allTransitivesDeps; } private List computeClasspathDependencies() { String classpath = System.getProperty("java.class.path"); String[] classpathEntries = classpath.split(System.getProperty("path.separator")); List availableDeps = new ArrayList<>(); for (String entry : classpathEntries) { availableDeps.add(entry.replace("../", "")); } return availableDeps; } private void initialTestSetup() { // required to run the test - specified in the test target testDeps = List.of("springboot/deps_filter_rules_legacy/TransitiveDepsFilterCaseA.jar", "rules_jvm_external~~maven~maven/junit/junit/4.13.2/processed_junit-4.13.2.jar", "rules_jvm_external~~maven~maven/org/hamcrest/hamcrest-core/2.2/processed_hamcrest-core-2.2.jar", "rules_jvm_external~~maven~maven/org/hamcrest/hamcrest/2.2/processed_hamcrest-2.2.jar", "rules_jvm_external~~maven~maven/org/assertj/assertj-core/3.25.3/processed_assertj-core-3.25.3.jar", "rules_jvm_external~~maven~maven/net/bytebuddy/byte-buddy/1.14.12/processed_byte-buddy-1.14.12.jar", "rules_java~~toolchains~remote_java_tools/java_tools/Runner_deploy.jar" ); // specified in the 'deps' attribute of 'deps_filter' depsList = List.of( "rules_jvm_external~~maven~maven/org/springframework/spring-jdbc/6.1.14/processed_spring-jdbc-6.1.14.jar", "rules_jvm_external~~maven~maven/org/springframework/spring-web/6.1.14/processed_spring-web-6.1.14.jar" ); transitivesOfFirstDep = List.of( "rules_jvm_external~~maven~maven/io/micrometer/micrometer-observation/1.13" + ".6/processed_micrometer-observation-1.13.6.jar", "rules_jvm_external~~maven~maven/io/micrometer/micrometer-commons/1.13.6/processed_micrometer-commons-1" + ".13.6.jar", "rules_jvm_external~~maven~maven/org/springframework/spring-beans/6.1.14/processed_spring-beans-6.1.14.jar", "rules_jvm_external~~maven~maven/org/springframework/spring-core/6.1.14/processed_spring-core-6.1.14.jar", "rules_jvm_external~~maven~maven/org/springframework/spring-jcl/6.1.14/processed_spring-jcl-6.1.14.jar" ); transitivesOfSecondDep = List.of( "rules_jvm_external~~maven~maven/org/springframework/spring-beans/6.1.14/processed_spring-beans-6.1.14.jar", "rules_jvm_external~~maven~maven/org/springframework/spring-core/6.1.14/processed_spring-core-6.1.14.jar", "rules_jvm_external~~maven~maven/org/springframework/spring-jcl/6.1.14/processed_spring-jcl-6.1.14.jar", "rules_jvm_external~~maven~maven/org/springframework/spring-tx/6.1.14/processed_spring-tx-6.1.14.jar" ); } } ================================================ FILE: springboot/deps_filter_rules_legacy/src/test/java/com/depsfilter/TransitiveDepsFilterCaseB.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.ArrayList; import java.util.HashSet; import java.util.List; import java.util.Set; import org.junit.Test; public class TransitiveDepsFilterCaseB { private List testDeps; private List depsList; private List transitivesOfFirstDep; private List transitivesOfSecondDep; @Test public void testTransitivesExclusion() { /* This test is for the 'deps_filter_disable_transitives' rule Corresponds to the 'filtered_deps_disable_transitives_case_B' rule in the BUILD file: deps_filter_disable_transitives( name = "filtered_deps_disable_transitives_case_B", deps = [ "@maven//:org_springframework_spring_jdbc", "@maven//:org_springframework_spring_web", ], deps_to_exclude_transitives = [ "@maven//:org_springframework_spring_web", ], testonly = True, ) This test verifies: - Build-time deps include "@maven//:org_springframework_spring_jdbc", its transitive deps, and "@maven//:org_springframework_spring_web" - Excluded deps include transitive deps of @maven//:org_springframework_spring_web, except those that are transitive deps of @maven//:org_springframework_spring_jdbc" This is validated by checking the available deps in the code. */ initialTestSetup(); List expectedExcludedTransitives = getExcludedTransitives(); List expectedNonExcludedTransitives = getNonExcludedTransitives(); List availableDeps = computeClasspathDependencies(); // Ensure that all expected excluded deps are not present in available deps. for (String excludedTransitive : expectedExcludedTransitives) { assertThat(availableDeps).doesNotContain(excludedTransitive); } // Ensure that all direct deps are present in available deps. for (String dep : depsList) { assertThat(availableDeps).contains(dep); } // Ensure that transitive deps of deps not specified in deps_to_exclude_transitives are present in available // deps. for (String nonExcludedTransitive : expectedNonExcludedTransitives) { assertThat(availableDeps).contains(nonExcludedTransitive); } // Ensure that combined list of testDeps, depsList, expectedExcludedTransitives, and // expectedNonExcludedTransitives is equal to combined list of availableDeps, and // expectedExcludedTransitives. List expectedCombinedDepsList = new ArrayList<>(); List actualCombinedDepsList = new ArrayList<>(); expectedCombinedDepsList.addAll(testDeps); expectedCombinedDepsList.addAll(depsList); expectedCombinedDepsList.addAll(expectedNonExcludedTransitives); expectedCombinedDepsList.addAll(expectedExcludedTransitives); actualCombinedDepsList.addAll(availableDeps); actualCombinedDepsList.addAll(expectedExcludedTransitives); assertThat(actualCombinedDepsList) .containsExactlyInAnyOrderElementsOf(expectedCombinedDepsList); } private List getExcludedTransitives() { // All transitive deps of specified deps in the exclusion list should be excluded, // except those that are also transitive deps of deps not in exclusion list // or the direct deps themselves List expectedExcludedTransitives = new ArrayList<>(); for (String transitive : transitivesOfFirstDep) { if ((!transitivesOfSecondDep.contains(transitive)) && (!depsList.contains(transitive))) { expectedExcludedTransitives.add(transitive); } } return expectedExcludedTransitives; } private List getNonExcludedTransitives() { // Transitive deps of direct deps that are not specified in the exclusion list List expectedNonExcludedTransitives = new ArrayList<>(); for (String transitive : transitivesOfSecondDep) { expectedNonExcludedTransitives.add(transitive); } return expectedNonExcludedTransitives; } private List computeClasspathDependencies() { String classpath = System.getProperty("java.class.path"); String[] classpathEntries = classpath.split(System.getProperty("path.separator")); List availableDeps = new ArrayList<>(); for (String entry : classpathEntries) { availableDeps.add(entry.replace("../", "")); } return availableDeps; } private void initialTestSetup() { // required to run the test - specified in the test target testDeps = List.of("springboot/deps_filter_rules_legacy/TransitiveDepsFilterCaseB.jar", "rules_jvm_external~~maven~maven/junit/junit/4.13.2/processed_junit-4.13.2.jar", "rules_jvm_external~~maven~maven/org/hamcrest/hamcrest-core/2.2/processed_hamcrest-core-2.2.jar", "rules_jvm_external~~maven~maven/org/hamcrest/hamcrest/2.2/processed_hamcrest-2.2.jar", "rules_jvm_external~~maven~maven/org/assertj/assertj-core/3.25.3/processed_assertj-core-3.25.3.jar", "rules_jvm_external~~maven~maven/net/bytebuddy/byte-buddy/1.14.12/processed_byte-buddy-1.14.12.jar", "rules_java~~toolchains~remote_java_tools/java_tools/Runner_deploy.jar" ); // specified in the 'deps' attribute of 'deps_filter' depsList = List.of( "rules_jvm_external~~maven~maven/org/springframework/spring-jdbc/6.1.14/processed_spring-jdbc-6.1.14.jar", "rules_jvm_external~~maven~maven/org/springframework/spring-web/6.1.14/processed_spring-web-6.1.14.jar" ); transitivesOfFirstDep = List.of( "rules_jvm_external~~maven~maven/io/micrometer/micrometer-observation/1.13" + ".6/processed_micrometer-observation-1.13.6.jar", "rules_jvm_external~~maven~maven/io/micrometer/micrometer-commons/1.13.6/processed_micrometer-commons-1" + ".13.6.jar", "rules_jvm_external~~maven~maven/org/springframework/spring-beans/6.1.14/processed_spring-beans-6.1.14.jar", "rules_jvm_external~~maven~maven/org/springframework/spring-core/6.1.14/processed_spring-core-6.1.14.jar", "rules_jvm_external~~maven~maven/org/springframework/spring-jcl/6.1.14/processed_spring-jcl-6.1.14.jar" ); transitivesOfSecondDep = List.of( "rules_jvm_external~~maven~maven/org/springframework/spring-beans/6.1.14/processed_spring-beans-6.1.14.jar", "rules_jvm_external~~maven~maven/org/springframework/spring-core/6.1.14/processed_spring-core-6.1.14.jar", "rules_jvm_external~~maven~maven/org/springframework/spring-jcl/6.1.14/processed_spring-jcl-6.1.14.jar", "rules_jvm_external~~maven~maven/org/springframework/spring-tx/6.1.14/processed_spring-tx-6.1.14.jar" ); } } ================================================ FILE: springboot/deps_filter_rules_legacy/src/test/java/com/depsfilter/TransitiveDepsFilterCaseC.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.ArrayList; import java.util.HashSet; import java.util.List; import java.util.Set; import org.junit.Test; public class TransitiveDepsFilterCaseC { private List testDeps; private List depsList; private List transitivesOfFirstDep; private List transitivesOfSecondDep; @Test public void testTransitivesExclusion() { /* This test is for the 'deps_filter_disable_transitives' rule Corresponds to the 'filtered_deps_disable_transitives_case_B' rule in the BUILD file: deps_filter_disable_transitives( name = "filtered_deps_disable_transitives_case_C", deps = [ "@maven//:org_springframework_spring_jdbc", "@maven//:org_springframework_spring_web", ], deps_to_exclude_transitives = [ "@maven//:org_springframework_spring_jdbc", ], testonly = True, ) This test verifies: - Build-time deps include "@maven//:org_springframework_spring_web", its transitive deps, and "@maven//:org_springframework_spring_jdbc" - Excluded deps include transitive deps of @maven//:org_springframework_spring_jdbc, except those that are transitive deps of @maven//:org_springframework_spring_web" This is validated by checking the available deps in the code. */ initialTestSetup(); List expectedExcludedTransitives = getExcludedTransitives(); List expectedNonExcludedTransitives = getNonExcludedTransitives(); List availableDeps = computeClasspathDependencies(); // Ensure that all expected excluded deps are not present in available deps. for (String excludedTransitive : expectedExcludedTransitives) { assertThat(availableDeps).doesNotContain(excludedTransitive); } // Ensure that all direct deps are present in available deps. for (String dep : depsList) { assertThat(availableDeps).contains(dep); } // Ensure that the transitive deps of direct deps, which are not listed in the exclusion list, // are included in the available dependencies. for (String nonExcludedTransitive : expectedNonExcludedTransitives) { assertThat(availableDeps).contains(nonExcludedTransitive); } // Ensure that combined list of testDeps, depsList, expectedExcludedTransitives, and // expectedNonExcludedTransitives is equal to combined list of availableDeps, and expectedExcludedTransitives. List expectedCombinedDepsList = new ArrayList<>(); List actualCombinedDepsList = new ArrayList<>(); expectedCombinedDepsList.addAll(testDeps); expectedCombinedDepsList.addAll(depsList); expectedCombinedDepsList.addAll(expectedNonExcludedTransitives); expectedCombinedDepsList.addAll(expectedExcludedTransitives); actualCombinedDepsList.addAll(availableDeps); actualCombinedDepsList.addAll(expectedExcludedTransitives); assertThat(actualCombinedDepsList) .containsExactlyInAnyOrderElementsOf(expectedCombinedDepsList); } private List getExcludedTransitives() { // All transitive deps of specified deps in the exclusion list should be excluded, // except those that are also transitives deps of deps not in exclusion list // or the direct deps themselves. List expectedExcludedTransitives = new ArrayList<>(); for (String transitive : transitivesOfSecondDep) { if ((!transitivesOfFirstDep.contains(transitive)) && (!depsList.contains(transitive))) { expectedExcludedTransitives.add(transitive); } } return expectedExcludedTransitives; } private List getNonExcludedTransitives() { // Transitive deps of direct deps that are not specified in the exclusion list List expectedNonExcludedTransitives = new ArrayList<>(); for (String transitive : transitivesOfFirstDep) { if (!expectedNonExcludedTransitives.contains(transitive)) { expectedNonExcludedTransitives.add(transitive); } } return expectedNonExcludedTransitives; } private List computeClasspathDependencies() { String classpath = System.getProperty("java.class.path"); String[] classpathEntries = classpath.split(System.getProperty("path.separator")); List availableDeps = new ArrayList<>(); for (String entry : classpathEntries) { availableDeps.add(entry.replace("../", "")); } return availableDeps; } private void initialTestSetup() { // required to run the test - specified in the test target testDeps = List.of("springboot/deps_filter_rules_legacy/TransitiveDepsFilterCaseC.jar", "rules_jvm_external~~maven~maven/junit/junit/4.13.2/processed_junit-4.13.2.jar", "rules_jvm_external~~maven~maven/org/hamcrest/hamcrest-core/2.2/processed_hamcrest-core-2.2.jar", "rules_jvm_external~~maven~maven/org/hamcrest/hamcrest/2.2/processed_hamcrest-2.2.jar", "rules_jvm_external~~maven~maven/org/assertj/assertj-core/3.25.3/processed_assertj-core-3.25.3.jar", "rules_jvm_external~~maven~maven/net/bytebuddy/byte-buddy/1.14.12/processed_byte-buddy-1.14.12.jar", "rules_java~~toolchains~remote_java_tools/java_tools/Runner_deploy.jar" ); // specified in the 'deps' attribute of 'deps_filter' depsList = List.of( "rules_jvm_external~~maven~maven/org/springframework/spring-jdbc/6.1.14/processed_spring-jdbc-6.1.14.jar", "rules_jvm_external~~maven~maven/org/springframework/spring-web/6.1.14/processed_spring-web-6.1.14.jar" ); transitivesOfFirstDep = List.of( "rules_jvm_external~~maven~maven/io/micrometer/micrometer-observation/1.13" + ".6/processed_micrometer-observation-1.13.6.jar", "rules_jvm_external~~maven~maven/io/micrometer/micrometer-commons/1.13.6/processed_micrometer-commons-1" + ".13.6.jar", "rules_jvm_external~~maven~maven/org/springframework/spring-beans/6.1.14/processed_spring-beans-6.1.14.jar", "rules_jvm_external~~maven~maven/org/springframework/spring-core/6.1.14/processed_spring-core-6.1.14.jar", "rules_jvm_external~~maven~maven/org/springframework/spring-jcl/6.1.14/processed_spring-jcl-6.1.14.jar" ); transitivesOfSecondDep = List.of( "rules_jvm_external~~maven~maven/org/springframework/spring-beans/6.1.14/processed_spring-beans-6.1.14.jar", "rules_jvm_external~~maven~maven/org/springframework/spring-core/6.1.14/processed_spring-core-6.1.14.jar", "rules_jvm_external~~maven~maven/org/springframework/spring-jcl/6.1.14/processed_spring-jcl-6.1.14.jar", "rules_jvm_external~~maven~maven/org/springframework/spring-tx/6.1.14/processed_spring-tx-6.1.14.jar" ); } } ================================================ FILE: springboot/deps_filter_rules_legacy/src/test/java/com/depsfilter/TransitiveDepsFilterCaseD.java ================================================ package com.depsfilter; import static org.assertj.core.api.Assertions.assertThat; import java.util.ArrayList; import java.util.HashSet; import java.util.List; import java.util.Set; import org.junit.Test; public class TransitiveDepsFilterCaseD { private List testDeps; private List depsList; private List transitivesOfFirstDep; private List transitivesOfSecondDep; @Test public void testTransitivesExclusion() { /* This test is for the 'deps_filter_disable_transitives' rule Corresponds to the 'filtered_deps_disable_transitives_case_B' rule in the BUILD file: deps_filter_disable_transitives( name = "filtered_deps_disable_transitives_case_D", deps = [ "@maven//:org_springframework_spring_jdbc", "@maven//:org_springframework_spring_web", ], testonly = True, ) This test verifies: - Build-time deps include "@maven//:org_springframework_spring_jdbc" and "@maven//:org_springframework_spring_web", and their transitive deps - No deps are excluded This is validated by checking the available deps in the code. */ initialTestSetup(); List allTransitivesDeps = getTransitiveDeps(); List availableDeps = computeClasspathDependencies(); // Ensure that all transitive deps are included in available deps. for (String transitive : allTransitivesDeps) { assertThat(availableDeps).contains(transitive); } // Ensure that all direct deps are included in available deps. for (String dep : depsList) { assertThat(availableDeps).contains(dep); } // Ensure that combined list of testDeps, depsList, and allTransitivesDeps // is equal to availableDeps List expectedCombinedDepsList = new ArrayList<>(); List actualCombinedDepsList = new ArrayList<>(); expectedCombinedDepsList.addAll(testDeps); expectedCombinedDepsList.addAll(depsList); expectedCombinedDepsList.addAll(allTransitivesDeps); actualCombinedDepsList.addAll(availableDeps); assertThat(actualCombinedDepsList).containsExactlyInAnyOrderElementsOf(expectedCombinedDepsList); } private List getTransitiveDeps() { // Compute transitive deps of both excluded and non-excluded deps Set uniqueTransitivesSet = new HashSet<>(); uniqueTransitivesSet.addAll(transitivesOfFirstDep); uniqueTransitivesSet.addAll(transitivesOfSecondDep); for (String directDependency : depsList) { uniqueTransitivesSet.remove(directDependency); } List allTransitivesDeps = List.copyOf(uniqueTransitivesSet); return allTransitivesDeps; } private List computeClasspathDependencies() { String classpath = System.getProperty("java.class.path"); String[] classpathEntries = classpath.split(System.getProperty("path.separator")); List availableDeps = new ArrayList<>(); for (String entry : classpathEntries) { availableDeps.add(entry.replace("../", "")); } return availableDeps; } private void initialTestSetup() { // required to run the test - specified in the test target testDeps = List.of("springboot/deps_filter_rules_legacy/TransitiveDepsFilterCaseD.jar", "rules_jvm_external~~maven~maven/junit/junit/4.13.2/processed_junit-4.13.2.jar", "rules_jvm_external~~maven~maven/org/hamcrest/hamcrest-core/2.2/processed_hamcrest-core-2.2.jar", "rules_jvm_external~~maven~maven/org/hamcrest/hamcrest/2.2/processed_hamcrest-2.2.jar", "rules_jvm_external~~maven~maven/org/assertj/assertj-core/3.25.3/processed_assertj-core-3.25.3.jar", "rules_jvm_external~~maven~maven/net/bytebuddy/byte-buddy/1.14.12/processed_byte-buddy-1.14.12.jar", "rules_java~~toolchains~remote_java_tools/java_tools/Runner_deploy.jar" ); // specified in the 'deps' attribute of 'deps_filter' depsList = List.of( "rules_jvm_external~~maven~maven/org/springframework/spring-jdbc/6.1.14/processed_spring-jdbc-6.1.14.jar", "rules_jvm_external~~maven~maven/org/springframework/spring-web/6.1.14/processed_spring-web-6.1.14.jar" ); transitivesOfFirstDep = List.of( "rules_jvm_external~~maven~maven/io/micrometer/micrometer-observation/1.13" + ".6/processed_micrometer-observation-1.13.6.jar", "rules_jvm_external~~maven~maven/io/micrometer/micrometer-commons/1.13.6/processed_micrometer-commons-1" + ".13.6.jar", "rules_jvm_external~~maven~maven/org/springframework/spring-beans/6.1.14/processed_spring-beans-6.1.14.jar", "rules_jvm_external~~maven~maven/org/springframework/spring-core/6.1.14/processed_spring-core-6.1.14.jar", "rules_jvm_external~~maven~maven/org/springframework/spring-jcl/6.1.14/processed_spring-jcl-6.1.14.jar" ); transitivesOfSecondDep = List.of( "rules_jvm_external~~maven~maven/org/springframework/spring-beans/6.1.14/processed_spring-beans-6.1.14.jar", "rules_jvm_external~~maven~maven/org/springframework/spring-core/6.1.14/processed_spring-core-6.1.14.jar", "rules_jvm_external~~maven~maven/org/springframework/spring-jcl/6.1.14/processed_spring-jcl-6.1.14.jar", "rules_jvm_external~~maven~maven/org/springframework/spring-tx/6.1.14/processed_spring-tx-6.1.14.jar" ); } } ================================================ FILE: springboot/deps_filter_transitive.bzl ================================================ # THIS VERSION OF THE FILTER IS DEPRECATED AND WILL BE REMOVED # Use deps_filter instead: # load("@rules_spring//springboot/deps_filter_rules_legacy:deps_filter.bzl", "deps_filter") # # Note: the attribute deps_exclude has been renamed deps_exclude_labels for deps_filter def _depaggregator_rule_impl(merged, ctx): """ This method processes declared deps and their transitive closures to assemble a cohesive set of jars essential for the build process. During this process, it excludes deps specified in 'deps_exclude', which lists jar labels to be omitted from packaging due to issues that cannot be resolved upstream. By default, with 'exclude_transitives' set to true, any transitive deps that are only required by excluded deps are also omitted, ensuring that only necessary transitives are included in the final package. It uses 'deps_exclude_paths' to exclude deps based on partial filename matches, ensuring problematic files are also excluded from the build. This method ensures that only necessary deps are included for the build process. """ exclude_transitives = ctx.attr.exclude_transitives # list to store jars to be included and a dictionary to track excluded jars jars = [] excludes = {} if exclude_transitives: # Dictionary to track transitive dependency paths that should be excluded transitives_excludes = {} # List to store deps info for deps present in 'deps_exclude' direct_excludes = [] # Iterate through the deps specified in 'deps_exclude' to collect # jars that should be excluded from the final set. for exclusion_info in ctx.attr.deps_exclude: # For each excluded dependency, add its compile-time JARs to the exclusion list for compile_jar in exclusion_info[JavaInfo].full_compile_jars.to_list(): excludes[compile_jar.path] = True if exclude_transitives: # Mark all transitives of the current dependency as excluded # This list will be updated later based on transitives of non-excluded deps direct_excludes.append(str(exclusion_info)) for transitive_jar in exclusion_info[JavaInfo].transitive_runtime_jars.to_list(): transitives_excludes[transitive_jar.path] = True if exclude_transitives: # Iterate over all deps, for non-excluded deps, mark their transitives as included. for deps_info in ctx.attr.deps: # skip the current dependency if it is listed in 'deps_exclude'. if str(deps_info) in direct_excludes: continue # For non-excluded deps, mark them and their transitive deps as included (not to be excluded) # (transitive_runtime_jars includes both the primary JAR and its transitive deps) for transitive_jar in deps_info[JavaInfo].transitive_runtime_jars.to_list(): if transitive_jar.path in transitives_excludes: transitives_excludes[transitive_jar.path] = False # update the excludes list for dep_path in transitives_excludes: # print("Transitive:", str(dep_path), "is excluded", transitives_excludes[dep_path]) if transitives_excludes[dep_path]: excludes[dep_path] = True # compute the final set of jars for dep in merged.transitive_runtime_jars.to_list(): # If the current JAR is in the exclusion list, skip it (do not include it) if excludes.get(dep.path, None) != None: pass else: # Default to including the JAR unless a pattern match excludes it include = True for pattern in ctx.attr.deps_exclude_paths: if dep.path.find(pattern) > -1: include = False break if include: jars.append(dep) return jars def _deps_filter_transitive_impl(ctx): """ This rule filters out specified deps and JARs from the compile-time and runtime deps. It utilizes the 'deps_exclude' attribute to omit specific JAR labels and the 'deps_exclude_paths' attribute to exclude deps based on partial paths in their filenames. By default, with 'exclude_transitives' set to true, any transitive deps solely required by the deps in 'deps_exclude' are also excluded. These exclusions ensure the final collection includes only the necessary elements for the build process, eliminating problematic deps. """ print("WARN: deps_filter_transitive has been moved to a new name. See rules_spring docs for details.") if len(ctx.attr.deps) == 0: fail("Error: 'deps' cannot be an empty list") # magical incantation for getting upstream transitive closure of java deps merged = java_common.merge([dep[java_common.provider] for dep in ctx.attr.deps]) runtime_dep_merged = java_common.merge([runtime_dep[java_common.provider] for runtime_dep in ctx.attr.runtime_deps]) compile_time_jars = _depaggregator_rule_impl(merged, ctx) runtime_jars = _depaggregator_rule_impl(runtime_dep_merged, ctx) if len(compile_time_jars) == 0: fail("Error: The rule must return at least one compile-time JAR. Excluding all compile-time dependencies is not allowed.") return [ DefaultInfo(files = depset(compile_time_jars,)), JavaInfo( compile_jar = None, output_jar = compile_time_jars[0], # output jar must be non-empty, adding a dummy value to it exports = [JavaInfo(source_jar = jar, compile_jar = jar, output_jar = jar) for jar in compile_time_jars], runtime_deps = [JavaInfo(source_jar = jar, compile_jar = jar, output_jar = jar) for jar in runtime_jars], deps = [JavaInfo(source_jar = jar, compile_jar = jar, output_jar = jar) for jar in compile_time_jars], ), ] deps_filter_transitive = rule( implementation = _deps_filter_transitive_impl, attrs = { "deps": attr.label_list(providers = [java_common.provider]), "runtime_deps": attr.label_list(providers = [java_common.provider], allow_empty = True), "deps_exclude": attr.label_list(providers = [java_common.provider], allow_empty = True), "deps_exclude_paths": attr.string_list(), "exclude_transitives": attr.bool(default = True), }, ) ================================================ FILE: springboot/detect_javax_classes.py ================================================ # # Copyright (c) 2023, salesforce.com, inc. # All rights reserved. # Licensed under the BSD 3-Clause license. # For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause # from collections import defaultdict import hashlib import os import sys import zipfile import tempfile def _check_for_javax_classes(springbootzip_filepath, ignorelisted_jars, output_filepath): """ Prints error message and returns True if javax classes were found, false otherwise. Jars in the ignorelisted_jars list are excluded from the check. """ # this will be set to True if any javax classes are found, that are not # contained by any jar in the ignorelist found_javax = False # this set will contain the jars that contain the violaters javax_containing_jars = set() # list of paths of classes that are javax # use each string entry as a key into the class_catalog dict javax_classes = [] javax_message_lines = "" # dict that maps the path to a class to all jars (as list) it was found in, # and the hash for each appearance # for example: # com/acme/common/HostUtil.class -> # [ # { bazel-out/.../foolib.jar, 5807cc49dfbda8dd937de3b33a885409 }, # { bazel-out/.../blahlib.jar, 5807cc49dfbda8dd937de3b33a885409 } # ] class_catalog = defaultdict(list) # Starting the search.... # iterate through the springboot jar file, and find inner jars, # open each inner jar and catalog each .class file found try: springbootzip = zipfile.ZipFile(springbootzip_filepath) except zipfile.BadZipFile: # this error happened to me when my computer ran out of disk space during a build result = "Spring Boot javax detection has failed for %s because the generated jar file is corrupt, please delete this file.\n" % springbootzip_filepath print(result) _write_result_to_output_file(output_filepath, result) return True sprintbootzipentries = springbootzip.infolist() for springbootzipentry in sprintbootzipentries: if springbootzipentry.filename.endswith(".jar"): jar_path = springbootzipentry.filename innerjar = springbootzip.open(springbootzipentry.filename) # create a temporary copy of the inner jar as a file on disk innerjar_binarycontent = innerjar.read() innerjar_tmp_fileondisk = tempfile.TemporaryFile() innerjar_tmp_fileondisk.write(innerjar_binarycontent) # initialize a ZipFile object using the temporary copy innerjar_zip = zipfile.ZipFile(innerjar_tmp_fileondisk) innerjar_zipentries = innerjar_zip.infolist() for innerjar_zipentry in innerjar_zipentries: innerjar_zipentry_path = innerjar_zipentry.filename if (innerjar_zipentry_path.startswith("javax")): if innerjar_zipentry_path.endswith(".class"): if innerjar_zipentry_path.endswith("module-info.class"): continue jar_base = os.path.basename(jar_path) if jar_base not in ignorelisted_jars: javax_containing_jars.add(jar_base) found_javax = True class_bytes = innerjar_zip.read(innerjar_zipentry_path) digest = hashlib.md5(class_bytes).hexdigest() class_catalog_entry = (jar_path, digest) class_catalog[innerjar_zipentry_path].append(class_catalog_entry) javax_message_lines += " class %s\n" % (innerjar_zipentry_path) javax_message_lines += " jar %s hash %s\n" % (jar_base, digest) # end innerzipentries for loop innerjar_tmp_fileondisk.close() if found_javax: result = "Spring Boot packaging has failed for %s because jars with unexpected javax classes, were found:\n" % springbootzip_filepath result += javax_message_lines result += "You should investigate the javax dependencies, and eliminate them or add these jars to the javaxdetect_ignorelist file:\n" for ignorelist_candidate in javax_containing_jars: result += " %s\n" % ignorelist_candidate print(result) _write_result_to_output_file(output_filepath, result) return found_javax def _parse_ignorelisted_jars_file(ignorelist_file): """ Reads the ignorelist.txt file and returns the jars as a set. File format: each line in the file is the name of a jar, like: foo.jar bar.jar """ ignorelisted_jars = set() if ignorelist_file != None: with open(ignorelist_file, "r") as lines: for line in lines: line = line.strip() if len(line) == 0 or line.startswith("#"): continue # cannot use the whole jar path as it is different for generated jars on linux and mac # this logic might need to change if two jars with the same name are part of the ignorelist jar = os.path.basename(line) ignorelisted_jars.add(jar) #if len(ignorelisted_jars) > 0: # print("Springboot javax class checker ignorelisted jars:") # for ignorelisted_jar in ignorelisted_jars: # print(" %s" % ignorelisted_jar) return ignorelisted_jars def _write_result_to_output_file(output_filepath, result): if output_filepath != None: f = open(output_filepath, "a") f.write(result) f.close() def run_with_ignorelist(springbootzip_filepath, ignorelisted_jars, output_filepath): found_javax = _check_for_javax_classes(springbootzip_filepath, ignorelisted_jars, output_filepath) if found_javax: raise Exception("Found javax classes in the packaged springboot jar") else: _write_result_to_output_file(output_filepath, "SUCCESS") return found_javax def run(springbootzip_filepath, ignorelist_file, output_filepath): """ Iterates through a Spring Boot jar and looks for classes in inner jars. If the same class (package name + class name) appears more than once, verify that the .class files have the same hash code. If there is a conflict, this invocation will fail with an error. If both jars are listed in the ignorelist, the conflict will be ignored. """ ignorelisted_jars = _parse_ignorelisted_jars_file(ignorelist_file) run_with_ignorelist(springbootzip_filepath, ignorelisted_jars, output_filepath) if __name__ == "__main__": # arg1 path to the spring boot jar file (required) # arg2 path to the text file containing the jars to ignore as sources of javax (optional) # arg3 outputfile (optional, will contain "SUCCESS" if the check passed, or the list of errors) ignorelist_file = None if len(sys.argv) > 2: ignorelist_file = sys.argv[2] if ignorelist_file == "no_ignorelist": ignorelist_file = None output_file = None if len(sys.argv) > 3: output_file = sys.argv[3] run(sys.argv[1], ignorelist_file, output_file) ================================================ FILE: springboot/empty.txt ================================================ ================================================ FILE: springboot/import_bundles/BUILD ================================================ # # Copyright (c) 2017-2024, salesforce.com, inc. # All rights reserved. # Licensed under the BSD 3-Clause license. # For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause # # List of standard imports bundles that most/all Spring Boot app will need. java_import( name = "springboot_required_deps", jars = [], visibility = ["//visibility:public"], exports = [ "@maven//:org_springframework_boot_spring_boot", "@maven//:org_springframework_boot_spring_boot_actuator", "@maven//:org_springframework_boot_spring_boot_actuator_autoconfigure", "@maven//:org_springframework_boot_spring_boot_autoconfigure", "@maven//:org_springframework_boot_spring_boot_loader", "@maven//:org_springframework_boot_spring_boot_starter", "@maven//:org_springframework_boot_spring_boot_starter_logging", "@maven//:org_springframework_spring_aop", "@maven//:org_springframework_spring_beans", "@maven//:org_springframework_spring_context", "@maven//:org_springframework_spring_core", "@maven//:org_springframework_spring_expression", "@maven//:org_springframework_spring_web", ], ) ================================================ FILE: springboot/import_bundles/README.md ================================================ ## Import Bundles for Spring Boot Starters This is a scheme for providing convenience bundles of dependencies for each open source Spring Boot starter. *springboot_required_deps* is a convenience bundle that contains the core list that all Spring Boot apps need. We used to maintain others, but have since removed all other bundles. ```starlark deps = [ "@rules_spring//springboot/import_bundles:springboot_required_deps", ] ``` ================================================ FILE: springboot/javax.md ================================================ ## Migrating from javax to jakarta for Spring Boot 3 The Java community is going through its Python2 → Python3 moment. Oracle donated source code to open source, but their lawyers said that the Java trademark must be protected. Therefore, the donated code must be repackaged from *javax* to *jakarta* (e.g. from *javax.servlet* to *jakarta.servlet*). The Maven GAVs change too (e.g. *javax.servlet:javax.servlet-api* to *jakarta.servlet:jakarta.servlet-api*). Read more [in this article](https://blogs.oracle.com/javamagazine/post/transition-from-java-ee-to-jakarta-ee). This is obviously super disruptive. These changes affect runtime, not just compile time. If you have a compiled jar file with code that references a class in the *javax.servlet* package, it will break at runtime if you deploy it with the newly packaged *jakarta* servlet jar. Therefore you have to make the switch across many libs, all at once. This is a big bang upgrade, folks. The Spring Boot project chose to force this migration with [Spring Boot 3](https://spring.io/blog/2022/11/24/spring-boot-3-0-goes-ga). Whether you like it or not, you must migrate to stay on a supported version of Spring Boot. Good times. ### Jakarta Migration Path (in a nutshell) There is a migration path for going from *javax* to *jakarta*. It doesn't make it easy, but it does allow you to break it up a little. The important thing to know is that there are two aspects of migration: the **GAV**, and the **Java package**. - the GAV migration (groupId, artifactId, version) moves from a *javax* groupId and artifactId, to a *jakarta* one - the Java package migration involves moving from classes in a *javax* package, to a *jakarta* package The GAV migration is the easier one, since it is just a configuration change. The Java package migration is tough, because it involves actual code level changes to use the migrated package names. ### Transitional Jars The Jakarta team helps you out a little bit by providing what I call *transitional jars*. These jars are half migrated jars that allow you to take the migration steps incrementally. The best way to explain them is to provide an example: - Javax Jar: - GAV: *javax.json:javax.json-api:1.1.4* - Java package: *javax.json* - Transitional Jar: - GAV: *jakarta.json:jakarta.json-api:1.1.6* - Java package: *javax.json* - Jakarta Jar: - GAV: *jakarta.json:jakarta.json-api:2.1.2* - Java package: *jakarta.json* This allows you to update to a transitional version of the *jakarta* GAV, without adopting the Java package change too. That first step is just a build metadata change. :key: After upgrading to the transitional jars, you should enable the [springboot rule duplicate class check](https://github.com/salesforce/rules_spring/blob/main/springboot/unwanted_classes.md#detecting-duplicate-classes) which should highlight any jars bringing in old versions of the *javax* classes. ### Not All javax is Migrating to jakarta Before you try to rip out *all* javax usages in your Spring Boot jar, know that not every *javax* package is migrating to *jakarta*. The detection tooling is empathetic to this. You can ignore jars that have non-migrating *javax* classes for this reason. ### Javax Detect Mode After upgrading to the transitional jars, and enabling the duplicate class checker, you need to continue to look for *javax* classes in your classpath that are not in a transitional jar. There are widely used projects out there that did bad things - they included standard *javax* classes in their jar files. While those projects **might** continue to function properly on old *javax* classes, they need to be researched. They hopefully have newer versions that use the newer *jakarta* classes. The springboot rule has a *javaxdetect* mode to help with this. When enabled, it will detect classes in the classpath located in a _javax.*_ package. If the jar that contains that class is not in your ignorelist, the build will fail. The intent is for you to analyze all *javax* classes in your classpath to determine if/when/how they will migrate to _jakarta_. Example: ```starlark springboot( name = "my-boot-app", boot_app_class = "com.acme.MyService", javaxdetect_enable = True, javaxdetect_ignorelist = "//tools/springboot:javaxdetect_ignorelist.txt", java_library = ":base_lib", ) ``` where the contents of the *javaxdetect_ignorelist.txt* file will look like this when you are transitioning: ``` # TEMPORARY IGNORES # These are jakarta transitional jars: they use jakarta GAV but still have javax Java packaging. # We need these entries until we switch to later versions that contain jakarta packaging. jakarta.activation-api-1.2.2.jar jakarta.annotation-api-1.3.5.jar jakarta.el-3.0.4.jar jakarta.enterprise.cdi-api-2.0.2.jar jakarta.inject-2.6.1.jar jakarta.inject-api-1.0.5.jar jakarta.interceptor-api-1.2.5.jar jakarta.jms-api-2.0.3.jar jakarta.json-1.1.6.jar jakarta.json-api-1.1.6.jar jakarta.jws-api-2.1.0.jar jakarta.persistence-api-2.2.3.jar jakarta.servlet-api-4.0.4.jar jakarta.transaction-api-1.3.3.jar jakarta.validation-api-2.0.2.jar jakarta.websocket-api-1.1.2.jar jakarta.websocket-client-api-1.1.2.jar jakarta.ws.rs-api-2.1.6.jar jakarta.xml.bind-api-2.3.3.jar jakarta.xml.soap-api-1.4.2.jar jakarta.xml.ws-api-2.3.3.jar # PERMANENT IGNORES # javax.measure:unit-api # This jar is the outcome of [JSR-363](https://jcp.org/en/jsr/detail?id=363). # It appears to have no public plans to migrate, and so will remain javax for the foreseeable future. unit-api-1.0.jar # com.google.code.findbugs:jsr305 # This was an early JSR that never progressed beyond proposal, so it is a dormant JSR. # However, Google emitted this findbugs jar, and a bunch of people use it. # But since it isn't an official javax product, it has no migration plan. jsr305-3.0.2.jar # javax.cache:cache-api # This is the outcome of [JSR-107](https://www.jcp.org/en/jsr/detail?id=107) (aka JCache). # Discussion about migration: [JCache for jakarta](https://github.com/jsr107/jsr107spec/issues/415) # But since JCache was never adopted by JavaEE, it is not planned for migration. cache-api-1.1.1.jar ``` For completeness, this is the BUILD file at *//tools/springboot*: ``` exports_files([ "javaxdetect_ignorelist.txt", ]) ``` ### Javax Reference Checking Ideally the *springboot()* rule would have a feature for *javax* reference checking. Meaning, it would decompile every class in the springboot classpath and check if any were referencing a *javax* package. We don't have that. I wish we did. ### Finishing the Jakarta Migration Once you have moved to the transitional jars, and have investigated and resolved jars with *javax* classes in them, you will be ready to finish your migration. You need to move from the **transitional GAV**, to the **jakarta GAV**. This is officially documented as the [JaveEE 10 migration.](https://blogs.oracle.com/javamagazine/post/transition-from-java-ee-to-jakarta-ee) When you do this step, remove the jakarta transitional jars from your ignore list since you should now be using newer versions that use jakarta packages. In addition, the following must happen at the same time as upgrading: - [Spring Boot 3](https://github.com/spring-projects/spring-boot/wiki/Spring-Boot-3.0-Migration-Guide) - [Spring 6](https://github.com/spring-projects/spring-framework/wiki/Upgrading-to-Spring-Framework-6.x) - [Jetty 11](https://webtide.com/jetty-10-and-11-have-arrived/) - and others, depending on what libraries your service uses It is going to be fun. ================================================ FILE: springboot/springboot.bzl ================================================ # # Copyright (c) 2017-2021, salesforce.com, inc. # All rights reserved. # Licensed under the BSD 3-Clause license. # For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause # # # Spring Boot Packager # # See the macro documentation below for details. # Spring Boot Executable JAR Layout specification # reverse engineered from the Spring Boot maven plugin # / # /META-INF/ # /META-INF/MANIFEST.MF <-- very specific manifest for Spring Boot (generated by this rule) # /BOOT-INF # /BOOT-INF/classes # /BOOT-INF/classes/git.properties <-- properties file containing details of the current source tree via Git # /BOOT-INF/classes/**/*.class <-- compiled application classes, must include @SpringBootApplication class # /BOOT-INF/classes/META-INF/* <-- application level META-INF config files (e.g. spring.factories) # /BOOT-INF/lib # /BOOT-INF/lib/*.jar <-- all upstream transitive dependency jars must be here (except spring-boot-loader) # /org/springframework/boot/loader # /org/springframework/boot/loader/**/*.class <-- the Spring Boot Loader classes must be here # *************************************************************** # Dependency Aggregator Rule # do not use directly, see the SpringBoot Macro below def _depaggregator_rule_impl(ctx): # magical incantation for getting upstream transitive closure of java deps merged = java_common.merge([dep[java_common.provider] for dep in ctx.attr.deps]) jars = [] excludes = {} for exclusion_info in ctx.attr.deps_exclude_labels: for compile_jar in exclusion_info[JavaInfo].full_compile_jars.to_list(): # print("Spring Boot Excluding: "+compile_jar.owner.name+" as "+compile_jar.path) excludes[compile_jar.path] = True for dep in merged.transitive_runtime_jars.to_list(): if excludes.get(dep.path, None) != None: # print("exclude by label " + dep.path) pass else: include = True for pattern in ctx.attr.deps_exclude_paths: if dep.path.find(pattern) > -1: # print("exclude by path " + dep.path) include = False break if include: # print("Spring Boot Including: "+dep.owner.name+" as "+dep.path) jars.append(dep) #print("AGGREGATED DEPS") #print(jars) return [DefaultInfo(files = depset(jars))] _depaggregator_rule = rule( implementation = _depaggregator_rule_impl, attrs = { "depaggregator_rule": attr.label(), "deps": attr.label_list(providers = [java_common.provider]), "deps_exclude_labels": attr.label_list(providers = [java_common.provider], allow_empty = True), "deps_exclude_paths": attr.string_list(), }, ) def _appjar_locator_impl(ctx): if java_common.provider in ctx.attr.app_dep: output_jars = ctx.attr.app_dep[java_common.provider].runtime_output_jars if len(output_jars) != 1: fail("springboot rule expected 1 app jar but found %s" % len(output_jars)) else: fail("Unable to locate the app jar") return [DefaultInfo(files = depset([output_jars[0]]))] _appjar_locator_rule = rule( implementation = _appjar_locator_impl, attrs = { "app_dep": attr.label(), }, ) # *************************************************************** # Check Dupe Classes Rule def _dupeclasses_rule_impl(ctx): # setup the output file (contains SUCCESS, NOT_RUN, or the list of errors) output = ctx.actions.declare_file(ctx.attr.out) outputs = [output] if not ctx.attr.dupeclassescheck_enable: ctx.actions.write(output, "NOT_RUN", is_executable = False) return [DefaultInfo(files = depset(outputs))] inputs = [] input_args = ctx.actions.args() # inputs (spring boot jar file, ignorelist) inputs.append(ctx.attr.springbootjar.files.to_list()[0]) input_args.add(ctx.attr.springbootjar.files.to_list()[0].path) if ctx.attr.dupeclassescheck_ignorelist != None: inputs.append(ctx.attr.dupeclassescheck_ignorelist.files.to_list()[0]) input_args.add(ctx.attr.dupeclassescheck_ignorelist.files.to_list()[0].path) else: input_args.add("no_ignorelist") # add the output file to the args, so python script knows where to write result input_args.add(output.path) # run the dupe checker ctx.actions.run( executable = ctx.executable.script, outputs = outputs, inputs = inputs, arguments = [input_args], progress_message = "Checking for duplicate classes in the Spring Boot jar...", mnemonic = "DupeCheck", ) return [DefaultInfo(files = depset(outputs))] _dupeclasses_rule = rule( implementation = _dupeclasses_rule_impl, attrs = { "dupeclasses_rule": attr.label(), "script": attr.label( executable = True, cfg = "exec", allow_files = True, ), "springbootjar": attr.label(), "dupeclassescheck_ignorelist": attr.label(allow_files = True), "dupeclassescheck_enable": attr.bool(), "out": attr.string(), }, ) # *************************************************************** # JAVAX DETECT Rule def _javaxdetect_rule_impl(ctx): # setup the output file (contains SUCCESS, NOT_RUN, or the list of errors) output = ctx.actions.declare_file(ctx.attr.out) outputs = [output] if not ctx.attr.javaxdetect_enable: ctx.actions.write(output, "NOT_RUN", is_executable = False) return [DefaultInfo(files = depset(outputs))] inputs = [] input_args = ctx.actions.args() # inputs (spring boot jar file, ignorelist) inputs.append(ctx.attr.springbootjar.files.to_list()[0]) input_args.add(ctx.attr.springbootjar.files.to_list()[0].path) if ctx.attr.javaxdetect_ignorelist != None: inputs.append(ctx.attr.javaxdetect_ignorelist.files.to_list()[0]) input_args.add(ctx.attr.javaxdetect_ignorelist.files.to_list()[0].path) else: input_args.add("no_ignorelist") # add the output file to the args, so python script knows where to write result input_args.add(output.path) # run the dupe checker ctx.actions.run( executable = ctx.executable.script, outputs = outputs, inputs = inputs, arguments = [input_args], progress_message = "Checking for javax classes in the Spring Boot jar (candidates for jakarta migration)...", mnemonic = "JavaxDetect", ) return [DefaultInfo(files = depset(outputs))] _javaxdetect_rule = rule( implementation = _javaxdetect_rule_impl, attrs = { "javaxdetect_rule": attr.label(), "script": attr.label( executable = True, cfg = "exec", allow_files = True, ), "springbootjar": attr.label(), "javaxdetect_ignorelist": attr.label(allow_files = True), "javaxdetect_enable": attr.bool(), "out": attr.string(), }, ) # *************************************************************** # BANNED DEPS RULE def _banneddeps_rule_impl(ctx): output = ctx.actions.declare_file(ctx.attr.out) outputs = [output] if ctx.attr.deps_banned == None: ctx.actions.write(output, "NOT_RUN", is_executable = False) return [DefaultInfo(files = depset(outputs))] # iterate through the transitive set; this set has already had the deps_exclude_labels # rules applied, so this is the filtered list found_banned = False banned_filenames = "" deps = ctx.attr.deps for dep in deps: for file in dep.files.to_list(): for currentmatcher in ctx.attr.deps_banned: if currentmatcher in file.basename: # found a banned dep banned_filenames = banned_filenames + file.basename + "\n" found_banned = True if found_banned: ctx.actions.write(output, "FAIL", is_executable = False) fail("Found banned jars in the springboot rule [" + ctx.label.name + "] dependency list. Filenames:\n" + banned_filenames + "\nYou can ignore these by setting deps_banned = [] on the springboot() rule.\n") else: ctx.actions.write(output, "SUCCESS", is_executable = False) return [DefaultInfo(files = depset(outputs))] _banneddeps_rule = rule( implementation = _banneddeps_rule_impl, attrs = { "banneddeps_rule": attr.label(), "springboot_rule_name": attr.string(), "deps_banned": attr.string_list(), "deps": attr.label_list(), "out": attr.string(), }, ) # *************************************************************** # Outer launcher script for "bazel run" _bazelrun_script_template = """#!/bin/bash set -e # bring in the resolved variables needed for running the script # SCRIPT_DIR is the directory in which bazel run executes SCRIPT_DIR="$( cd "$( dirname "${BASH_SOURCE[0]}" )" &> /dev/null && pwd )" # Detect Java Toolchain (optional) # If the bazelrun_java_toolchain attribute on the springboot rule is set, the springboot # rule impl below will replace the java_toolchain_attr tag with the relative path # from exec root to the JVM. We have to do some Bash hijinks to resolve the # absolute path. JAVA_TOOLCHAIN_RELATIVE=%java_toolchain_attr% if [ -z ${JAVA_TOOLCHAIN_RELATIVE+x} ]; then # the springboot rule did not set the bazelrun_java_toolchain attribute unset JAVA_TOOLCHAIN else # the springboot rule did set the bazelrun_java_toolchain attribute, convert # it into an absolute path using exec_root exec_root=${SCRIPT_DIR%%bazel-out*} JAVA_TOOLCHAIN="${exec_root}${JAVA_TOOLCHAIN_RELATIVE}" JAVA_TOOLCHAIN_NAME=%java_toolchain_name_attr% fi # the env variables file is found in SCRIPT_DIR source $SCRIPT_DIR/%name%_bazelrun_env.sh # the inner bazelrun script is found in the runfiles subdir # this is either default_bazelrun_script.sh or a custom one provided by the user source %bazelrun_script% """ # *************************************************************** # SpringBoot Rule # do not use directly, see the SpringBoot Macro below def _springboot_rule_impl(ctx): outs = depset(transitive = [ ctx.attr.app_compile_rule.files, ctx.attr.genmanifest_rule.files, ctx.attr.bazelrun_script.files, ctx.attr.genbazelrunenv_rule.files, ctx.attr.gengitinfo_rule.files, ctx.attr.genjar_rule.files, ]) # resolve the full path of the launcher script that runs "java -jar " when calling # "bazel run" with the springboot target (bazel run //examples/helloworld) and string sub it # into the _bazelrun_script_template text defined above outer_bazelrun_script_contents = _bazelrun_script_template \ .replace("%bazelrun_script%", ctx.attr.bazelrun_script.files.to_list()[0].short_path) \ .replace("%name%", ctx.attr.name) # the bazelrun_java_toolchain optional, if set, we use it as the jvm for bazel run if ctx.attr.bazelrun_java_toolchain != None: # lookup the path to selected java toolchain, and string sub it into the bazel run script # text _bazelrun_script_template defined above java_runtime = ctx.attr.bazelrun_java_toolchain[java_common.JavaToolchainInfo].java_runtime java_bin = [f for f in java_runtime.files.to_list() if f.path.endswith("bin/java") or f.path.endswith("bin/java.exe")][0] outer_bazelrun_script_contents = outer_bazelrun_script_contents \ .replace("%java_toolchain_attr%", java_bin.path) outer_bazelrun_script_contents = outer_bazelrun_script_contents \ .replace("%java_toolchain_name_attr%", ctx.attr.bazelrun_java_toolchain.label.name) else: outer_bazelrun_script_contents = outer_bazelrun_script_contents \ .replace("%java_toolchain_attr%", "") outer_bazelrun_script_file = ctx.actions.declare_file("%s" % ctx.label.name) ctx.actions.write(outer_bazelrun_script_file, outer_bazelrun_script_contents, is_executable = True) # the jar and launcher script we build needs to be part of runfiles so that it ends # up in the working directory that "bazel run" uses runfiles_list = ctx.attr.genjar_rule.files.to_list() runfiles_list.append(ctx.attr.bazelrun_script.files.to_list()[0]) # and add any data files to runfiles if ctx.attr.bazelrun_data != None: for data_target in ctx.attr.bazelrun_data: for data_target in data_target.files.to_list(): runfiles_list.append(data_target) return [DefaultInfo( files = outs, executable = outer_bazelrun_script_file, runfiles = ctx.runfiles(files = runfiles_list), )] _springboot_rule = rule( implementation = _springboot_rule_impl, executable = True, attrs = { "app_compile_rule": attr.label(), "dep_aggregator_rule": attr.label(), "genmanifest_rule": attr.label(), "genbazelrunenv_rule": attr.label(), "gengitinfo_rule": attr.label(), "genjar_rule": attr.label(), "dupecheck_rule": attr.label(), "javaxdetect_rule": attr.label(), "banneddeps_rule": attr.label(), "apprun_rule": attr.label(), "bazelrun_script": attr.label(allow_files = True), "bazelrun_data": attr.label_list(allow_files = True), "bazelrun_java_toolchain": attr.label( mandatory = False, default = "@bazel_tools//tools/jdk:current_java_toolchain", providers = [java_common.JavaToolchainInfo], ), }, ) # *************************************************************** # SpringBoot Macro # this is the entrypoint into the springboot rule def springboot( name, java_library, boot_app_class, boot_launcher_class = "org.springframework.boot.loader.JarLauncher", deps = None, deps_banned = ["junit", "mockito"], # detects common mistake of test dep pollution deps_exclude_labels = None, deps_exclude = None, deps_exclude_paths = None, deps_index_file = None, deps_use_starlark_order = None, dupeclassescheck_enable = None, dupeclassescheck_ignorelist = None, javaxdetect_enable = None, javaxdetect_ignorelist = None, include_git_properties_file = True, bazelrun_java_toolchain = None, bazelrun_script = None, bazelrun_jvm_flags = None, bazelrun_jvm_flag_list = None, bazelrun_env_flag_list = None, bazelrun_data = None, bazelrun_background = False, addins = [], tags = [], testonly = False, visibility = None, bazelrun_addopens = [], bazelrun_addexports = [], jartools_toolchains = ["@bazel_tools//tools/jdk:current_host_java_runtime"], # Issue 250 exclude = [], # deprecated classpath_index = "@rules_spring//springboot:empty.txt", # deprecated use_build_dependency_order = True, # deprecated fail_on_duplicate_classes = False, # deprecated duplicate_class_allowlist = None, # deprecated jvm_flags = "", # deprecated data = [], # deprecated restricted_to = None, target_compatible_with = []): """Bazel rule for packaging an executable Spring Boot application. Note that the rule README has more detailed usage instructions for each attribute. Args: name: **Required**. The name of the Spring Boot application. Typically this is set the same as the package name. Ex: *helloworld*. java_library: **Required**. The built jar, identified by the name of the java_library rule, that contains the Spring Boot application. boot_app_class: **Required**. The fully qualified name of the class annotated with @SpringBootApplication. Ex: *com.sample.SampleMain* deps: Optional. An additional set of Java dependencies to add to the executable. Normally all dependencies are set on the *java_library*. deps_banned: Optional. A list of strings to match against the jar filenames in the transitive graph of dependencies for this springboot app. If any of these strings is found within any jar name, the rule will fail. This is useful for detecting jars that should never go to production. The list of dependencies is obtained after the deps_exclude_labels and deps_exclude_paths processing has run. Default: [ "junit", "mockito" ] deps_exclude_labels: Optional. A list of jar labels that will be omitted from the final packaging step. This is a manual option for eliminating a problematic dependency that cannot be eliminated upstream. Ex: *["@maven//:commons_cli_commons_cli"]*. deps_exclude: Deprecated. Use deps_exclude_labels instead. Functions the same as deps_exclude_labels but retained for backward compatibility. deps_exclude_paths: Optional. This attribute provides a list of partial paths that will be omitted from the final packaging step if the string is contained within the dep filename. This is a more raw method than deps_exclude_labels for eliminating a problematic dependency/file that cannot be eliminated upstream. Ex: [*jackson-databind-*]. deps_index_file: Optional. Uses Spring Boot's [classpath index feature](https://docs.spring.io/spring-boot/docs/current/reference/html/appendix-executable-jar-format.html#executable-jar-war-index-files-classpath) to define classpath order. This feature is not commonly used, as the application must be extracted from the jar file for it to work. Ex: *my_classpath_index.idx* deps_use_starlark_order: When running the Spring Boot application from the executable jar file, setting this attribute to *True* will use the classpath order as expressed by the order of deps in the BUILD file. Otherwise it is random order. dupeclassescheck_enable: If *True*, will analyze the list of dependencies looking for any class that appears more than once, but with a different hash. This indicates that your dependency tree has conflicting libraries. dupeclassescheck_ignorelist: Optional. When using the duplicate class check, this attribute provides a file that contains a list of libraries excluded from the analysis. Ex: *dupeclass_libs.txt* javaxdetect_enable: If *True*, will analyze the list of dependencies looking for any class from javax.* package. This is a candidate for migration to jakarta. javaxdetect_ignorelist: Optional. When using the javax detect check, this attribute provides a file that contains a list of libraries excluded from the analysis. Ex: *javaxdetect_ignorelist.txt* include_git_properties_file: If *True*, will include a git.properties file in the resulting jar. bazelrun_java_toolchain: Optional. Label to the Java toolchain to use when launching the application using 'bazel run' bazelrun_script: Optional. When launching the application using 'bazel run', a default launcher script is used. This attribute can be used to provide a customized launcher script. Ex: *my_custom_script.sh* bazelrun_jvm_flags: Optional. Deprecated form of bazelrun_jvm_flag_list. Ex: *-Dcustomprop=gold -DcustomProp2=silver* bazelrun_jvm_flag_list: Optional. When launching the application using 'bazel run', an optional set of JVM flags to pass to the JVM at startup. Ex: *['-Dcustomprop=gold', '-DcustomProp2=silver']* bazelrun_env_flag_list: Optional. When launching the application using 'bazel run', an optional set of environment variables to pass to the launcher script at startup. Ex: *['PROP1=gold', 'PROP2=silver']* bazelrun_data: Uncommon option to add data files to runfiles. Behaves like the *data* attribute defined for *java_binary*. bazelrun_background: Optional. If True, the *bazel run* launcher will not block. The run command will return and process will remain running. addins: Uncommon option to add additional files to the root of the springboot jar. For example a license file. Pass an array of files from the package. tags: Optional. Bazel standard attribute. testonly: Optional. Bazel standard attribute. Defaults to False. visibility: Optional. Bazel standard attribute. jartools_toolchains: Optional. Toolchains for running build tools like singlejar, override for obscure use cases. Default: ["@bazel_tools//tools/jdk:current_java_runtime"] restricted_to: Optional. Bazel standard attribute. target_compatible_with: Optional. Bazel standard attribute. exclude: Deprecated synonym of *deps_exclude_labels* and *deps_exclude*. classpath_index: Deprecated synonym of *deps_index_file* use_build_dependency_order: Deprecated synonym of *deps_use_starlark_order* fail_on_duplicate_classes: Deprecated synonym of *dupeclassescheck_enable* duplicate_class_allowlist: Deprecated synonym of *dupeclassescheck_ignorelist* jvm_flags: Deprecated synonym of *bazelrun_jvm_flags* data: Deprecated synonym of *bazelrun_data* """ # NOTE: if you add/change any params, be sure to rerun the stardoc generator (see BUILD file) # Create the subrule names dep_aggregator_rule = name + "_" + native.package_name() + "_deps" appjar_locator_rule = name + "_" + native.package_name() + "_appjar_locator" genmanifest_rule = name + "_" + native.package_name() + "_genmanifest" genbazelrunenv_rule = name + "_" + native.package_name() + "_genbazelrunenv" gengitinfo_rule = name + "_" + native.package_name() + "_gengitinfo" genjar_rule = name + "_" + native.package_name() + "_genjar" dupecheck_rule = name + "_" + native.package_name() + "_dupecheck" javaxdetect_rule = name + "_" + native.package_name() + "_javaxdetect" bannedcheck_rule = name + "_" + native.package_name() + "_bannedcheck" apprun_rule = name + "_" + native.package_name() + "_apprun" # Handle deprecated attribute names; if modern name is not set then take # the legacy attribute value (which may be set to a default, or set by the user) if deps_exclude_labels == None and deps_exclude != None: deps_exclude_labels = deps_exclude if deps_exclude_labels == None: deps_exclude_labels = exclude if deps_index_file == None: deps_index_file = classpath_index if deps_use_starlark_order == None: deps_use_starlark_order = use_build_dependency_order if dupeclassescheck_enable == None: dupeclassescheck_enable = fail_on_duplicate_classes if dupeclassescheck_ignorelist == None: dupeclassescheck_ignorelist = duplicate_class_allowlist if bazelrun_jvm_flags == None: bazelrun_jvm_flags = jvm_flags if bazelrun_jvm_flags == None: bazelrun_jvm_flags = "" if bazelrun_jvm_flag_list != None: bazelrun_jvm_flags = bazelrun_jvm_flags + " ".join(bazelrun_jvm_flag_list) bazelrun_env_flags = "" if bazelrun_env_flag_list != None: bazelrun_env_flags = " ".join(bazelrun_env_flag_list) if bazelrun_data == None: bazelrun_data = data # assemble deps; generally all deps will come transitively through the java_library # but a user may choose to add in more deps directly into the springboot jar (rare) java_deps = [java_library] if deps != None: java_deps = [java_library] + deps # SUBRULE 1: AGGREGATE UPSTREAM DEPS # Aggregate transitive closure of upstream Java deps _depaggregator_rule( name = dep_aggregator_rule, deps = java_deps, deps_exclude_labels = deps_exclude_labels, deps_exclude_paths = deps_exclude_paths, tags = tags, testonly = testonly, restricted_to = restricted_to, target_compatible_with = target_compatible_with, ) # SUBRULE 2: GENERATE THE MANIFEST # NICER: derive the Build JDK and Boot Version values by scanning transitive deps genmanifest_out = name + "_MANIFEST.MF" native.genrule( name = genmanifest_rule, srcs = [":" + dep_aggregator_rule], cmd = "$(location @rules_spring//springboot:write_manifest.sh) " + boot_app_class + " " + boot_launcher_class + " $@ $(JAVABASE) $(SRCS)", # message = "SpringBoot rule is writing the MANIFEST.MF...", tools = ["@rules_spring//springboot:write_manifest.sh"], outs = [genmanifest_out], tags = tags, testonly = testonly, restricted_to = restricted_to, target_compatible_with = target_compatible_with, toolchains = jartools_toolchains, # so that JAVABASE is computed ) # SUBRULE 2B: GENERATE THE GIT PROPERTIES gengitinfo_out = name + "_git.properties" native.genrule( name = gengitinfo_rule, cmd = "$(location @rules_spring//springboot:write_gitinfo_properties.sh) $@", tools = ["@rules_spring//springboot:write_gitinfo_properties.sh"], outs = [gengitinfo_out], tags = tags, testonly = testonly, restricted_to = restricted_to, target_compatible_with = target_compatible_with, stamp = 1, ) # SUBRULE 2C: CLASSPATH INDEX # see https://github.com/salesforce/rules_spring/issues/81 _appjar_locator_rule( name = appjar_locator_rule, app_dep = java_library, tags = tags, testonly = testonly, restricted_to = restricted_to, target_compatible_with = target_compatible_with, ) # SUBRULE 3: INVOKE THE BASH SCRIPT THAT DOES THE PACKAGING # The resolved input_file_paths array is made available as the $(SRCS) token in the cmd string. # Skylark will convert the logical input_file_paths into real file system paths when surfaced in $(SRCS) # cmd format (see springboot_pkg.sh) # param0: directory containing the springboot rule # param1: location of the jar utility (singlejar) # param2: boot application main classname (the @SpringBootApplication class) # param3: spring boot launcher class # param4: jdk path for running java tools e.g. jar; $(JAVABASE) # param5: compiled application jar name # param6: use build file deps order [True|False] # param7: include git.properties file in resulting jar # param8: executable jar output filename to write to # param9: compiled application jar # param10: manifest file # param11: git.properties file # param12: classpath_index file # param13-N: upstream transitive dependency jar(s) native.genrule( name = genjar_rule, srcs = [ ":" + appjar_locator_rule, ":" + genmanifest_rule, ":" + gengitinfo_rule, deps_index_file, ] + addins + [ "@rules_spring//springboot:addin_end.txt", ":" + dep_aggregator_rule, ], cmd = "$(location @rules_spring//springboot:springboot_pkg.sh) " + "$(location @bazel_tools//tools/jdk:singlejar) " + boot_app_class + " " + boot_launcher_class + " $(JAVABASE) " + name + " " + str(deps_use_starlark_order) + " " + str(include_git_properties_file) + " $@ $(SRCS)", tools = [ "@rules_spring//springboot:springboot_pkg.sh", "@bazel_tools//tools/jdk:singlejar", ], tags = tags, testonly = testonly, restricted_to = restricted_to, target_compatible_with = target_compatible_with, outs = [_get_springboot_jar_file_name(name)], toolchains = jartools_toolchains, # so that JAVABASE is computed visibility = visibility, ) # SUBRULE 3B: GENERATE THE ENV VARIABLES USED BY THE BAZELRUN LAUNCHER SCRIPT genbazelrunenv_out = name + "_bazelrun_env.sh" native.genrule( name = genbazelrunenv_rule, srcs = bazelrun_data, cmd = "$(location @rules_spring//springboot:write_bazelrun_env.sh) " + name + " " + _get_springboot_jar_file_name(name) + " " + _get_relative_package_path() + " $@ " + _convert_starlarkbool_to_bashbool(bazelrun_background) + " $(SRCS)" + " start_flags" + " " + " ".join(["--add-exports=" + element for element in bazelrun_addexports]) + " " + " ".join(["--add-opens=" + element for element in bazelrun_addopens]) + " " + bazelrun_jvm_flags + " start_envs" + " " + bazelrun_env_flags, # message = "SpringBoot rule is writing the bazel run launcher env...", tools = ["@rules_spring//springboot:write_bazelrun_env.sh"], outs = [genbazelrunenv_out], tags = tags, testonly = testonly, restricted_to = restricted_to, target_compatible_with = target_compatible_with, ) # SUBRULE 4a: RUN THE DUPE CHECKER (if enabled) # Skip the dupeclasses_rule instantiation entirely if disabled because # running this rule requires Python3 installed. If a workspace does not have # Python3 available, they can just never enable dupeclassescheck_enable and be ok dupecheck_rule_label = None if dupeclassescheck_enable: _dupeclasses_rule( name = dupecheck_rule, script = "@rules_spring//springboot:check_dupe_classes", springbootjar = genjar_rule, dupeclassescheck_enable = dupeclassescheck_enable, dupeclassescheck_ignorelist = dupeclassescheck_ignorelist, out = "dupecheck_results.txt", tags = tags, testonly = testonly, restricted_to = restricted_to, target_compatible_with = target_compatible_with, ) dupecheck_rule_label = ":" + dupecheck_rule # SUBRULE 4b: RUN THE JAVAX DETECTOR (if enabled) # Skip the javaxdetect_rule instantiation entirely if disabled because # running this rule requires Python3 installed. If a workspace does not have # Python3 available, they can just never enable javaxdetect_enable and be ok javaxdetect_rule_label = None if javaxdetect_enable: _javaxdetect_rule( name = javaxdetect_rule, script = "@rules_spring//springboot:detect_javax_classes", springbootjar = genjar_rule, javaxdetect_enable = javaxdetect_enable, javaxdetect_ignorelist = javaxdetect_ignorelist, out = "javaxdetect_results.txt", tags = tags, testonly = testonly, restricted_to = restricted_to, target_compatible_with = target_compatible_with, ) javaxdetect_rule_label = ":" + javaxdetect_rule # SUBRULE 4c: RUN THE BANNED DEP CHECKER (if enabled) # Skip the bannedcheck_rule instantiation entirely if disabled because # running this rule requires Python3 installed. If a workspace does not have # Python3 available, they can just never enable dupeclassescheck_enable and be ok bannedcheck_rule_label = None if deps_banned != None: _banneddeps_rule( springboot_rule_name = name, name = bannedcheck_rule, deps = [":" + dep_aggregator_rule], deps_banned = deps_banned, out = "bannedcheck_results.txt", tags = tags, testonly = testonly, restricted_to = restricted_to, target_compatible_with = target_compatible_with, ) bannedcheck_rule_label = ":" + bannedcheck_rule # SUBRULE 5: PROVIDE A WELL KNOWN RUNNABLE RULE TYPE FOR IDE SUPPORT # The presence of this rule makes a Spring Boot entry point class runnable # in IntelliJ (it won't run as part of a packaged Spring Boot jar, ie this # won't run java -jar springboot.jar, but close enough) # Making the springboot rule itself executable is not recognized by IntelliJ # (because IntelliJ doesn't know how to handle the springboot rule type or # because of a misconfiguration on our end?) native.java_binary( name = apprun_rule, main_class = boot_app_class, runtime_deps = java_deps, tags = tags, testonly = testonly, restricted_to = restricted_to, target_compatible_with = target_compatible_with, ) if bazelrun_script == None: bazelrun_script = "@rules_spring//springboot:default_bazelrun_script.sh" # MASTER RULE: Create the composite rule that will aggregate the outputs of the subrules _springboot_rule( name = name, app_compile_rule = java_library, bazelrun_java_toolchain = bazelrun_java_toolchain, dep_aggregator_rule = ":" + dep_aggregator_rule, genmanifest_rule = ":" + genmanifest_rule, genbazelrunenv_rule = ":" + genbazelrunenv_rule, gengitinfo_rule = ":" + gengitinfo_rule, genjar_rule = ":" + genjar_rule, dupecheck_rule = dupecheck_rule_label, javaxdetect_rule = javaxdetect_rule_label, apprun_rule = ":" + apprun_rule, bazelrun_script = bazelrun_script, bazelrun_data = bazelrun_data, tags = tags, testonly = testonly, restricted_to = restricted_to, target_compatible_with = target_compatible_with, visibility = visibility, ) # end springboot macro def _get_springboot_jar_file_name(name): if name.endswith(".jar"): fail("the name attribute of the springboot rule should not end with '.jar'") return name + ".jar" def _convert_starlarkbool_to_bashbool(starlarkbool): if starlarkbool: return "true" return "false" def _get_relative_package_path(): """Convert the current package name into a relative file system path. Because this value is used as a positional argument, if native.package_name() returns empty string (e.g. the target is //:foo), we replace it with a token so that it won't confuse the parsing of the positional arguments. """ if not native.package_name(): return "root" return native.package_name() + "/" ================================================ FILE: springboot/springboot_doc.md ================================================ ## Springboot() Attributes This page has moved [here](attributes.bzl). ================================================ FILE: springboot/springboot_pkg.sh ================================================ #!/bin/bash # # Copyright (c) 2017-2021, salesforce.com, inc. # All rights reserved. # Licensed under the BSD 3-Clause license. # For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause # # This script outputs a proper Spring Boot executable jar. # This script is callable from a Bazel build (via a genrule in springboot.bzl). # It takes a standard Bazel java_binary output executable jar and 'springboot-ifies' it. # See springboot.bzl to see how it is invoked from the build. # You should not be trying to invoke this file directly from your BUILD file. # Debugging? This script outputs a lot of useful debugging information under # /tmp/bazel/debug/springboot for each Spring Boot app. # fail on error (https://github.com/salesforce/rules_spring/issues/100) set -e ruledir=$(pwd) singlejar_cmd=$(pwd)/$1 mainclass=$2 spring_boot_launcher_class=${3} javabase=$4 appjar_name=$5 deps_starlark_order=$6 include_git_properties_file=$7 outputjar=$8 appjar=$9 manifest=${10} gitpropsfile=${11} deps_index_file=${12} first_addin_arg=13 # converting starlark booleans to bash booleans if [ $deps_starlark_order = "True" ]; then deps_starlark_order=true else deps_starlark_order=false fi if [ $include_git_properties_file = "True" ]; then include_git_properties_file=true else include_git_properties_file=false fi # package name (not guaranteed to be globally unique) packagename=$(basename $appjar_name) # generate a package working path sha (globally unique). this allows this rule to function correctly # if sandboxing is disabled. the wrinkle is deriving the right shasum util shasum_output=$(shasum -h 2>/dev/null) || true if [[ $shasum_output = *"Usage"* ]]; then shasum_install_msg="Hashing command line utility 'shasum' will be used" packagesha_raw=$(echo "$outputjar" | shasum ) else # linux command is sha1sum, assume that packagesha_raw=$(echo "$outputjar" | sha1sum ) shasum_install_msg="Hashing command line utility 'sha1sum' will be used" fi export packagesha=$(echo "$packagesha_raw" | cut -d " " -f 1 ) # Build time telemetry build_date_time=$(date) build_time_start=$SECONDS springboot_rule_tmpdir=${tmpdir:-/tmp}/bazel mkdir -p $springboot_rule_tmpdir # by mistake, this variable got lower cased for a while; it should be upper case but # now we should check for either, through 2025 if [ -z "${debug_springboot_rule}" ]; then if [ -z "${DEBUG_SPRINGBOOT_RULE}" ]; then debugfile=/dev/null debug_notset=1 fi fi if [ -z "${debug_notset}" ]; then debugdir=$springboot_rule_tmpdir/debug/springboot mkdir -p $debugdir debugfileName=$packagename-$packagesha debugfile=$debugdir/${debugfileName}.log echo "SPRING BOOT DEBUG LOG: $debugfile" fi >$debugfile # Write debug header echo "" >> $debugfile echo "*************************************************************************************" >> $debugfile echo "Build time: $build_date_time" >> $debugfile echo "SPRING BOOT PACKAGER FOR BAZEL" >> $debugfile echo " ruledir $ruledir (build working directory)" >> $debugfile echo " singlejar $singlejar_cmd (path to the singlejar utility)" >> $debugfile echo " mainclass $mainclass (classname of the @SpringBootApplication class for the manifest.MF file entry)" >> $debugfile echo " bootloader $spring_boot_launcher_class (classname of the Spring Boot Loader to use)" >> $debugfile echo " outputjar $outputjar (the executable JAR that will be built from this rule)" >> $debugfile echo " javabase $javabase (the path to the JDK2)" >> $debugfile echo " appjar $appjar (contains the .class files for the Spring Boot application)" >> $debugfile echo " appjar_name $appjar_name (unused, is the appjar filename without the .jar extension)" >> $debugfile echo " manifest $manifest (the location of the generated manifest.MF file)" >> $debugfile echo " deps_index_file $deps_index_file (the location of the classpath index file - optional)" >> $debugfile echo " deplibs (list of upstream transitive dependencies, these will be incorporated into the jar file in BOOT-INF/lib )" >> $debugfile echo " gitpropsfile $gitpropsfile (the location of the generated git.properties file)" >> $debugfile echo "*************************************************************************************" >> $debugfile # compute path to jar utility pushd . > /dev/null cd $javabase/bin jar_command=$(pwd)/jar popd > /dev/null echo "Jar command:" >> $debugfile echo $jar_command >> $debugfile echo $shasum_install_msg >> $debugfile echo "Unique identifier for this build: [$packagesha] computed from [$packagesha_raw]" >> $debugfile # Setup working directories. Working directory is unique to this package path (uses SHA of path) # to tolerate non-sandboxed builds if so configured. base_working_dir=$ruledir/$packagesha working_dir=$base_working_dir/working echo "DEBUG: packaging working directory $working_dir" >> $debugfile mkdir -p $working_dir/BOOT-INF/lib mkdir -p $working_dir/BOOT-INF/classes # We need a unique scratch work area TMP_working_dir=$base_working_dir/tmp mkdir -p $TMP_working_dir # Addins is the feature to add files to the root of the springboot jar # The addins are listed in order as args, until the addin_end.txt file marks the end i=$first_addin_arg while [ "$i" -le "$#" ]; do eval "addin=\${$i}" echo " ADDINt: $addin" >> $debugfile if [[ $addin == *addin_end.txt ]]; then i=$((i + 1)) echo " ADDIN end found: $addin" >> $debugfile break fi echo " ADDIN: $addin" >> $debugfile cp $addin $working_dir i=$((i + 1)) done first_jar_arg=$i echo "" >> $debugfile # log the list of dep jars we were given i=$first_jar_arg while [ "$i" -le "$#" ]; do eval "lib=\${$i}" echo " DEPLIB: $lib" >> $debugfile i=$((i + 1)) done echo "" >> $debugfile # Extract the compiled Boot application classes into BOOT-INF/classes # this must include the application's main class (annotated with @SpringBootApplication) cd $working_dir/BOOT-INF/classes # Extract all files except META-INF/MANIFEST.MF to avoid duplicate manifest entries $jar_command -xf $ruledir/$appjar # Remove the extracted MANIFEST.MF to prevent duplicate entries in the final jar rm -f META-INF/MANIFEST.MF # Copy all transitive upstream dependencies into BOOT-INF/lib # The dependencies are passed as arguments to the script, starting at index $first_jar_arg cd $working_dir # Below we iterate over all deps and build a string that contains all jar paths, # space separated boot_inf_lib_jars="" i=$first_jar_arg while [ "$i" -le "$#" ]; do eval "lib=\${$i}" libname=$(basename $lib) libdir=$(dirname $lib) echo "DEBUG: libname: $libname" >> $debugfile echo "DEBUG: libdir: $libdir" >> $debugfile # Some paths may contain % as a result of Bazel URL encoding the folder name, such as # user@example.com becoming user%40example.com. Such folders fail to load (see Issue #270). # Translate % to _ to avoid this issue. libdir=${libdir//%/_} echo "DEBUG: sanitized libdir: $libdir" >> $debugfile if [[ $libname == *jar ]]; then # we only want to process .jar files as libs if [[ $libname == *spring-boot-loader* ]] || [[ $libname == *spring_boot_loader* ]] || [[ $libname == librootclassloader_lib* ]]; then # if libname contains the string 'spring-boot-loader' then... # the Spring Boot Loader classes are special, they must be extracted at the root level /, # not in BOOT-INF/lib/loader.jar nor BOOT-INF/classes/**/*.class # we only extract org/* and com/* since we don't want the toplevel META-INF files $jar_command xf $ruledir/$lib com org META-INF/services else # copy the jar into BOOT-INF/lib, being mindful to prevent name collisions by using subdirectories (see Issue #61) # the logic to truncate paths below doesn't need to be perfect, it just hopes to simplify the jar paths so they look better for most cases # for maven_install deps, the algorithm to correctly identify the end of the server path and the groupId is not defined # # a note on duplicate artifacts: # if the same dep (same gav) is brought in multiple times by different # maven_install rules, we do not end up with multiple copies of the same # jar. our logic handles this case because of how we truncate the paths # below: both (identical) jars will get copied into the same location, # the 2nd one overwriting the first one, and therefore we end of with # only a single jar in the final assembly, as desired # example: 2 maven_install rules bring in spring-boot-starter-jetty: # "maven" rule: external/maven/v1/https/repo1.maven.org/maven2/org/springframework/boot/spring-boot-starter-jetty/2.4.1/spring-boot-starter-jetty-2.4.1.jar # "spring_boot_starter_jetty" rule: external/spring_boot_starter_jetty/v1/https/repo1.maven.org/maven2/org/springframework/boot/spring-boot-starter-jetty/2.4.1/spring-boot-starter-jetty-2.4.1.jar # the relative destpath we compute below starts after "maven2" # # related to above, a note on duplicate jar entries: # if the jar cmd is called with the same path more than once, for example: # jar -cf foo.jar a/b/c.txt d/e/f.txt a/b/c.txt, the first path "wins", # subsequent duplicate paths are ignored. so for the example above, the # jar will have entries: a/b/c.txt, d/e/f.txt # this "first one wins" behavior is also what we want when duplicate # dependencies are encountered if [[ ${libdir} == *external*maven2* ]]; then # this is a maven_install jar probably from maven central # libdir: bazel-out/darwin-fastbuild/bin/external/maven/v1/https/repo1.maven.org/maven2/org/springframework/boot/spring-boot-starter-logging/2.2.1.RELEASE/spring-boot-starter-logging-2.2.1.RELEASE.jar # libdestdir: BOOT-INF/lib/org/springframework/boot/spring-boot-starter-logging/2.2.1.RELEASE/spring-boot-starter-logging-2.2.1.RELEASE.jar libdestdir="BOOT-INF/lib/${libdir#*maven2}" elif [[ ${libdir} == *external*public* ]]; then # this is a maven_install jar probably from Sonatype Nexus # libdir: bazel-out/darwin-fastbuild/bin/external/maven/v1/https/ournexus.acme.com/nexus/content/groups/public/org/springframework/boot/spring-boot-starter-logging/2.2.1.RELEASE/spring-boot-starter-logging-2.2.1.RELEASE.jar # libdestdir: BOOT-INF/lib/org/springframework/boot/spring-boot-starter-logging/2.2.1.RELEASE/spring-boot-starter-logging-2.2.1.RELEASE.jar libdestdir="BOOT-INF/lib/${libdir#*public}" elif [[ ${libdir} == bazel-out* ]]; then # this is an internally built jar from the workspace, use the Bazel package name as the path to prevent name collisions # libdir: bazel-out/darwin-fastbuild/bin/projects/libs/acme/blue_lib/liblue_lib.jar # libdestdir: BOOT-INF/lib/projects/libs/acme/blue_lib/liblue_lib.jar libdestdir="BOOT-INF/lib/${libdir#*bin}" else # something else, just copy into BOOT-INF/lib using the full path as it exists # this works fine, but you will see some Bazel internal output dirs as part of the path in the jar libdestdir="BOOT-INF/lib/${libdir}" fi mkdir -p ${libdestdir} libdestpath=${libdestdir}/$libname boot_inf_lib_jars="${boot_inf_lib_jars} ${libdestpath}" cp -f $ruledir/$lib $libdestpath fi fi i=$((i + 1)) done elapsed_trans=$(( $SECONDS - build_time_start )) echo "DEBUG: finished copying transitives into BOOT-INF/lib, elapsed time (seconds): $elapsed_trans" >> $debugfile # Generate Spring Boot index files for jarmode=tools support echo "DEBUG: generating Spring Boot index files" >> $debugfile # Generate classpath.idx echo "DEBUG: generating BOOT-INF/classpath.idx" >> $debugfile classpath_idx_file="BOOT-INF/classpath.idx" > $classpath_idx_file # Create empty file for jar_path in $boot_inf_lib_jars; do if [[ -f "$jar_path" ]]; then # Clean up double slashes and use the actual jar path as it appears in the jar file clean_jar_path=$(echo "$jar_path" | sed 's|//|/|g') echo "- \"$clean_jar_path\"" >> $classpath_idx_file fi done # Generate layers.idx echo "DEBUG: generating BOOT-INF/layers.idx" >> $debugfile layers_idx_file="BOOT-INF/layers.idx" cat > $layers_idx_file << 'EOF' - "dependencies": - "BOOT-INF/lib/" - "spring-boot-loader": - "org/" - "snapshot-dependencies": - "application": - "BOOT-INF/classes/" - "BOOT-INF/classpath.idx" - "BOOT-INF/layers.idx" - "META-INF/" EOF # Inject the Git properties into a properties file in the jar # (the -f is needed when remote caching is used, as cached files come down as r-x and # if you rerun the build it needs to overwrite) if [[ "$include_git_properties_file" == true ]]; then echo "DEBUG: adding git.properties" >> $debugfile cat $ruledir/$gitpropsfile >> $debugfile cp -f $ruledir/$gitpropsfile $working_dir/BOOT-INF/classes/git.properties fi # Inject the classpath index (unless it is the default empty.txt file). Requires Spring Boot version 2.3+ # https://docs.spring.io/spring-boot/docs/current/reference/html/appendix-executable-jar-format.html#executable-jar-war-index-files-classpath if [[ ! $deps_index_file = *empty.txt ]]; then cp $ruledir/$deps_index_file $working_dir/BOOT-INF/classpath.idx fi # Create the output jar cd $working_dir # Write debug telemetry data echo "DEBUG: Creating the JAR file $working_dir" >> $debugfile echo "DEBUG: jar contents:" >> $debugfile find . >> $debugfile elapsed_pre_jar=$(( $SECONDS - build_time_start )) echo "DEBUG: elapsed time (seconds): $elapsed_pre_jar" >> $debugfile # First use jar to create a correct jar file for Spring Boot # Note that a critical part of this step is to pass option 0 into the jar command # that tells jar not to compress the jar, only package it. Spring Boot does not # allow the jar file to be compressed (it will fail at startup). raw_output_jar=$ruledir/${outputjar}.raw echo "DEBUG: Running jar command to produce $raw_output_jar" >> $debugfile # The current working directory now has exactly the structure we want to jar up # HOWEVER, instead of running jar just once, we run jar multiple times to ensure # that the jar entries are added in the required order to the jar: # Spring Boot Loader -> BOOT-INF/classes -> BOOT-INF/lib # A different order can create confusing classpath ordering issues when # the uber jar is executed using java -jar # Move BOOT-INF/classes and BOOT-INF/lib out of the way, into this tmp directory tmp_boot_inf_dir=$TMP_working_dir/boot_inf # We need this directory to be clean (we'll re-create it below) rm -rf $tmp_boot_inf_dir # Move BOOT-INF/classes tmp_classes_dir=$tmp_boot_inf_dir/classes mkdir -p "${tmp_classes_dir}/BOOT-INF" mv BOOT-INF/classes "${tmp_classes_dir}/BOOT-INF" # Move BOOT-INF/lib tmp_lib_dir=$tmp_boot_inf_dir/lib mkdir -p "${tmp_lib_dir}/BOOT-INF" mv BOOT-INF/lib "${tmp_lib_dir}/BOOT-INF" # Given the mv cmds above, we now jar everything EXCEPT BOOT-INF/classes and BOOT-INF/lib $jar_command -cfm0 $raw_output_jar $ruledir/$manifest . 2>&1 | tee -a $debugfile # Now add BOOT-INF/classes cd $tmp_classes_dir $jar_command -uf0 $raw_output_jar . 2>&1 | tee -a $debugfile cd $working_dir # Finally add BOOT-INF/lib cd $tmp_lib_dir if [ "$deps_starlark_order" == true ]; then # if this command fails due to the command line being too long, please see the docs # about setting deps_starlark_order=False as a workaround $jar_command -uf0 $raw_output_jar $boot_inf_lib_jars 2>&1 | tee -a $debugfile else $jar_command -uf0 $raw_output_jar . 2>&1 | tee -a $debugfile fi cd $working_dir ( # Use Bazel's singlejar to re-jar it which normalizes timestamps as Jan 1 2010 # note that it does not use the manifest from the jar file, which is a bummer # so we have to respecify the manifest data # TODO we should rewrite write_manfiest.sh to produce inputs compatible for singlejar (Issue #27) singlejar_options="--normalize --dont_change_compression" # add in --verbose for more details from command singlejar_mainclass="--main_class $spring_boot_launcher_class" # #205: Execute the singlejar command from the original ruledir, so the build-data.properties file # contains a deterministic, relative path for 'build.target'. cd "$ruledir" $singlejar_cmd $singlejar_options $singlejar_mainclass \ --deploy_manifest_lines "Start-Class: $mainclass" \ --deploy_manifest_lines "Spring-Boot-Classes: BOOT-INF/classes/" \ --deploy_manifest_lines "Spring-Boot-Lib: BOOT-INF/lib/" \ --deploy_manifest_lines "Spring-Boot-Classpath-Index: BOOT-INF/classpath.idx" \ --deploy_manifest_lines "Spring-Boot-Layers-Index: BOOT-INF/layers.idx" \ --sources $raw_output_jar \ --output "$outputjar" 2>&1 | tee -a $debugfile ) if [ $? -ne 0 ]; then echo "ERROR: Failed creating the JAR file $working_dir." | tee -a $debugfile fi cd $ruledir # Elapsed build time build_time_end=$SECONDS build_time_duration=$(( build_time_end - build_time_start )) echo "DEBUG: SpringBoot packaging subrule elapsed time (seconds) for $packagename: $build_time_duration" >> $debugfile ================================================ FILE: springboot/src/main/java/com/salesforce/rulesspring/cli/SpringBootInspector.java ================================================ package com.salesforce.rulesspring.cli; import java.io.BufferedWriter; import java.io.File; import java.io.FileWriter; import com.salesforce.rulesspring.index.SpringBootIndexReporter; import com.salesforce.rulesspring.index.IndexOfFiles; import com.salesforce.rulesspring.index.SpringBootJarIndexer; public class SpringBootInspector { public static void main(String[] args) throws Exception { if (args.length < 3) { System.out.println("ERROR: this tool needs at least 3 arguments"); usage(); return; } Command cmd = parseArgs(args); if (cmd == null) { // command line was invalid, and reason was already logged, just exit return; } if ("inspector".equals(cmd.mode)) { File jarFile = new File(cmd.jarFilepath); if (!jarFile.exists()) { System.err.println("ERROR: File "+cmd.jarFilepath+" does not exist."); return; } System.out.println("Spring Boot Jar absolute path: "+jarFile.getAbsolutePath()); if ("index".equals(cmd.operation)) { File indexFile = new File(cmd.outputPath); if (indexFile.exists()) { System.err.println("ERROR: File "+indexFile.getAbsolutePath()+" already exists and we don't overwrite files."); return; } System.out.println("Index output file absolute path: "+indexFile.getAbsolutePath()); SpringBootJarIndexer indexer = new SpringBootJarIndexer(jarFile); IndexOfFiles index = indexer.indexJar(cmd.recursive); SpringBootIndexReporter reporter = new SpringBootIndexReporter(); String report = reporter.generateReport(index, cmd.reportOptions); BufferedWriter writer = new BufferedWriter(new FileWriter(indexFile)); writer.write(report); writer.close(); System.out.println("Wrote index file as "+cmd.outputPath); } else { System.err.println("Operation "+cmd.operation+" is not implemented."); } } } protected static void usage() { System.out.println("Spring Boot Jar Inspector"); System.out.println("Usage:"); System.out.println(" java -jar springboot-cli.jar MODE OPERATION [operation specific args]"); System.out.println(" MODE: 'inspector' for running operations on a single Spring Boot jar; 'comparator' when running operations with multiple Spring Boot jars"); System.out.println(" OPERATION: a keyword that activates a particular operation; operations are documented below"); System.out.println("\n"); System.out.println("INSPECTOR OPERATIONS:"); System.out.println("\n"); System.out.println(" index: generates an index of files within the Spring Boot jar."); System.out.println(" java -jar springboot-cli.jar inspect index SPRING-BOOT-JAR-PATH INDEX-REPORT-PATH [--recursive] [--report REPORT-OPTIONS]"); System.out.println(" SPRING-BOOT-JAR-PATH: path to your Spring Boot executable jar file; it must exist"); System.out.println(" INDEX-REPORT-PATH: path to write the report from this tool; it must not already exist"); System.out.println(" --recursive: if present, inspector will also index the contents of the nested jars found inside the Spring Boot jar"); System.out.println(" REPORT-OPTIONS: optional list of modifiers to the reporting engine; see docs for details"); } protected static Command parseArgs(String[] args) { // TODO this is pretty awkward but keeping it simple for now Command cmd = new Command(); cmd.mode = args[0]; cmd.operation = args[1]; System.out.println("Mode: "+cmd.mode); System.out.println("Operation: "+cmd.operation); int optionalArgIndex = 2; if ("inspector".equals(cmd.mode)) { if ("index".equals(cmd.operation)) { if (args.length < 4) { System.out.println("ERROR: Not enough arguments for the index command."); usage(); return null; } cmd.jarFilepath = args[2]; cmd.outputPath = args[3]; System.out.println("Spring Boot Jar: "+cmd.jarFilepath); System.out.println("Index output file: "+cmd.outputPath); optionalArgIndex = 4; } } parseOptionalArgs(args, optionalArgIndex, cmd); return cmd; } protected static void parseOptionalArgs(String[] args, int index, Command cmd) { for (int i = index; i libraries = new ArrayList<>(); protected List classes = new ArrayList<>(); protected List resources = new ArrayList<>(); public IndexOfFiles(String jarPath) { this.jarPath = jarPath; } public IndexOfFiles(IndexedFile parentIndex, String jarPath) { this.parentIndex = parentIndex; this.isNestedJarIndex = true; this.jarPath = jarPath; } public void addIndexEntry(IndexedFile indexEntry) { switch (indexEntry.type) { case LIBRARY: libraries.add(indexEntry); break; case CLASS: classes.add(indexEntry); break; case RESOURCE: resources.add(indexEntry); break; default: throw new IllegalStateException("Somebody added a new Index entry type, but forgot to build an index collection for it."); } } public String getJarPath() { return jarPath; } public IndexedFile getParentIndex() { return parentIndex; } public List getLibraries() { return libraries; } public List getClasses() { return classes; } public List getResources() { return resources; } } ================================================ FILE: springboot/src/main/java/com/salesforce/rulesspring/index/IndexedFile.java ================================================ package com.salesforce.rulesspring.index; import java.nio.file.attribute.FileTime; import java.util.Comparator; import java.util.zip.ZipEntry; /** * Represents a file found inside of a jar file. */ public class IndexedFile { // library (jar), class, or resource file protected IndexFileType type; // full path inside of the jar file protected String fullPath; // the filename, i.e. the last path element of the fullPath protected String filename; protected long sizeInBytes = 0; protected long createdTimeMillis = 0; protected long modifiedTimeMillis = 0; // if this index entry is for a file found in a nested jar inside of an outer jar, parentLibrary will // point to the index of the parent jar protected IndexedFile parentLibrary = null; static IndexedFile parseZipEntry(IndexedFile parentLibrary, ZipEntry zipEntry) { IndexedFile indexEntry = new IndexedFile(); indexEntry.fullPath = zipEntry.getName(); indexEntry.filename = indexEntry.fullPath; String fp = indexEntry.fullPath; if (fp.contains("/")) { int lastSlash = fp.lastIndexOf("/"); indexEntry.filename = fp.substring(lastSlash+1); } if (fp.contains("BOOT-INF/lib") && fp.endsWith(".jar")) { indexEntry.type = IndexFileType.LIBRARY; } else if (fp.endsWith(".class")) { indexEntry.type = IndexFileType.CLASS; } else { indexEntry.type = IndexFileType.RESOURCE; } indexEntry.sizeInBytes = zipEntry.getSize(); FileTime fTime = zipEntry.getCreationTime(); if (fTime != null) { indexEntry.createdTimeMillis = fTime.toMillis(); } fTime = zipEntry.getLastModifiedTime(); if (fTime != null) { indexEntry.modifiedTimeMillis = fTime.toMillis(); } return indexEntry; } public static class FullPathComparator implements Comparator { @Override public int compare(IndexedFile e1, IndexedFile e2) { return e1.fullPath.compareTo(e2.fullPath); } } public static class FilenameComparator implements Comparator { @Override public int compare(IndexedFile e1, IndexedFile e2) { return e1.filename.compareTo(e2.filename); } } } ================================================ FILE: springboot/src/main/java/com/salesforce/rulesspring/index/SpringBootIndexReporter.java ================================================ package com.salesforce.rulesspring.index; import java.util.Comparator; import java.util.List; /** * Generates the text report with the results of an indexing operation. * This class is pretty simple, so the code serves as the documentation. *

* To see what options are implemented, see parseOptions() below. */ public class SpringBootIndexReporter { protected boolean includeLibs = true; protected boolean includeClasses = true; protected boolean includeResources = true; protected boolean prettyHeadings = true; protected boolean writeFullPaths = false; protected boolean writeFileSize = false; protected boolean writeCreatedTime = false; protected boolean writeModifiedTime = false; protected boolean sortOnFullPaths = false; public SpringBootIndexReporter() { } public String generateReport(IndexOfFiles index) { return this.generateReport(index, null); } public String generateReport(IndexOfFiles index, String options) { StringBuffer result = new StringBuffer(); parseOptions(options); Comparator sortOrder = new IndexedFile.FilenameComparator(); if (sortOnFullPaths) { sortOrder = new IndexedFile.FullPathComparator(); } if (prettyHeadings) { result.append("Jar File: "); result.append(index.getJarPath()); result.append("\n"); } if (includeLibs) { index.libraries.sort(sortOrder); processList(index.libraries, "Libraries", result); } if (includeClasses) { index.classes.sort(sortOrder); processList(index.classes, "Classes", result); } if (includeResources) { index.resources.sort(sortOrder); processList(index.resources, "Resources", result); } return result.toString(); } protected void parseOptions(String options) { if (options == null) { return; } includeLibs = options.contains("L"); // write the list of .jar files found includeClasses = options.contains("C"); // write the list of .class files found includeResources = options.contains("R"); // write the list of other files found prettyHeadings = options.contains("H"); // write pretty headings into the output writeFullPaths = options.contains("F"); // write full paths of each entry writeFileSize = options.contains("Z"); // write the file size of each file writeCreatedTime = options.contains("B"); // write the created time of each file writeModifiedTime = options.contains("M"); // write the modified time of each file sortOnFullPaths = options.contains("S"); // when sorting, sort on the path and not the filename } protected void processList(List list, String headingLabel, StringBuffer result) { if (prettyHeadings) { result.append("\n\n"); result.append(headingLabel); result.append("\n---------------\n"); } for (IndexedFile lib : list) { if (writeFullPaths) { result.append(lib.fullPath); } else { result.append(lib.filename); } if (writeFileSize) { result.append(" size="); result.append(""+lib.sizeInBytes); } if (writeCreatedTime) { result.append(" created="); result.append(""+lib.createdTimeMillis); } if (writeModifiedTime) { result.append(" modified="); result.append(""+lib.modifiedTimeMillis); } result.append("\n"); } } } ================================================ FILE: springboot/src/main/java/com/salesforce/rulesspring/index/SpringBootJarIndexer.java ================================================ package com.salesforce.rulesspring.index; import java.io.File; import java.io.IOException; import java.util.Collections; import java.util.Enumeration; import java.util.zip.ZipEntry; import java.util.zip.ZipFile; /** * Produces an index from the contents of a Spring Boot jar. */ public class SpringBootJarIndexer { protected File bootJarFile; public SpringBootJarIndexer(File jarFile) { this.bootJarFile = jarFile; } /** * Index the contents of the Spring Boot jar. * * @param recursive if true, it will produce child indices of each nested jar inside the Spring Boot executable jar. */ public IndexOfFiles indexJar(boolean recursive) throws IOException { IndexOfFiles index = new IndexOfFiles(bootJarFile.getAbsolutePath()); try (ZipFile zipFile = new ZipFile(this.bootJarFile)) { Enumeration entries = zipFile.entries(); for (ZipEntry entry : Collections.list(entries)) { if (entry.isDirectory()) { continue; } IndexedFile indexEntry = IndexedFile.parseZipEntry(null, entry); index.addIndexEntry(indexEntry); if (recursive && indexEntry.type.equals(IndexFileType.LIBRARY)) { // TODO do the nested indexing indexJar(indexEntry, entry); } } } return index; } /** * Create a child index for a nested jar. */ protected IndexOfFiles indexJar(IndexedFile parentLibrary, ZipEntry nestedJar) throws IOException { // TODO this needs to be reworked to open the jar from the ZipEntry IndexOfFiles index = new IndexOfFiles(bootJarFile.getAbsolutePath()); try (ZipFile zipFile = new ZipFile(this.bootJarFile)) { Enumeration entries = zipFile.entries(); for (ZipEntry entry : Collections.list(entries)) { if (entry.isDirectory()) { continue; } IndexedFile indexEntry = IndexedFile.parseZipEntry(parentLibrary, entry); index.addIndexEntry(indexEntry); } } return index; } } ================================================ FILE: springboot/src/test/java/com/salesforce/rulesspring/index/SpringBootJarIndexerTest.java ================================================ package com.salesforce.rulesspring.index; public class SpringBootJarIndexerTest { } ================================================ FILE: springboot/testing_springboot.md ================================================ ## Implementing Tests for SpringBoot Applications in Bazel Before reading this document, please read Spring Boot documentation on how to write Spring Boot tests in general. Documents that explain the *SpringBootTest* annotation is what you should look for. This document explains how to invoke those tests from your Bazel build. Be sure to also look at the [example application](../../examples/helloworld) for actual test implementations. The code snippets below assume you have a Spring Boot application with *BUILD* file as: ```starlark java_library( name = "helloworld_lib", srcs = glob(["src/main/java/**/*.java"]), resources = glob(["src/main/resources/**"]), deps = ...redacted..., ) springboot( name = "helloworld", boot_app_class = "com.sample.SampleMain", java_library = ":helloworld_lib", ) ``` ### Unit Tests Your unit tests should operate against the *java_library* target, not the *springboot* target. Because of this, unit tests are just standard Bazel Java. Your *BUILD* file will have: ```starlark test_deps = [ "@maven//:junit_junit", "@maven//:org_hamcrest_hamcrest_core", ] java_test( name = "SampleRestUnitTest", srcs = ["src/test/java/com/sample/SampleRestUnitTest.java"], deps = [ ":helloworld_lib" ] + test_deps, ) ``` ### Functional Tests (starts an application context) Functional tests need to invoke the Spring Boot machinery to start up the application with the Spring application context. Functional tests should target the *java_library*, not the output of the *springboot* rule. This may be unexpected as you may worry that your tests are not testing the artifact that will be promoted to production. See the next *Integration Tests* section for another option. Your functional test will have the standard Spring Boot annotations: ```java @RunWith(SpringRunner.class) @SpringBootTest(classes = SampleMain.class, webEnvironment = SpringBootTest.WebEnvironment.RANDOM_PORT) public class SampleRestFuncTest { ... ``` with *BUILD* file ```starlark springboottest_deps = [ "@maven//:org_springframework_spring_beans", "@maven//:org_springframework_boot_spring_boot_test", "@maven//:org_springframework_spring_test", ] java_test( name = "SampleRestFuncTest", srcs = ["src/test/java/com/sample/SampleRestFuncTest.java"], deps = [ ":helloworld_lib" ] + test_deps + springboottest_deps, resources = glob(["src/test/resources/**"]), ) ``` ### Spring Boot Jar Tests and Integration Tests Within Salesforce, almost all testing is done as Unit and Functional tests against the *java_library* jar. But we also like to run a small number of final checks against the *springboot* deployable jar. These tests, and all integration tests, are done within a Docker container. We rely on external Bazel tools for this, and we don't offer anything of interest beyond what those tools provide. We refer you to that documentation. - [rules_oci](https://github.com/bazel-contrib/rules_oci) - [testcontainers](https://www.testcontainers.org/) ### Code Coverage Since Unit and Functional tests are run against the *java_library*, and not the *springboot* rule, code coverage is done with standard Bazel Java techniques. We do provide a convenience script to show how to run *lcov* to generate the html report. But none of this is specific to *springboot*. ```bash bazel coverage //examples/helloworld/... ./tools/codecoverage/coverage-report.sh ``` ================================================ FILE: springboot/tests/check_dupe_classes_test.py ================================================ # # Copyright (c) 2019-2021, salesforce.com, inc. # All rights reserved. # Licensed under the BSD 3-Clause license. # For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause # import os import subprocess import tempfile import shutil import unittest import check_dupe_classes import platform FAKE_CONT1 = "This is some class bytecode" FAKE_CONT2 = "This is some other class bytecode" ALLOWLIST_PATH = "" class TestVerifyDupeClasses(unittest.TestCase): def setUp(self): global ALLOWLIST_PATH self.tempdir = tempfile.mkdtemp("TestVerifyConflict") ALLOWLIST_PATH = self._write_allowlist_file() def tearDown(self): shutil.rmtree(self.tempdir) def test_single_jar_with_two_unique_class(self): classes_dir = self._create_fake_class("MyClass.class", "classes", "com/salesforce", FAKE_CONT1) classes_dir = self._create_fake_class("MyClass2.class", "classes", "com/salesforce", FAKE_CONT2) jar_dir = os.path.join(self.tempdir, "inner_jar2") os.makedirs(jar_dir) jar_file = self._create_jar("myjar.jar", jar_dir, classes_dir) springbootjar = self._create_springboot_jar("sb2.jar", jar_dir) check_dupe_classes.run(springbootjar, ALLOWLIST_PATH, None) def test_two_jars_with_duplicate_class__same_content(self): classes_dir1 = self._create_fake_class("MyClass.class", "classes1", "com/salesforce", FAKE_CONT1) # make the jar more interesting: add another class self._create_fake_class("MyClass2.class", "classes1", "com/salesforce", FAKE_CONT2) classes_dir2 = self._create_fake_class("MyClass.class", "classes2", "com/salesforce", FAKE_CONT1) jar_dir = os.path.join(self.tempdir, "inner_jar3") os.makedirs(jar_dir) jar_file1 = self._create_jar("myjar1.jar", jar_dir, classes_dir1) jar_file2 = self._create_jar("myjar2.jar", jar_dir, classes_dir2) springbootjar = self._create_springboot_jar("sb3.jar", jar_dir) check_dupe_classes.run(springbootjar, ALLOWLIST_PATH, None) def test_two_jars_with_duplicate_class__different_content(self): classes_dir1 = self._create_fake_class("MyClass.class", "classes1", "com/salesforce", FAKE_CONT1) classes_dir2 = self._create_fake_class("MyClass.class", "classes2", "com/salesforce", FAKE_CONT2) jar_dir = os.path.join(self.tempdir, "inner_jar4") os.makedirs(jar_dir) jar_file1 = self._create_jar("myjar1.jar", jar_dir, classes_dir1) jar_file2 = self._create_jar("myjar2.jar", jar_dir, classes_dir2) springbootjar = self._create_springboot_jar("sb4.jar", jar_dir) with self.assertRaises(Exception) as ctx: check_dupe_classes.run(springbootjar, ALLOWLIST_PATH, None) self.assertIn("Found duplicate classes", str(ctx.exception)) def test_two_jars_with_duplicate_class_allowlisted__different_content(self): classes_dir1 = self._create_fake_class("MyClass.class", "classes1", "com/salesforce", FAKE_CONT1) classes_dir2 = self._create_fake_class("MyClass.class", "classes2", "com/salesforce", FAKE_CONT2) jar_dir = os.path.join(self.tempdir, "inner_jar5") os.makedirs(jar_dir) jar_file1 = self._create_jar("myjar20.jar", jar_dir, classes_dir1) jar_file2 = self._create_jar("myjar21.jar", jar_dir, classes_dir2) springbootjar = self._create_springboot_jar("sb5.jar", jar_dir) check_dupe_classes.run(springbootjar, ALLOWLIST_PATH, None) # HELPERS def _create_jar(self, name, jar_dir, classes_dir): jar_file = os.path.join(jar_dir, name) self._run("jar cf %s %s" % (jar_file, "."), cwd=classes_dir) assert os.path.exists(jar_file) return jar_file def _create_springboot_jar(self, name, innerjar_dir): jar_file = os.path.join(self.tempdir, name) self._run("jar cf %s %s" % (jar_file, "."), cwd=innerjar_dir) assert os.path.exists(jar_file) return jar_file def _create_fake_class(self, name, root_classes_dir, package, content): classes_dir = os.path.join(self.tempdir, root_classes_dir) package_dir = os.path.join(classes_dir, package) if not os.path.exists(package_dir): os.makedirs(package_dir) class_file = os.path.join(package_dir, name) with open(class_file, "w") as f: f.write(content) return classes_dir def _write_index_file(self, jar_files): index_file_path = os.path.join(self.tempdir, "classes.txt") print(index_file_path) with open(index_file_path, "wb") as f: for jar_file in jar_files: f.write(("%s%s\n" % (check_dupe_classes.JARNAME_PREFIX, jar_file)).encode()) f.write(self._run("unzip -l %s" % jar_file)) return index_file_path def _write_allowlist_file(self): allowlist_file_path = os.path.join(self.tempdir, "allowlist.txt") with open(allowlist_file_path, "w") as f: f.write(self.tempdir+ "/myjar20.jar\n") f.write(self.tempdir+ "/myjar21.jar\n") return allowlist_file_path def _run(self, cmd, cwd=None): if not cwd: cwd = self.tempdir output = subprocess.Popen(cmd, cwd=cwd, shell=True, stdout=subprocess.PIPE).stdout.read() return output if __name__ == '__main__': unittest.main() ================================================ FILE: springboot/unwanted_classes.md ================================================ ## Detecting, Excluding and Suppressing Unwanted Classes and Dependencies Spring Boot jars normally aggregate a great number of dependency jars, many from outside the Bazel build (external Maven-built jars). The Spring Boot rule will copy the transitive closure of all Java jar deps into the [Spring Boot executable jar](https://docs.spring.io/spring-boot/docs/current/reference/html/appendix-executable-jar-format.html). This is normally what you want. But sometimes you have a transitive dependency that causes problems when included in your Spring Boot jar, but you don't have the control to remove it from your dependency graph. This can cause problems such as: - multiple jars have the same class, but at different versions - an unwanted class carries a Spring annotation such that the class gets instantiated at startup - a jar file should never be deployed to production, by version_conflict_policy These problems are difficult to detect ordinarily. The Spring Boot rule has a set of strategies and features for dealing with this situation, which unfortunately is somewhat common. ## Detection ### Detecting Duplicate Classes There is a feature on the *springboot* rule that will fail the build if duplicate classes are detected. It is disabled by default, but can be enabled with an attribute: ```starlark springboot( name = "helloworld", boot_app_class = "com.sample.SampleMain", java_library = ":helloworld_lib", dupeclassescheck_enable = True, ) ``` It will scan all inner jars file, and fail the build if: - the same class (package + classname) is found in more than one inner jar, AND... - the MD5 hash of the classfile bytes differ The dupe class checking feature requires Python3, which is included by default in MODULE.bazel. If you don't have Python3 available for your build, *dupeclassescheck_enable* must be False. *Advanced:* In some cases, you will have a classes that are duplicated and would normally fail this check - but you cannot remove them. There is an [ignorelist](#duplicate-class-detection-ignorelist) feature that will ignore specific jars with duplicated classes. ### Detecting Banned Dependencies In some cases your repository will contain jar files that should *never* be included in your springboot application. Perhaps there is a licensing issue, or a security issue, or you just want to be hygienic. But if a transitive dependency 5 layers deep in your app's graph decides to add such a jar, you won't ordinarily be notified of the problem. Bazel will silently add the jar to your springboot transitive graph, and the jar will get packaged into your service. The *deps_banned* attribute is provided for this case. It should be set to the list of strings to look for in the dependency filenames. If the string is found, the rule will fail with a descriptive message. ```starlark springboot( name = "helloworld", boot_app_class = "com.sample.SampleMain", java_library = ":helloworld_lib", # Example use cases # 1. Some Maven libs forget to make junit/mockito test scoped # 2. lombok is only needed at compile time # 3. topsecret-1.2.3.jar has some code in it that should only be used by internal apps # 4. acme-5.0.0.jar is a commercial jar, that isn't licensed for production use deps_banned = ["junit", "mockito", "lombok", "topsecret", "acme"], ) ``` The list of dependencies is obtained after the *deps_exclude_labels* and *deps_exclude_paths* processing has run. ### Brute Force Class Listing In some cases, it can be helpful to get a full catalog of the classes included in all dependency jars for your springboot application. The script to do this is located here: - [jar exploder utility](../tools/jar_explode) ## Remediation ### Removing Unwanted Libraries and Classes by Removing a Dependency in the BUILD File The best way to handle unwanted libraries and classes is to remove the dependency that brings in the unwanted artifact from the *java_library* rule. This eliminates it from usage for the Spring Boot application. Bazel query is the best way to do this: ```bash # find the label of libraries containing the duplicated classes in your java_library bazel query 'deps(//examples/helloworld:helloworld_lib)' | grep webmvc ``` ```bash # find the path from your java_library to that unwanted library bazel query 'somepath(//examples/helloworld:helloworld_lib, "@maven//:org_springframework_spring_webmvc")' ``` ### Removing Unwanted Classes with a Deps Filter The next best way to exclude dependencies is to remove them before they are added to the ```java_library``` rule invocation. This mechanism is not specific to ```springboot``` at all - it is provided by rules_spring because it is a commmon use case. The benefits to excluding dependencies this way (as opposed to the exclude lists) is that your test execution will use the actual classpath set into the ```springboot``` executable jar. A simple example is below, and there is detailed documentation in the filter directory: - [deps_filter documentation](deps_filter_rules_legacy/README.md) In this example, the springboot jar wants the red, green and blue libraries, but does not want the yellow library (a transitive). ```starlark # load("@rules_spring//springboot/deps_filter_rules_legacy:deps_filter.bzl", "deps_filter") deps = [ "@maven//:com_colors_red", "@maven//:com_colors_green", "@maven//:com_colors_blue", ] deps_filter( name = "filtered_deps", deps = deps, # input list of deps deps_exclude_labels = [ "@maven//:com_colors_yellow", # yellow is a transitive of green, and we don't want it ], exclude_transitives = True, # also exclude any transitive of yellow ) java_library( name = "base_lib", deps = [":filtered_deps"], # the filtered deps has yellow removed ... ) springboot( ... java_library = ":base_lib", ... ) ``` ### Removing Unwanted Classes with an Exclude List (deprecated) An exclude list can be passed to the Spring Boot rule which will prevent that dependency from being copied into the jar during the packaging step. This was our original mechanism of removing dependencies from the dependency graph. :warning: The Exclude list approach is not recommended. The Filter list is more accurate. With Exclude lists, your tests will run without the exclusions, such that your test classpath will not match what will run with your executable jar. There are two forms: *deps_exclude_labels* and *deps_exclude_paths*. - *deps_exclude_labels* uses Bazel labels to match the desired target to exclude. - *deps_exclude_paths* is a partial String match against the file path of the dependency within the jar. The first one is more elegant and maintainable, as the label will be validated by Bazel. However, in some cases this can be tedious as a given dep may be exposed under many labels. This is the case when you have many *maven_install* rules that transitively bring in the same dependency. You may have to exclude the same dependency multiple times if you use the label approach. The path approach is easier for these cases. It is used like this: ```starlark # WARNING: This is an obsolete example. Use the filter mechanism instead. springboot( name = "helloworld", boot_app_class = "com.sample.SampleMain", java_library = ":helloworld_lib", deps_exclude_labels = [ "@maven//:com_google_protobuf_protobuf_java", "//protos/third-party/google/protobuf:any_java_proto", ], deps_exclude_paths = [ "jackson-databind", # will exclude any dep that has 'jackson-databind' in the path "google", # will exclude any dep that has 'google' in the path ], ) ``` ### Suppressing Unwanted Classes with Classpath Ordering In Java, the JVM will load classes from the classpath. If multiple versions of the same class are in the classpath, the class version that is loaded first will 'win'. Therefore, another way to suppress an old version of a class is to make sure the newer version is loaded first. There are two ways to affect the ordering. #### Classpath Ordering using the BUILD file When the Spring Boot jar file is executed using `java -jar`, the runtime classpath order is based on the order of the jar entries written into the jar file. The earlier entries will be loaded before the later entries. The Spring Boot rule uses a specific order for writing the dependencies into the jar file: - Internal Spring Boot classes - Service classes (`srcs` of the `java_library` rule that the `springboot` rule references) - Dependencies (`deps` and `runtime_deps` of the `java_library` rule the `springboot` rule references) The order of the dependencies is based on Bazel's `depset` order, which is strongly influenced by BUILD file order. The earlier entries in the `deps` list will be loaded before the later entries. However, note that transitive dependencies are traversed in depth first order. What this means is you can choose which version of the class 'wins' by putting the dependency jar higher in the `deps` list in the BUILD file. This order isn't guaranteed by Bazel, but seems to be reliable. To view the order of dependencies written into the Spring Boot jar, use the command `jar -tvf {springboot jar}`. The output of that command is faithful to the order of written entries. #### Example [lib1](../../examples/helloworld/libs/lib1) and [lib2](../../examples/helloworld/libs/lib2) have a duplicate class: [lib1's IntentionalDupedClass](../../examples/helloworld/libs/lib1/src/main/java/com/bazel/demo/IntentionalDupedClass.java) and [lib2's IntentionalDupedClass](../../examples/helloworld/libs/lib2/src/main/java/com/bazel/demo/IntentionalDupedClass.java). In the example's [BUILD file](../../examples/helloworld/BUILD), if `lib1` appears before `lib2` in `deps`, you will see the following output when running `bazel run sample/helloworld`: ``` SampleMain: Intentional duped class version: Hello LIB1! ``` In the BUILD file, if you move `lib2` in front of `lib1` and re-run, you will see: ``` SampleMain: Intentional duped class version: Hello LIB2! ``` ##### Disabling BUILD file classpath dependency ordering The current implementation of this feature uses the `jar` command line utility. Explicit jar entry ordering is implemented by specifying an explicit file list when running `jar`. Very large dependency sets may cause the jar command to exceed the system command line length limit. If you run into errors, you can disable this feature by setting the attribute `deps_use_starlark_order` to `False`. #### Classpath Ordering with a Classpath Index Another approach for defining a particular classpath order is with a *classpath index*. The classpath index is a [Spring Boot feature](https://docs.spring.io/spring-boot/docs/current/reference/html/appendix-executable-jar-format.html#executable-jar-war-index-files-classpath) (starting with Spring Boot 2.3) that allows you to instruct the Spring Boot loader to load one jar before another. The feature is explained in the Spring Boot documentation: - [Spring Boot Classpath Index](https://docs.spring.io/spring-boot/docs/current/reference/html/appendix-executable-jar-format.html#executable-jar-war-index-files-classpath) The Spring Boot rule exposes the *deps_index_file* attribute: ```starlark springboot( name = "helloworld", boot_app_class = "com.sample.SampleMain", java_library = ":helloworld_lib", # if you have conflicting classes in dependency jar files, you can define the order in which the jars are loaded deps_index_file = "helloworld_classpath.idx", ) ``` :fire: However, there is a major caveat with this Spring Boot feature. It only works if you first explode the executable jar, and then invoke the *JarLauncher*: ```bash $ jar -xf helloworld.jar $ java org.springframework.boot.loader.JarLauncher ``` ### Ignoring Duplicate Classes Sometimes you have transitives that are out of your control that bring in duplicate classes. If you cannot use the exclusion solutions shown above, you would normally be blocked from using the duplicate class checker. It would always fail. For this reason, the duplicate class detection feature supports an *ignorelist*. The *ignorelist* instructs the checker to ignore certain jars from the dupe checker process. To use this feature, create a text file in the same directory as the BUILD file (e.g. *my_ignorelist.txt*). Add a jar filename on each line like this: ``` # write the filename of the jar files that should be excluded from dupe detection jakarta.annotation-api-1.3.5.jar spring-jcl-5.2.1.RELEASE.jar libfoo1.jar libfoo2.jar ``` and then follow this pattern in the BUILD file: ```starlark springboot( name = "helloworld", boot_app_class = "com.sample.SampleMain", java_library = ":helloworld_lib", dupeclassescheck_enable = True, dupeclassescheck_ignorelist = "my_allowlist.txt", ) ``` Note that you must list **both** jars in which the duplicate class exists in order for the duplicate to be ignored. ================================================ FILE: springboot/write_bazelrun_env.sh ================================================ #!/bin/bash # # Copyright (c) 2021, salesforce.com, inc. # All rights reserved. # Licensed under the BSD 3-Clause license. # For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause # # This file is used to generate the environment variables used by the # default_bazelrun_script.sh for launching Spring Boot applications with # bazel run, as in 'bazel run //examples/helloworld' set -e RULE_NAME=${1} SPRINGBOOTJAR_FILENAME=${2} LABEL_PATH=${3} OUTPUTFILE_PATH=${4} DO_BACKGROUND=${5} start_varargs=6 if [ "$LABEL_PATH" == "root" ]; then # token that indicates that the target is in the root path, which for the # purposes of the label path, is empty string LABEL_PATH="" fi # start the output file with the fixed args echo "export RULE_NAME=$RULE_NAME" > $OUTPUTFILE_PATH echo "export LABEL_PATH=$LABEL_PATH" >> $OUTPUTFILE_PATH echo "export SPRINGBOOTJAR_FILENAME=$SPRINGBOOTJAR_FILENAME" >> $OUTPUTFILE_PATH echo "export DO_BACKGROUND=$DO_BACKGROUND" >> $OUTPUTFILE_PATH # start processing of dynamic args, which will appear in this order: # zero or more datafiles, zero or more jvm flags, zero or more env variables DATAFILES="" JVM_FLAGS="" jvm_flags_started=0 envs_started=0 i=$start_varargs while [ "$i" -le "$#" ]; do eval "arg=\${$i}" if [ "$arg" = "start_flags" ]; then jvm_flags_started=1 elif [ "$arg" = "start_envs" ]; then envs_started=1 jvm_flags_started=0 else if [ $jvm_flags_started -eq 1 ]; then JVM_FLAGS="$JVM_FLAGS $arg" elif [ $envs_started -eq 1 ]; then echo "export $arg" >> $OUTPUTFILE_PATH else DATAFILES="${DATAFILES}$arg " fi fi i=$((i + 1)) done echo "export DATAFILES=\"$DATAFILES\"" >> $OUTPUTFILE_PATH echo "export JVM_FLAGS=\"$JVM_FLAGS\"" >> $OUTPUTFILE_PATH if [ -f "$LABEL_PATH/application.properties" ]; then echo "export USE_EXTERNAL_CONFIG=true" >> $OUTPUTFILE_PATH fi # DEBUG output #echo "Generating 'bazel run' env." #echo "SPRINGBOOTJAR_FILENAME=$SPRINGBOOTJAR_FILENAME" #echo "LABEL_PATH=$LABEL_PATH" #echo "OUTPUTFILE_PATH=$OUTPUTFILE_PATH" #echo "DO_BACKGROUND=$DO_BACKGROUND" #echo "DATAFILES=$DATAFILES" #echo "JVM_FLAGS=$JVM_FLAGS" #echo "CURRENT DIR: $(pwd)" #echo "LABEL_PATH: $LABEL_PATH" ================================================ FILE: springboot/write_gitinfo_properties.sh ================================================ #!/bin/bash # # Copyright (c) 2017-2021, salesforce.com, inc. # All rights reserved. # Licensed under the BSD 3-Clause license. # For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause # # Inject the Git properties into a properties file in the jar. # This matches what the Maven git-commit-id-plugin # PERF NOTE: # Be aware that for dev builds, we mute the git properties (build stamping) to allow many developers # to share cache entries for Spring Boot jars. This is a major perf optimization. # See //tools/buildstamp/README.md for details. set -e # Create the properties file gitpropsfile=$1 echo "# git info injected by Bazel build" > $gitpropsfile ruledir=$(pwd) stableprops=$ruledir/bazel-out/stable-status.txt volatileprops=$ruledir/bazel-out/volatile-status.txt # BUILD ENVIRONMENT PROPERTIES echo "" >> $gitpropsfile for key in git.build.user.email git.build.host git.build.time; do value=$(grep $key $volatileprops | cut -d " " -f 2-100) if [[ $? == 0 ]]; then echo "$key=$value" >> $gitpropsfile fi done # BRANCH PROPERTIES echo "" >> $gitpropsfile for key in STABLE_git.branch STABLE_git.dirty STABLE_git.remote.origin.url; do value=$(grep $key $stableprops | cut -d " " -f 2-100) if [[ $? == 0 ]]; then git_key=$(echo $key | cut -d '_' -f 2) echo "$git_key=$value" >> $gitpropsfile fi done # LAST COMMIT PROPERTIES echo "" >> $gitpropsfile # we do git.commit.id SHA as a one-off, because we have to change the name to match # the git-commit-id-plugin value=$(grep git.commit.id.sha $stableprops | cut -d " " -f 2-100) if [[ $? == 0 ]]; then echo "git.commit.id=$value" >> $gitpropsfile fi for key in STABLE_git.commit.user.email STABLE_git.commit.user.name STABLE_git.commit.id.abbrev STABLE_git.commit.id.describe STABLE_git.closest.tag.name STABLE_git.commit.time STABLE_git.commit.message.short; do value=$(grep $key $stableprops | cut -d " " -f 2-100) if [[ $? == 0 ]]; then git_key=$(echo $key | cut -d '_' -f 2) echo "$git_key=$value" >> $gitpropsfile fi done ================================================ FILE: springboot/write_manifest.sh ================================================ #!/bin/bash # # Copyright (c) 2017-2021, salesforce.com, inc. # All rights reserved. # Licensed under the BSD 3-Clause license. # For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause # set -e mainclass=$1 springbootlauncherclass=$2 manifestfile=$3 javabase=$4 found_spring_jar=0 # Looking for the springboot jar injected by springboot.bzl and extracting the version for var in "$@" do if [[ $var = *"spring-boot-"* ]] || [[ $var = *"spring_boot_"* ]]; then # determine the version of spring boot # this little area of the rule has had problems in the past; reconsider whether doing # this is worth it; and certainly carefully review prior issues here before making changes # Issues: #130, #119, #111 $javabase/bin/jar xf $var META-INF/MANIFEST.MF || continue spring_version=$(grep 'Implementation-Version' META-INF/MANIFEST.MF | cut -d : -f2 | tr -d '[:space:]') rm -rf META-INF # we do want to validate that the deps include spring boot, and this is a # convenient place to do it, but it is a little misplaced as we are # generating the manifest in this script found_spring_jar=1 break fi done if [[ $found_spring_jar -ne 1 ]]; then echo "ERROR: //springboot/write_manifest.sh could not find the spring-boot jar" exit 1 fi #get the java -version details # todo this isn't the best value to use. it is the version that will be used by the jar tool # to package the boot jar but not for compiling the code (java_toolchain) java_string=$($javabase/bin/java -version 2>&1) #get the first line of the version details and get the version java_version=$(echo "$java_string" | head -n1 | cut -d ' ' -f 3 | awk '{print substr($0, 2, length($0)-2)}' ) echo "Manifest-Version: 1.0" > $manifestfile echo "Created-By: Bazel" >> $manifestfile echo "Built-By: Bazel" >> $manifestfile echo "Main-Class: $springbootlauncherclass" >> $manifestfile echo "Spring-Boot-Classes: BOOT-INF/classes/" >> $manifestfile echo "Spring-Boot-Lib: BOOT-INF/lib/" >> $manifestfile echo "Spring-Boot-Version: $spring_version" >> $manifestfile echo "Build-Jdk: $java_version" >> $manifestfile echo "Start-Class: $mainclass" >> $manifestfile ================================================ FILE: tools/buildstamp/README.md ================================================ ## Build Stamping Bazel has a feature to optionally add 'stamping' information to particular build artifacts. That feature is described [in this Bazel documentation](https://bazel.build/docs/user-manual#workspace-status). We sometimes stamp Spring Boot applications with Git information (such as branch, commit id, build time, etc) such that the data can be found in the [/actuator/info](https://docs.spring.io/spring-boot/docs/current/reference/html/production-ready-features.html#production-ready-endpoints) endpoint. This helps with troubleshooting as we can determine exactly what source code built the application. Great, right? #### The Downsides of Stamping The main issue with stamping is that it reduces the benefit of Bazel remote build caching. Once an artifact is stamped with Git data, it cannot be shared via the remote cache with other builds. Also, any other artifact that depends on that artifact will also miss the remote cache. This is a big limitation. #### Full Stamping is Disabled by Default at Salesforce Internally at Salesforce, we like to make use of remote caching for developer builds. To mitigate the remote caching limitation, our build by default has very limited build stamping. It does **not** include the Git data in the stamp. This allows multiple machines to share the same remote cache artifacts, particularly for Spring Boot. Details about how this is done is explained in the Internals section below. #### Run a Build with Full Stamping The default behavior of the build is optimized for remote caching performance. But when you are building artifacts for deployment to shared environments (e.g. test envs, prod) you should run your build with the full stamp. This will allow others to figure out who built the artifact, when, and with what Git coordinates. When troubleshooting problems, that extra data is critical. To signal to the build that you want full stamping, you can create a marker file to enable it: ```bash $ cd [your workspace] (i.e. top level directory of your repo where WORKSPACE is) $ touch full_stamp.txt (marker file that triggers full stamping) $ bazel build //... ``` Full stamping is also signaled if the environment variable *IS_RELEASE_BUILD* is set to true. This may be more convenient for CI systems. ```bash $ export IS_RELEASE_BUILD=true $ bazel build //... ``` ### BUILD File Configuration The way to signal to Bazel to stamp a particular artifact is to add an attribute to the rule in your BUILD file: ``` stamp = 1 ``` This is done automatically for you in the [Spring Boot rule](../../springboot/springboot.bzl) when it generates the *git.properties* file, as seen in this snippet: ```starlark gengitinfo_out = "git.properties" native.genrule( name = gengitinfo_rule, cmd = "$(location @rules_spring//springboot:write_gitinfo_properties.sh) $@", tools = ["@rules_spring//springboot:write_gitinfo_properties.sh"], outs = [gengitinfo_out], tags = tags, stamp = 1, ) ``` ### Internals #### Understand stable-status.txt and volatiles-status.txt The Bazel documentation provides a good explanation for how stamping works in Bazel, so please visit that first: - [Bazel Build Stamping](https://bazel.build/docs/user-manual#workspace-status) #### Monorepo Stamping Implementation The build is configured to **always** run the stamping code, configured here: - [.bazelrc](../../.base-bazelrc#L55) The stamping code is in this directory, and has our custom code to do the stamping: - [get_workspace_status](get_workspace_status) That script is where we do performance optimization to **only apply a full stamp when doing important builds**. The way we do this is by halting the script before it writes the Git data into the *stable-status.txt* file by default. This is where we make that choice: - [Halt stamping of Git data by default](get_workspace_status#L46) If the file *full_stamp.txt* exists at the top level of the monorepo, it will run the full stamping code. ================================================ FILE: tools/buildstamp/get_workspace_status ================================================ # # Copyright (c) 2017-2021, salesforce.com, inc. # All rights reserved. # Licensed under the BSD 3-Clause license. # For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause # # This script is executed with every 'bazel build' command if .bazelrc (or included file) # has these settings: # build --stamp # build --workspace_status_command tools/buildstamp/get_workspace_status # Which enables Bazel *stamping* for every build. # This script writes Git data to:: # bazel-out/volatile-status.txt # bazel-out/stable-status.txt # If anything in stable-status.txt changes, it will trigger a rebuild of any target that # has stamp=1 as an attribute (such as the Spring Boot rule). # Changes to volatile-status.txt do not trigger rebuilds of those targets. # # More information: # Bazel stamping: https://docs.bazel.build/versions/master/user-manual.html#flag--workspace_status_command # Spring Boot git.properties: //springboot/write_gitinfo_properties.sh # Spring Boot info actuator endpoint: ttps://docs.spring.io/spring-boot/docs/current/reference/html/production-ready-features.html#production-ready-endpoints # ******************************** # ******************************** # TEST FOR FULL STAMPING # ******************************** # ******************************** # if IS_RELEASE_BUILD=true or the file full_stamp.txt exists, full stamping is enabled if [ "$IS_RELEASE_BUILD" = true ]; then echo "IS_RELEASE_BUILD environment variable set: $IS_RELEASE_BUILD" else if [[ ! -f full_stamp.txt ]]; then echo "full_stamp.txt file was not detected" exit 0 fi echo "full_stamp.txt file detected" fi echo "Full Bazel build stamping enabled. Adding Git properties to stamp. See //tools/buildstamp for details." # ******************************** # GIT # ******************************** # This data is then later consumed by the //springboot rule (perhaps other rules as well) to write # a git.properties file into the Spring Boot jar, which is then surfaced in the Spring Boot # actuator info endpoint. # BUILD ENVIRONMENT PROPERTIES # git.build.user.email git_email=$(git config --get user.email) if [[ $? == 0 ]]; then echo "git.build.user.email $git_email" fi # git.build.host git_build_host=$(hostname) echo "git.build.host $git_build_host" # git.build.time git_build_time=$(date -u '+%Y-%m-%d @ %H\:%M\:%S -0000') if [[ $? == 0 ]]; then echo "git.build.time $git_build_time" fi # BRANCH PROPERTIES # git.branch git_branch=$(git rev-parse --abbrev-ref HEAD) if [[ $? == 0 ]]; then echo "STABLE_git.branch $git_branch" fi # dirty? (modified files in branch when built) git diff-index --quiet HEAD -- if [[ $? == 0 ]]; then git_status="false" else git_status="true" fi echo "STABLE_git.dirty $git_status" # git.remote.origin.url git_remote_url=$(git config --get remote.origin.url) if [[ $? == 0 ]]; then echo "STABLE_git.remote.origin.url $git_remote_url" fi # LAST COMMIT PROPERTIES # git.commit.user.email (email of last commit author) git_commit_email=$(git log -1 --pretty=format:'%ae') if [[ $? == 0 ]]; then echo "STABLE_git.commit.user.email $git_commit_email" fi # git.commit.user.name git_commit_author=$(git log -1 --pretty=format:'%an') if [[ $? == 0 ]]; then echo "STABLE_git.commit.user.name $git_commit_author" fi # git.commit.id.sha git_commit_id=$(git log -1 --pretty=format:'%H') if [[ $? == 0 ]]; then echo "STABLE_git.commit.id.sha $git_commit_id" fi # git.commit.id.abbrev git_commit_id_short=$(git log -1 --pretty=format:'%h') if [[ $? == 0 ]]; then echo "STABLE_git.commit.id.abbrev $git_commit_id_short" fi # git.commit.time git_commit_time=$(git log -1 --pretty=format:'%ai') if [[ $? == 0 ]]; then echo "STABLE_git.commit.time $git_commit_time" fi # git.commit.message.short (just going with commit 'status' here) git_commit_msg=$(git log -1 --pretty=format:'%s') if [[ $? == 0 ]]; then echo "STABLE_git.commit.message.short $git_commit_msg" fi # git.commit.id.describe git_commit_describe=$(git describe) if [[ $? == 0 ]]; then echo "STABLE_git.commit.id.describe $git_commit_describe" fi # git.closest.tag.name git_closest_tag=$(git describe --abbrev=0) if [[ $? == 0 ]]; then echo "STABLE_git.closest.tag.name $git_closest_tag" fi ================================================ FILE: tools/codecoverage/coverage-report.sh ================================================ #!/usr/bin/env bash # # Copyright (c) 2021, salesforce.com, inc. # All rights reserved. # Licensed under the BSD 3-Clause license. # For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause # if [ ! -f "WORKSPACE" ]; then echo "ERROR Please run this script from the workspace root." exit 1 fi echo "" echo "Before running this script, you must run a coverage job in Bazel." echo "bazel coverage //examples/helloworld/..." echo "" echo "Press enter to continue..." read GOFORIT1 echo "This script requires lcov to be installed (e.g. brew install lcov)" echo "Your lcov version:" lcov --version echo "" echo "Press enter to continue..." read GOFORIT2 find bazel-testlogs/ -type f -name "coverage.dat" -not -empty -exec genhtml -o coverage-reports {} + echo "" echo "Report generation complete." echo "You can view the report by opening ./coverage-reports/index.html in a browser." ================================================ FILE: tools/formatter/README.md ================================================ # Bazel File Formatter This script runs the Bazel buildifier tool on all of our Bazel files (BUILD, \*.bzl). Execute it from the root of the repo. ```bash cd rules-spring ./tools/formatter/format_bazel_files.sh ``` Please do not mix functional and formatting changes in a PR. Before running the script, make sure you have a clean Git workspace. ================================================ FILE: tools/formatter/format_bazel_files.sh ================================================ # # Copyright (c) 2019-2021, salesforce.com, inc. # All rights reserved. # Licensed under the BSD 3-Clause license. # For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause # echo "This script will format all repo BUILD and .bzl files according to style standards." echo "" echo "NOTE: It requires that you have Go installed. https://golang.org/doc/install" echo "" if [ ! -f "WORKSPACE" ]; then echo "Please launch this script from the root of the repo." echo " ./tools/formatter/format_bazel_files.sh" exit 1 fi echo "Before running, we will check that you have a clean Git workspace." echo "Do not mix functional changes together with formatting changes in the same PR." echo "Press Enter to continue..." read MR_BOJANGLES git status echo "" echo "Is your Git workspace clean? Press Enter to continue, or ctrl-c to bail." echo "In the next step, we will make sure you have 'buildifer' installed, which is the tool that does the formatting." echo "Press Enter to continue..." read TAMBOURINE_MAN go get github.com/bazelbuild/buildtools/buildifier echo "" echo "If the previous step didn't emit any errors, we are ready to do the formatting." echo "After the formatting is done, review the diffs and submit a PR." echo "Press Enter to continue..." read VANDALS_STOLE_THE_HANDLE find . -name BUILD | xargs ~/go/bin/buildifier find . -name BUILD.bazel | xargs ~/go/bin/buildifier find . -name BUILD | xargs ~/go/bin/buildifier --lint=fix find . -name BUILD.bazel | xargs ~/go/bin/buildifier --lint=fix find . -name '*.bzl' | xargs ~/go/bin/buildifier echo "" echo "Now we will run the manual linter, which will show what issues remain in the files." echo "They are informational and can be fixed manually if you wish." echo "Press Enter to continue..." read BLOWIN_IN_THE_WIND find . -name BUILD | xargs ~/go/bin/buildifier --lint=warn find . -name BUILD.bazel | xargs ~/go/bin/buildifier --lint=warn find . -name '*.bzl' | xargs ~/go/bin/buildifier --lint=warn ================================================ FILE: tools/get_github_stats_downloads.py ================================================ import requests ''' This script queries GitHub to get the number of downloads of the releases of our rule. ''' owner = "salesforce" repo = "rules_spring" h = {"Accept": "application/vnd.github.v3+json"} u = f"https://api.github.com/repos/{owner}/{repo}/releases?per_page=100" r = requests.get(u, headers=h).json() r.reverse() # older tags first print("GitHub download stats for releases of the Bazel Spring Boot rule:") print("=================================================================") for rel in r: if rel['assets']: tag = rel['tag_name'] dls = rel['assets'][0]['download_count'] pub = rel['published_at'] print(f"PubDate: {pub} | Tag: {tag} | Dls: {dls} ") ================================================ FILE: tools/jar_explode/README.md ================================================ ## Jar Explode Debug Utility Spring Boot jars typically contain hundreds of upstream dependency jars. In cases where you have ClassNotFound errors or class version conflicts, it can be helpful to get a full searchable catalog of which classes are in the jar (or not). Use this utility to extract the springboot jar, and the nested dependency jars, such that the .class files can be searched for and located. ``` # Example: find out which jars contain the GrpcUtil class $ ./jar_explode.sh ../../bazel-bin/examples/helloworld/heloworld.jar $ cd /tmp/bazel/springbootexplode $ find . -name GrpcUtil.class ``` ================================================ FILE: tools/jar_explode/jar_explode.sh ================================================ #!/bin/bash # This is a handy utility script to explode classes from the generated springboot jar # into /tmp so you can do searches to find where a certain class is coming from. # Example: find out which jars contain the GrpcUtil class # $ ./jar_explode.sh ../../bazel-bin/examples/helloworld/heloworld.jar # $ cd /tmp/bazel/springbootexplode # $ find . -name GrpcUtil.class SPRINGBOOTJAR=$1 JAR=$(basename $1) rm -rf /tmp/bazel/springbootexplode mkdir -p /tmp/bazel/springbootexplode/extract cp $1 /tmp/bazel/springbootexplode/extract pushd . cd /tmp/bazel/springbootexplode BASEDIR=$(pwd) cd extract jar -xvf $JAR cd BOOT-INF/lib for f in $(find . -name '*.jar'); do jarname="$(basename -- $f)" echo "Processing $jarname file.."; mkdir $BASEDIR/$jarname cp $f $BASEDIR/$jarname pushd . cd $BASEDIR/$jarname jar -xvf $jarname popd done echo "Extracted the springboot classes to $BASEDIR" popd . ================================================ FILE: tools/license/BUILD ================================================ filegroup( name = "standard_package", srcs = glob(["**"]), ) ================================================ FILE: tools/license/licenses_used.bzl ================================================ # Copyright 2022 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. """License compliance checking.""" load( "@rules_license//rules:gather_licenses_info.bzl", "gather_licenses_info", "write_licenses_info", ) def _licenses_used_impl(ctx): # Gather all licenses and make it available as JSON write_licenses_info(ctx, ctx.attr.deps, ctx.outputs.out) return [DefaultInfo(files = depset([ctx.outputs.out]))] _licenses_used = rule( implementation = _licenses_used_impl, doc = """Internal tmplementation method for licenses_used().""", attrs = { "deps": attr.label_list( doc = """List of targets to collect LicenseInfo for.""", aspects = [gather_licenses_info], ), "out": attr.output( doc = """Output file.""", mandatory = True, ), }, ) def licenses_used(name, deps, out = None, **kwargs): """Collects LicensedInfo providers for a set of targets and writes as JSON. The output is a single JSON array, with an entry for each license used. See gather_licenses_info.bzl:write_licenses_info() for a description of the schema. Args: name: The target. deps: A list of targets to get LicenseInfo for. The output is the union of the result, not a list of information for each dependency. out: The output file name. Default: .json. **kwargs: Other args Usage: licenses_used( name = "license_info", deps = [":my_app"], out = "license_info.json", ) """ if not out: out = name + ".json" _licenses_used(name = name, deps = deps, out = out, **kwargs)