Skip to content
Open
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
52 changes: 50 additions & 2 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -16,11 +16,13 @@ A compatible file can be produced by downloading from the [Authzed Playground].

## Usage

### Single file validation

Add the following to any workflow:

```yaml
steps:
- uses: "actions/checkout@v4"
- uses: "actions/checkout@v6"
- uses: "authzed/action-spicedb-validate@v1"
with:
validationfile: "myschema.zaml"
Expand All @@ -29,7 +31,53 @@ steps:
> **Note:** The `actions/checkout` step is required before running this action.
> Without it, your repository files won't be available and validation will fail with "no such file or directory".

The `validationfile` path should be relative to the repository root.
### Multiple files validation

You can validate multiple files using the `validationfiles` input:

```yaml
steps:
- uses: "actions/checkout@v6"
- uses: "authzed/action-spicedb-validate@v1"
with:
validationfiles: |
schemas/schema1.zaml
schemas/schema2.zaml
```

Comma-separated values are also supported:

```yaml
steps:
- uses: "actions/checkout@v6"
- uses: "authzed/action-spicedb-validate@v1"
with:
validationfiles: "schemas/schema1.zaml, schemas/schema2.zaml"
```

You can also use glob patterns (including recursive `**` patterns):

```yaml
steps:
- uses: "actions/checkout@v6"
- uses: "authzed/action-spicedb-validate@v1"
with:
validationfiles: "schemas/**/*.zaml"
```

### Inputs

| Input | Description | Required |
|-------|-------------|----------|
| `validationfile` | Path to a single validation file | No* |
| `validationfiles` | List of paths to validate (newline or comma separated, supports glob patterns including `**`) | No* |
| `fail-on-warn` | Whether validation warnings should cause the validation to fail | No |

\* At least one of `validationfile` or `validationfiles` must be provided.

The `validationfile`/`validationfiles` paths should be relative to the repository root.

> **Note:** File paths with spaces are supported when using newline-separated literal paths or the single `validationfile` input. Glob patterns in paths with spaces may not expand correctly. Filenames containing literal glob characters (`*`, `?`, `[`) or commas must use the single `validationfile` input.

See [test-schema.zaml] for an example of an input file.

Expand Down
7 changes: 5 additions & 2 deletions action.yml
Original file line number Diff line number Diff line change
Expand Up @@ -4,8 +4,11 @@ description: "Runs the `zed validate` command on the provided schema and test da
author: "authzed"
inputs:
validationfile:
description: "path to the YAML file containing schema, test relationships, assertions and expected relations"
required: true
description: "path to the validation file containing schema, test relationships, assertions and expected relations (for single file validation)"
required: false
validationfiles:
description: "list of paths to validation files (newline or comma separated, supports glob patterns)"
required: false
fail-on-warn:
description: "whether validation warnings should cause the validation to fail"
required: false
Expand Down
72 changes: 69 additions & 3 deletions entrypoint.sh
Original file line number Diff line number Diff line change
@@ -1,6 +1,72 @@
#/bin/bash
ARGS=""
#!/bin/bash
set -e

# Enable recursive globbing for ** patterns (bash 4+)
# Guard for bash 3.x compatibility (e.g., macOS default)
shopt -s nullglob
shopt -s globstar 2>/dev/null || true

ARGS=""
[[ $INPUT_FAIL_ON_WARN == "true" ]] && ARGS+=" --fail-on-warn"

/zed validate $ARGS $INPUT_VALIDATIONFILE
# Collect all files to validate
FILES=()
HAD_INPUT=0

# Handle single file input (backward compatibility)
if [[ -n "$INPUT_VALIDATIONFILE" ]]; then
HAD_INPUT=1
FILES+=("$INPUT_VALIDATIONFILE")
fi

# Handle multiple files input
if [[ -n "$INPUT_VALIDATIONFILES" ]]; then
HAD_INPUT=1
# Replace commas with newlines and process each entry
# Use printf instead of echo to avoid option interpretation
while IFS= read -r entry; do
# Trim leading/trailing whitespace without breaking spaces in paths
entry="${entry#"${entry%%[![:space:]]*}"}"
entry="${entry%"${entry##*[![:space:]]}"}"
[[ -z "$entry" ]] && continue

# Check if entry contains glob pattern characters
if [[ "$entry" == *"*"* || "$entry" == *"?"* || "$entry" == *"["* ]]; then
# Expand glob pattern safely without eval (globstar enabled for ** support)
# Use an array assignment for safe glob expansion
expanded=()
# shellcheck disable=SC2206
expanded=($entry)
for file in "${expanded[@]}"; do
[[ -f "$file" ]] && FILES+=("$file")
done
else
FILES+=("$entry")
fi
done <<< "$(printf '%s\n' "$INPUT_VALIDATIONFILES" | tr ',' '\n')"
fi

# Check if we have any files to validate
if [[ $HAD_INPUT -eq 0 ]]; then
echo "Error: No validation files provided. Set either 'validationfile' or 'validationfiles' input."
exit 1
fi

if [[ ${#FILES[@]} -eq 0 ]]; then
echo "Error: No files matched the provided patterns."
exit 1
fi

# Validate each file
FAILED=0
for file in "${FILES[@]}"; do
echo "Validating $file..."
# ARGS is intentionally unquoted for word splitting (may be empty or --fail-on-warn)
# Use -- to prevent filenames starting with - from being interpreted as options
# shellcheck disable=SC2086
if ! /zed validate $ARGS -- "$file"; then
FAILED=1
fi
done

exit $FAILED
Loading