Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -120,6 +120,11 @@ public final class CelPolicyCompilerTool implements Callable<Integer> {
description = "Optimize field selection for version skew mitigation")
private boolean optimizeFieldSelection = false;

@Option(
names = {"--simple_variables"},
description = "Enable inline variable definitions (e.g., '- var_name: expr') in the policy")
private boolean simpleVariables = false;

private static final CelOptions CEL_OPTIONS =
CelOptions.current()
.populateMacroCalls(true)
Expand Down Expand Up @@ -195,7 +200,9 @@ public Integer call() {
CelPolicy policy;
try {
CelPolicyParser policyParser =
CelPolicyParserFactory.newYamlParserBuilder().enableSimpleVariables(true).build();
CelPolicyParserFactory.newYamlParserBuilder()
.enableSimpleVariables(simpleVariables)
.build();
String policyYaml = new String(readFileBytes(effectivePolicyPath), UTF_8);
policy = policyParser.parse(policyYaml, effectivePolicyPath);
} catch (Exception e) {
Expand Down
2 changes: 1 addition & 1 deletion policy/src/test/java/dev/cel/policy/tools/BUILD.bazel
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@ compile_cel_policy(
optimize_field_selection = True,
policy = ":test_policy.yaml",
proto_srcs = ["@cel_spec//proto/cel/expr/conformance/proto3:test_all_types_proto"],
simple_variables = True,
)

java_library(
Expand All @@ -28,7 +29,6 @@ java_library(
data = [
":compiled_test_policy.binarypb",
":test_all_types_fds",
":test_policy.yaml",
"//testing/environment:proto3_message_variables",
],
deps = [
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -233,6 +233,39 @@ public void compile_withBaseConfig_success() throws Exception {
assertThat(result).isEqualTo(Optional.of(true));
}

@Test
public void compile_withVariables_success() throws Exception {
String configPath = createFile("config.yaml", "name: test-env\n");
String policyPath =
createFile(
"policy.yaml",
"name: p\n"
+ "rule:\n"
+ " variables:\n"
+ " - name: my_sum\n"
+ " expression: 10 + 20\n"
+ " match:\n"
+ " - condition: variables.my_sum == 30\n"
+ " output: 'true'\n");
File outputFile = tempFolder.newFile("output.binarypb");
CommandLine cmd = new CommandLine(new CelPolicyCompilerTool());

int exitCode =
cmd.execute(
"--policy",
policyPath,
"--config",
configPath,
"--output",
outputFile.getAbsolutePath());

assertThat(exitCode).isEqualTo(0);
CheckedExpr checkedExpr =
CheckedExpr.parseFrom(Files.toByteArray(outputFile), ExtensionRegistry.getEmptyRegistry());
CelAbstractSyntaxTree ast = CelProtoAbstractSyntaxTree.fromCheckedExpr(checkedExpr).getAst();
assertThat(celRuntime.createProgram(ast).eval()).isEqualTo(Optional.of(true));
}

@Test
public void compile_withSimpleVariables_success() throws Exception {
String configPath = createFile("config.yaml", "name: test-env\n");
Expand All @@ -246,26 +279,24 @@ public void compile_withSimpleVariables_success() throws Exception {
+ " match:\n"
+ " - condition: variables.my_sum == 30\n"
+ " output: 'true'\n");

File outputFile = tempFolder.newFile("output.binarypb");

CommandLine cmd = new CommandLine(new CelPolicyCompilerTool());

int exitCode =
cmd.execute(
"--policy",
policyPath,
"--config",
configPath,
"--simple_variables",
"--output",
outputFile.getAbsolutePath());

assertThat(exitCode).isEqualTo(0);

CheckedExpr checkedExpr =
CheckedExpr.parseFrom(Files.toByteArray(outputFile), ExtensionRegistry.getEmptyRegistry());
CelAbstractSyntaxTree ast = CelProtoAbstractSyntaxTree.fromCheckedExpr(checkedExpr).getAst();
Object result = celRuntime.createProgram(ast).eval();
assertThat(result).isEqualTo(Optional.of(true));
assertThat(celRuntime.createProgram(ast).eval()).isEqualTo(Optional.of(true));
}

@Test
Expand Down
4 changes: 3 additions & 1 deletion policy/src/test/java/dev/cel/policy/tools/test_policy.yaml
Original file line number Diff line number Diff line change
@@ -1,7 +1,9 @@
# Copyright 2026 Google LLC
name: "test_policy"
rule:
variables:
- is_valid_int: proto3.single_int32 == 100
match:
- condition: proto3.single_int32 == 100 && has(proto3.single_nested_message)
- condition: variables.is_valid_int && has(proto3.single_nested_message)
output: '"ALLOW"'
- output: '"DENY"'
1 change: 0 additions & 1 deletion policy/tools/BUILD.bazel
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,5 @@ alias(
bzl_library(
name = "compile_cel_policy_bzl",
srcs = ["compile_cel_policy.bzl"],
visibility = ["//visibility:private"],
deps = ["@rules_proto//proto:defs"],
)
12 changes: 11 additions & 1 deletion policy/tools/compile_cel_policy.bzl
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@ def compile_cel_policy(
output_format = "binarypb",
output_version = "canonical",
optimize_field_selection = False,
simple_variables = False,
visibility = None):
"""Compiles a CEL policy into a CheckedExpr binarypb or textpb with optional select optimization.

Expand All @@ -43,7 +44,13 @@ def compile_cel_policy(
output: (optional) str file name for the output checked expression (default derived from label name and format)
output_format: (optional) str either "binarypb", "textpb", or "textproto" (default "binarypb")
output_version: (optional) str either "canonical" or "v1alpha1" (default "canonical")
optimize_field_selection: (optional) bool whether to enable AST select optimization (default False)
optimize_field_selection: (optional) bool whether to enable AST select optimization (default False).
When True, embeds field numbers, wire types, and default values directly into the compiled
`CheckedExpr` AST. This enables version-skew and field-rename resilience (evaluating unknown
fields from raw wire bytes on older clients) and faster field selections, at the cost of a
larger serialized AST payload.
simple_variables: (optional) bool whether to enable inline variable definitions (e.g.,
`- var_name: expr` instead of `- name: var_name` / `expression: expr`) in the policy (default False)
visibility: (optional) visibility to use on the genrule macro (default None)
"""
if output_format not in ("binarypb", "textpb", "textproto"):
Expand Down Expand Up @@ -87,6 +94,9 @@ def compile_cel_policy(
if optimize_field_selection:
args.append("--optimize_field_selection")

if simple_variables:
args.append("--simple_variables")

cmd = (
"$(location //policy/tools:cel_policy_compiler_tool) " +
" ".join(args)
Expand Down
Loading