Learn more about `Postgres check constraints <https://www.postgresql.org/docs/current/ddl-constraints.html>`__.
Using Postgres triggers
-----------------------
If the validation logic is more complex and requires the use of data from other tables
and/or functions, then you can use `Postgres triggers <https://www.postgresql.org/docs/current/sql-createtrigger.html>`__.
**Example:** Validate that an article's ``content`` does not exceed a certain number of words.
Suppose we have the following table:
..code-block:: sql
article (id uuid, title text, content text)
Now, we can head to the ``Data -> SQL`` tab in the console and
create a `Postgres function <https://www.postgresql.org/docs/current/sql-createfunction.html>`__
that checks if an article's content exceeds a certain number of words,
and then add a `Postgres trigger <https://www.postgresql.org/docs/current/sql-createtrigger.html>`__
that will call this function every time before an article is inserted or updated.
..code-block:: plpgsql
CREATE FUNCTION check_content_length()
RETURNS trigger AS $$
DECLARE content_length INTEGER;
BEGIN
-- split article content into words and get count
select array_length(regexp_split_to_array(NEW.content, '\s'),1) INTO content_length;
-- throw an error if article content is too long
IF content_length > 100 THEN
RAISE EXCEPTION 'Content can not have more than 100 words';
END IF;
-- return the article row if no error
RETURN NEW;
END;
$$ LANGUAGE plpgsql;
CREATE TRIGGER check_content_length_trigger
BEFORE INSERT OR UPDATE ON "article"
FOR EACH ROW
EXECUTE PROCEDURE check_content_length();
Now, if we try to insert an article whose content has more than 100 words, we'll receive
the following error:
..graphiql::
:view_only:
:query:
mutation {
insert_article(
objects: {
title: "lorem ipsum"
content: "Lorem ipsum dolor sit amet, consectetur adipiscing elit. Aenean et nisl dolor. Nulla eleifend odio et velit aliquet, sed convallis quam bibendum. Cras consequat elit quis est vehicula, nec dignissim dolor cursus. Phasellus suscipit magna ac turpis pulvinar ultricies. Nulla sed lacus sed metus egestas scelerisque nec sed urna. Fusce lorem velit, efficitur sed luctus in, fringilla ac urna. Maecenas fermentum augue sit amet malesuada imperdiet. Suspendisse mattis dignissim quam, at tempor dui tincidunt sed. Maecenas placerat erat nec erat aliquet rutrum. Mauris congue velit nec ultrices dapibus. Duis aliquam, est ac ultricies viverra, ante augue dignissim massa, quis iaculis ex dui in ex. Curabitur pharetra neque ac nisl fringilla, vel pellentesque orci molestie.",
}
) {
affected_rows
}
}
:response:
{
"errors": [
{
"message": "postgres query error",
"extensions": {
"internal": {
"error": {
"exec_status": "FatalError",
"message": "Content can not have more than 100 words",
For actual examples of data validations with actions, refer to the `actions examples repo <https://github.com/hasura/hasura-actions-examples/tree/master/data-validations>`__.