Args

Báo cáo vấn đề Xem nguồn Nightly · 7.3 · 7.2 · 7.1 · 7.0 · 6.5

Một đối tượng đóng gói dữ liệu cần thiết để xây dựng một phần hoặc toàn bộ một dòng lệnh theo cách tiết kiệm bộ nhớ.

Thường xảy ra trường hợp một hành động yêu cầu một dòng lệnh lớn chứa các giá trị được tích luỹ từ các phần phụ thuộc bắc cầu. Ví dụ: dòng lệnh trình liên kết có thể liệt kê mọi tệp đối tượng mà tất cả thư viện cần được liên kết. Phương pháp hay nhất là lưu trữ dữ liệu bắc cầu như vậy trong depset để chúng có thể được nhiều mục tiêu chia sẻ. Tuy nhiên, nếu tác giả quy tắc phải chuyển đổi các nhóm phần phụ thuộc này thành danh sách chuỗi để tạo một dòng lệnh hành động, thì việc này sẽ làm mất hiệu quả tối ưu hoá việc chia sẻ bộ nhớ này.

Vì lý do này, các hàm xây dựng hành động chấp nhận cả đối tượng Args ngoài chuỗi. Mỗi đối tượng Args đại diện cho một chuỗi và phần tách, với các phép biến đổi tuỳ chọn để thao tác với dữ liệu. Các đối tượng Args không xử lý phần phụ thuộc mà chúng đóng gói cho đến giai đoạn thực thi, khi đến thời điểm tính toán dòng lệnh. Cách này giúp trì hoãn mọi hoạt động sao chép tốn kém cho đến khi giai đoạn phân tích hoàn tất. Hãy xem trang Tối ưu hoá hiệu suất để biết thêm thông tin.

Args được tạo bằng cách gọi ctx.actions.args(). Chúng có thể được truyền dưới dạng tham số arguments của ctx.actions.run() hoặc ctx.actions.run_shell(). Mỗi lần đột biến của một đối tượng Args sẽ thêm các giá trị vào dòng lệnh cuối cùng.

Tính năng map_each hỗ trợ bạn tuỳ chỉnh cách các mục được chuyển đổi thành chuỗi. Nếu bạn không cung cấp hàm map_each, thì lượt chuyển đổi chuẩn sẽ như sau:

  • Các giá trị đã là chuỗi sẽ được giữ nguyên.
  • Các đối tượng File được chuyển thành giá trị File.path.
  • Tất cả các loại khác được chuyển thành chuỗi theo cách không được chỉ định. Vì lý do này, bạn nên tránh truyền các giá trị không phải là chuỗi hoặc loại File vào add(), và nếu truyền các giá trị đó đến add_all() hoặc add_joined() thì bạn nên cung cấp hàm map_each.

Khi sử dụng định dạng chuỗi (các tham số format, format_eachformat_joined của phương thức add*()), mẫu định dạng được diễn giải giống như việc thay thế % trên chuỗi, ngoại trừ việc mẫu phải có đúng một phần giữ chỗ thay thế và phần giữ chỗ đó phải là %s. Bạn có thể thoát phần trăm cố định dưới dạng %%. Định dạng được áp dụng sau khi giá trị được chuyển đổi thành chuỗi theo cách trên.

Mỗi phương thức add*() đều có một biểu mẫu thay thế chấp nhận một tham số vị trí bổ sung là "tên đối số" cần chèn trước phần còn lại của đối số. Đối với add_alladd_joined, chuỗi bổ sung sẽ không được thêm nếu trình tự đó trống. Ví dụ: cùng một cách sử dụng có thể thêm --foo val1 val2 val3 --bar hoặc chỉ --bar vào dòng lệnh, tuỳ thuộc vào việc trình tự đã cho có chứa val1..val3 hay không.

Nếu kích thước của dòng lệnh có thể lớn hơn kích thước tối đa mà hệ thống cho phép, thì các đối số có thể được chuyển sang tệp tham số. Xem use_param_file()set_param_file_format().

Ví dụ: Giả sử chúng ta muốn tạo dòng lệnh:

--foo foo1.txt foo2.txt ... fooN.txt --bar bar1.txt,bar2.txt,...,barM.txt --baz
Chúng ta có thể dùng đối tượng Args sau:
# foo_deps and bar_deps are depsets containing
# File objects for the foo and bar .txt files.
args = ctx.actions.args()
args.add_all("--foo", foo_deps)
args.add_joined("--bar", bar_deps, join_with=",")
args.add("--baz")
ctx.actions.run(
  ...
  arguments = [args],
  ...
)

