BazelCon 2022 akan hadir pada 16-17 November ke New York dan online.
Daftar sekarang.

Visibilitas

Tetap teratur dengan koleksi Simpan dan kategorikan konten berdasarkan preferensi Anda.

Halaman ini mencakup spesifikasi visibilitas, praktik terbaik, dan contoh.

Visibilitas mengontrol apakah target dapat digunakan (bergantung pada) oleh target dalam paket lainnya. Ini membantu orang lain membedakan antara API publik library Anda dan detail implementasinya, dan merupakan alat penting untuk membantu menerapkan struktur saat ruang kerja Anda berkembang.

Jika Anda perlu menonaktifkan pemeriksaan visibilitas (misalnya saat bereksperimen), gunakan --check_visibility=false.

Untuk detail selengkapnya tentang paket dan sub-paket, lihat Konsep dan terminologi.

Spesifikasi visibilitas

Semua target aturan memiliki atribut visibility yang menggunakan daftar label. Satu target dapat dilihat oleh yang lain jika berada dalam paket yang sama, atau jika dilihat oleh salah satu label.

Setiap label memiliki salah satu bentuk berikut:

  • "//visibility:public": Siapa saja dapat menggunakan target ini. (Mungkin tidak digabungkan dengan spesifikasi lainnya.)

  • "//visibility:private": Hanya target dalam paket ini yang dapat menggunakan target ini. (Mungkin tidak digabungkan dengan spesifikasi lainnya.)

  • "//foo/bar:__pkg__": Memberikan akses ke target yang ditentukan dalam //foo/bar (tetapi tidak ke sub-paketnya). Di sini, __pkg__ adalah bagian khusus dari sintaksis yang mewakili semua target dalam paket.

  • "//foo/bar:__subpackages__": Memberikan akses ke target yang ditentukan dalam //foo/bar, atau sub-paket langsung atau tidak langsungnya. Sekali lagi, __subpackages__ adalah sintaksis khusus.

  • "//foo/bar:my_package_group": Memberikan akses ke semua paket yang diberi nama oleh grup paket tertentu.

    • Grup paket tidak mendukung sintaks __pkg__ dan __subpackages__ yang khusus. Dalam grup paket, "//foo/bar" setara dengan "//foo/bar:__pkg__" dan "//foo/bar/..." setara dengan "//foo/bar:__subpackages__".

Misalnya, jika//some/package:mytarget punyavisibility tetapkan ke [":__subpackages__", "//tests:__pkg__"], maka dapat digunakan oleh target apa pun yang merupakan bagian dari//some/package/... dan struktur sumber, serta target yang ditentukan dalam//tests/BUILD, tetapi bukan berdasarkan target yang ditentukan di//tests/integration/BUILD Domain.

Sebagai kasus khusus, target package_group sendiri tidak memiliki atribut visibility; konten tersebut selalu terlihat oleh publik.

Visibilitas tidak dapat ditetapkan ke target non-package_group tertentu. Tindakan tersebut akan memicu error "Label tidak merujuk ke grup paket" atau "Siklus dalam grafik dependensi".

Visibilitas target aturan

Jika target aturan tidak menetapkan atribut visibility, visibilitasnya diberikan oleh default_visibility yang ditentukan dalam package dari file BUILD target. Jika tidak ada deklarasi default_visibility seperti itu, visibilitasnya adalah //visibility:private.

Visibilitas config_setting secara historis belum diterapkan. --incompatible_enforce_config_setting_visibility dan --incompatible_config_setting_private_default_visibility menyediakan logika migrasi untuk bergabung dengan aturan lain.

Jika --incompatible_enforce_config_setting_visibility=false, setiap config_setting tanpa syarat dapat dilihat oleh semua target.

Selain itu, jika --incompatible_config_setting_private_default_visibility=false, config_setting yang tidak secara eksplisit menetapkan visibilitas adalah //visibility:public (mengabaikan paket default_visibility).

Selain itu, jika --incompatible_config_setting_private_default_visibility=true, config_setting akan menggunakan logika visibilitas yang sama seperti semua aturan lainnya.

