BazelCon 2022 findet vom 16. bis 17. November in New York und online statt.
Jetzt anmelden

Anleitung zur Bazel-Abfrage

Mit Sammlungen den Überblick behalten Sie können Inhalte basierend auf Ihren Einstellungen speichern und kategorisieren.

Auf dieser Seite werden die ersten Schritte mit der Abfragesprache von Bazel zum Verfolgen von Abhängigkeiten in Ihrem Code beschrieben.

Sprachinformationen und Details zum Flag --output finden Sie in den Referenzhandbüchern, der Bazel-Abfragereferenz und der Bazel-Cquery-Referenz. Wenn Sie Hilfe benötigen, geben Sie bazel help query oder bazel help cquery in die Befehlszeile ein.

Verwenden Sie das Flag --keep_going, um eine Abfrage auszuführen und dabei Fehler wie fehlende Ziele zu ignorieren.

Abhängigkeiten einer Regel finden

Verwenden Sie die Funktion deps in der Bazel-Abfrage, um die Abhängigkeiten von //foo aufzurufen:

$ bazel query "deps(//foo)"
//foo:foo
//foo:foo-dep
...

Dies ist der Satz aller Ziele, die zum Erstellen von //foo erforderlich sind.

Abhängigkeitskette zwischen zwei Paketen verfolgen

Die Bibliothek //third_party/zlib:zlibonly ist in der BUILD-Datei für //foo nicht enthalten, ist aber eine indirekte Abhängigkeit. Wie können wir diesen Abhängigkeitspfad verfolgen? Es gibt zwei nützliche Funktionen: allpaths und somepath. Unter Umständen möchten Sie Tool-Abhängigkeiten auch mit --notool_deps ausschließen, wenn es Ihnen nur wichtig ist, was im erstellten Artefakt enthalten ist, und nicht alle möglichen Jobs.

Um die Grafik aller Abhängigkeiten zu visualisieren, senden Sie die Bazel-Abfrageausgabe über das dot-Befehlszeilentool:

$ bazel query "allpaths(//foo, third_party/...)" --notool_deps --output graph | dot -Tsvg > /tmp/deps.svg

Wenn eine Abhängigkeitsgrafik groß und kompliziert ist, kann es hilfreich sein, mit einem einzigen Pfad zu beginnen:

$ bazel query "somepath(//foo:foo, third_party/zlib:zlibonly)"
//foo:foo
//translations/tools:translator
//translations/base:base
//third_party/py/MySQL:MySQL
//third_party/py/MySQL:_MySQL.so
//third_party/mysql:mysql
//third_party/zlib:zlibonly

Wenn Sie --output graph nicht mit allpaths angeben, wird eine vereinfachte Liste der Abhängigkeitsgrafik angezeigt.

$ bazel query "allpaths(//foo, third_party/...)"
  ...many errors detected in BUILD files...
//foo:foo
//translations/tools:translator
//translations/tools:aggregator
//translations/base:base
//tools/pkg:pex
//tools/pkg:pex_phase_one
//tools/pkg:pex_lib
//third_party/python:python_lib
//translations/tools:messages
//third_party/py/xml:xml
//third_party/py/xml:utils/boolean.so
//third_party/py/xml:parsers/sgmlop.so
//third_party/py/xml:parsers/pyexpat.so
//third_party/py/MySQL:MySQL
//third_party/py/MySQL:_MySQL.so
//third_party/mysql:mysql
//third_party/openssl:openssl
//third_party/zlib:zlibonly
//third_party/zlib:zlibonly_v1_2_3
//third_party/python:headers
//third_party/openssl:crypto

Nebenbemerkung: Implizite Abhängigkeiten

Die BUILD-Datei für //foo verweist niemals auf //translations/tools:aggregator. Wo also ist die direkte Abhängigkeit?

