क्वेरी गाइड

इस पेज पर, Bazel की क्वेरी लैंग्वेज का इस्तेमाल करके, अपने कोड में डिपेंडेंसी का पता लगाने का तरीका बताया गया है.

किसी भाषा के बारे में जानकारी और --output फ़्लैग के बारे में जानकारी पाने के लिए, कृपया रेफ़रंस मैन्युअल, Bazel क्वेरी रेफ़रंस और Bazel cquery रेफ़रंस देखें. कमांड लाइन पर bazel help query या bazel help cquery टाइप करके मदद पाई जा सकती है.

क्वेरी को एक्ज़िक्यूट करते समय, गड़बड़ियों को अनदेखा करने के लिए, --keep_going फ़्लैग का इस्तेमाल करें. जैसे, टारगेट मौजूद न होने की गड़बड़ी.

किसी नियम की डिपेंडेंसी ढूंढना

//foo की डिपेंडेंसी देखने के लिए, Bazel क्वेरी में deps फ़ंक्शन का इस्तेमाल करें:

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

यह //foo बनाने के लिए ज़रूरी सभी टारगेट का सेट है.

दो पैकेज के बीच डिपेंडेंसी चेन का पता लगाना

लाइब्रेरी //third_party/zlib:zlibonly, //foo के लिए BUILD फ़ाइल में नहीं है. हालांकि, यह इनडायरेक्ट डिपेंडेंसी है. हम इस डिपेंडेंसी पाथ का पता कैसे लगा सकते हैं? यहां दो काम के फ़ंक्शन दिए गए हैं: allpaths और somepath. अगर आपको सिर्फ़ बनाए गए आर्टफ़ैक्ट में शामिल चीज़ों के बारे में जानना है, तो टूलिंग डिपेंडेंसी को --notool_deps के साथ बाहर रखा जा सकता है. ऐसा तब किया जा सकता है, जब आपको हर संभावित काम के बारे में नहीं जानना हो.

सभी डिपेंडेंसी का ग्राफ़ देखने के लिए, Bazel क्वेरी के आउटपुट को dot कमांड-लाइन टूल के ज़रिए पाइप करें:

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

डिपेंडेंसी ग्राफ़ बड़ा और मुश्किल होने पर, एक पाथ से शुरुआत करना मददगार हो सकता है:

$ 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

अगर allpaths के साथ --output graph तय नहीं किया जाता है, तो आपको डिपेंडेंसी ग्राफ़ की फ़्लैट सूची मिलेगी.

$ 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

अहम जानकारी: इंप्लिसिट डिपेंडेंसी

//foo के लिए BUILD फ़ाइल, कभी भी //translations/tools:aggregator का रेफ़रंस नहीं देती. तो, डायरेक्ट डिपेंडेंसी कहां है?

कुछ नियमों में, अतिरिक्त लाइब्रेरी या टूल पर इंप्लिसिट डिपेंडेंसी शामिल होती हैं. उदाहरण के लिए, genproto नियम बनाने के लिए, आपको सबसे पहले प्रोटोकॉल कंपाइलर बनाना होगा. इसलिए, हर genproto नियम में प्रोटोकॉल कंपाइलर पर इंप्लिसिट डिपेंडेंसी होती है. इन डिपेंडेंसी का ज़िक्र, बिल्ड फ़ाइल में नहीं किया जाता. हालांकि, इन्हें बिल्ड टूल में जोड़ा जाता है. फ़िलहाल, इंप्लिसिट डिपेंडेंसी के पूरे सेट के बारे में कोई जानकारी उपलब्ध नहीं है. --noimplicit_deps का इस्तेमाल करके, क्वेरी के नतीजों से इन डिपेंडेंसी को फ़िल्टर किया जा सकता है. cquery के लिए, इसमें हल की गई टूलचेन शामिल होंगी.

रिवर्स डिपेंडेंसी

आपको उन टारगेट के सेट के बारे में जानना पड़ सकता है जो किसी टारगेट पर निर्भर करते हैं. उदाहरण के लिए, अगर आपको कोई कोड बदलना है, तो आपको यह जानना पड़ सकता है कि आप कौनसे अन्य कोड को तोड़ने वाले हैं. u के ट्रांज़िटिव क्लोज़र में, x में मौजूद टारगेट की रिवर्स डिपेंडेंसी ढूंढने के लिए, rdeps(u, x) का इस्तेमाल किया जा सकता है.

Bazel की Sky Query , allrdeps फ़ंक्शन के साथ काम करती है. इसकी मदद से, तय किए गए यूनिवर्स में रिवर्स डिपेंडेंसी के बारे में क्वेरी की जा सकती है.

अन्य इस्तेमाल

डिपेंडेंसी के कई रिलेशनशिप का विश्लेषण करने के लिए, bazel query का इस्तेमाल किया जा सकता है.

क्या मौजूद है ...

foo के तहत कौनसे पैकेज मौजूद हैं?

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

foo पैकेज में कौनसे नियम तय किए गए हैं?

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

foo पैकेज में मौजूद नियमों से कौनसी फ़ाइलें जनरेट होती हैं?

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

Starlark मैक्रो foo से कौनसे टारगेट जनरेट होते हैं?

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

//foo बनाने के लिए, BUILD फ़ाइलों का कौनसा सेट ज़रूरी है?

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

