Add .bazelignore content to blacklisted subdirectories in cquery and aquery's
QueryEnvironment.

Fixes #7229.

Context: ConfiguredTargetQueryEnvironment and ActionGraphQueryEnvironment were not taking into account the content of .bazelignore file when getTargetsMatchingPattern. This caused a precondition check for recursive pkg lookup in RecursivePkgValueRootPackageExtractor to fail.

Changes:
- Get the blacklisted PathFragments from .bazelignore from the walkableGraph.
- Rm checkAllPathsAreUnder checks in GraphBackedRecursivePackageProvider, in the same manner it's handled in EnvironmentBackedRecursivePackageProvider.

RELNOTES: None
PiperOrigin-RevId: 240270920
diff --git a/src/main/java/com/google/devtools/build/lib/pkgcache/RecursivePackageProvider.java b/src/main/java/com/google/devtools/build/lib/pkgcache/RecursivePackageProvider.java
index 998c36d..b6651c9 100644
--- a/src/main/java/com/google/devtools/build/lib/pkgcache/RecursivePackageProvider.java
+++ b/src/main/java/com/google/devtools/build/lib/pkgcache/RecursivePackageProvider.java
@@ -37,11 +37,10 @@
    * @param eventHandler any errors emitted during package lookup and loading for {@code directory}
    *     and non-excluded directories beneath it will be reported here
    * @param directory a {@link RootedPath} specifying the directory to search
-   * @param blacklistedSubdirectories a set of {@link PathFragment}s, all of which are beneath
-   *     {@code directory} (not necessarily strictly), specifying transitive subdirectories that
-   *     have been blacklisted
-   * @param excludedSubdirectories a set of {@link PathFragment}s, all of which are beneath {@code
-   *     directory} (not necessarily strictly), specifying transitive subdirectories to exclude
+   * @param blacklistedSubdirectories a set of {@link PathFragment}s specifying transitive
+   *     subdirectories that have been blacklisted
+   * @param excludedSubdirectories a set of {@link PathFragment}s specifying transitive
+   *     subdirectories to exclude
    */
   Iterable<PathFragment> getPackagesUnderDirectory(
       ExtendedEventHandler eventHandler,
diff --git a/src/main/java/com/google/devtools/build/lib/query2/ActionGraphQueryEnvironment.java b/src/main/java/com/google/devtools/build/lib/query2/ActionGraphQueryEnvironment.java
index 464df93..68ff864 100644
--- a/src/main/java/com/google/devtools/build/lib/query2/ActionGraphQueryEnvironment.java
+++ b/src/main/java/com/google/devtools/build/lib/query2/ActionGraphQueryEnvironment.java
@@ -280,33 +280,38 @@
       }
       return immediateSuccessfulFuture(null);
     }
+
     AsyncFunction<TargetParsingException, Void> reportBuildFileErrorAsyncFunction =
         exn -> {
           reportBuildFileError(owner, exn.getMessage());
           return Futures.immediateFuture(null);
         };
-    return QueryTaskFutureImpl.ofDelegate(
-        Futures.catchingAsync(
-            patternToEval.evalAdaptedForAsync(
-                resolver,
-                ImmutableSet.of(),
-                ImmutableSet.of(),
-                (Callback<Target>)
-                    partialResult -> {
-                      List<ConfiguredTargetValue> transformedResult = new ArrayList<>();
-                      for (Target target : partialResult) {
-                        ConfiguredTargetValue configuredTargetValue =
-                            getConfiguredTargetValue(target.getLabel());
-                        if (configuredTargetValue != null) {
-                          transformedResult.add(configuredTargetValue);
+    try {
+      return QueryTaskFutureImpl.ofDelegate(
+          Futures.catchingAsync(
+              patternToEval.evalAdaptedForAsync(
+                  resolver,
+                  getBlacklistedPackagePrefixesPathFragments(),
+                  /* excludedSubdirectories= */ ImmutableSet.of(),
+                  (Callback<Target>)
+                      partialResult -> {
+                        List<ConfiguredTargetValue> transformedResult = new ArrayList<>();
+                        for (Target target : partialResult) {
+                          ConfiguredTargetValue configuredTargetValue =
+                              getConfiguredTargetValue(target.getLabel());
+                          if (configuredTargetValue != null) {
+                            transformedResult.add(configuredTargetValue);
+                          }
                         }
-                      }
-                      callback.process(transformedResult);
-                    },
-                QueryException.class),
-            TargetParsingException.class,
-            reportBuildFileErrorAsyncFunction,
-            MoreExecutors.directExecutor()));
+                        callback.process(transformedResult);
+                      },
+                  QueryException.class),
+              TargetParsingException.class,
+              reportBuildFileErrorAsyncFunction,
+              MoreExecutors.directExecutor()));
+    } catch (InterruptedException e) {
+      return immediateCancelledFuture();
+    }
   }
 
   private ConfiguredTargetValue getConfiguredTargetValue(Label label) throws InterruptedException {
diff --git a/src/main/java/com/google/devtools/build/lib/query2/ConfiguredTargetQueryEnvironment.java b/src/main/java/com/google/devtools/build/lib/query2/ConfiguredTargetQueryEnvironment.java
index 231f0df..e41357d 100644
--- a/src/main/java/com/google/devtools/build/lib/query2/ConfiguredTargetQueryEnvironment.java
+++ b/src/main/java/com/google/devtools/build/lib/query2/ConfiguredTargetQueryEnvironment.java
@@ -225,27 +225,33 @@
           reportBuildFileError(owner, exn.getMessage());
           return Futures.immediateFuture(null);
         };
