@@ -361,6 +361,53 @@ added: v22.5.0
361361Compiles a SQL statement into a [ prepared statement] [ ] . This method is a wrapper
362362around [ ` sqlite3_prepare_v2() ` ] [ ] .
363363
364+ ### ` database.createSQLTagStore([maxSize]) `
365+
366+ <!-- YAML
367+ added: REPLACEME
368+ -->
369+
370+ * ` maxSize ` {integer} The maximum number of prepared statements to cache.
371+ ** Default:** ` 1000 ` .
372+ * Returns: {SQLTagStore} A new SQL tag store for caching prepared statements.
373+
374+ Creates a new ` SQLTagStore ` , which is an LRU (Least Recently Used) cache for
375+ storing prepared statements. This allows for the efficient reuse of prepared
376+ statements by tagging them with a unique identifier.
377+
378+ When a tagged SQL literal is executed, the ` SQLTagStore ` checks if a prepared
379+ statement for that specific SQL string already exists in the cache. If it does,
380+ the cached statement is used. If not, a new prepared statement is created,
381+ executed, and then stored in the cache for future use. This mechanism helps to
382+ avoid the overhead of repeatedly parsing and preparing the same SQL statements.
383+
384+ ``` mjs
385+ import { DatabaseSync } from ' node:sqlite' ;
386+
387+ const db = new DatabaseSync (' :memory:' );
388+ const sql = db .createSQLTagStore ();
389+
390+ db .exec (' CREATE TABLE users (id INT, name TEXT)' );
391+
392+ // Using the 'run' method to insert data.
393+ // The tagged literal is used to identify the prepared statement.
394+ sql .run ` INSERT INTO users VALUES (1, 'Alice')` ;
395+ sql .run ` INSERT INTO users VALUES (2, 'Bob')` ;
396+
397+ // Using the 'get' method to retrieve a single row.
398+ const id = 1 ;
399+ const user = sql .get ` SELECT * FROM users WHERE id = ${ id} ` ;
400+ console .log (user); // { id: 1, name: 'Alice' }
401+
402+ // Using the 'all' method to retrieve all rows.
403+ const allUsers = sql .all ` SELECT * FROM users ORDER BY id` ;
404+ console .log (allUsers);
405+ // [
406+ // { id: 1, name: 'Alice' },
407+ // { id: 2, name: 'Bob' }
408+ // ]
409+ ```
410+
364411### ` database.createSession([options]) `
365412
366413<!-- YAML
@@ -504,6 +551,120 @@ times with different bound values. Parameters also offer protection against
504551[ SQL injection] [ ] attacks. For these reasons, prepared statements are preferred
505552over hand-crafted SQL strings when handling user input.
506553
554+ ## Class: ` SQLTagStore `
555+
556+ <!-- YAML
557+ added: REPLACEME
558+ -->
559+
560+ This class represents a single LRU (Least Recently Used) cache for storing
561+ prepared statements.
562+
563+ Instances of this class are created via the database.createSQLTagStore() method,
564+ not by using a constructor. The store caches prepared statements based on the
565+ provided SQL query string. When the same query is seen again, the store
566+ retrieves the cached statement and safely applies the new values through
567+ parameter binding, thereby preventing attacks like SQL injection.
568+
569+ The cache has a maxSize that defaults to 1000 statements, but a custom size can
570+ be provided (e.g., database.createSQLTagStore(100)). All APIs exposed by this
571+ class execute synchronously.
572+
573+ ### ` sqlTagStore.all(sqlTemplate[, ...values]) `
574+
575+ <!-- YAML
576+ added: REPLACEME
577+ -->
578+
579+ * ` sqlTemplate ` {Template Literal} A template literal containing the SQL query.
580+ * ` ...values ` {any} Values to be interpolated into the template literal.
581+ * Returns: {Array} An array of objects representing the rows returned by the query.
582+
583+ Executes the given SQL query and returns all resulting rows as an array of objects.
584+
585+ ### ` sqlTagStore.get(sqlTemplate[, ...values]) `
586+
587+ <!-- YAML
588+ added: REPLACEME
589+ -->
590+
591+ * ` sqlTemplate ` {Template Literal} A template literal containing the SQL query.
592+ * ` ...values ` {any} Values to be interpolated into the template literal.
593+ * Returns: {Object | undefined} An object representing the first row returned by
594+ the query, or ` undefined ` if no rows are returned.
595+
596+ Executes the given SQL query and returns the first resulting row as an object.
597+
598+ ### ` sqlTagStore.iterate(sqlTemplate[, ...values]) `
599+
600+ <!-- YAML
601+ added: REPLACEME
602+ -->
603+
604+ * ` sqlTemplate ` {Template Literal} A template literal containing the SQL query.
605+ * ` ...values ` {any} Values to be interpolated into the template literal.
606+ * Returns: {Iterator} An iterator that yields objects representing the rows returned by the query.
607+
608+ Executes the given SQL query and returns an iterator over the resulting rows.
609+
610+ ### ` sqlTagStore.run(sqlTemplate[, ...values]) `
611+
612+ <!-- YAML
613+ added: REPLACEME
614+ -->
615+
616+ * ` sqlTemplate ` {Template Literal} A template literal containing the SQL query.
617+ * ` ...values ` {any} Values to be interpolated into the template literal.
618+ * Returns: {Object} An object containing information about the execution, including ` changes ` and ` lastInsertRowid ` .
619+
620+ Executes the given SQL query, which is expected to not return any rows (e.g., INSERT, UPDATE, DELETE).
621+
622+ ### ` sqlTagStore.size() `
623+
624+ <!-- YAML
625+ added: REPLACEME
626+ -->
627+
628+ * Returns: {integer} The number of prepared statements currently in the cache.
629+
630+ A read-only property that returns the number of prepared statements currently in the cache.
631+
632+ ### ` sqlTagStore.capacity `
633+
634+ <!-- YAML
635+ added: REPLACEME
636+ -->
637+
638+ * Returns: {integer} The maximum number of prepared statements the cache can hold.
639+
640+ A read-only property that returns the maximum number of prepared statements the cache can hold.
641+
642+ ### ` sqlTagStore.db `
643+
644+ <!-- YAML
645+ added: REPLACEME
646+ -->
647+
648+ * {DatabaseSync} The ` DatabaseSync ` instance that created this ` SQLTagStore ` .
649+
650+ A read-only property that returns the ` DatabaseSync ` object associated with this ` SQLTagStore ` .
651+
652+ ### ` sqlTagStore.reset() `
653+
654+ <!-- YAML
655+ added: REPLACEME
656+ -->
657+
658+ Resets the LRU cache, clearing all stored prepared statements.
659+
660+ ### ` sqlTagStore.clear() `
661+
662+ <!-- YAML
663+ added: REPLACEME
664+ -->
665+
666+ An alias for ` sqlTagStore.reset() ` .
667+
507668### ` statement.all([namedParameters][, ...anonymousParameters]) `
508669
509670<!-- YAML
0 commit comments