Skip to content

Commit

Permalink
Merge pull request rails#43963 from fatkodima/fix-postgres-check-cons…
Browse files Browse the repository at this point in the history
…traint-expression

Correctly parse complex check constraint expressions for PostgreSQL
  • Loading branch information
kamipo authored and CGA1123 committed Jul 31, 2023
1 parent de96c2e commit 39b6157
Show file tree
Hide file tree
Showing 2 changed files with 15 additions and 2 deletions.
Expand Up @@ -523,7 +523,7 @@ def check_constraints(table_name) # :nodoc:
scope = quoted_scope(table_name)

check_info = exec_query(<<-SQL, "SCHEMA")
SELECT conname, pg_get_constraintdef(c.oid) AS constraintdef, c.convalidated AS valid
SELECT conname, pg_get_constraintdef(c.oid, true) AS constraintdef, c.convalidated AS valid
FROM pg_constraint c
JOIN pg_class t ON c.conrelid = t.oid
WHERE c.contype = 'c'
Expand All @@ -535,7 +535,7 @@ def check_constraints(table_name) # :nodoc:
name: row["conname"],
validate: row["valid"]
}
expression = row["constraintdef"][/CHECK \({2}(.+)\){2}/, 1]
expression = row["constraintdef"][/CHECK \((.+)\)/m, 1]

CheckConstraintDefinition.new(table_name, expression, options)
end
Expand Down
13 changes: 13 additions & 0 deletions activerecord/test/cases/migration/check_constraint_test.rb
Expand Up @@ -37,6 +37,19 @@ def test_check_constraints
else
assert_equal "price > discounted_price", constraint.expression
end

if current_adapter?(:PostgreSQLAdapter)
begin
# Test that complex expression is correctly parsed from the database
@connection.add_check_constraint(:trades,
"CASE WHEN price IS NOT NULL THEN true ELSE false END", name: "price_is_required")

constraint = @connection.check_constraints("trades").find { |c| c.name == "price_is_required" }
assert_includes constraint.expression, "WHEN price IS NOT NULL"
ensure
@connection.remove_check_constraint(:trades, name: "price_is_required")
end
end
end

def test_add_check_constraint
Expand Down

0 comments on commit 39b6157

Please sign in to comment.