Hội viên

thêm

Args Args.add(arg_name_or_value, value=unbound, *, format=None)

Thêm một đối số vào dòng lệnh này.

Thông số

Thông số Mô tả
arg_name_or_value bắt buộc
Nếu hai tham số vị trí được truyền, tham số này sẽ được diễn giải là tên đối số. Tên đối số được thêm vào trước giá trị mà không cần xử lý. Nếu chỉ truyền một tham số vị trí, tham số đó sẽ được diễn giải là value (xem bên dưới).
value mặc định là unbound
Đối tượng cần nối. Lượt chuyển đổi đó sẽ được chuyển đổi thành một chuỗi bằng cách sử dụng lượt chuyển đổi chuẩn nêu trên. Vì không có tham số map_each cho hàm này, nên value phải là một chuỗi hoặc File. Bạn phải truyền danh sách, bộ dữ liệu, nhóm phần phụ thuộc hoặc thư mục File đến add_all() hoặc add_joined() thay vì phương thức này.
format string; hoặc None; giá trị mặc định là None
Mẫu chuỗi định dạng, sẽ được áp dụng cho phiên bản chuỗi định dạng của value.

add_all

Args Args.add_all(arg_name_or_values, values=unbound, *, map_each=None, format_each=None, before_each=None, omit_if_empty=True, uniquify=False, expand_directories=True, terminate_with=None, allow_closure=False)

Thêm nhiều đối số vào dòng lệnh này. Các mục được xử lý theo kiểu trì hoãn trong giai đoạn thực thi.

Hầu hết quá trình xử lý diễn ra đối với một danh sách các đối số cần được thêm vào, theo các bước sau:

  1. Mỗi mục trong thư mục File sẽ được thay thế bằng tất cả các File có trong thư mục đó theo quy tắc đệ quy.
  2. Nếu bạn cung cấp map_each, thì giá trị này sẽ được áp dụng cho từng mục và các danh sách chuỗi thu được sẽ được nối với nhau để tạo thành danh sách đối số ban đầu. Nếu không, danh sách đối số ban đầu là kết quả của việc áp dụng lượt chuyển đổi chuẩn cho mỗi mục.
  3. Mỗi đối số trong danh sách được định dạng bằng format_each nếu có.
  4. Nếu uniquify là true, các đối số trùng lặp sẽ bị xoá. Lần xuất hiện đầu tiên là lần xuất hiện còn lại.
  5. Nếu đã cung cấp một chuỗi before_each, thì chuỗi đó sẽ được chèn dưới dạng một đối số mới trước mỗi đối số hiện có trong danh sách. Thao tác này sẽ tăng gấp đôi số lượng đối số cần thêm vào điểm này một cách hiệu quả.
  6. Ngoại trừ trường hợp danh sách trống và omit_if_empty là true (mặc định), tên đối số và terminate_with sẽ được chèn lần lượt làm đối số đầu và đối số cuối, nếu có.
Xin lưu ý rằng chuỗi trống là các đối số hợp lệ và bạn phải tuân thủ tất cả các bước xử lý này.

Thông số

Thông số Mô tả
arg_name_or_values bắt buộc
Nếu hai tham số vị trí được truyền, tham số này sẽ được diễn giải là tên đối số. Tên đối số được thêm vào trước values dưới dạng một đối số riêng biệt mà không cần xử lý. Tên đối số này sẽ không được thêm nếu omit_if_empty là true (mặc định) và không có mục nào khác được thêm vào (như xảy ra nếu values trống hoặc tất cả các mục của nó đều bị lọc). Nếu chỉ truyền một tham số vị trí, thì tham số đó sẽ được hiểu là values (xem bên dưới).
values sequence; hoặc phần phụ thuộc; mặc định là unbound
Danh sách, bộ dữ liệu hoặc tập hợp có các mục sẽ được thêm vào.
map_each callable; hoặc None; mặc định là None
Một hàm chuyển đổi mỗi mục thành không có hoặc có nhiều chuỗi, có thể được xử lý thêm trước khi nối. Nếu thông số này không được cung cấp, thì lượt chuyển đổi chuẩn sẽ được sử dụng.

Hàm này được truyền một hoặc hai đối số vị trí: mục cần chuyển đổi, theo sau là DirectoryExpander không bắt buộc. Đối số thứ hai sẽ chỉ được truyền nếu hàm được cung cấp là do người dùng xác định (không tích hợp sẵn) và khai báo nhiều tham số.