Bestimmte Regeln umfassen implizite Abhängigkeiten von zusätzlichen Bibliotheken oder Tools. Wenn Sie beispielsweise eine genproto-Regel erstellen möchten, müssen Sie zuerst den Protokoll-Compiler erstellen, sodass jede genproto-Regel eine implizite Abhängigkeit vom Protokoll-Compiler aufweist. Diese Abhängigkeiten werden nicht in der Build-Datei erwähnt, sondern vom Build-Tool hinzugefügt. Der vollständige Satz impliziter Abhängigkeiten ist derzeit nicht dokumentiert. Mit --noimplicit_deps können Sie diese Spalten aus Ihren Abfrageergebnissen herausfiltern. Bei cquery umfasst dies aufgelöste Toolchains.

Umgekehrte Abhängigkeiten

Vielleicht möchten Sie wissen, welche Gruppe von Zielen von einem bestimmten Ziel abhängt. Wenn du beispielsweise Code ändern möchtest, solltest du wissen, welcher Code gerade nicht mehr funktioniert. Sie können rdeps(u, x) verwenden, um die umgekehrten Abhängigkeiten der Ziele in x innerhalb der vorübergehenden Schließung von u zu finden.

Die Sky-Abfrage von Bazel unterstützt die Funktion allrdeps, mit der Sie umgekehrte Abhängigkeiten in einem von Ihnen angegebenen Universum abfragen können.

Verschiedene Anwendungsfälle

Mit bazel query können Sie viele Abhängigkeitsbeziehungen analysieren.

Was existiert ...

Welche Pakete gibt es unter foo?

bazel query 'foo/...' --output package

Welche Regeln sind im Paket foo definiert?

bazel query 'kind(rule, foo:*)' --output label_kind

Welche Dateien werden durch Regeln im Paket foo generiert?

bazel query 'kind("generated file", //foo:*)'

Welche Ziele werden vom Starlark-Makro foo generiert?

bazel query 'attr(generator_function, foo, //path/to/search/...)'

Welche BUILD-Dateien sind erforderlich, um //foo zu erstellen?

bazel query 'buildfiles(deps(//foo))' | cut -f1 -d:

Auf welche einzelnen Tests wird ein test_suite erweitert?

bazel query 'tests(//foo:smoke_tests)'

Was sind C++-Tests?

bazel query 'kind(cc_.*, tests(//foo:smoke_tests))'

Welche sind klein? Mittel? Groß?

bazel query 'attr(size, small, tests(//foo:smoke_tests))'

bazel query 'attr(size, medium, tests(//foo:smoke_tests))'

bazel query 'attr(size, large, tests(//foo:smoke_tests))'

Welche Tests unter foo entsprechen einem Muster?

bazel query 'filter("pa?t", kind(".*_test rule", //foo/...))'

Das Muster ist ein Regex und wird auf den vollständigen Namen der Regel angewendet. Ähnlich wie die Vorgehensweise

bazel query 'kind(".*_test rule", //foo/...)' | grep -E 'pa?t'

Welches Paket enthält die Datei path/to/file/bar.java?

 bazel query path/to/file/bar.java --output=package

Was ist das Build-Label für path/to/file/bar.java??

bazel query path/to/file/bar.java

Bei welchen Regelzielen enthält die Datei path/to/file/bar.java die Quelle?

fullname=$(bazel query path/to/file/bar.java)
bazel query "attr('srcs', $fullname, ${fullname//:*/}:*)"

Welche Paketabhängigkeiten gibt es ...

Von welchen Paketen hängt foo ab? (Was benötige ich, um foo zu erstellen?)

bazel query 'buildfiles(deps(//foo:foo))' --output package

Von welchen Paketen hängt die Baumstruktur foo ab, mit Ausnahme von foo/contrib?

bazel query 'deps(foo/... except foo/contrib/...)' --output package

Welche Regelabhängigkeiten bestehen ...

Von welchen genproto-Regeln hängt die Leiste ab?

bazel query 'kind(genproto, deps(bar/...))'

Suchen Sie die Definition einiger JNI-Bibliothek (C++), die von einer Java-Binärregel in der Servlet-Struktur abhängig ist.

bazel query 'some(kind(cc_.*library, deps(kind(java_binary, //java/com/example/frontend/...))))' --output location
...Suchen Sie jetzt die Definitionen aller Java-Binärdateien, die von ihnen abhängen
bazel query 'let jbs = kind(java_binary, //java/com/example/frontend/...) in
  let cls = kind(cc_.*library, deps($jbs)) in
    $jbs intersect allpaths($jbs, $cls)'

