import { getStr } from "./wasm.ts";import { Status, Types, Values } from "./constants.ts";import SqliteError from "./error.ts";import { RowObjects } from "./row_objects.ts";
export interface ColumnName { name: string; originName: string; tableName: string;}
export class Rows { private _db: any; private _stmt: number; private _done: boolean;
constructor(db: any, stmt: number) { this._db = db; this._stmt = stmt; this._done = false;
if (!this._db) { this._done = true; } }
return(): IteratorResult<any> { if (this._done) { return { done: true, value: undefined }; } this._db._wasm.finalize(this._stmt); this._db._transactions.delete(this); this._done = true; return { done: true, value: undefined }; }
done() { this.return(); }
next(): IteratorResult<any[]> { if (this._done) return { value: undefined, done: true }; const row = this._get(); const status = this._db._wasm.step(this._stmt); switch (status) { case Status.SqliteRow: break; case Status.SqliteDone: this.return(); break; default: this.return(); throw this._db._error(status); break; } return { value: row, done: false }; }
columns(): ColumnName[] { if (this._done) { throw new SqliteError( "Unable to retrieve column names as transaction is finalized.", ); }
const columnCount = this._db._wasm.column_count(this._stmt); const columns: ColumnName[] = []; for (let i = 0; i < columnCount; i++) { const name = getStr( this._db._wasm, this._db._wasm.column_name(this._stmt, i), ); const originName = getStr( this._db._wasm, this._db._wasm.column_origin_name(this._stmt, i), ); const tableName = getStr( this._db._wasm, this._db._wasm.column_table_name(this._stmt, i), ); columns.push({ name, originName, tableName }); } return columns; }
asObjects<T extends any = Record<string, any>>(): RowObjects<T> { return new RowObjects<T>(this); }
[Symbol.iterator]() { return this; }
private _get(): any[] { const row = []; for ( let i = 0, c = this._db._wasm.column_count(this._stmt); i < c; i++ ) { switch (this._db._wasm.column_type(this._stmt, i)) { case Types.Integer: row.push(this._db._wasm.column_int(this._stmt, i)); break; case Types.Float: row.push(this._db._wasm.column_double(this._stmt, i)); break; case Types.Text: row.push( getStr( this._db._wasm, this._db._wasm.column_text(this._stmt, i), ), ); break; case Types.Blob: { const ptr = this._db._wasm.column_blob(this._stmt, i); if (ptr === 0) { row.push(null); } else { const length = this._db._wasm.column_bytes(this._stmt, i); row.push( new Uint8Array(this._db._wasm.memory.buffer, ptr, length).slice(), ); } break; } case Types.BigInteger: { const ptr = this._db._wasm.column_text(this._stmt, i); row.push(BigInt(getStr(this._db._wasm, ptr))); break; } default: row.push(null); break; } } return row; }}
export const Empty = new Rows(null, Values.Null);