-    return QueryTaskFutureImpl.ofDelegate(
-        Futures.catchingAsync(
-            patternToEval.evalAdaptedForAsync(
-                resolver,
-                ImmutableSet.of(),
-                ImmutableSet.of(),
-                (Callback<Target>)
-                    partialResult -> {
-                      List<ConfiguredTarget> transformedResult = new ArrayList<>();
-                      for (Target target : partialResult) {
-                        ConfiguredTarget configuredTarget = getConfiguredTarget(target.getLabel());
-                        if (configuredTarget != null) {
-                          transformedResult.add(configuredTarget);
+
+    try {
+      return QueryTaskFutureImpl.ofDelegate(
+          Futures.catchingAsync(
+              patternToEval.evalAdaptedForAsync(
+                  resolver,
+                  getBlacklistedPackagePrefixesPathFragments(),
+                  /* excludedSubdirectories= */ ImmutableSet.of(),
+                  (Callback<Target>)
+                      partialResult -> {
+                        List<ConfiguredTarget> transformedResult = new ArrayList<>();
+                        for (Target target : partialResult) {
+                          ConfiguredTarget configuredTarget =
+                              getConfiguredTarget(target.getLabel());
+                          if (configuredTarget != null) {
+                            transformedResult.add(configuredTarget);
+                          }
                         }
-                      }
-                      callback.process(transformedResult);
-                    },
-                QueryException.class),
-            TargetParsingException.class,
-            reportBuildFileErrorAsyncFunction,
-            MoreExecutors.directExecutor()));
+                        callback.process(transformedResult);
+                      },
+                  QueryException.class),
+              TargetParsingException.class,
+              reportBuildFileErrorAsyncFunction,
+              MoreExecutors.directExecutor()));
+    } catch (InterruptedException e) {
+      return immediateCancelledFuture();
+    }
   }
 
   private ConfiguredTarget getConfiguredTarget(Label label) throws InterruptedException {
diff --git a/src/main/java/com/google/devtools/build/lib/query2/PostAnalysisQueryEnvironment.java b/src/main/java/com/google/devtools/build/lib/query2/PostAnalysisQueryEnvironment.java
index 044db34..c193b1a 100644
--- a/src/main/java/com/google/devtools/build/lib/query2/PostAnalysisQueryEnvironment.java
+++ b/src/main/java/com/google/devtools/build/lib/query2/PostAnalysisQueryEnvironment.java
@@ -53,6 +53,7 @@
 import com.google.devtools.build.lib.query2.engine.ThreadSafeOutputFormatterCallback;
 import com.google.devtools.build.lib.query2.engine.Uniquifier;
 import com.google.devtools.build.lib.rules.AliasConfiguredTarget;
+import com.google.devtools.build.lib.skyframe.BlacklistedPackagePrefixesValue;
 import com.google.devtools.build.lib.skyframe.ConfiguredTargetKey;
 import com.google.devtools.build.lib.skyframe.ConfiguredTargetValue;
 import com.google.devtools.build.lib.skyframe.GraphBackedRecursivePackageProvider;
@@ -63,6 +64,7 @@
 import com.google.devtools.build.lib.skyframe.SkyframeExecutor;
 import com.google.devtools.build.lib.skyframe.TargetPatternValue;
 import com.google.devtools.build.lib.skyframe.TargetPatternValue.TargetPatternKey;
+import com.google.devtools.build.lib.vfs.PathFragment;
 import com.google.devtools.build.skyframe.SkyKey;
 import com.google.devtools.build.skyframe.WalkableGraph;
 import java.io.IOException;
@@ -226,6 +228,13 @@
     return (ConfiguredTargetValue) walkableGraphSupplier.get().getValue(key);
   }
 
+  ImmutableSet<PathFragment> getBlacklistedPackagePrefixesPathFragments()
+      throws InterruptedException {
+    return ((BlacklistedPackagePrefixesValue)
+            walkableGraphSupplier.get().getValue(BlacklistedPackagePrefixesValue.key()))
+        .getPatterns();
+  }
+
   @Nullable
   protected abstract T getValueFromKey(SkyKey key) throws InterruptedException;
 