test_suite से कौनसे अलग-अलग टेस्ट मिलते हैं?

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

इनमें से C++ टेस्ट कौनसे हैं?

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

इनमें से छोटे टेस्ट कौनसे हैं? मीडियम टेस्ट कौनसे हैं? बड़े टेस्ट कौनसे हैं?

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))'

foo के तहत, पैटर्न से मेल खाने वाले टेस्ट कौनसे हैं?

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

पैटर्न एक रेगुलर एक्सप्रेशन है और इसे नियम के पूरे नाम पर लागू किया जाता है. यह

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

path/to/file/bar.java फ़ाइल किस पैकेज में है?

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

path/to/file/bar.java? के लिए बिल्ड लेबल क्या है?

bazel query path/to/file/bar.java

कौनसे नियम टारगेट में, path/to/file/bar.java को सोर्स के तौर पर शामिल किया गया है?

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

कौनसी पैकेज डिपेंडेंसी मौजूद हैं ...

foo किन पैकेज पर निर्भर करता है? (foo बनाने के लिए मुझे क्या देखना होगा)

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

foo/contrib को छोड़कर, foo ट्री किन पैकेज पर निर्भर करता है?

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

कौनसी नियम डिपेंडेंसी मौजूद हैं ...

बार, किन genproto नियमों पर निर्भर करता है?

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

servlet ट्री में, किसी ऐसे JNI (C++) लाइब्रेरी की परिभाषा ढूंढें जिस पर Java बाइनरी नियम ट्रांज़िटिव तरीके से निर्भर करता है.

bazel query 'some(kind(cc_.*library, deps(kind(java_binary, //java/com/example/frontend/...))))' --output location
...अब उन सभी Java बाइनरी की परिभाषाएं ढूंढें जो उन पर निर्भर करते हैं
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)'

कौनसी फ़ाइल डिपेंडेंसी मौजूद हैं ...

foo बनाने के लिए, Java सोर्स फ़ाइलों का कौनसा पूरा सेट ज़रूरी है?

सोर्स फ़ाइलें:

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

जनरेट की गई फ़ाइलें:

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

QUX के टेस्ट बनाने के लिए, Java सोर्स फ़ाइलों का कौनसा पूरा सेट ज़रूरी है?

सोर्स फ़ाइलें:

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

जनरेट की गई फ़ाइलें:

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

X और Y के बीच डिपेंडेंसी में कौनसे अंतर मौजूद हैं ...

//foo किन टारगेट पर निर्भर करता है, जबकि //foo:foolib नहीं करता?

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

foo के टेस्ट, किन C++ लाइब्रेरी पर निर्भर करते हैं, जबकि //foo प्रोडक्शन बाइनरी नहीं करती?

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

यह डिपेंडेंसी क्यों मौजूद है ...

bar, groups2 पर क्यों निर्भर करता है?

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

इस क्वेरी के नतीजे मिलने के बाद, अक्सर आपको पता चलेगा कि कोई एक टारगेट, bar की ऐसी डिपेंडेंसी है जिसकी उम्मीद नहीं थी या जो बहुत ज़्यादा और अवांछित है. इसके बाद, क्वेरी को इस तरह बेहतर बनाया जा सकता है:

docker/updater:updater_systest (py_test) से लेकर किसी ऐसी cc_library तक का पाथ दिखाएं जिस पर यह निर्भर करता है:

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

लाइब्रेरी //photos/frontend:lib, एक ही लाइब्रेरी //third_party/jpeglib और //third_party/jpeg के दो वैरिएंट पर क्यों निर्भर करती है?

इस क्वेरी का मतलब है: "//photos/frontend:lib का वह सबग्राफ़ दिखाएं जो दोनों लाइब्रेरी पर निर्भर करता है". टॉपोलॉजिकल क्रम में दिखाए जाने पर, नतीजे का आखिरी एलिमेंट सबसे ज़्यादा संभावित वजह होता है.

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

कौनसी चीज़ ... पर निर्भर करती है

बार के तहत मौजूद कौनसे नियम, Y पर निर्भर करते हैं?

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

T के पैकेज में, कौनसे टारगेट सीधे तौर पर T पर निर्भर करते हैं?

bazel query 'same_pkg_direct_rdeps(T)'

मैं किसी डिपेंडेंसी को कैसे तोड़ूं ...

bar को X पर निर्भर न बनाने के लिए, मुझे किन डिपेंडेंसी पाथ को तोड़ना होगा?

ग्राफ़ को svg फ़ाइल में आउटपुट करने के लिए:

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

अन्य सुविधाएं

//foo-tests बिल्ड में, कितने सीक्वेंशियल चरण हैं?

फ़िलहाल, क्वेरी लैंग्वेज आपको x से y तक का सबसे लंबा पाथ नहीं दिखा सकती. हालांकि, यह शुरुआती पॉइंट से सबसे दूर मौजूद नोड ढूंढ सकती है या आपको x से हर उस y तक के सबसे लंबे पाथ की लंबाई दिखा सकती है जिस पर वह निर्भर करता है. maxrank का इस्तेमाल करें:

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

नतीजे से पता चलता है कि इस बिल्ड में, 85 की लंबाई वाले पाथ मौजूद हैं. इन्हें क्रम से होना चाहिए.