drizzle-team / drizzle-team/drizzle-orm
[BUG]: Negative limit not working in SQLite
- Dominant language
- TypeScript
- Stars
- 35.8k
- Forks
- 1.6k
- Avg merge
- 2d 7h
- Merged PRs (30d)
- 4
Description
### What version of `drizzle-orm` are you using?
0.33.0
### What version of `drizzle-kit` are you using?
0.24.2
### Describe the Bug
It should be possible to set a negative limit in SQLite. I think it used to work in drizzle but recently my query stopped working.
I suspect it was [after this PR](https://github.com/drizzle-team/drizzle-orm/pull/2255/files#diff-adcc028702cd08186c718f5b4bd7ba08e9b009c71ce47ee0cf828d90f812c99c).
In SQLite, a negative limit may be used to skip the first `n` results and get all following results.
> If the LIMIT expression evaluates to a negative value, then there is no upper bound on the number of rows returned.
Source: https://www.sqlite.org/draft/lang_select.html#the_limit_clause
SQLite is unique is using negative limits for this purpose. Here is the equivalent functionality in different dialects:
| Dialect | Code |
|----------|----------------------------------------------------------------------------|
| Postgres | `SELECT * FROM mytable ORDER BY mycol ASC OFFSET 1` |
| SQLite | `SELECT * FROM mytable ORDER BY mycol ASC LIMIT -1 OFFSET 1` |
| MySQL | `SELECT * FROM tbl LIMIT 1, 18446744073709551615` |
Source: https://stackoverflow.com/a/70244586
### Expected behavior
Here is my Drizzle Query and Schema:
```ts
export const log = sqliteTable('log', {
id: text('id').primaryKey(),
message: text('message'),
createdAt: integer('created_at')
.default(sql`(cast(unixepoch('subsec') * 1000 as integer))`)
.notNull(),
});
await drizzle
.select({ id: log.id })
.from(log)
.orderBy(desc(log.createdAt))
.limit(-1)
.offset(50)
.all();
```
I expected it to generate SQL like this:
```sql
select
"id"
from
"log"
order by
"log"."created_at" desc
limit
-1
offset
50;
```
What I actual got was this:
```sql
select
"id"
from
"log"
order by
"log"."created_at" desc
offset
50;
```
Note that in SQLite, it is a syntax error to use `offset` without `limit` clause. So SQLite throws a syntax error like this:
```txt
Parse error: near "offset": syntax error
" from "log" order by "log"."created_at" desc offset 50;
error here ---^
```
### Environment & setup
_No response_
Contributor guide
Research direction
Reproduce the SQLite query using `.limit(-1).offset(50)` and compare it with the generated SQL shown in the issue. Trace the SQLite query-generation entry point for limit and offset handling; done means the negative limit is preserved so SQLite receives a valid LIMIT/OFFSET query.
Written by the indexing model from the issue text.
Assessment
- Tech stack
- sqlite, typescript
- Domain
- databases
- Issue type
- Bug
- Difficulty
- 3/5
- Estimated time
- 1-2 days
- Activity status
- Active
- Clarity
- Mostly clear
- Newbie friendliness
- 68/100