diff --git a/src/main/java/com/google/devtools/build/lib/skyframe/EnvironmentBackedRecursivePackageProvider.java b/src/main/java/com/google/devtools/build/lib/skyframe/EnvironmentBackedRecursivePackageProvider.java
index 1c4daf4..8e10e71 100644
--- a/src/main/java/com/google/devtools/build/lib/skyframe/EnvironmentBackedRecursivePackageProvider.java
+++ b/src/main/java/com/google/devtools/build/lib/skyframe/EnvironmentBackedRecursivePackageProvider.java
@@ -162,7 +162,7 @@
     if (blacklistedSubdirectories.contains(directory)) {
       return ImmutableList.of();
     }
-    ImmutableSet filteredBlacklistedSubdirectories =
+    ImmutableSet<PathFragment> filteredBlacklistedSubdirectories =
         ImmutableSet.copyOf(
             Iterables.filter(
                 blacklistedSubdirectories,
diff --git a/src/main/java/com/google/devtools/build/lib/skyframe/GraphBackedRecursivePackageProvider.java b/src/main/java/com/google/devtools/build/lib/skyframe/GraphBackedRecursivePackageProvider.java
index 2c3ebca..8c82a17 100644
--- a/src/main/java/com/google/devtools/build/lib/skyframe/GraphBackedRecursivePackageProvider.java
+++ b/src/main/java/com/google/devtools/build/lib/skyframe/GraphBackedRecursivePackageProvider.java
@@ -174,9 +174,6 @@
       return ImmutableList.of();
     }
 
-    PathFragment.checkAllPathsAreUnder(blacklistedSubdirectories, directory);
-    PathFragment.checkAllPathsAreUnder(excludedSubdirectories, directory);
-
     // Check that this package is covered by at least one of our universe patterns.
     boolean inUniverse = false;
     for (TargetPatternKey patternKey : universeTargetPatternKeys) {
@@ -220,6 +217,7 @@
     List<Root> roots =
         checkValidDirectoryAndGetRoots(
             repository, directory, blacklistedSubdirectories, excludedSubdirectories);
+
     return rootPackageExtractor.getPackagesFromRoots(
         graph,
         roots,
diff --git a/src/main/java/com/google/devtools/build/lib/skyframe/RecursivePkgValueRootPackageExtractor.java b/src/main/java/com/google/devtools/build/lib/skyframe/RecursivePkgValueRootPackageExtractor.java
index 3adda7e..df3e53e 100644
--- a/src/main/java/com/google/devtools/build/lib/skyframe/RecursivePkgValueRootPackageExtractor.java
+++ b/src/main/java/com/google/devtools/build/lib/skyframe/RecursivePkgValueRootPackageExtractor.java
@@ -37,6 +37,13 @@
       ImmutableSet<PathFragment> blacklistedSubdirectories,
       ImmutableSet<PathFragment> excludedSubdirectories)
       throws InterruptedException {
+
+    ImmutableSet filteredBlacklistedSubdirectories =
+        ImmutableSet.copyOf(
+            Iterables.filter(
+                blacklistedSubdirectories,
+                path -> !path.equals(directory) && path.startsWith(directory)));
+
     LinkedHashSet<PathFragment> packageNames = new LinkedHashSet<>();
     for (Root root : roots) {
       // Note: no need to check if lookup == null because it will never be null.
@@ -48,7 +55,7 @@
                   RecursivePkgValue.key(
                       repository,
                       RootedPath.toRootedPath(root, directory),
-                      blacklistedSubdirectories));
+                      filteredBlacklistedSubdirectories));
       Preconditions.checkState(
           lookup != null,
           "Root %s in repository %s could not be found in the graph.",
diff --git a/src/test/shell/bazel/bazelignore_test.sh b/src/test/shell/bazel/bazelignore_test.sh
index 3f91685..abd575b 100755
--- a/src/test/shell/bazel/bazelignore_test.sh
+++ b/src/test/shell/bazel/bazelignore_test.sh
@@ -73,4 +73,35 @@
     bazel build //foo/bar/... || fail "Could not build valid target"
 }
 
+test_aquery_specific_target() {
+    rm -rf work && mkdir work && cd work
+    touch WORKSPACE
+    mkdir -p foo/ignoreme
+    cat > foo/ignoreme/BUILD <<'EOI'
+genrule(
+  name = "ignoreme",
+  outs = ["ignore.txt"],
+  cmd = "echo Hello World > $@",
+)
+EOI
+    mkdir -p foo
+    cat > foo/BUILD <<'EOI'
+genrule(
+  name = "out",
+  outs = ["out.txt"],
+  cmd = "echo Hello World > $@",
+)
+EOI
+    bazel aquery ... > output 2> "$TEST_log" \
+        || fail "Aquery should complete without error."
+    cat output >> "$TEST_log"
+    assert_contains "ignoreme" output
+
+    echo foo/ignoreme > .bazelignore
+    bazel aquery ... > output 2> "$TEST_log" \
+        || fail "Aquery should complete without error."
+    cat output >> "$TEST_log"
+    assert_not_contains "ignoreme" output
+}
+
 run_suite "Integration tests for .bazelignore"