Praktik terbaiknya adalah memperlakukan semua target config_setting seperti aturan lainnya: menetapkan visibility secara eksplisit pada config_setting mana pun yang digunakan di luar paketnya.

Contoh

File //frobber/bin/BUILD:

# This target is visible to everyone
cc_binary(
    name = "executable",
    visibility = ["//visibility:public"],
    deps = [":library"],
)

# This target is visible only to targets declared in the same package
cc_library(
    name = "library",
    # No visibility -- defaults to private since no
    # package(default_visibility = ...) was used.
)

# This target is visible to targets in package //object and //noun
cc_library(
    name = "subject",
    visibility = [
        "//noun:__pkg__",
        "//object:__pkg__",
    ],
)

# See package group "//frobber:friends" (below) for who can
# access this target.
cc_library(
    name = "thingy",
    visibility = ["//frobber:friends"],
)

File //frobber/BUILD:

# This is the package group declaration to which target
# //frobber/bin:thingy refers.
#
# Our friends are packages //frobber, //fribber and any
# subpackage of //fribber.
package_group(
    name = "friends",
    packages = [
        "//fribber/...",
        "//frobber",
    ],
)

Visibilitas target file yang dihasilkan

Target file yang dihasilkan memiliki visibilitas yang sama dengan target aturan yang menghasilkannya.

Visibilitas target file sumber

Secara default, target file sumber hanya terlihat dari paket yang sama. Untuk membuat file sumber dapat diakses dari paket lain, gunakan exports_files.

Jika panggilan ke exports_files menentukan atribut visibilitas, visibilitas tersebut akan berlaku. Jika tidak, file bersifat publik (default_visibility akan diabaikan).

Jika memungkinkan, lebih baik menampilkan library atau jenis aturan lain, bukan file sumber. Misalnya, deklarasikan java_library, bukan mengekspor file .java. Sebaiknya gunakan target aturan untuk hanya menyertakan sumber dalam paketnya sendiri secara langsung.

Contoh

File //frobber/data/BUILD:

exports_files(["readme.txt"])

File //frobber/bin/BUILD:

cc_binary(
  name = "my-program",
  data = ["//frobber/data:readme.txt"],
)

Perilaku lama

Jika tanda --incompatible_no_implicit_file_export tidak disetel, perilaku lama akan diterapkan.

Dengan perilaku lama, file yang digunakan oleh minimal satu target aturan dalam paket diekspor secara implisit menggunakan spesifikasi default_visibility. Lihat proposal desain untuk mengetahui detail selengkapnya.

Visibilitas file bzl

Pernyataan load saat ini tidak dapat dilihat. Anda dapat memuat file bzl di mana saja di ruang kerja.

Namun, pengguna dapat memilih untuk menjalankan linter Buildifier. Pemeriksaan bzl-visibility memberikan peringatan jika pengguna load dari bawah subdirektori bernama internal atau private.

Visibilitas dependensi implisit

Beberapa aturan memiliki dependensi implisit. Misalnya, aturan C++ mungkin secara implisit bergantung pada compiler C++.

Saat ini, dependensi implisit diperlakukan seperti dependensi normal. Semua itu harus terlihat oleh semua instance aturan. Perilaku ini dapat diubah menggunakan --incompatible_visibility_private_attributes_at_definition.

Praktik terbaik

  • Hindari menyetel visibilitas default ke publik. Pendekatan ini mungkin cocok untuk pembuatan prototipe atau codebase kecil, tetapi tidak disarankan dalam codebase besar: cobalah untuk secara eksplisit menyertakan target yang merupakan bagian dari antarmuka publik.

  • Gunakan package_group untuk berbagi spesifikasi visibilitas di antara beberapa target. Ini sangat berguna saat target di banyak file BUILD harus diekspos ke kumpulan paket yang sama.

  • Gunakan spesifikasi visibilitas yang terperinci saat menghentikan target. Batasi visibilitas bagi pengguna saat ini untuk menghindari dependensi baru.