|
1 | 1 | import type { BaseStorageOptions, SQLiteDBCore } from './types'
|
2 |
| -import { SQLITE_DETERMINISTIC, SQLITE_DIRECTONLY, SQLITE_UTF8 } from 'wa-sqlite' |
| 2 | +import { SQLITE_DETERMINISTIC, SQLITE_DIRECTONLY, SQLITE_OK, SQLITE_UTF8 } from 'wa-sqlite' |
3 | 3 | import { SQLITE_ROW } from 'wa-sqlite/src/sqlite-constants.js'
|
4 | 4 | import { importDatabase } from './io'
|
5 | 5 |
|
@@ -225,16 +225,37 @@ export async function* iterator(
|
225 | 225 | core: SQLiteDBCore,
|
226 | 226 | sql: string,
|
227 | 227 | parameters?: SQLiteCompatibleType[],
|
228 |
| -): AsyncIterableIterator<Record<string, SQLiteCompatibleType>> { |
| 228 | + chunkSize = 1, |
| 229 | +): AsyncIterableIterator<Record<string, SQLiteCompatibleType>[]> { |
229 | 230 | const { sqlite, pointer } = core
|
| 231 | + // eslint-disable-next-line unicorn/no-new-array |
| 232 | + let cache = new Array(chunkSize) |
230 | 233 | for await (const stmt of sqlite.statements(pointer, sql)) {
|
231 | 234 | if (parameters?.length) {
|
232 | 235 | sqlite.bind_collection(stmt, parameters)
|
233 | 236 | }
|
| 237 | + let idx = 0 |
234 | 238 | const cols = sqlite.column_names(stmt)
|
235 |
| - while (await sqlite.step(stmt) === SQLITE_ROW) { |
236 |
| - const row = sqlite.row(stmt) |
237 |
| - yield Object.fromEntries(cols.map((key, i) => [key, row[i]])) |
| 239 | + while (1) { |
| 240 | + const result = await sqlite.step(stmt) |
| 241 | + if (result === SQLITE_ROW) { |
| 242 | + const row = sqlite.row(stmt) |
| 243 | + cache[idx] = Object.fromEntries(cols.map((key, i) => [key, row[i]])) |
| 244 | + if (++idx === chunkSize) { |
| 245 | + yield cache.slice(0, idx) |
| 246 | + idx = 0 |
| 247 | + } |
| 248 | + } else if (result === SQLITE_OK) { |
| 249 | + if (++idx === chunkSize) { |
| 250 | + yield [] |
| 251 | + } |
| 252 | + } else { |
| 253 | + if (idx > 0) { |
| 254 | + yield cache.slice(0, idx) |
| 255 | + } |
| 256 | + break |
| 257 | + } |
238 | 258 | }
|
239 | 259 | }
|
| 260 | + cache = undefined! |
240 | 261 | }
|
0 commit comments