or run

npx @tessl/cli init
Log in

Version

Tile

Overview

Evals

Files

Files

docs

backup.mdconstants.mddatabase.mdindex.mdstatement.md

statement.mddocs/

0

# Prepared Statements

1

2

Statement preparation and execution with parameter binding. The Statement class extends EventEmitter and provides efficient query execution for repeated operations with different parameters.

3

4

## Capabilities

5

6

### Bind Parameters

7

8

Binds parameters to the prepared statement.

9

10

```javascript { .api }

11

/**

12

* Binds parameters to the prepared statement

13

* @param params - Parameters to bind (array, object, or individual values)

14

* @param callback - Optional callback called when binding completes

15

* @returns Statement instance for chaining

16

*/

17

bind(params?: any, callback?: (err: Error | null) => void): this;

18

19

/**

20

* Binds multiple parameters as separate arguments

21

*/

22

bind(...params: any[]): this;

23

```

24

25

**Usage Examples:**

26

27

```javascript

28

const stmt = db.prepare("INSERT INTO users (name, email, age) VALUES (?, ?, ?)");

29

30

// Bind with array

31

stmt.bind(["Alice", "alice@example.com", 25], (err) => {

32

if (err) console.error('Bind error:', err.message);

33

});

34

35

// Bind with individual parameters

36

stmt.bind("Bob", "bob@example.com", 30);

37

38

// Named parameters (using object)

39

const namedStmt = db.prepare("INSERT INTO users (name, email) VALUES ($name, $email)");

40

namedStmt.bind({

41

$name: "Charlie",

42

$email: "charlie@example.com"

43

});

44

```

45

46

### Reset Statement

47

48

Resets the statement to its initial state.

49

50

```javascript { .api }

51

/**

52

* Resets the statement to its initial state

53

* @param callback - Optional callback called when reset completes

54

* @returns Statement instance for chaining

55

*/

56

reset(callback?: (err: null) => void): this;

57

```

58

59

**Usage Examples:**

60

61

```javascript

62

const stmt = db.prepare("SELECT * FROM users WHERE age > ?");

63

64

// Use statement

65

stmt.bind([18]).get((err, row) => {

66

console.log('First query result:', row);

67

68

// Reset and reuse

69

stmt.reset().bind([25]).get((err, row) => {

70

console.log('Second query result:', row);

71

});

72

});

73

```

74

75

### Finalize Statement

76

77

Finalizes the statement and releases its resources.

78

79

```javascript { .api }

80

/**

81

* Finalizes the statement and releases resources

82

* @param callback - Optional callback called when finalization completes

83

* @returns Database instance that created this statement

84

*/

85

finalize(callback?: (err: Error) => void): Database;

86

```

87

88

**Usage Examples:**

89

90

```javascript

91

const stmt = db.prepare("INSERT INTO logs (message) VALUES (?)");

92

93

// Use statement multiple times

94

stmt.run("Log entry 1");

95

stmt.run("Log entry 2");

96

stmt.run("Log entry 3");

97

98

// Always finalize when done

99

stmt.finalize((err) => {

100

if (err) {

101

console.error('Finalization error:', err.message);

102

} else {

103

console.log('Statement finalized successfully');

104

}

105

});

106

```

107

108

### Execute Statement

109

110

Executes the prepared statement (non-query operations).

111

112

```javascript { .api }

113

/**

114

* Executes the prepared statement

115

* @param params - Optional parameters to bind before execution

116

* @param callback - Optional callback with RunResult context

117

* @returns Statement instance for chaining

118

*/

119

run(params?: any, callback?: (this: RunResult, err: Error | null) => void): this;

120

121

/**

122

* Executes with multiple parameters as separate arguments

123

*/

124

run(...params: any[]): this;

125

```

126

127

**Usage Examples:**

128

129

```javascript

130

const insertStmt = db.prepare("INSERT INTO users (name, email) VALUES (?, ?)");

131

132

// Execute with parameters

133

insertStmt.run(["Alice", "alice@example.com"], function(err) {

134

if (err) {

135

console.error('Insert error:', err.message);

136

} else {

137

console.log(`Inserted user with ID: ${this.lastID}`);

138

console.log(`Changes made: ${this.changes}`);

139

}

140

});

141

142

// Execute with individual parameters

143

insertStmt.run("Bob", "bob@example.com");

144

145

// Chaining operations

146

insertStmt

147

.run("Charlie", "charlie@example.com")

148

.run("David", "david@example.com")

149

.finalize();

150

```

