drizzle-team / drizzle-team/drizzle-orm

[BUG]: drizzle-kit pull truncates PostgreSQL NOT VALID check constraints

Open Beginner friendly
#6,214 0 comments 0 reactions 0 assignees View on GitHub
bug drizzle/kit
Dominant language
TypeScript
Stars
35.8k
Forks
1.6k
Avg merge
2d 7h
Merged PRs (30d)
4

Description

### What version of `drizzle-orm` and `drizzle-kit` are you using?

- `drizzle-orm`: `1.0.0-rc.4`
- `drizzle-kit`: `1.0.0-rc.4`

The same parsing logic is still present in the `rc5` branch at commit [`82aba1ae`](https://github.com/drizzle-team/drizzle-orm/commit/82aba1ae44d28c6b1a0bd905439c51ad1af1e550).

### Describe the bug

When PostgreSQL returns a check constraint definition ending in `NOT VALID`, `drizzle-kit pull` removes the final character of the complete definition instead of extracting the check expression.

For example, a definition such as:

```sql
CHECK ((version >= 0)) NOT VALID
```

is emitted in `schema.ts` as:

```ts
check("documents_version_check", sql`(version >= 0)) NOT VALI`)
```

The migration generated by `pull` consequently contains invalid SQL using `NOT VALI`.

### Reproduction

Create a table and add a `NOT VALID` check constraint:

```sql
CREATE TABLE documents (
id integer GENERATED ALWAYS AS IDENTITY PRIMARY KEY,
version integer NOT NULL
);

ALTER TABLE documents
ADD CONSTRAINT documents_version_check
CHECK (version >= 0) NOT VALID;
```

Run `drizzle-kit pull` against the database and inspect the generated `schema.ts` and migration SQL.

### Expected behavior

The generated check expression should be syntactically valid. Ideally Drizzle should preserve the `NOT VALID` state; if that state is not currently modeled, it should at least not become part of a corrupted SQL expression.

```ts
check("documents_version_check", sql`version >= 0`)
```

### Suspected cause

The PostgreSQL introspector currently assumes that every definition is exactly `CHECK (...)` and removes fixed numbers of characters:

https://github.com/drizzle-team/drizzle-orm/blob/82aba1ae44d28c6b1a0bd905439c51ad1af1e550/drizzle-kit/src/dialects/postgres/introspect.ts#L884-L896

```ts
value: check.definition.startsWith("CHECK (")
? check.definition.slice(7, -1)
: check.definition
```

With `CHECK (...) NOT VALID`, `slice(7, -1)` removes only the final `D` from `VALID`.

Issue found and analyzed using AI tools, in this case gpt-5.6-sol max, but manually reviewed and checked by me.

Contributor guide

Open the contributing guide

Research direction

Start in drizzle-kit/src/dialects/postgres/introspect.ts around lines 884-896 and inspect how PostgreSQL check definitions are parsed. Reproduce the issue with the supplied documents_version_check SQL, run drizzle-kit pull, and inspect schema.ts and the generated migration. Done means the check expression remains syntactically valid without truncating the NOT VALID suffix.

Written by the indexing model from the issue text.

Assessment

Tech stack
postgresql, typescript
Domain
databases
Issue type
Bug
Difficulty
2/5
Estimated time
1-3 hours
Activity status
Active
Clarity
Clearly specified
Newbie friendliness
84/100

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.