Dış Bağımlılıklarla Çalışma

Bazel, başka projelerdeki hedeflere bağlı olabilir. Bu diğer projelerden gelen bağımlılıklara dış bağımlılıklar adı verilir.

Çalışma alanı dizinindeki WORKSPACE dosyası (veya WORKSPACE.bazel dosyası), Bazel'a diğer projelerin kaynaklarını nasıl alacağını bildirir. Bu diğer projeler, kendi hedefleri olan bir veya daha fazla BUILD dosyası içerebilir. Ana projedeki BUILD dosyaları, WORKSPACE dosyasındaki adlarını kullanarak bu harici hedeflere bağlı olabilir.

Örneğin, bir sistemde iki proje olduğunu varsayalım:

/
  home/
    user/
      project1/
        WORKSPACE
        BUILD
        srcs/
          ...
      project2/
        WORKSPACE
        BUILD
        my-libs/

project1, /home/user/project2/BUILD içinde tanımlanan :foo hedefine bağlı olmak isterse /home/user/project2 adresinde project2 adlı bir depo bulunabileceğini belirtebilir. O zaman /home/user/project1/BUILD içindeki hedefler @project2//:foo bağlı olabilir.

WORKSPACE dosyası, kullanıcıların dosya sisteminin diğer bölümlerindeki veya internetten indirilen hedeflere bağlı kalmasına olanak tanır. BUILD dosyaları ile aynı söz dizimini kullanır ancak depo kuralları (bazen workspace kuralları olarak da bilinir) adı verilen farklı bir kural grubuna izin verir. Bazel, birkaç yerleşik depo kuralı ve bir dizi yerleşik Starlark depo kuralı içerir. Kullanıcılar daha karmaşık davranışlar için özel depo kuralları da yazabilir.

Desteklenen harici bağımlılık türleri

Birkaç temel tür dış bağımlılık kullanılabilir:

Diğer Bazel projelerine bağlı olarak

İkinci bir Bazel projesindeki hedefleri kullanmak istiyorsanız local_repository veya git_repository ya da http_archive üzerinden yerel dosya sisteminden sembolik bağlantı oluşturabilir, git deposuna başvurabilir ya da projeyi indirebilirsiniz (sırayla).

Örneğin, bir proje (my-project/) üzerinde çalıştığınızı ve iş arkadaşınızın coworkers-project/ projesindeki hedeflere bağlı kalmak istediğinizi varsayalım. Her iki proje de Bazel kullanır. Böylece iş arkadaşınızın projesini dış bağımlılık olarak ekleyebilir ve ardından iş arkadaşınızın kendi DERLEME dosyalarınızdan tanımladığı herhangi bir hedefi kullanabilirsiniz. Aşağıdakileri my_project/WORKSPACE içine eklersiniz:

local_repository(
    name = "coworkers_project",
    path = "/path/to/coworkers-project",
)

İş arkadaşınızın bir //foo:bar hedefi varsa projenizde bu hedef için @coworkers_project//foo:bar ifadesi kullanılabilir. Harici proje adları geçerli çalışma alanı adları olmalıdır.

Bazel dışı projelere bağlı olarak

Önünde new_ bulunan kurallar (ör. new_local_repository), Bazel kullanmayan projelerden hedef oluşturmanıza olanak tanır.

Örneğin, bir proje (my-project/) üzerinde çalıştığınızı ve iş arkadaşınızın projesine (coworkers-project/) bağlı olmak istediğinizi varsayalım. İş arkadaşınızın projesi, derlemek için make kullanıyor, ancak siz bu dosyanın oluşturduğu .so dosyalarından birini kullanmak istiyorsunuz. Bunu yapmak için aşağıdakileri my_project/WORKSPACE öğesine ekleyin:

new_local_repository(
    name = "coworkers_project",
    path = "/path/to/coworkers-project",
    build_file = "coworker.BUILD",
)

build_file, mevcut projenin üzerine yerleştirilecek bir BUILD dosyası belirtir. Örneğin:

cc_library(
    name = "some-lib",
    srcs = glob(["**"]),
    visibility = ["//visibility:public"],
)

Daha sonra projenizin BUILD dosyalarında @coworkers_project//:some-lib hizmetine güvenebilirsiniz.

Harici paketlere bağlı olarak

Maven yapıları ve depoları

Maven depolarındaki yapıları indirmek ve Java bağımlılıkları olarak kullanılabilir hale getirmek için rules_jvm_external kural kümesini kullanın.

Bağımlılıkları getirme

Varsayılan olarak, bazel build sırasında harici bağımlılıklar gerektiği şekilde getirilir. Belirli bir hedef grubu için gereken bağımlılıkları önceden getirmek isterseniz bazel fetch değerini kullanın. Tüm harici bağımlılıkları koşulsuz olarak getirmek için bazel sync değerini kullanın. Getirilen depolar çıktı tabanında depolandığı için getirme işlemi çalışma alanı başına gerçekleşir.

Gölgeleme bağımlılıkları

