diff --git a/src/main/java/com/google/devtools/build/lib/analysis/actions/CustomCommandLine.java b/src/main/java/com/google/devtools/build/lib/analysis/actions/CustomCommandLine.java index 5f80db92a19e17..ac8dc1fc1d7378 100644 --- a/src/main/java/com/google/devtools/build/lib/analysis/actions/CustomCommandLine.java +++ b/src/main/java/com/google/devtools/build/lib/analysis/actions/CustomCommandLine.java @@ -34,6 +34,7 @@ import com.google.devtools.build.lib.actions.PathMapper; import com.google.devtools.build.lib.actions.SingleStringArgFormatter; import com.google.devtools.build.lib.cmdline.Label; +import com.google.devtools.build.lib.cmdline.RepositoryMapping; import com.google.devtools.build.lib.collect.nestedset.NestedSet; import com.google.devtools.build.lib.concurrent.BlazeInterners; import com.google.devtools.build.lib.concurrent.ThreadSafety.Immutable; @@ -580,9 +581,16 @@ static class PrefixArg implements ArgvFragment { private static final UUID PREFIX_UUID = UUID.fromString("a95eccdf-4f54-46fc-b925-c8c7e1f50c95"); - private static void push(List arguments, String before, Object arg) { + private static void push( + List arguments, + String before, + Object arg, + @Nullable RepositoryMapping mainRepoMapping) { arguments.add(INSTANCE); arguments.add(before); + if (mainRepoMapping != null) { + arguments.add(mainRepoMapping); + } arguments.add(arg); } @@ -594,6 +602,9 @@ public int eval( PathMapper pathMapper) { String before = (String) arguments.get(argi++); Object arg = arguments.get(argi++); + if (arg instanceof RepositoryMapping mainRepoMapping) { + arg = ((Label) arguments.get(argi++)).getDisplayForm(mainRepoMapping); + } builder.add(before + CommandLineItem.expandToCommandLine(arg)); return argi; } @@ -606,7 +617,11 @@ public int addToFingerprint( Fingerprint fingerprint) { fingerprint.addUUID(PREFIX_UUID); fingerprint.addString((String) arguments.get(argi++)); - fingerprint.addString(CommandLineItem.expandToCommandLine(arguments.get(argi++))); + Object arg = arguments.get(argi++); + if (arg instanceof RepositoryMapping mainRepoMapping) { + arg = ((Label) arguments.get(argi++)).getDisplayForm(mainRepoMapping); + } + fingerprint.addString(CommandLineItem.expandToCommandLine(arg)); return argi; } } @@ -752,6 +767,7 @@ public static final class Builder { * *

Prefer this over its dynamic cousin, as using static strings saves memory. */ + @CanIgnoreReturnValue public Builder add(@CompileTimeConstant String value) { return addObjectInternal(value); } @@ -761,6 +777,7 @@ public Builder add(@CompileTimeConstant String value) { * *

If the value is null, neither the arg nor the value is added. */ + @CanIgnoreReturnValue public Builder add(@CompileTimeConstant String arg, @Nullable String value) { return addObjectInternal(arg, value); } @@ -797,6 +814,7 @@ public Builder addObject(@Nullable Object value) { *

There are many other ways you can try to avoid calling this. In general, try to use * constants or objects that are already on the heap elsewhere. */ + @CanIgnoreReturnValue public Builder addDynamicString(@Nullable String value) { return addObjectInternal(value); } @@ -807,6 +825,7 @@ public Builder addDynamicString(@Nullable String value) { *

Prefer this over manually calling {@link Label#getCanonicalForm}, as it avoids a copy of * the label value. */ + @CanIgnoreReturnValue public Builder addLabel(@Nullable Label value) { return addObjectInternal(value); } @@ -819,6 +838,7 @@ public Builder addLabel(@Nullable Label value) { * *

If the value is null, neither the arg nor the value is added. */ + @CanIgnoreReturnValue public Builder addLabel(@CompileTimeConstant String arg, @Nullable Label value) { return addObjectInternal(arg, value); } @@ -829,6 +849,7 @@ public Builder addLabel(@CompileTimeConstant String arg, @Nullable Label value) *

Prefer this over manually calling {@link PathFragment#getPathString}, as it avoids storing * a copy of the path string. */ + @CanIgnoreReturnValue public Builder addPath(@Nullable PathFragment value) { return addObjectInternal(value); } @@ -841,6 +862,7 @@ public Builder addPath(@Nullable PathFragment value) { * *

If the value is null, neither the arg nor the value is added. */ + @CanIgnoreReturnValue public Builder addPath(@CompileTimeConstant String arg, @Nullable PathFragment value) { return addObjectInternal(arg, value); } @@ -851,6 +873,7 @@ public Builder addPath(@CompileTimeConstant String arg, @Nullable PathFragment v *

Prefer this over manually calling {@link Artifact#getExecPath}, as it avoids storing a * copy of the artifact path string. */ + @CanIgnoreReturnValue public Builder addExecPath(@Nullable Artifact value) { return addObjectInternal(value); } @@ -863,16 +886,19 @@ public Builder addExecPath(@Nullable Artifact value) { * *

If the value is null, neither the arg nor the value is added. */ + @CanIgnoreReturnValue public Builder addExecPath(@CompileTimeConstant String arg, @Nullable Artifact value) { return addObjectInternal(arg, value); } /** Adds a lazily expanded string. */ + @CanIgnoreReturnValue public Builder addLazyString(@Nullable OnDemandString value) { return addObjectInternal(value); } /** Adds a lazily expanded string. */ + @CanIgnoreReturnValue public Builder addLazyString(@CompileTimeConstant String arg, @Nullable OnDemandString value) { return addObjectInternal(arg, value); } @@ -887,23 +913,33 @@ public Builder addFormatted(@FormatString String formatStr, Object... args) { } /** Concatenates the passed prefix string and the string. */ + @CanIgnoreReturnValue public Builder addPrefixed(@CompileTimeConstant String prefix, @Nullable String arg) { - return addPrefixedInternal(prefix, arg); + return addPrefixedInternal(prefix, arg, /* mainRepoMapping= */ null); } - /** Concatenates the passed prefix string and the label using {@link Label#getCanonicalForm}. */ - public Builder addPrefixedLabel(@CompileTimeConstant String prefix, @Nullable Label arg) { - return addPrefixedInternal(prefix, arg); + /** + * Concatenates the passed prefix string and the label using {@link Label#getDisplayForm}, which + * is identical to {@link Label#getCanonicalForm()} for main repo labels. + */ + @CanIgnoreReturnValue + public Builder addPrefixedLabel( + @CompileTimeConstant String prefix, + @Nullable Label arg, + RepositoryMapping mainRepoMapping) { + return addPrefixedInternal(prefix, arg, mainRepoMapping); } /** Concatenates the passed prefix string and the path. */ + @CanIgnoreReturnValue public Builder addPrefixedPath(@CompileTimeConstant String prefix, @Nullable PathFragment arg) { - return addPrefixedInternal(prefix, arg); + return addPrefixedInternal(prefix, arg, /* mainRepoMapping= */ null); } /** Concatenates the passed prefix string and the artifact's exec path. */ + @CanIgnoreReturnValue public Builder addPrefixedExecPath(@CompileTimeConstant String prefix, @Nullable Artifact arg) { - return addPrefixedInternal(prefix, arg); + return addPrefixedInternal(prefix, arg, /* mainRepoMapping= */ null); } /** @@ -912,6 +948,7 @@ public Builder addPrefixedExecPath(@CompileTimeConstant String prefix, @Nullable *

If you are converting long lists or nested sets of a different type to string lists, * please try to use a different method that supports what you are trying to do directly. */ + @CanIgnoreReturnValue public Builder addAll(@Nullable Collection values) { return addCollectionInternal(values); } @@ -922,6 +959,7 @@ public Builder addAll(@Nullable Collection values) { *

If you are converting long lists or nested sets of a different type to string lists, * please try to use a different method that supports what you are trying to do directly. */ + @CanIgnoreReturnValue public Builder addAll(@Nullable NestedSet values) { return addNestedSetInternal(values); } @@ -934,6 +972,7 @@ public Builder addAll(@Nullable NestedSet values) { * *

If values is empty, the arg isn't added. */ + @CanIgnoreReturnValue public Builder addAll(@CompileTimeConstant String arg, @Nullable Collection values) { return addCollectionInternal(arg, values); } @@ -943,11 +982,13 @@ public Builder addAll(@CompileTimeConstant String arg, @Nullable CollectionIf values is empty, the arg isn't added. */ + @CanIgnoreReturnValue public Builder addAll(@CompileTimeConstant String arg, @Nullable NestedSet values) { return addNestedSetInternal(arg, values); } /** Adds the passed vector arg. See {@link VectorArg}. */ + @CanIgnoreReturnValue public Builder addAll(VectorArg vectorArg) { return addVectorArgInternal(vectorArg); } @@ -957,16 +998,19 @@ public Builder addAll(VectorArg vectorArg) { * *

If values is empty, the arg isn't added. */ + @CanIgnoreReturnValue public Builder addAll(@CompileTimeConstant String arg, VectorArg vectorArg) { return addVectorArgInternal(arg, vectorArg); } /** Adds the passed paths to the command line. */ + @CanIgnoreReturnValue public Builder addPaths(@Nullable Collection values) { return addCollectionInternal(values); } /** Adds the passed paths to the command line. */ + @CanIgnoreReturnValue public Builder addPaths(@Nullable NestedSet values) { return addNestedSetInternal(values); } @@ -976,6 +1020,7 @@ public Builder addPaths(@Nullable NestedSet values) { * *

If values is empty, the arg isn't added. */ + @CanIgnoreReturnValue public Builder addPaths( @CompileTimeConstant String arg, @Nullable Collection values) { return addCollectionInternal(arg, values); @@ -986,12 +1031,14 @@ public Builder addPaths( * *

If values is empty, the arg isn't added. */ + @CanIgnoreReturnValue public Builder addPaths( @CompileTimeConstant String arg, @Nullable NestedSet values) { return addNestedSetInternal(arg, values); } /** Adds the passed vector arg. See {@link VectorArg}. */ + @CanIgnoreReturnValue public Builder addPaths(VectorArg vectorArg) { return addVectorArgInternal(vectorArg); } @@ -1001,6 +1048,7 @@ public Builder addPaths(VectorArg vectorArg) { * *

If values is empty, the arg isn't added. */ + @CanIgnoreReturnValue public Builder addPaths(@CompileTimeConstant String arg, VectorArg vectorArg) { return addVectorArgInternal(arg, vectorArg); } @@ -1011,11 +1059,13 @@ public Builder addPaths(@CompileTimeConstant String arg, VectorArg *

Do not use this method if the list is derived from a flattened nested set. Instead, figure * out how to avoid flattening the set and use {@link #addExecPaths(NestedSet)}. */ + @CanIgnoreReturnValue public Builder addExecPaths(@Nullable Collection values) { return addCollectionInternal(values); } /** Adds the artifacts' exec paths to the command line. */ + @CanIgnoreReturnValue public Builder addExecPaths(@Nullable NestedSet values) { return addNestedSetInternal(values); } @@ -1028,6 +1078,7 @@ public Builder addExecPaths(@Nullable NestedSet values) { * *

If values is empty, the arg isn't added. */ + @CanIgnoreReturnValue public Builder addExecPaths( @CompileTimeConstant String arg, @Nullable Collection values) { return addCollectionInternal(arg, values); @@ -1038,12 +1089,14 @@ public Builder addExecPaths( * *

If values is empty, the arg isn't added. */ + @CanIgnoreReturnValue public Builder addExecPaths( @CompileTimeConstant String arg, @Nullable NestedSet values) { return addNestedSetInternal(arg, values); } /** Adds the passed vector arg. See {@link VectorArg}. */ + @CanIgnoreReturnValue public Builder addExecPaths(VectorArg vectorArg) { return addVectorArgInternal(vectorArg); } @@ -1053,6 +1106,7 @@ public Builder addExecPaths(VectorArg vectorArg) { * *

If values is empty, the arg isn't added. */ + @CanIgnoreReturnValue public Builder addExecPaths(@CompileTimeConstant String arg, VectorArg vectorArg) { return addVectorArgInternal(arg, vectorArg); } @@ -1129,10 +1183,11 @@ private Builder addObjectInternal(@CompileTimeConstant String arg, @Nullable Obj } @CanIgnoreReturnValue - private Builder addPrefixedInternal(String prefix, @Nullable Object arg) { + private Builder addPrefixedInternal( + String prefix, @Nullable Object arg, @Nullable RepositoryMapping mainRepoMapping) { Preconditions.checkNotNull(prefix); if (arg != null) { - PrefixArg.push(arguments, prefix, arg); + PrefixArg.push(arguments, prefix, arg, mainRepoMapping); } return this; } diff --git a/src/main/java/com/google/devtools/build/lib/rules/java/JavaCompilationHelper.java b/src/main/java/com/google/devtools/build/lib/rules/java/JavaCompilationHelper.java index 85421a57a6ed91..a6d53368a86cc9 100644 --- a/src/main/java/com/google/devtools/build/lib/rules/java/JavaCompilationHelper.java +++ b/src/main/java/com/google/devtools/build/lib/rules/java/JavaCompilationHelper.java @@ -208,7 +208,8 @@ public JavaCompileOutputs createOutputs(JavaOutput output) { return builder.build(); } - public void createCompileAction(JavaCompileOutputs outputs) throws RuleErrorException { + public void createCompileAction(JavaCompileOutputs outputs) + throws RuleErrorException, InterruptedException { if (outputs.genClass() != null) { createGenJarAction( outputs.output(), @@ -542,7 +543,7 @@ private Artifact turbineOutput(Artifact classJar, String newExtension) { * @param headerDeps the .jdeps output of this java compilation */ public void createHeaderCompilationAction(Artifact headerJar, Artifact headerDeps) - throws RuleErrorException { + throws RuleErrorException, InterruptedException { JavaTargetAttributes attributes = getAttributes(); @@ -687,7 +688,8 @@ public void createSourceJarAction(Artifact outputJar, @Nullable Artifact gensrcJ * @return the header jar (if requested), or ijar (if requested), or else the class jar */ public Artifact createCompileTimeJarAction( - Artifact runtimeJar, JavaCompilationArtifacts.Builder builder) throws RuleErrorException { + Artifact runtimeJar, JavaCompilationArtifacts.Builder builder) + throws RuleErrorException, InterruptedException { Artifact jar; boolean isFullJar = false; if (shouldUseHeaderCompilation()) { diff --git a/src/main/java/com/google/devtools/build/lib/rules/java/JavaCompileActionBuilder.java b/src/main/java/com/google/devtools/build/lib/rules/java/JavaCompileActionBuilder.java index dae194bb7d1edb..f27ec299aa0675 100644 --- a/src/main/java/com/google/devtools/build/lib/rules/java/JavaCompileActionBuilder.java +++ b/src/main/java/com/google/devtools/build/lib/rules/java/JavaCompileActionBuilder.java @@ -171,7 +171,7 @@ public JavaCompileActionBuilder( this.execGroup = execGroup; } - public JavaCompileAction build() throws RuleErrorException { + public JavaCompileAction build() throws RuleErrorException, InterruptedException { // TODO(bazel-team): all the params should be calculated before getting here, and the various // aggregation code below should go away. @@ -271,7 +271,7 @@ private ImmutableSet allOutputs() { } private CustomCommandLine buildParamFileContents(ImmutableList javacOpts) - throws RuleErrorException { + throws RuleErrorException, InterruptedException { CustomCommandLine.Builder result = CustomCommandLine.builder(); @@ -304,7 +304,8 @@ private CustomCommandLine buildParamFileContents(ImmutableList javacOpts } else { // @-prefixed strings will be assumed to be filenames and expanded by // {@link JavaLibraryBuildRequest}, so add an extra &at; to escape it. - result.addPrefixedLabel("@", targetLabel); + result.addPrefixedLabel( + "@", targetLabel, ruleContext.getAnalysisEnvironment().getMainRepoMapping()); } } result.add("--injecting_rule_kind", injectingRuleKind); diff --git a/src/main/java/com/google/devtools/build/lib/rules/java/JavaHeaderCompileAction.java b/src/main/java/com/google/devtools/build/lib/rules/java/JavaHeaderCompileAction.java index 50aaac54823d87..4b1e299dbc80d1 100644 --- a/src/main/java/com/google/devtools/build/lib/rules/java/JavaHeaderCompileAction.java +++ b/src/main/java/com/google/devtools/build/lib/rules/java/JavaHeaderCompileAction.java @@ -368,7 +368,8 @@ public Builder enableDirectClasspath(boolean enableDirectClasspath) { } /** Builds and registers the action for a header compilation. */ - public void build(JavaToolchainProvider javaToolchain) throws RuleErrorException { + public void build(JavaToolchainProvider javaToolchain) + throws RuleErrorException, InterruptedException { checkNotNull(outputDepsProto, "outputDepsProto must not be null"); checkNotNull(sourceFiles, "sourceFiles must not be null"); checkNotNull(sourceJars, "sourceJars must not be null"); @@ -478,7 +479,8 @@ public void build(JavaToolchainProvider javaToolchain) throws RuleErrorException } else { // @-prefixed strings will be assumed to be params filenames and expanded, // so add an extra @ to escape it. - commandLine.addPrefixedLabel("@", targetLabel); + commandLine.addPrefixedLabel( + "@", targetLabel, ruleContext.getAnalysisEnvironment().getMainRepoMapping()); } } diff --git a/src/main/java/com/google/devtools/build/lib/rules/java/JavaStarlarkCommon.java b/src/main/java/com/google/devtools/build/lib/rules/java/JavaStarlarkCommon.java index 3f82911e020668..1de0a74b4a560e 100644 --- a/src/main/java/com/google/devtools/build/lib/rules/java/JavaStarlarkCommon.java +++ b/src/main/java/com/google/devtools/build/lib/rules/java/JavaStarlarkCommon.java @@ -134,7 +134,11 @@ public void createHeaderCompilationAction( Object injectingRuleKind, boolean enableDirectClasspath, Sequence additionalInputs) - throws EvalException, TypeException, RuleErrorException, LabelSyntaxException { + throws EvalException, + TypeException, + RuleErrorException, + LabelSyntaxException, + InterruptedException { checkJavaToolchainIsDeclaredOnRule(ctx.getRuleContext()); JavaTargetAttributes.Builder attributesBuilder = new JavaTargetAttributes.Builder(javaSemantics) @@ -199,7 +203,11 @@ public void createCompilationAction( boolean enableDirectClasspath, Sequence additionalInputs, Sequence additionalOutputs) - throws EvalException, TypeException, RuleErrorException, LabelSyntaxException { + throws EvalException, + TypeException, + RuleErrorException, + LabelSyntaxException, + InterruptedException { checkJavaToolchainIsDeclaredOnRule(ctx.getRuleContext()); JavaCompileOutputs outputs = JavaCompileOutputs.builder() diff --git a/src/main/java/com/google/devtools/build/lib/starlarkbuildapi/java/JavaCommonApi.java b/src/main/java/com/google/devtools/build/lib/starlarkbuildapi/java/JavaCommonApi.java index 119c9f22520375..ba028d51b81562 100644 --- a/src/main/java/com/google/devtools/build/lib/starlarkbuildapi/java/JavaCommonApi.java +++ b/src/main/java/com/google/devtools/build/lib/starlarkbuildapi/java/JavaCommonApi.java @@ -522,7 +522,11 @@ void createHeaderCompilationAction( Object injectingRuleKind, boolean enableDirectClasspath, Sequence additionalInputs) - throws EvalException, TypeException, RuleErrorException, LabelSyntaxException; + throws EvalException, + TypeException, + RuleErrorException, + LabelSyntaxException, + InterruptedException; @StarlarkMethod( name = "create_compilation_action", @@ -586,7 +590,11 @@ void createCompilationAction( boolean enableDirectClasspath, Sequence additionalInputs, Sequence additionalOutputs) - throws EvalException, TypeException, RuleErrorException, LabelSyntaxException; + throws EvalException, + TypeException, + RuleErrorException, + LabelSyntaxException, + InterruptedException; @StarlarkMethod( name = "default_javac_opts", diff --git a/src/test/java/com/google/devtools/build/lib/actions/CustomCommandLineTest.java b/src/test/java/com/google/devtools/build/lib/actions/CustomCommandLineTest.java index 9313289a5c6bd9..e2566cd09e7649 100644 --- a/src/test/java/com/google/devtools/build/lib/actions/CustomCommandLineTest.java +++ b/src/test/java/com/google/devtools/build/lib/actions/CustomCommandLineTest.java @@ -20,6 +20,7 @@ import com.google.common.base.Joiner; import com.google.common.collect.ImmutableList; +import com.google.common.collect.ImmutableMap; import com.google.devtools.build.lib.actions.Artifact.SpecialArtifact; import com.google.devtools.build.lib.actions.Artifact.TreeFileArtifact; import com.google.devtools.build.lib.actions.ArtifactRoot.RootType; @@ -28,6 +29,8 @@ import com.google.devtools.build.lib.analysis.actions.CustomCommandLine.VectorArg; import com.google.devtools.build.lib.analysis.actions.CustomCommandLine.VectorArg.SimpleVectorArg; import com.google.devtools.build.lib.cmdline.Label; +import com.google.devtools.build.lib.cmdline.RepositoryMapping; +import com.google.devtools.build.lib.cmdline.RepositoryName; import com.google.devtools.build.lib.collect.nestedset.NestedSet; import com.google.devtools.build.lib.collect.nestedset.NestedSetBuilder; import com.google.devtools.build.lib.collect.nestedset.Order; @@ -126,7 +129,8 @@ public void addPrefixed_addsPrefixForArguments() throws Exception { .containsExactly("prefix-foo"); assertThat( builder() - .addPrefixedLabel("prefix-", Label.parseCanonical("//a:b")) + .addPrefixedLabel( + "prefix-", Label.parseCanonical("//a:b"), /* mainRepoMapping= */ null) .build() .arguments()) .containsExactly("prefix-//a:b"); @@ -137,6 +141,22 @@ public void addPrefixed_addsPrefixForArguments() throws Exception { .containsExactly("prefix-dir/file1.txt"); } + @Test + public void addPrefixedLabel_emitsExternalLabelInDisplayForm() throws Exception { + assertThat( + builder() + .addPrefixedLabel( + "prefix-", + Label.parseCanonical("@@canonical_name//a:b"), + RepositoryMapping.create( + ImmutableMap.of( + "apparent_name", RepositoryName.createUnvalidated("canonical_name")), + RepositoryName.MAIN)) + .build() + .arguments()) + .containsExactly("prefix-@apparent_name//a:b"); + } + @Test public void addAll_addsAllArguments() throws Exception { assertThat(builder().addAll(list("val1", "val2")).build().arguments()) @@ -527,7 +547,7 @@ public void addNulls_addsNothing() throws Exception { .addExecPath("foo", null) .addLazyString("foo", null) .addPrefixed("prefix", null) - .addPrefixedLabel("prefix", null) + .addPrefixedLabel("prefix", null, /* mainRepoMapping= */ null) .addPrefixedPath("prefix", null) .addPrefixedExecPath("prefix", null) .addAll((ImmutableList) null) diff --git a/src/test/shell/bazel/bazel_java_test.sh b/src/test/shell/bazel/bazel_java_test.sh index a77f00874b2411..d19b27f9a00023 100755 --- a/src/test/shell/bazel/bazel_java_test.sh +++ b/src/test/shell/bazel/bazel_java_test.sh @@ -1998,4 +1998,90 @@ EOF expect_log "buildozer 'add deps @c//:c' //pkg:a" } +function test_strict_deps_error_external_repo_header_compile_action() { + cat << 'EOF' > MODULE.bazel +bazel_dep( + name = "lib_c", + repo_name = "c", +) +local_path_override( + module_name = "lib_c", + path = "lib_c", +) +EOF + + mkdir -p pkg + cat << 'EOF' > pkg/BUILD +java_binary(name = "Main", srcs = ["Main.java"], deps = [":a"]) +java_library(name = "a", srcs = ["A.java"], deps = [":b"]) +java_library(name = "b", srcs = ["B.java"], deps = ["@c"]) +EOF + cat << 'EOF' > pkg/Main.java +public class Main extends A {} +EOF + cat << 'EOF' > pkg/A.java +public class A extends B implements C {} +EOF + cat << 'EOF' > pkg/B.java +public class B implements C {} +EOF + + mkdir -p lib_c + cat << 'EOF' > lib_c/MODULE.bazel +module(name = "lib_c") +EOF + cat << 'EOF' > lib_c/BUILD +java_library(name = "c", srcs = ["C.java"], visibility = ["//visibility:public"]) +EOF + cat << 'EOF' > lib_c/C.java +public interface C {} +EOF + + bazel build //pkg:a >& $TEST_log && fail "build should fail" + expect_log "buildozer 'add deps @c//:c' //pkg:a" +} + +function test_strict_deps_error_external_repo_compile_action() { + cat << 'EOF' > MODULE.bazel +bazel_dep( + name = "lib_c", + repo_name = "c", +) +local_path_override( + module_name = "lib_c", + path = "lib_c", +) +EOF + + mkdir -p pkg + cat << 'EOF' > pkg/BUILD +java_library(name = "a", srcs = ["A.java"], deps = [":b"]) +java_library(name = "b", srcs = ["B.java"], deps = ["@c"]) +EOF + cat << 'EOF' > pkg/A.java +public class A extends B { + boolean foo() { + return this instanceof C; + } +} +EOF + cat << 'EOF' > pkg/B.java +public class B implements C {} +EOF + + mkdir -p lib_c + cat << 'EOF' > lib_c/MODULE.bazel +module(name = "lib_c") +EOF + cat << 'EOF' > lib_c/BUILD +java_library(name = "c", srcs = ["C.java"], visibility = ["//visibility:public"]) +EOF + cat << 'EOF' > lib_c/C.java +public interface C {} +EOF + + bazel build //pkg:a >& $TEST_log && fail "build should fail" + expect_log "buildozer 'add deps @c//:c' //pkg:a" +} + run_suite "Java integration tests" diff --git a/src/test/shell/bazel/local_repository_test.sh b/src/test/shell/bazel/local_repository_test.sh index b5742870ee7959..8f67d33494193b 100755 --- a/src/test/shell/bazel/local_repository_test.sh +++ b/src/test/shell/bazel/local_repository_test.sh @@ -1411,7 +1411,7 @@ EOF bazel build @x_repo//a >& $TEST_log && fail "Building @x_repo//a should error out" expect_log "** Please add the following dependencies:" - expect_log "@@x_repo//x to @@x_repo//a" + expect_log " @x_repo//x to @x_repo//a" } # This test verifies that the `public` pattern includes external dependencies.