151

152

### Get Single Row

153

154

Retrieves a single row using the prepared statement.

155

156

```javascript { .api }

157

/**

158

* Gets a single row using the prepared statement

159

* @param params - Optional parameters to bind before execution

160

* @param callback - Callback receiving the result row

161

* @returns Statement instance for chaining

162

*/

163

get<T>(params?: any, callback?: (this: RunResult, err: Error | null, row?: T) => void): this;

164

165

/**

166

* Gets with multiple parameters as separate arguments

167

*/

168

get(...params: any[]): this;

169

```

170

171

**Usage Examples:**

172

173

```javascript

174

const selectStmt = db.prepare("SELECT * FROM users WHERE age > ? AND city = ?");

175

176

// Get with array parameters

177

selectStmt.get([25, "New York"], (err, row) => {

178

if (err) {

179

console.error('Query error:', err.message);

180

} else if (row) {

181

console.log(`Found user: ${row.name}, age ${row.age}`);

182

} else {

183

console.log('No user found matching criteria');

184

}

185

});

186

187

// Get with individual parameters

188

selectStmt.get(30, "London", (err, row) => {

189

if (row) {

190

console.log(`User: ${row.name}`);

191

}

192

});

193

194

// With named parameters

195

const namedSelectStmt = db.prepare("SELECT * FROM users WHERE name = $name");

196

namedSelectStmt.get({ $name: "Alice" }, (err, row) => {

197

console.log('Found user:', row);

198

});

199

```

200

201

### Get All Rows

202

203

Retrieves all rows using the prepared statement.

204

205

```javascript { .api }

206

/**

207

* Gets all rows using the prepared statement

208

* @param params - Optional parameters to bind before execution

209

* @param callback - Callback receiving array of result rows

210

* @returns Statement instance for chaining

211

*/

212

all<T>(params?: any, callback?: (this: RunResult, err: Error | null, rows: T[]) => void): this;

213

214

/**

215

* Gets all with multiple parameters as separate arguments

216

*/

217

all(...params: any[]): this;

218

```

219

220

**Usage Examples:**

221

222

```javascript

223

const selectAllStmt = db.prepare("SELECT * FROM users WHERE age BETWEEN ? AND ?");

224

225

// Get all with parameters

226

selectAllStmt.all([18, 65], (err, rows) => {

227

if (err) {

228

console.error('Query error:', err.message);

229

} else {

230

console.log(`Found ${rows.length} users`);

231

rows.forEach(row => {

232

console.log(`- ${row.name}, age ${row.age}`);

233

});

234

}

235

});

236

237

// Reuse with different parameters

238

selectAllStmt.all([25, 35], (err, rows) => {

239

console.log(`Users aged 25-35: ${rows.length}`);

240

});

241

```

242

243

### Iterate Through Rows

244

245

Processes rows one by one using the prepared statement.

246

247

```javascript { .api }

248

/**

249

* Iterates through rows using the prepared statement

250

* @param params - Optional parameters to bind before execution

251

* @param callback - Callback called for each row

252

* @param complete - Optional callback called when iteration completes

253

* @returns Statement instance for chaining

254

*/

255

each<T>(

256

params?: any,

257

callback?: (this: RunResult, err: Error | null, row: T) => void,

258

complete?: (err: Error | null, count: number) => void

259

): this;

260

261

/**

262

* Iterates with multiple parameters as separate arguments

263

*/

264

each(...params: any[]): this;

265

```

266

267

**Usage Examples:**

268

269

```javascript

270

const processStmt = db.prepare("SELECT id, name, email FROM users WHERE active = ?");

271

272

// Process each active user

273

processStmt.each([1], (err, row) => {

274

if (err) {

275

console.error('Row processing error:', err.message);

276

} else {

277

console.log(`Processing user ${row.id}: ${row.name}`);

278

// Perform processing logic here

279

}

280

}, (err, count) => {

281

if (err) {

282

console.error('Iteration error:', err.message);

283

} else {

284

console.log(`Processed ${count} active users`);

285

}

286

});

287

288

// Process with different parameters

289

processStmt.each([0], (err, row) => {

290

console.log(`Inactive user: ${row.name}`);

291

}, (err, count) => {

292

console.log(`Found ${count} inactive users`);

293

});

294

```

295

296

### Map Query Results

297

298

Maps query results to key-value pairs using the prepared statement.

299

300

