Validating OSCAL Documents
This guide explains how to validate OSCAL documents using the oscal-cli.
OSCAL documents are complex structured data that must conform to precise specifications. Validation catches problems early, before invalid documents cause issues in downstream tools or processes. Common problems validation detects include:
- Syntax errors - Malformed XML, JSON, or YAML that can't be parsed
- Missing required fields - Required elements like UUIDs, titles, or timestamps
- Invalid data formats - UUIDs that aren't valid, dates in wrong formats, etc.
- Structural violations - Elements in wrong locations or with invalid cardinality
- Constraint violations - Business rules beyond basic schema requirements
Integrating validation into your workflow—especially in CI/CD pipelines—ensures that OSCAL artifacts meet quality standards before they're used in production.
The validate command checks OSCAL documents at multiple levels:
- Well-formedness - Valid XML, JSON, or YAML syntax
- Schema compliance - Conformance to the OSCAL model structure
- Constraint validation - Metaschema-defined validation rules that express business logic beyond basic schema requirements
# Validate JSON
oscal-cli validate ssp.json
# Validate XML
oscal-cli validate catalog.xml
# Validate YAML
oscal-cli validate profile.yaml
oscal-cli validate --show-stack-trace ssp.json
Check only that the document is valid XML/JSON/YAML:
oscal-cli validate --as=xml catalog.xml
Include Metaschema constraint validation (experimental):
oscal-cli validate catalog.json
The CLI automatically detects the OSCAL document type from the content. You can validate any type with the same command—the CLI inspects the root element to determine validation rules. The following examples demonstrate validation for each supported document type:
oscal-cli validate /path/to/catalog.json
oscal-cli validate /path/to/profile.json
oscal-cli validate /path/to/mapping.json
oscal-cli validate /path/to/ssp.json
oscal-cli validate /path/to/component-definition.json
oscal-cli validate /path/to/assessment-plan.json
oscal-cli validate /path/to/assessment-results.json
oscal-cli validate /path/to/poam.json
Validate files directly from URLs:
oscal-cli validate https://raw.githubusercontent.com/usnistgov/oscal-content/main/nist.gov/SP800-53/rev5/json/NIST_SP-800-53_rev5_catalog.json
The validator reports issues in a structured format that helps you locate and fix problems. Here's what to expect:
A successful validation produces minimal output:
Validation completed with 0 errors.
When validation fails, each issue is reported with its location and description:
[ERROR] /document/metadata/title: Required field 'title' is missing
Each error message includes three pieces of information:
- Severity level (ERROR, WARNING, INFO)
- JSON Pointer or XPath location
- Description of the issue
The following examples show frequent validation errors and how to fix them. These cover the most common issues you'll encounter when working with OSCAL documents:
[ERROR] /catalog/metadata: Required property 'title' is missing
Fix: Add the required field to your document.
[ERROR] /catalog/uuid: Value 'not-a-uuid' is not a valid UUID
Fix: Use a valid UUID v4 format.
[ERROR] /catalog/metadata/last-modified: Value is not a valid date-time
Fix: Use ISO 8601 format: 2024-01-15T10:30:00Z
[ERROR] /profile/imports/0/href: Referenced resource not found
Fix: Ensure the referenced file exists or URL is accessible.
When managing multiple OSCAL documents, you can validate them in bulk using shell scripting. This is particularly useful for pre-commit checks or CI/CD pipelines:
# Using shell expansion
for f in *.json; do
echo "Validating $f"
oscal-cli validate "$f"
done
# Using find
find . -name "*.json" -exec oscal-cli validate {} \;
If you're using Docker, you can run the CLI without installing Java. Mount your local files into the container to validate them:
# Validate a local file
docker run --rm -v "$(pwd):/data" \
ghcr.io/metaschema-framework/oscal-cli:latest \
validate /data/ssp.json
# Validate multiple files
docker run --rm -v "$(pwd):/data" \
ghcr.io/metaschema-framework/oscal-cli:latest \
sh -c 'for f in /data/*.json; do oscal-cli validate "$f"; done'
Integrating validation into your CI/CD pipeline ensures OSCAL artifacts are checked automatically on every commit or pull request. Here's an example for GitHub Actions:
- name: Validate OSCAL
run: |
for file in $(find . -name "*.json" -path "*/oscal/*"); do
oscal-cli validate "$file"
done
The CLI uses standard exit codes that work well with CI/CD systems—zero means success, non-zero means failure:
| Code | Meaning |
|---|---|
| 0 | Validation passed |
| 1 | Validation failed |
| 2 | Invalid arguments or file not found |
Continue learning about the OSCAL CLI with these related guides:
- Converting Formats - Convert between XML, JSON, YAML
- CLI Reference - Complete command reference