Welche Dateiabhängigkeiten gibt es ...

Was sind die vollständigen Java-Quelldateien, die zum Erstellen von foo erforderlich sind?

Quelldateien:

bazel query 'kind("source file", deps(//path/to/target/foo/...))' | grep java$

Erstellte Dateien:

bazel query 'kind("generated file", deps(//path/to/target/foo/...))' | grep java$

Welche vollständigen Java-Quelldateien sind erforderlich, um QUX-Tests zu erstellen?

Quelldateien:

bazel query 'kind("source file", deps(kind(".*_test rule", javatests/com/example/qux/...)))' | grep java$

Erstellte Dateien:

bazel query 'kind("generated file", deps(kind(".*_test rule", javatests/com/example/qux/...)))' | grep java$

Welche Unterschiede in den Abhängigkeiten zwischen X und Y bestehen ...

Welche Ziele sind in //foo abhängig von //foo:foolib?

bazel query 'deps(//foo) except deps(//foo:foolib)'

Welche C++-Bibliotheken hängen von den foo-Tests ab, die von der //foo-Produktionsbinde nicht abhängen?

bazel query 'kind("cc_library", deps(kind(".*test rule", foo/...)) except deps(//foo))'

Warum existiert diese Abhängigkeit ...

Warum hängt bar von groups2 ab?

bazel query 'somepath(bar/...,groups2/...:*)'

Wenn die Ergebnisse dieser Abfrage vorliegen, werden Sie oft feststellen, dass ein einzelnes Ziel eine unerwartete oder schwerwiegende und unerwünschte Abhängigkeit von bar hervorhebt. Die Abfrage kann dann weiter optimiert werden:

Zeig mir einen Pfad von docker/updater:updater_systest (py_test) zu cc_library, von dem es abhängig ist:

bazel query 'let cc = kind(cc_library, deps(docker/updater:updater_systest)) in
  somepath(docker/updater:updater_systest, $cc)'

Warum hängt die Bibliothek //photos/frontend:lib von zwei Varianten derselben Bibliothek //third_party/jpeglib und //third_party/jpeg ab?

Die Abfrage sieht folgendermaßen aus: &showt den Teilgraph von //photos/frontend:lib, der von beiden Bibliotheken abhängt. Bei der Darstellung in absteigender Reihenfolge ist das letzte Element des Ergebnisses wahrscheinlich der Täter.

bazel query 'allpaths(//photos/frontend:lib, //third_party/jpeglib)
                intersect
               allpaths(//photos/frontend:lib, //third_party/jpeg)'
//photos/frontend:lib
//photos/frontend:lib_impl
//photos/frontend:lib_dispatcher
//photos/frontend:icons
//photos/frontend/modules/gadgets:gadget_icon
//photos/thumbnailer:thumbnail_lib
//third_party/jpeg/img:renderer

Was hängt davon ab ...

Welche Regeln unter Leiste hängen von Y ab?

bazel query 'bar/... intersect allpaths(bar/..., Y)'

Welche Ziele hängen direkt von T im T&s-Paket ab?

bazel query 'same_pkg_direct_rdeps(T)'

Wie unterbrich ich eine Abhängigkeit ...

Welche Abhängigkeitspfade muss ich unterbrechen, damit bar nicht mehr von X abhängt?

So geben Sie das Diagramm in einer svg-Datei aus:

bazel query 'allpaths(bar/...,X)' --output graph | dot -Tsvg > /tmp/dep.svg

Verschiedenes

Wie viele sequenzielle Schritte gibt es im //foo-tests-Build?

Leider liefert die Abfragesprache derzeit nicht den längsten Pfad von x nach y, aber den am weitesten entfernten (oder besser a) Knoten vom Startpunkt aus oder zeigt die Längen des längsten Pfads von x zu jedem y, von dem er abhängt. Verwende maxrank:

bazel query 'deps(//foo-tests)' --output maxrank | tail -1
85 //third_party/zlib:zutil.c

Das Ergebnis gibt an, dass Pfade der Länge 85 vorhanden sind, die in dieser Reihenfolge in diesem Build auftreten müssen.