Loại giá trị trả về phụ thuộc vào số lượng đối số cần tạo cho mục:

  • Trong trường hợp thông thường, khi mỗi mục chuyển thành một chuỗi, hàm sẽ trả về chuỗi đó.
  • Nếu mục cần được lọc ra hoàn toàn, hàm phải trả về None.
  • Nếu một mục chuyển thành nhiều chuỗi, hàm sẽ trả về danh sách các chuỗi đó.
Việc trả về một chuỗi hoặc None có tác dụng tương tự như việc trả về một danh sách có độ dài 1 hoặc độ dài 0 tương ứng. Tuy nhiên, cách này hiệu quả và dễ đọc hơn là tránh tạo danh sách khi không cần thiết.

Thông thường, các mục là thư mục sẽ tự động được mở rộng nội dung khi bạn đặt expand_directories=True. Tuy nhiên, thao tác này sẽ không mở rộng các thư mục bên trong những giá trị khác – ví dụ: khi các mục là cấu trúc có thư mục làm trường. Trong trường hợp này, bạn có thể áp dụng đối số DirectoryExpander để lấy các tệp của một thư mục nhất định theo cách thủ công.

Để tránh việc giữ lại ngoài ý muốn các cấu trúc dữ liệu lớn trong giai đoạn phân tích vào giai đoạn thực thi, bạn phải khai báo hàm map_each bằng câu lệnh def cấp cao nhất; theo mặc định thì đó có thể không phải là một hàm đóng hàm lồng nhau.

Cảnh báo: Các câu lệnh print() được thực thi trong lệnh gọi đến map_each sẽ không cho thấy kết quả nào.

format_each string; hoặc None; giá trị mặc định là None
Một mẫu chuỗi định dạng không bắt buộc, áp dụng cho mỗi chuỗi do hàm map_each trả về. Chuỗi định dạng phải có đúng một "%s" phần giữ chỗ.
before_each string; hoặc None; giá trị mặc định là None
Một đối số không bắt buộc cần được thêm vào trước khi thêm mỗi đối số bắt nguồn từ values.
omit_if_empty giá trị mặc định là True
Nếu đúng, nếu không có đối số nào bắt nguồn từ values để được thêm vào, thì tất cả các quá trình xử lý tiếp theo sẽ bị chặn và dòng lệnh sẽ không thay đổi. Nếu giá trị là false, tên đối số và terminate_with (nếu được cung cấp) sẽ vẫn được thêm vào bất kể có đối số khác hay không.
uniquify giá trị mặc định là False
Nếu đúng, các đối số trùng lặp bắt nguồn từ values sẽ bị loại bỏ. Chỉ còn lần xuất hiện đầu tiên của mỗi đối số. Thông thường, tính năng này không cần thiết vì phần phụ thuộc đã bỏ qua các phần trùng lặp, nhưng có thể hữu ích nếu map_each trả về cùng một chuỗi cho nhiều mục.
expand_directories mặc định là True
Nếu đúng, mọi thư mục trong values sẽ được mở rộng thành một danh sách tệp phẳng. Việc này xảy ra trước khi áp dụng map_each.
terminate_with string; hoặc None; giá trị mặc định là None
Đối số không bắt buộc nối sau tất cả các đối số khác. Đối số này sẽ không được thêm nếu omit_if_empty là true (mặc định) và không có mục nào khác được thêm vào (như sẽ xảy ra nếu values trống hoặc tất cả các mục của đối số này đều được lọc).
allow_closure mặc định là False
Nếu là đúng (true), cho phép sử dụng các hàm đóng trong các tham số hàm như map_each. Thông thường, việc này là không cần thiết và có nguy cơ giữ lại các cấu trúc dữ liệu lớn trong giai đoạn phân tích vào giai đoạn thực thi.

add_joined

Args Args.add_joined(arg_name_or_values, values=unbound, *, join_with, map_each=None, format_each=None, format_joined=None, omit_if_empty=True, uniquify=False, expand_directories=True, allow_closure=False)

Thêm một đối số vào dòng lệnh này bằng cách nối nhiều giá trị với nhau bằng một dấu phân cách. Các mục được xử lý từng phần trong giai đoạn thực thi.

Quá trình xử lý tương tự như add_all(), nhưng danh sách các đối số bắt nguồn từ values được kết hợp thành một đối số duy nhất như thể bằng join_with.join(...), sau đó được định dạng bằng mẫu chuỗi format_joined đã cho. Không giống như add_all(), không có tham số before_each hoặc terminate_with vì các tham số này thường không hữu ích khi các mục được kết hợp thành một đối số duy nhất.