```javascript { .api }

301

/**

302

* Maps query results to key-value pairs using the prepared statement

303

* @param params - Optional parameters to bind before execution

304

* @param callback - Callback receiving mapped results

305

* @returns Statement instance for chaining

306

*/

307

map<T>(params?: any, callback?: (this: RunResult, err: Error | null, result: {[key: string]: T}) => void): this;

308

309

/**

310

* Maps with multiple parameters as separate arguments

311

*/

312

map(...params: any[]): this;

313

```

314

315

**Usage Examples:**

316

317

```javascript

318

const mapStmt = db.prepare("SELECT id, name FROM users WHERE department = ?");

319

320

// Map users by ID

321

mapStmt.map(["Engineering"], (err, result) => {

322

if (err) {

323

console.error('Map error:', err.message);

324

} else {

325

// result = { "1": "Alice", "2": "Bob", ... }

326

console.log('Engineering users:');

327

Object.entries(result).forEach(([id, name]) => {

328

console.log(`ID ${id}: ${name}`);

329

});

330

}

331

});

332

333

// Map users from different department

334

mapStmt.map(["Marketing"], (err, result) => {

335

console.log(`Marketing has ${Object.keys(result).length} users`);

336

});

337

```

338

339

## Advanced Usage Patterns

340

341

### Transaction-like Operations

342

343

```javascript

344

const stmt = db.prepare("INSERT INTO users (name, email) VALUES (?, ?)");

345

346

db.serialize(() => {

347

db.run("BEGIN TRANSACTION");

348

349

try {

350

stmt.run("User1", "user1@example.com");

351

stmt.run("User2", "user2@example.com");

352

stmt.run("User3", "user3@example.com");

353

354

db.run("COMMIT", (err) => {

355

if (err) {

356

console.error('Commit failed:', err.message);

357

db.run("ROLLBACK");

358

} else {

359

console.log('Transaction completed successfully');

360

}

361

stmt.finalize();

362

});

363

} catch (error) {

364

console.error('Transaction error:', error.message);

365

db.run("ROLLBACK");

366

stmt.finalize();

367

}

368

});

369

```

370

371

### Batch Processing

372

373

```javascript

374

const batchStmt = db.prepare("INSERT INTO logs (timestamp, level, message) VALUES (?, ?, ?)");

375

376

const logEntries = [

377

[Date.now(), "INFO", "Application started"],

378

[Date.now(), "DEBUG", "Configuration loaded"],

379

[Date.now(), "WARNING", "High memory usage detected"],

380

[Date.now(), "ERROR", "Database connection failed"]

381

];

382

383

db.serialize(() => {

384

logEntries.forEach(([timestamp, level, message]) => {

385

batchStmt.run(timestamp, level, message);

386

});

387

388

batchStmt.finalize((err) => {

389

if (err) {

390

console.error('Batch processing failed:', err.message);

391

} else {

392

console.log(`Processed ${logEntries.length} log entries`);

393

}

394

});

395

});

396

```

397

398

### Parameter Binding Patterns

399

400

```javascript

401

// Positional parameters (?)

402

const positionalStmt = db.prepare("SELECT * FROM users WHERE age > ? AND city = ?");

403

positionalStmt.get([25, "New York"], callback);

404

405

// Named parameters ($name, :name, @name)

406

const namedStmt = db.prepare("SELECT * FROM users WHERE name = $name AND email = $email");

407

namedStmt.get({

408

$name: "Alice",

409

$email: "alice@example.com"

410

}, callback);

411

412

// Mixed parameters (not recommended, but supported)

413

const mixedStmt = db.prepare("SELECT * FROM users WHERE id = ? AND name = $name");

414

mixedStmt.bind([123]).bind({ $name: "Bob" }).get(callback);

415

```

416

417

## Statement Lifecycle

418

419

```javascript

420

// 1. Prepare - creates the statement

421

const stmt = db.prepare("INSERT INTO users (name) VALUES (?)");

422

423

// 2. Bind (optional) - can be done separately or with run/get/all/each

424

stmt.bind(["Alice"]);

425

426

// 3. Execute - run the statement (can be done multiple times)

427

stmt.run(); // Uses previously bound parameters

428

stmt.run(["Bob"]); // Binds new parameters and executes

429

430

// 4. Reset (optional) - clears bindings and state

431

stmt.reset();

432

433

// 5. Finalize - must be called to free resources

434

stmt.finalize((err) => {

435

if (err) console.error('Finalization error:', err);

436

});

437

```