Grup eksekusi memungkinkan beberapa platform eksekusi dalam satu target. Setiap grup eksekusi memiliki dependensi toolchain sendiri dan melakukan resolusi toolchain sendiri.
Latar belakang
Grup eksekusi memungkinkan penulis aturan menentukan kumpulan tindakan, yang masing-masing memiliki platform eksekusi yang berpotensi berbeda. Beberapa platform eksekusi dapat memungkinkan tindakan dieksekusi secara berbeda, misalnya mengompilasi aplikasi iOS di pekerja jarak jauh (Linux), lalu menautkan/menandatangani kode di pekerja Mac lokal.
Kemampuan untuk menentukan grup tindakan juga membantu mengurangi penggunaan mnemonik tindakan sebagai proxy untuk menentukan tindakan. Mnemonik tidak dijamin unik dan hanya dapat mereferensikan satu tindakan. Hal ini sangat membantu dalam mengalokasikan resource tambahan ke tindakan intensif memori dan pemrosesan tertentu seperti penautan dalam build C++ tanpa mengalokasikan secara berlebihan ke tugas yang kurang menuntut.
Menentukan grup eksekusi
Selama definisi aturan, penulis aturan dapat
mendeklarasikan
kumpulan grup eksekusi. Di setiap grup eksekusi, penulis aturan dapat menentukan semua yang diperlukan untuk memilih platform eksekusi untuk grup eksekusi tersebut, yaitu batasan apa pun melalui exec_compatible_with dan jenis toolchain melalui toolchain.
# foo.bzl
my_rule = rule(
_impl,
exec_groups = {
“link”: exec_group(
exec_compatible_with = [ "@platforms//os:linux" ]
toolchains = ["//foo:toolchain_type"],
),
“test”: exec_group(
toolchains = ["//foo_tools:toolchain_type"],
),
},
attrs = {
"_compiler": attr.label(cfg = config.exec("link"))
},
)
Dalam cuplikan kode di atas, Anda dapat melihat bahwa dependensi alat juga dapat menentukan
transisi untuk grup exec menggunakan
cfg
parameter atribut dan
config
modul. Modul ini mengekspos fungsi exec yang mengambil satu parameter string yang merupakan nama grup exec tempat dependensi harus dibuat.
Seperti pada aturan native, grup eksekusi test ada secara default pada aturan pengujian Starlark.
Warisan grup eksekusi
Selain menentukan batasan dan toolchain-nya sendiri, grup eksekusi baru dapat mendeklarasikan bahwa grup tersebut ingin mewarisi dari grup eksekusi default aturan, dengan meneruskan parameter copy_from_rule = True. Terjadi error jika menetapkan copy_from_rule ke benar dan juga meneruskan exec_compatible_with atau toolchains.
Grup eksekusi yang mewarisi dari grup eksekusi default akan menyalin batasan, toolchain, dan properti eksekusi dari default. Hal ini mencakup batasan dan properti eksekusi yang ditetapkan di tingkat target, bukan hanya yang ditentukan oleh aturan itu sendiri. Dengan kata lain, mengingat hal berikut:
# foo.bzl
my_rule = rule(
_impl,
exec_groups = {
“copied”: exec_group(
copy_from_rule = True,
# This will inherit exec_compatible_with and toolchains.
# Setting them here directly would be an error, however.
),
},
toolchains = ["//foo_tools:toolchain_type"],
exec_compatible_with = ["@platforms//os:linux"],
)
# BUILD
my_rule(
name = "demo",
exec_compatible_with = [":local_constraint"],
)
Grup eksekusi copied untuk target demo yang dikonfigurasi akan menyertakan semua
hal berikut:
- //fool_tools:toolchain_type
- @platforms//os:linux
- :local_constraint
Mengakses grup eksekusi
Dalam penerapan aturan, Anda dapat mendeklarasikan bahwa tindakan harus dijalankan di platform eksekusi grup eksekusi. Anda dapat melakukannya dengan menggunakan exec_group
parameter dari metode pembuatan tindakan, khususnya ctx.actions.run dan
ctx.actions.run_shell.
# foo.bzl
def _impl(ctx):
ctx.actions.run(
inputs = [ctx.attr._some_tool, ctx.srcs[0]]
exec_group = "compile",
# ...
)
Penulis aturan juga akan dapat mengakses toolchain yang di-resolve grup eksekusi, mirip dengan cara Anda dapat mengakses toolchain target yang di-resolve:
# foo.bzl
def _impl(ctx):
foo_info = ctx.exec_groups["link"].toolchains["//foo:toolchain_type"].fooinfo
ctx.actions.run(
inputs = [foo_info, ctx.srcs[0]]
exec_group = "link",
# ...
)
Menggunakan grup eksekusi untuk menetapkan properti eksekusi
Grup eksekusi terintegrasi dengan atribut
exec_properties
yang ada di setiap aturan dan memungkinkan penulis target menentukan
dict string properti yang kemudian diteruskan ke mesin eksekusi. Misalnya, jika Anda ingin menetapkan beberapa properti, misalnya memori, untuk target dan memberikan alokasi memori yang lebih tinggi untuk tindakan tertentu, Anda akan menulis entri exec_properties dengan kunci yang ditambah grup eksekusi, seperti:
# BUILD
my_rule(
name = 'my_target',
exec_properties = {
'mem': '12g',
'link.mem': '16g'
}
…
)
Semua tindakan dengan exec_group = "link" akan melihat kamus properti exec
sebagai {"mem": "16g"}. Seperti yang Anda lihat di sini, setelan tingkat grup eksekusi mengganti setelan tingkat target.
Grup eksekusi untuk aturan native
Grup eksekusi berikut tersedia untuk tindakan yang ditentukan oleh aturan native:
test: Tindakan peluncur pengujian.cpp_link: Tindakan penautan C++.
Membuat grup exec untuk menetapkan properti exec
Terkadang, Anda ingin menggunakan grup exec untuk memberikan properti exec yang berbeda untuk tindakan tertentu, tetapi sebenarnya tidak menginginkan toolchain atau batasan yang berbeda dari aturan. Untuk situasi ini, Anda dapat membuat grup exec menggunakan parameter copy_from_rule:
# foo.bzl
# Creating an exec group with `copy_from_rule=True` is the same as explicitly
# setting the exec group's toolchains and constraints to the same values as the
# rule's respective parameters.
my_rule = rule(
_impl,
exec_compatible_with = ["@platforms//os:linux"],
toolchains = ["//foo:toolchain_type"],
exec_groups = {
# The following two groups have the same toolchains and constraints:
“foo”: exec_group(copy_from_rule = True),
"bar": exec_group(
exec_compatible_with = ["@platforms//os:linux"],
toolchains = ["//foo:toolchain_type"],
),
},
)
#
Grup eksekusi dan properti eksekusi platform
Anda dapat menentukan exec_properties untuk grup eksekusi arbitrer pada target platform (tidak seperti exec_properties yang ditetapkan langsung pada target, tempat properti untuk grup eksekusi yang tidak diketahui ditolak). Target kemudian mewarisi exec_properties platform eksekusi yang memengaruhi grup eksekusi default dan grup eksekusi relevan lainnya.
Misalnya, anggaplah menjalankan pengujian C++ memerlukan beberapa resource yang tersedia, tetapi tidak diperlukan untuk mengompilasi dan menautkan; hal ini dapat dimodelkan sebagai berikut:
constraint_setting(name = "resource")
constraint_value(name = "has_resource", constraint_setting = ":resource")
platform(
name = "platform_with_resource",
constraint_values = [":has_resource"],
exec_properties = {
"test.resource": "...",
},
)
cc_test(
name = "my_test",
srcs = ["my_test.cc"],
exec_compatible_with = [":has_resource"],
)
exec_properties yang ditentukan langsung pada target lebih diutamakan daripada yang diwarisi dari platform eksekusi.