Bazel karmaşık bir yapıdır ve derleme sırasında birçok farklı şey yapar. Bunların bazıları derleme performansını etkileyebilir. Bu sayfada, bazı Bazel kavramlarının derleme performansı üzerindeki etkileri eşleştirilmektedir. Kapsamlı olmasa da metrikleri ayıklayarak derleme performansı sorunlarını nasıl belirleyeceğinize ve bunları düzeltmek için neler yapabileceğinize dair bazı örnekleri ekledik. Bu bilgiyle, performans regresyonlarını araştırırken bu kavramları uygulayabileceğinizi umuyoruz.
Temiz ve Artımlı derlemeler
Temiz bir derleme her şeyi sıfırdan oluşturur. Buna karşılık, artımlı bir derleme önceden tamamlanmış bazı çalışmaları yeniden kullanır.
Temiz ve artımlı derlemeleri ayrı ayrı incelemenizi öneririz. Özellikle de Bazel'ın önbelleklerinin durumuna bağlı olan metrikleri toplarken / toplarken (örneğin, istek boyutu metrikleri oluşturma). Ayrıca, iki farklı kullanıcı deneyimini temsil ederler. Sıfırdan temiz bir derleme başlatmaya kıyasla (sıfır önbellek nedeniyle daha uzun sürer) geliştiriciler kod tekrarladıkça çok daha sık gerçekleşir (genellikle önbellek zaten sıcak olduğundan bu daha hızlı gerçekleşir).
Derlemeleri sınıflandırmak için BEP'deki CumulativeMetrics.num_analyses
alanını kullanabilirsiniz. num_analyses <= 1
, temiz bir yapıdır. Aksi takdirde, muhtemelen derlemeyi artımlı bir derleme olarak geniş bir kategorize edebiliriz. Kullanıcı farklı flag'lere veya farklı hedeflere geçerek etkili bir derleme oluşturmaya neden olmuş olabilir. Artımlılığın daha titiz bir şekilde tanımlanması, muhtemelen buluşsal biçimde olmalıdır; örneğin, yüklenen paketlerin sayısına bakılması (PackageMetrics.packages_loaded
).
Derleme performansı için proxy olarak belirleyici derleme metrikleri
Derleme performansını ölçmek, belirli metriklerin (örneğin, Bazel'ın CPU süresi veya uzak bir kümedeki sıra süreleri) belirleyici olmaması nedeniyle zor olabilir. Bu nedenle, Bazel'ın yaptığı çalışmaların miktarı için proxy olarak belirleyici metrikler kullanmak yararlı olabilir ve bu da performansını etkiler.
Derleme isteğinin boyutu, derleme performansını önemli ölçüde etkileyebilir. Daha büyük bir yapı, derleme grafiklerinin analiz edilmesi ve oluşturulmasında daha fazla çalışma yapıldığını gösterebilir. Derlemelerin organik büyümesi, daha fazla bağımlılık eklendikçe/oluşturulduğunda doğal olarak geliştirmeyle birlikte gerçekleşir. Bu nedenle karmaşıklık düzeyi arttıkça yapı oluşturmanın maliyeti de artar.
Bu sorunu çeşitli derleme aşamalarına ayırabilir ve her aşamada gerçekleştirilen çalışmalar için proxy metriği olarak aşağıdaki metrikleri kullanabiliriz:
PackageMetrics.packages_loaded
: Başarıyla yüklenen paketlerin sayısı. Buradaki bir regresyon, yükleme aşamasında her bir BUILD dosyasının okunması ve ayrıştırılması için yapılması gereken daha fazla çalışmayı temsil eder.TargetMetrics.targets_configured
: Derlemede yapılandırılan hedef ve özellik sayısını temsil eder. Regresyon, yapılandırılmış hedef grafiğin oluşturulması ve geçişi için yapılan daha fazla çalışmayı temsil eder.- Bunun nedeni genellikle bağımlılık eklenmesi ve geçişli kapanmanın grafiğini oluşturmaktır.
- Yeni bağımsız kaynakların eklenmiş olabileceği yerleri bulmak için cquery aracını kullanın.
ActionSummary.actions_created
: Derlemede oluşturulan işlemleri temsil eder. Regresyon ise işlem grafiğinin oluşturulmasında yapılan diğer çalışmaları temsil eder. Buna, çalıştırılmamış olabilecek kullanılmayan işlemler de dahildir.- Regresyonları ayıklamak için aquery kullanın.
--skyframe_state
'nı daha ayrıntılı olarak incelemeden önce--output=summary
ile başlamanızı öneririz.
- Regresyonları ayıklamak için aquery kullanın.
ActionSummary.actions_executed
: Yapılan işlem sayısı. Regresyon doğrudan bu işlemlerin yürütülmesi için yapılan çalışmaları temsil eder.- BEP, en çok yürütülen işlem türlerini gösteren işlem istatistiklerini
ActionData
yazır. Varsayılan olarak, en popüler 20 işlem türü toplanır ancak yürütülen tüm işlem türleri için bu verileri toplamak üzere--experimental_record_metrics_for_all_mnemonics
türünü iletebilirsiniz. - Bu, ne tür işlemler yapıldığını (ayrıca) anlamanıza yardımcı olur.
- BEP, en çok yürütülen işlem türlerini gösteren işlem istatistiklerini
BuildGraphSummary.outputArtifactCount
: Yürütülen işlemler tarafından oluşturulan yapıların sayısıdır.- Yürütülen işlemlerin sayısı artmadıysa bir kural uygulaması değiştirilmiş olabilir.
Bu metriklerin tamamı yerel önbelleğin durumundan etkilendiği için bu metrikleri çıkardığınız derlemelerin temiz derlemeler olduğundan emin olmanız gerekir.
Bu metriklerden herhangi birindeki regresyonun, duvar süresi, işlem süresi ve bellek kullanımındaki regresyonlarla birlikte görülebildiğini gözlemledik.
Yerel kaynakların kullanımı
Bazel, yerel makinenizde çeşitli kaynaklar tüketir (hem derleme grafiğini analiz etmek hem de yürütmeyi çalıştırmak ve yerel işlemleri çalıştırmak için). Bu işlem, makinenizin derlemeyi yaparken gösterdiği performansı / stok durumunu ve diğer görevleri etkileyebilir.
Harcanan süre
Belki de gürültüye en açık olan metrikler (ve derlemeden derlemeye büyük ölçüde farklılık gösterebilir) zaman, özellikle de duvar süresi, işlem süresi ve sistem saatidir. Bu metrikleri temel alan bir karşılaştırma almak için bazel-bench'i kullanabilir ve yeterli sayıda --runs
ile ölçümünüzün istatistiksel önemini artırabilirsiniz.
Duvar saati, geçen gerçek zamandır.
- Yalnızca gerçek zamanlı düzenlemeler geri dönüyorsa JSON izleme profili toplamanızı ve farkları aramanızı öneririz. Aksi takdirde, diğer geri çekilen metrikleri, duvarın süresini etkilemiş olabilecekleri için araştırmak daha verimli olacaktır.
CPU süresi, kullanıcı kodunu yürüten CPU tarafından harcanan süredir.
- CPU süresi iki proje kaydında geri düşerse bir Starlark CPU profili toplamanızı öneririz. CPU'nun yoğun olarak kullanıldığı işlerin çoğu burada yapıldığından, analizi analiz aşamasıyla sınırlamak için muhtemelen
--nobuild
kullanmanız gerekir.
- CPU süresi iki proje kaydında geri düşerse bir Starlark CPU profili toplamanızı öneririz. CPU'nun yoğun olarak kullanıldığı işlerin çoğu burada yapıldığından, analizi analiz aşamasıyla sınırlamak için muhtemelen
Sistem süresi, CPU'nun çekirdekteki harcadığı süredir.
- Sistem saati geri düşerse Bazel dosya sisteminizdeki dosyaları okuduğunda genellikle I/O ile ilişkili olur.
Sistem genelinde yük profili oluşturma
JSON iz profili oluşturucu, Bazel 6.0'da kullanılan --experimental_collect_load_average_in_profiler
işaretini kullanarak çağrı sırasındaki sistem yükü ortalamasını toplar.
Şekil 1. Sistem yükü ortalamasını içeren profil.
Bazel çağrısı sırasındaki yüksek yük, Bazel'ın makinenize paralel olarak çok fazla yerel işlem planladığının göstergesi olabilir. Özellikle kapsayıcı ortamlarında (en azından #16512 birleşene kadar) --local_cpu_resources
ve --local_ram_resources
özelliklerini ayarlamayı deneyebilirsiniz.
Bazel bellek kullanımını izleme
Bazel'ın bellek kullanımını alabileceğiniz iki ana kaynak vardır: Bazel info
ve
BEP.
bazel info used-heap-size-after-gc
:System.gc()
çağrısından sonra bayt cinsinden kullanılan bellek miktarı.- Bazel bank bu metrik için de karşılaştırmalar sağlar.
- Ayrıca
peak-heap-size
,max-heap-size
,used-heap-size
vecommitted-heap-size
mevcuttur (belgelere bakın), ancak alaka düzeyi daha düşüktür.
BEP
MemoryMetrics.peak_post_gc_heap_size
: GC sonrası bayt cinsinden en yüksek JVM yığın boyutunun boyutu (tam GC'yi zorunlu kılmaya çalışan--memory_profile
ayarı gerekir).
Hafıza kullanımındaki regresyon genellikle istek boyutu oluşturma metriklerindeki bir regresyondan kaynaklanır. Bu durum genellikle bağımlıların eklenmesi veya kural uygulamasında yapılan bir değişiklikten kaynaklanır.
Bazel'ın bellek ayak izini daha ayrıntılı bir şekilde analiz etmek için kurallar için yerleşik bellek profilleyiciyi kullanmanızı öneririz.
Kalıcı çalışanların bellek profili oluşturma
Kalıcı çalışanlar derlemeleri önemli ölçüde hızlandırmaya yardımcı olabilir (özellikle yorumlanan diller için) bellek ayak izi sorunlu olabilir. Bazel, özellikle çalışanlarına ne kadar bellek kullandığını (hafıza bazında) WorkerMetrics.WorkerStats.worker_memory_in_kb
alanında belirtir.
JSON iz profili profilleyici, --experimental_collect_system_network_usage
işaretini (Bazel 6.0'daki yeni) ileterek çağrı sırasında kalıcı çalışan belleği kullanımını da toplar.
2. Şekil. Çalışanların bellek kullanımını içeren profil.
--worker_max_instances
değerini (varsayılan 4) düşürmek, kalıcı çalışanlar tarafından kullanılan bellek miktarını azaltmaya yardımcı olabilir. Bazel'ın kaynak yöneticisini ve planlayıcısını daha akıllı hale getirmek için aktif olarak çalışıyoruz. Böylece, gelecekte bu tür hassas düzenlemeler daha az zorunlu olacak.
Uzak derlemeler için ağ trafiğini izleme
Uzaktan yürütme sırasında Bazel, işlemlerin yürütülmesi sonucunda oluşturulan yapıları indirir. Bu nedenle, ağ bant genişliğiniz derlemenizin performansını etkileyebilir.
Derlemeleriniz için uzaktan yürütme özelliğini kullanıyorsanız BEP'den NetworkMetrics.SystemNetworkStats
protosunu kullanarak çağrı sırasında ağ trafiğini izlemeyi düşünebilirsiniz (--experimental_collect_system_network_usage
öğesinin iletilmesi gerekir).
Buna ek olarak, JSON izleme profilleri, --experimental_collect_system_network_usage
flag'ini (Bazel 6.0'daki yeni) geçirerek sistem genelinde ağ kullanımını görüntülemenize olanak tanır.
3.Şekil Sistem genelinde ağ kullanımını içeren profil.
Uzaktan yürütme kullanırken yüksek düzeyde ancak yine de düz bir ağ kullanımı, derlemenizdeki darboğazın ağ olduğunu gösterebilir. Henüz kullanmıyorsanız --remote_download_minimal
'i geçerek Derlemeyi Bayt olmadan etkinleştirme seçeneğini değerlendirin.
Bu, gereksiz ara yapıların indirilmesini önleyerek derlemelerinizi hızlandırır.
Diğer bir seçenek de indirme bant genişliğinden tasarruf etmek için yerel bir disk önbelleği yapılandırmaktır.