이 페이지에서는 Bazel에서 사용되는 언어인 Starlark(이전 명칭: Skylark)에 관해 간략히 설명합니다. 함수 및 유형의 전체 목록은 Bazel API 참조를 확인하세요.
언어에 관한 자세한 내용은 Starlark의 GitHub 저장소를 참고하세요.
Starlark 구문 및 동작의 신뢰할 수 있는 사양은 Starlark 언어 사양을 참고하세요.
구문
Starlark의 문법은 Python3에서 영감을 받았습니다. 다음은 Starlark에서 유효한 구문입니다.
def fizz_buzz(n):
"""Print Fizz Buzz numbers from 1 to n."""
for i in range(1, n + 1):
s = ""
if i % 3 == 0:
s += "Fizz"
if i % 5 == 0:
s += "Buzz"
print(s if s else i)
fizz_buzz(20)
Starlark의 시맨틱스는 Python과 다를 수 있지만, Starlark에서 오류가 발생하는 경우를 제외하고는 동작 차이는 드뭅니다. 지원되는 Python 유형은 다음과 같습니다.
변경 가능성
Starlark는 불변성을 선호합니다. 변경 가능한 두 가지 데이터 구조인 목록과 사전을 사용할 수 있습니다. 목록에 값을 추가하거나 사전에서 항목을 삭제하는 등 변경 가능한 데이터 구조의 변경사항은 현재 컨텍스트에서 생성된 객체에만 유효합니다. 컨텍스트가 완료되면 값을 변경할 수 없게 됩니다.
Bazel 빌드에서 병렬 실행을 사용하기 때문입니다. 빌드 중에 각 .bzl
파일과 각 BUILD
파일은 자체 실행 컨텍스트를 가져옵니다. 또한 각 규칙은 자체 컨텍스트에서 분석됩니다.
foo.bzl
파일을 예로 들어 살펴보겠습니다.
# `foo.bzl`
var = [] # declare a list
def fct(): # declare a function
var.append(5) # append a value to the list
fct() # execute the fct function
Bazel은 foo.bzl
가 로드될 때 var
를 만듭니다. 따라서 var
는 foo.bzl
의 컨텍스트에 속합니다. fct()
가 실행되면 foo.bzl
의 컨텍스트 내에서 실행됩니다. foo.bzl
평가가 완료되면 환경에 값이 [5]
인 변경 불가능한 항목 var
이 포함됩니다.
다른 bar.bzl
가 foo.bzl
에서 기호를 로드하면 로드된 값은 변경 불가능한 상태로 유지됩니다. 따라서 bar.bzl
의 다음 코드는 잘못되었습니다.
# `bar.bzl`
load(":foo.bzl", "var", "fct") # loads `var`, and `fct` from `./foo.bzl`
var.append(6) # runtime error, the list stored in var is frozen
fct() # runtime error, fct() attempts to modify a frozen list
bzl
파일에 정의된 전역 변수는 변수를 정의한 bzl
파일 외부에서 변경할 수 없습니다. bzl
파일을 사용하는 위의 예와 마찬가지로 규칙에서 반환하는 값은 변경할 수 없습니다.
BUILD 파일과 .bzl 파일의 차이점
BUILD
파일은 규칙을 호출하여 타겟을 등록합니다. .bzl
파일은 상수, 규칙, 매크로, 함수에 관한 정의를 제공합니다.
네이티브 함수 및 네이티브 규칙은 BUILD
파일의 전역 기호입니다. bzl
파일은 native
모듈을 사용하여 이를 로드해야 합니다.
BUILD
파일에는 두 가지 문법적 제한사항이 있습니다. 1) 함수 선언은 불법이고 2) *args
및 **kwargs
인수는 허용되지 않습니다.
Python과의 차이점
전역 변수는 변경할 수 없습니다.
최상위 수준에서는
for
문이 허용되지 않습니다. 대신 함수 내에서 사용하세요.BUILD
파일에서는 리스트 이해를 사용할 수 있습니다.최상위 수준에서는
if
문이 허용되지 않습니다. 하지만if
표현식(first = data[0] if len(data) > 0 else None
)은 사용할 수 있습니다.사전을 반복하는 데 사용되는 확정된 순서입니다.
재귀는 허용되지 않습니다.
Int 유형은 부호 있는 32비트 정수로 제한됩니다. 오버플로가 발생하면 오류가 발생합니다.
반복 중에 컬렉션을 수정하는 것은 오류입니다.
등식 테스트를 제외하고 비교 연산자
<
,<=
,>=
,>
등은 값 유형 전체에 정의되어 있지 않습니다. 요약하면5 < 'foo'
는 오류를 발생시키고5 == "5"
는 false를 반환합니다.튜플에서 후행 쉼표는 튜플이 괄호 사이에 있는 경우에만(
1,
대신(1,)
을 쓸 때) 유효합니다.사전 리터럴에는 중복 키가 있을 수 없습니다. 예를 들어
{"a": 4, "b": 7, "a": 1}
은 오류입니다.문자열은 따옴표로 표현됩니다 (예: repr 호출 시).
문자열은 반복할 수 없습니다.
다음 Python 기능은 지원되지 않습니다.