Mümkün olduğunda projenizde tek bir sürüm politikasının olması önerilir. Bu, derlediğiniz ve son ikili programınıza eklediğiniz bağımlılıklar için gereklidir. Ancak bunun doğru olmadığı durumlarda, bağımlılıkları gölgelendirmek mümkündür. Aşağıdaki senaryoyu inceleyin:

projem/WORKSPACE

workspace(name = "myproject")

local_repository(
    name = "A",
    path = "../A",
)
local_repository(
    name = "B",
    path = "../B",
)

A/WORKSPACE

workspace(name = "A")

load("@bazel_tools//tools/build_defs/repo:http.bzl", "http_archive")
http_archive(
    name = "testrunner",
    urls = ["https://github.com/testrunner/v1.zip"],
    sha256 = "...",
)

B/ÇALIŞMA ALANI

workspace(name = "B")

load("@bazel_tools//tools/build_defs/repo:http.bzl", "http_archive")
http_archive(
    name = "testrunner",
    urls = ["https://github.com/testrunner/v2.zip"],
    sha256 = "..."
)

Hem A hem de B bağımlılığı testrunner değerine bağlıdır ancak testrunner ürününün farklı sürümlerine bağlıdır. Bu test koşucularının myproject içinde rahat bir şekilde bir arada bulunmamaları için bir neden yok ancak aynı ada sahip oldukları için birbirleriyle çatışacaklar. Her iki bağımlılığı da bildirmek için projemi/WORKSPACE'i güncelleyin:

workspace(name = "myproject")

load("@bazel_tools//tools/build_defs/repo:http.bzl", "http_archive")
http_archive(
    name = "testrunner-v1",
    urls = ["https://github.com/testrunner/v1.zip"],
    sha256 = "..."
)
http_archive(
    name = "testrunner-v2",
    urls = ["https://github.com/testrunner/v2.zip"],
    sha256 = "..."
)
local_repository(
    name = "A",
    path = "../A",
    repo_mapping = {"@testrunner" : "@testrunner-v1"}
)
local_repository(
    name = "B",
    path = "../B",
    repo_mapping = {"@testrunner" : "@testrunner-v2"}
)

Bu mekanizma, elmasları birleştirmek için de kullanılabilir. Örneğin, A ve B aynı bağımlılığa sahipse ancak farklı adlarla adlandırıyorsa bu bağımlılıklar projem/WORKSPACE'te birleştirilebilir.

Komut satırından depoları geçersiz kılma

Beyan edilen depoyu komut satırından yerel bir depoyla geçersiz kılmak için --override_repository işaretini kullanın. Bu işareti kullandığınızda, kaynak kodunuzu değiştirmeden harici depoların içeriği değiştirilir.

Örneğin, @foo parametresini /path/to/local/foo yerel dizinine geçersiz kılmak için --override_repository=foo=/path/to/local/foo işaretini iletin.

Kullanım alanlarından bazıları şunlardır:

  • Hata ayıklama sorunları. Örneğin, bir http_archive deposunu geçersiz kılarak daha kolay değişiklik yapabileceğiniz yerel bir dizin oluşturabilirsiniz.
  • Tedarikçi firma. Ağ çağrıları yapamadığınız bir ortamdaysanız ağ tabanlı depo kurallarını yerel dizinlere işaret edecek şekilde geçersiz kılın.

Proxy kullanma

Bazel, HTTPS_PROXY ve HTTP_PROXY ortam değişkenlerinden proxy adreslerini alır ve HTTP/HTTPS dosyalarını indirmek için kullanır (belirtilirse).

IPv6 desteği

Yalnızca IPv6 kullanan makinelerde Bazel, bağımlılıkları değişiklik yapmadan indirebilir. Ancak çift yığınlı IPv4/IPv6 makinelerde Bazel, Java ile aynı kuralı uygular: IPv4 etkinse IPv4 tercih edilir. Bazı durumlarda, örneğin IPv4 ağının harici adresleri çözümleyememesi/harici adreslere erişememesi Network unreachable istisnalarına ve derleme hatalarına yol açabilir. Bu durumlarda, java.net.preferIPv6Addresses=true sistem özelliğini kullanarak Bazel'ın davranışını IPv6'yı tercih etme şeklini geçersiz kılabilirsiniz. Özellikle:

  • --host_jvm_args=-Djava.net.preferIPv6Addresses=true başlangıç seçeneğini kullanın. Örneğin, aşağıdaki satırı .bazelrc dosyanıza ekleyerek:

    startup --host_jvm_args=-Djava.net.preferIPv6Addresses=true

  • İnternete bağlanması gereken Java derleme hedefleri çalıştırıyorsanız (entegrasyon testlerinde bazen buna ihtiyaç duyulursa) --jvmopt=-Djava.net.preferIPv6Addresses=true araç işaretini de kullanın. Örneğin .bazelrc dosyanızda aşağıdaki satırı kullanabilirsiniz:

    build --jvmopt=-Djava.net.preferIPv6Addresses

  • Örneğin, bağımlılık sürümünün çözümlenmesi için rules_jvm_external kullanıyorsanız Coursier'a JVM seçenekleri sağlamak için COURSIER_OPTS ortam değişkenine -Djava.net.preferIPv6Addresses=true de ekleyin

