Data quality checks in CI with Great Expectations
Traditional continuous integration validates code, but it rarely validates the data that code produces. For data engineers, data scientists, and ML engineers, much of the effort goes into cleaning data and keeping pipelines healthy—work that can quietly degrade when a SQL change breaks an assumption downstream.
Great Expectations, an open source project, addresses that gap by letting teams define declarative expectations about their data: value ranges, column presence, uniqueness, or any number of custom rules. These expectations act as unit tests for data. When integrated into a GitHub Actions workflow, a validation failure can surface directly on a pull request—linking to a dashboard that compares each expectation against the observed value.
What gets validated and when
The standard pattern works like this: a pull request modifies a SQL file, which triggers a workflow. The workflow applies the proposed query against a development database, then runs the Great Expectations GitHub Action to validate the results. If validation fails, GitHub Actions posts a comment on the pull request with a link to a data validation dashboard, making the data quality issue visible right where the review happens.
Expectations can be authored in a few ways. Great Expectations can bootstrap a first set of rules automatically by profiling your data, or you can define them manually through its declarative API. Many teams adopt a hybrid approach: let Great Expectations generate the initial rules, then refine them as pipeline behavior becomes clearer.
The tooling connects to a broad range of external data sources, including S3, GCS, Azure Blob Storage, and many databases. Configuration details are covered in the project’s documentation.
Running it in your workflow
To use Great Expectations in CI, add the Great Expectations GitHub Action to your repository. The action is maintained in partnership with the Great Expectations team, and the repository includes setup instructions. If your data lives behind a private network, note that self-hosted runners can be used to run the workflow where the data is reachable.



