Bazel, सोर्स कोड से सॉफ़्टवेयर बनाता है. सोर्स कोड को डायरेक्ट्री ट्री में व्यवस्थित किया जाता है. इसे वर्कस्पेस कहा जाता है. वर्कस्पेस में मौजूद सोर्स फ़ाइलों को पैकेज के नेस्टेड पदानुक्रम में व्यवस्थित किया जाता है. हर पैकेज एक डायरेक्ट्री होती है. इसमें मिलती-जुलती सोर्स फ़ाइलों का सेट और एक BUILD
फ़ाइल होती है. BUILD
फ़ाइल से यह तय होता है कि सोर्स से कौनसे सॉफ़्टवेयर आउटपुट बनाए जा सकते हैं.
Workspace
वर्कस्पेस, आपके फ़ाइल सिस्टम पर एक डायरेक्ट्री ट्री होता है. इसमें उस सॉफ़्टवेयर के लिए सोर्स फ़ाइलें होती हैं जिसे आपको बनाना है. हर वर्कस्पेस में WORKSPACE
नाम की एक टेक्स्ट फ़ाइल होती है. यह खाली हो सकती है या इसमें आउटपुट बनाने के लिए ज़रूरी बाहरी डिपेंडेंसी के रेफ़रंस हो सकते हैं.
WORKSPACE
नाम की फ़ाइल वाली डायरेक्ट्री को Workspace का रूट माना जाता है. इसलिए, Bazel किसी भी डायरेक्ट्री ट्री को अनदेखा करता है. यह डायरेक्ट्री ट्री, किसी ऐसे फ़ाइल फ़ोल्डर में होता है जिसकी रूट डायरेक्ट्री में WORKSPACE
फ़ाइल होती है. ऐसा इसलिए, क्योंकि ये डायरेक्ट्री ट्री एक और फ़ाइल फ़ोल्डर बनाते हैं.
Bazel, WORKSPACE
फ़ाइल के एलियास के तौर पर WORKSPACE.bazel
फ़ाइल का भी इस्तेमाल करता है. अगर दोनों फ़ाइलें मौजूद हैं, तो WORKSPACE.bazel
का इस्तेमाल किया जाता है.
डेटा स्टोर करने की जगह
कोड को रिपॉज़िटरी में व्यवस्थित किया जाता है. WORKSPACE
फ़ाइल वाली डायरेक्ट्री, मुख्य रिपॉज़िटरी का रूट होती है. इसे @
भी कहा जाता है. अन्य (बाहरी) रिपॉज़िटरी को WORKSPACE
फ़ाइल में, वर्कस्पेस के नियमों का इस्तेमाल करके तय किया जाता है. इसके अलावा, इन्हें Bzlmod सिस्टम में मौजूद मॉड्यूल और एक्सटेंशन से जनरेट किया जाता है. ज़्यादा जानकारी के लिए, बाहरी डिपेंडेंसी की खास जानकारी देखें.
Bazel के साथ बंडल किए गए वर्कस्पेस के नियमों के बारे में, Build Encyclopedia में Workspace Rules सेक्शन में बताया गया है. साथ ही, एम्बेड किए गए Starlark रिपॉज़िटरी के नियमों के बारे में भी बताया गया है.
बाहरी रिपॉज़िटरी, खुद एक रिपॉज़िटरी होती हैं. इसलिए, इनमें अक्सर WORKSPACE
फ़ाइल भी मौजूद होती है. हालांकि, Bazel इन अतिरिक्त WORKSPACE
फ़ाइलों को अनदेखा करता है. खास तौर पर, ट्रांज़िटिव तौर पर निर्भर रहने वाली रिपॉज़िटरी अपने-आप नहीं जुड़ती हैं.
पैकेज
किसी रिपॉज़िटरी में कोड को व्यवस्थित करने की मुख्य इकाई पैकेज होती है. पैकेज, मिलती-जुलती फ़ाइलों का कलेक्शन होता है. इसमें यह जानकारी भी होती है कि आउटपुट आर्टफ़ैक्ट बनाने के लिए, इन फ़ाइलों का इस्तेमाल कैसे किया जा सकता है.
पैकेज को ऐसी डायरेक्ट्री के तौर पर तय किया जाता है जिसमें BUILD
(या BUILD.bazel
) नाम की फ़ाइल होती है. पैकेज में उसकी डायरेक्ट्री की सभी फ़ाइलें शामिल होती हैं. साथ ही, इसके नीचे मौजूद सभी सबडायरेक्ट्री भी शामिल होती हैं. हालांकि, इसमें वे सबडायरेक्ट्री शामिल नहीं होती हैं जिनमें BUILD
फ़ाइल मौजूद होती है.
इस परिभाषा के हिसाब से, कोई भी फ़ाइल या डायरेक्ट्री दो अलग-अलग पैकेज का हिस्सा नहीं हो सकती.
उदाहरण के लिए, यहां दिए गए डायरेक्ट्री ट्री में दो पैकेज हैं: my/app
और सबपैकेज my/app/tests
. ध्यान दें कि my/app/data
कोई पैकेज नहीं है, बल्कि यह पैकेज my/app
से जुड़ी एक डायरेक्ट्री है.
src/my/app/BUILD
src/my/app/app.cc
src/my/app/data/input.txt
src/my/app/tests/BUILD
src/my/app/tests/test.cc
टारगेट
पैकेज, टारगेट का कंटेनर होता है. इन्हें पैकेज की BUILD
फ़ाइल में तय किया जाता है. ज़्यादातर टारगेट, दो मुख्य तरह के होते हैं: फ़ाइलें और नियम.
फ़ाइलों को दो कैटगरी में बांटा गया है. सोर्स फ़ाइलें आम तौर पर, लोगों के प्रयासों से लिखी जाती हैं और इन्हें रिपॉज़िटरी में सेव किया जाता है. जनरेट की गई फ़ाइलों को कभी-कभी डिराइव की गई फ़ाइलें या आउटपुट फ़ाइलें भी कहा जाता है. इन्हें चेक इन नहीं किया जाता, बल्कि सोर्स फ़ाइलों से जनरेट किया जाता है.
दूसरे तरह के टारगेट की जानकारी, नियम के ज़रिए दी जाती है. हर नियम इंस्टेंस, इनपुट फ़ाइलों के सेट और आउटपुट फ़ाइलों के सेट के बीच के संबंध के बारे में बताता है. किसी नियम के इनपुट, सोर्स फ़ाइलें हो सकती हैं. हालांकि, ये अन्य नियमों के आउटपुट भी हो सकते हैं.
किसी नियम के लिए इनपुट, सोर्स फ़ाइल है या जनरेट की गई फ़ाइल, इससे ज़्यादातर मामलों में कोई फ़र्क़ नहीं पड़ता. सिर्फ़ उस फ़ाइल का कॉन्टेंट मायने रखता है. इस वजह से, किसी जटिल सोर्स फ़ाइल को नियम के हिसाब से जनरेट की गई फ़ाइल से आसानी से बदला जा सकता है. ऐसा तब होता है, जब किसी स्ट्रक्चर्ड फ़ाइल को मैन्युअल तरीके से बनाए रखना बहुत मुश्किल हो जाता है और कोई व्यक्ति उसे जनरेट करने के लिए प्रोग्राम लिखता है. उस फ़ाइल का इस्तेमाल करने वाले लोगों को कोई बदलाव करने की ज़रूरत नहीं है. इसके उलट, जनरेट की गई फ़ाइल को, सिर्फ़ लोकल बदलावों वाली सोर्स फ़ाइल से आसानी से बदला जा सकता है.
किसी नियम के इनपुट में, दूसरे नियम भी शामिल हो सकते हैं. इस तरह के संबंधों का सटीक मतलब अक्सर काफ़ी जटिल होता है. यह भाषा या नियम पर निर्भर करता है. हालांकि, यह समझना आसान है: C++ लाइब्रेरी के नियम A के लिए, C++ लाइब्रेरी का कोई दूसरा नियम B इनपुट हो सकता है. इस डिपेंडेंसी का असर यह होता है कि कंपाइलेशन के दौरान, B की हेडर फ़ाइलें A के लिए उपलब्ध होती हैं. साथ ही, लिंकिंग के दौरान B के सिंबल A के लिए उपलब्ध होते हैं. इसके अलावा, एक्ज़ीक्यूशन के दौरान B का रनटाइम डेटा A के लिए उपलब्ध होता है.
सभी नियमों का एक वैरिएंट यह है कि किसी नियम से जनरेट की गई फ़ाइलें हमेशा उसी पैकेज से जुड़ी होती हैं जिससे नियम जुड़ा होता है. किसी दूसरे पैकेज में फ़ाइलें जनरेट नहीं की जा सकतीं. हालांकि, ऐसा अक्सर होता है कि किसी नियम के इनपुट, किसी दूसरे पैकेज से आते हैं.
पैकेज ग्रुप, पैकेज के ऐसे सेट होते हैं जिनका मकसद कुछ नियमों के ऐक्सेस को सीमित करना होता है. पैकेज ग्रुप, package_group
फ़ंक्शन के हिसाब से तय किए जाते हैं. इनमें तीन प्रॉपर्टी होती हैं: इनमें शामिल पैकेज की सूची, इनका नाम, और इनमें शामिल अन्य पैकेज ग्रुप. इन्हें सिर्फ़ इन तरीकों से रेफ़र किया जा सकता है: नियमों के visibility
एट्रिब्यूट से या package
फ़ंक्शन के default_visibility
एट्रिब्यूट से. ये फ़ाइलें न तो जनरेट करते हैं और न ही उनका इस्तेमाल करते हैं. ज़्यादा जानकारी के लिए, package_group
दस्तावेज़ पढ़ें.