Geçişli bağımlılıklar

Bazel yalnızca WORKSPACE dosyanızda listelenen bağımlılıkları okur. Projeniz (A), WORKSPACE dosyasında üçüncü bir projeye (C) bağımlılık listeleyen başka bir projeye (B) bağımlıysa projenizin WORKSPACE dosyasına hem B hem de C eklemeniz gerekir. Bu şart WORKSPACE dosya boyutunu baloncuk olarak gösterebilir ancak 1.0 sürümünde bir kitaplığın C içermesi ve 2.0'da C kitaplığının bulunması ihtimalini sınırlar.

Dış bağımlılıkları önbelleğe alma

Varsayılan olarak, Bazel harici bağımlılıkları yalnızca tanımları değişirse yeniden indirir. Tanımda başvurulan dosyalarda (yamalar veya BUILD dosyaları gibi) yapılan değişiklikler de Bazel tarafından dikkate alınır.

Yeniden indirmeyi zorunlu kılmak için bazel sync kodunu kullanın.

Düzen

Harici bağımlılıkların tümü, çıktı tabanındaki external alt dizininin altındaki bir dizine indirilir. Yerel bir depo olduğunda, yeni bir dizin oluşturmak yerine burada bir sembolik bağlantı oluşturulur. Aşağıdakileri çalıştırarak external dizinini görebilirsiniz:

ls $(bazel info output_base)/external

bazel clean çalıştırıldığında harici dizinin silinmeyeceğini unutmayın. Tüm harici yapıları kaldırmak için bazel clean --expunge işlevini kullanın.

Çevrimdışı derlemeler

Bazen bir derlemeyi çevrimdışı modda çalıştırmak istenen veya gereklidir. Uçakta seyahat etmek gibi basit kullanım alanlarında, gerekli depoların bazel fetch veya bazel sync ile önceden getirilmesi yeterli olabilir. Ayrıca, --nofetch seçeneğinin kullanılması, derleme sırasında daha fazla depoyu getirme işlevi devre dışı bırakılabilir.

Gerekli dosyaların Bazel'dan farklı bir tüzel kişi tarafından sağlandığı gerçek çevrimdışı derlemeler için Bazel, --distdir seçeneğini destekler. Bir depo kuralı, bazel'dan ctx.download veya ctx.download_and_extract aracılığıyla bir dosya getirmesini istediğinde ve gereken dosyanın karma toplamını sağladığında, Bazel ilk olarak sağlanan ilk URL'nin temel adıyla eşleşen bir dosya için bu seçenek tarafından belirtilen dizinlere bakar ve karma eşleşirse bu yerel kopyayı kullanır.

Bazel, dağıtım yapısından çevrimdışı önyükleme yapmak için bu tekniği kullanır. Bunu, gerekli tüm dış bağımlılıkları dahili bir distdir_tarda toplayarak yapar.

Ancak Bazel, ağa çağrı yapıp yapmadığını bilmeden depo kurallarında rastgele komutların yürütülmesine izin verir. Bu nedenle Bazel'ın derlemeleri tamamen çevrimdışı olarak zorunlu kılma seçeneği yoktur. Dolayısıyla, bir derlemenin çevrimdışı düzgün çalışıp çalışmadığını test etmek, Bazel'ın başlatma testinde yaptığı gibi ağın harici olarak engellenmesini gerektirir.

En iyi uygulamalar

Kod deposu kuralları

Bir depo kuralı genellikle şunlardan sorumlu olmalıdır:

  • Sistem ayarlarını algılama ve dosyalara yazma.
  • Sistemin başka bir yerinde kaynak bulma.
  • URL'lerden kaynaklar indiriliyor.
  • DERLEME dosyaları oluşturma veya harici depo dizininde sembolik bağlantılar oluşturma.

Mümkün olduğunda repository_ctx.execute kullanmaktan kaçının. Örneğin, Make kullanarak derleme içeren Bazel C++ dışında bir kitaplık kullanılırken ctx.execute(["make"]) çalıştırmak yerine repository_ctx.download() kullanılması ve ardından bunu oluşturan bir DERLEME dosyası yazılması tercih edilir.

git_repository ve new_git_repository için http_archive ürününü tercih et. Bunun nedenleri şunlardır:

  • Git deposu kuralları, git(1) sistemine bağlıdır. HTTP indirme aracı ise Bazel'de yerleşiktir ve sistem bağımlılığı yoktur.
  • http_archive ayna olarak urls listesini ve git_repository yalnızca tek bir remote listesini destekler.
  • http_archive, depo önbelleği ile çalışır, ancak git_repository ile çalışmaz. Daha fazla bilgi için bkz. #5116.

bind() kullanmayın. Sorunları ve alternatifleri hakkında uzun açıklamalar için "Bağlamayı kaldırmayı düşünün" bölümüne bakın.