Nếu sau khi lọc không có chuỗi nào để nối vào một đối số và nếu omit_if_empty là true (mặc định), thì sẽ không có quá trình xử lý nào được thực hiện. Ngược lại, nếu không có chuỗi nào để kết hợp nhưng omit_if_empty là false, thì chuỗi đã kết hợp sẽ là một chuỗi trống.

Thông số

Thông số Mô tả
arg_name_or_values bắt buộc
Nếu hai tham số vị trí được truyền, tham số này sẽ được diễn giải là tên đối số. Tên đối số được thêm trước values mà không cần xử lý. Đối số này sẽ không được thêm nếu omit_if_empty là true (mặc định) và không có chuỗi nào bắt nguồn từ values để kết hợp với nhau (điều này có thể xảy ra nếu values trống hoặc tất cả các mục của đối số này được lọc). Nếu chỉ truyền một tham số vị trí, thì tham số đó sẽ được hiểu là values (xem bên dưới).
values sequence; hoặc phần phụ thuộc; mặc định là unbound
Danh sách, bộ dữ liệu hoặc tập hợp có các mục sẽ được kết hợp.
join_with bắt buộc
Chuỗi phân tách dùng để kết hợp các chuỗi có được bằng cách áp dụng map_eachformat_each, theo cách tương tự như string.join().
map_each có thể gọi; hoặc None; giá trị mặc định là None
giống như đối với add_all.
format_each string; hoặc None; giá trị mặc định là None
Tương tự như đối với add_all.
format_joined string; hoặc None; giá trị mặc định là None
Một mẫu chuỗi định dạng không bắt buộc được áp dụng cho chuỗi đã kết hợp. Chuỗi định dạng phải có đúng một "%s" phần giữ chỗ.
omit_if_empty giá trị mặc định là True
Nếu là true, nếu không có chuỗi nào để kết hợp với nhau (do values trống hoặc tất cả các mục đã được lọc) thì tất cả các quá trình xử lý tiếp theo sẽ bị chặn và dòng lệnh sẽ không thay đổi. Nếu là false, thì ngay cả khi không có chuỗi nào để kết hợp với nhau, 2 đối số sẽ được thêm vào: tên đối số theo sau là một chuỗi trống (là kết hợp logic của các chuỗi 0).
uniquify mặc định là False
Tương tự như đối với add_all.
expand_directories giá trị mặc định là True
Tương tự như đối với add_all.
allow_closure giá trị mặc định là False
Tương tự như đối với add_all.

set_param_file_format

Args Args.set_param_file_format(format)

Đặt định dạng của tệp thông số, nếu định dạng được sử dụng

Thông số

Thông số Mô tả
format bắt buộc
Phải là một trong các giá trị:
  • "multiline": Mỗi mục (tên đối số hoặc giá trị) được viết nguyên văn vào tệp param kèm theo ký tự dòng mới.
  • "shell": Giống như "multiline", nhưng các mục được trích dẫn shell
  • "flag_per_line": Giống như "multiline", nhưng (1) chỉ các cờ (bắt đầu bằng '--') được ghi vào tệp thông số và (2) giá trị của các cờ, nếu có, được viết trên cùng một dòng với '=' dòng phân cách. Đây là định dạng mà thư viện cờ Abseil dự kiến.

Định dạng mặc định là "shell" nếu không được gọi.

use_param_file

Args Args.use_param_file(param_file_arg, *, use_always=False)

Làm tràn đối số lên tệp thông số, thay thế chúng bằng một con trỏ tới tệp thông số. Sử dụng khi đối số của bạn có thể quá lớn so với giới hạn độ dài lệnh của hệ thống.

Bazel có thể chọn elide ghi tệp tham số vào cây đầu ra trong quá trình thực thi để đảm bảo tính hiệu quả. Nếu bạn đang gỡ lỗi hành động và muốn kiểm tra tệp thông số, hãy truyền --materialize_param_files vào bản dựng.

Thông số

Thông số Mô tả
param_file_arg bắt buộc
Một chuỗi định dạng với một "%s". Nếu đối số bị tràn sang tệp thông số, thì chúng sẽ được thay thế bằng một đối số bao gồm chuỗi này được định dạng bằng đường dẫn của tệp thông số.

Ví dụ: nếu đối số bị tràn sang tệp thông số "params.txt", hãy chỉ định "--file=%s" sẽ khiến dòng lệnh hành động chứa "--file=params.txt".

use_always giá trị mặc định là False
Liệu có luôn tràn đối số vào tệp thông số hay không. Nếu giá trị là false, bazel sẽ quyết định xem có cần chuyển các đối số hay không dựa trên hệ thống và độ dài đối số của bạn.