2N/A#
pragma ident "%Z%%M% %I% %E% SMI" 2N/A** The author disclaims copyright to this source code. In place of 2N/A** a legal notice, here is a blessing: 2N/A** May you do good and not evil. 2N/A** May you find forgiveness for yourself and forgive others. 2N/A** May you share freely, never taking more than you give. 2N/A************************************************************************* 2N/A** A TCL Interface to SQLite 2N/A#
ifndef NO_TCL /* Omit this whole file if TCL is unavailable */ 2N/A** If TCL uses UTF-8 and SQLite is configured to use iso8859, then we 2N/A** have to do a translation when going between the two. Set the 2N/A** UTF_TRANSLATION_NEEDED macro to indicate that we need to do 2N/A** New SQL functions can be created as TCL scripts. Each such function 2N/A** is described by an instance of the following structure. 2N/A** There is one instance of this structure for each SQLite database 2N/A** that has been opened by the SQLite TCL interface. 2N/A char *
zBusy;
/* The busy callback routine */ 2N/A char *
zCommit;
/* The commit hook callback routine */ 2N/A char *
zTrace;
/* The trace callback routine */ 2N/A char *
zAuth;
/* The authorization callback routine */ 2N/A int rc;
/* Return code of most recent sqlite_exec() */ 2N/A** An instance of this structure passes information thru the sqlite 2N/A** logic from the original TCL command into the callback routine. 2N/A char *
zArray;
/* The array into which data is written */ 2N/A int once;
/* Set for first callback only */ 2N/A int tcl_rc;
/* Return code from TCL script */ 2N/A int nColName;
/* Number of entries in the azColName[] array */ 2N/A** Called for each row of the result. 2N/A** This version is used when TCL expects UTF-8 data but the database 2N/A** uses the ISO8859 format. A translation must occur from ISO8859 into 2N/A int nCol,
/* Number of columns in the result */ 2N/A char **
azCol,
/* Data for each column */ 2N/A char **
azN /* Name for each column */ 2N/A#
endif /* UTF_TRANSLATION_NEEDED */ 2N/A** Called for each row of the result. 2N/A** This version is used when either of the following is true: 2N/A** (1) This version of TCL uses UTF-8 and the data in the 2N/A** SQLite database is already in the UTF-8 format. 2N/A** (2) This version of TCL uses ISO8859 and the data in the 2N/A** SQLite database is already in the ISO8859 format. 2N/A int nCol,
/* Number of columns in the result */ 2N/A char **
azCol,
/* Data for each column */ 2N/A char **
azN /* Name for each column */ 2N/A** This is an alternative callback for database queries. Instead 2N/A** of invoking a TCL script to handle the result, this callback just 2N/A** appends each column of the result to a list. After the query 2N/A** is complete, the list is returned. 2N/A int nCol,
/* Number of columns in the result */ 2N/A char **
azCol,
/* Data for each column */ 2N/A char **
azN /* Name for each column */ 2N/A** This is a second alternative callback for database queries. A the 2N/A** first column of the first row of the result is made the TCL result. 2N/A int nCol,
/* Number of columns in the result */ 2N/A char **
azCol,
/* Data for each column */ 2N/A char **
azN /* Name for each column */ 2N/A** Called when the command is deleted. 2N/A** This routine is called when a database file is locked while trying 2N/A** This routine is invoked as the 'progress callback' for the database. 2N/A** This routine is called by the SQLite trace handler whenever a new 2N/A** block of SQL is executed. The TCL script in pDb->zTrace is executed. 2N/A** This routine is called when a transaction is committed. The 2N/A** TCL script in pDb->zCommit is executed. If it returns non-zero or 2N/A** if it throws an exception, the transaction is rolled back instead 2N/A** of being committed. 2N/A** This routine is called to evaluate an SQL function implemented 2N/A** This is the authentication function. It appends the authentication 2N/A** type code and the two arguments to zCmd[] then invokes the result 2N/A** on the interpreter. The reply is examined to determine if the 2N/A** authentication fails or succeeds. 2N/A#
endif /* SQLITE_OMIT_AUTHORIZATION */ 2N/A** The "sqlite" command below creates a new Tcl command for each 2N/A** connection it opens to an SQLite database. This routine is invoked 2N/A** whenever one of those connection-specific commands is executed 2N/A** in Tcl. For example, if you run Tcl code like this: 2N/A** sqlite db1 "my_database" 2N/A** The first command opens a connection to the "my_database" database 2N/A** and calls that connection "db1". The second command causes this 2N/A** subroutine to be invoked. 2N/A "authorizer",
"busy",
"changes",
2N/A "close",
"commit_hook",
"complete",
2N/A "errorcode",
"eval",
"function",
2N/A "last_insert_rowid",
"last_statement_changes",
"onecolumn",
2N/A "progress",
"rekey",
"timeout",
2N/A /* $db authorizer ?CALLBACK? 2N/A ** Invoke the given callback to authorize each SQL operation as it is 2N/A ** compiled. 5 arguments are appended to the callback before it is 2N/A ** (1) The authorization type (ex: SQLITE_CREATE_TABLE, SQLITE_INSERT, ...) 2N/A ** (2) First descriptive name (depends on authorization type) 2N/A ** (3) Second descriptive name 2N/A ** (4) Name of the database (ex: "main", "temp") 2N/A ** (5) Name of trigger that is doing the access 2N/A ** The callback should return on of the following strings: SQLITE_OK, 2N/A ** SQLITE_IGNORE, or SQLITE_DENY. Any other return value is an error. 2N/A ** If this method is invoked with no arguments, the current authorization 2N/A ** callback string is returned. 2N/A /* $db busy ?CALLBACK? 2N/A ** Invoke the given callback if an SQL statement attempts to open 2N/A ** a locked database file. 2N/A /* $db progress ?N CALLBACK? 2N/A ** Invoke the given callback every N virtual machine opcodes while executing 2N/A ** Return the number of rows that were modified, inserted, or deleted by 2N/A ** the most recent "eval". 2N/A ** $db last_statement_changes 2N/A ** Return the number of rows that were modified, inserted, or deleted by 2N/A ** the last statment to complete execution (excluding changes due to 2N/A ** Shutdown the database 2N/A /* $db commit_hook ?CALLBACK? 2N/A ** Invoke the given callback just before committing every SQL transaction. 2N/A ** If the callback throws an exception or returns non-zero, then the 2N/A ** transaction is aborted. If CALLBACK is an empty string, the callback 2N/A ** Return TRUE if SQL is a complete SQL statement. Return FALSE if 2N/A ** additional lines of input are needed. This is similar to the 2N/A ** built-in "info complete" command of Tcl. 2N/A ** Return the numeric error code that was returned by the most recent 2N/A ** call to sqlite_exec(). 2N/A ** $db eval $sql ?array { ...code... }? 2N/A ** The SQL statement in $sql is evaluated. For each row, the values are 2N/A ** placed in elements of the array named "array" and ...code... is executed. 2N/A ** If "array" and "code" are omitted, then no callback is every invoked. 2N/A ** If "array" is an empty string, then the values are placed in variables 2N/A ** that have the same name as the fields extracted by the query. 2N/A ** $db function NAME SCRIPT 2N/A ** Create a new SQL function called NAME. Whenever that function is 2N/A ** called, invoke SCRIPT to evaluate the function. 2N/A ** $db last_insert_rowid 2N/A ** Return an integer which is the ROWID for the most recent insert. 2N/A ** $db onecolumn SQL 2N/A ** Return a single column from a single row of the given SQL query. 2N/A ** Change the encryption key on the currently open database. 2N/A ** $db timeout MILLESECONDS 2N/A ** Delay for the number of milliseconds specified when a file is locked. 2N/A /* $db trace ?CALLBACK? 2N/A ** Make arrangements to invoke the CALLBACK routine for each SQL statement 2N/A ** that is executed. The text of the SQL is appended to CALLBACK before 2N/A }
/* End of the SWITCH statement */ 2N/A** sqlite DBNAME FILENAME ?MODE? ?-key KEY? 2N/A** This is the main Tcl command. When the "sqlite" Tcl command is 2N/A** invoked, this routine runs to process that command. 2N/A** The first argument, DBNAME, is an arbitrary name for a new 2N/A** database connection. This command creates a new command named 2N/A** DBNAME that is used to control that connection. The database 2N/A** connection is deleted when the DBNAME command is deleted. 2N/A** The second argument is the name of the directory that contains 2N/A** the sqlite database that is to be accessed. 2N/A** For testing purposes, we also support the following: 2N/A** Return the encoding used by LIKE and GLOB operators. Choices 2N/A** are UTF-8 and iso8859. 2N/A** Return the version number of the SQLite library. 2N/A** sqlite -tcl-uses-utf 2N/A** Return "1" if compiled with a Tcl uses UTF-8. Return "0" if 2N/A** not. Used by tests to make sure the library was compiled 2N/A "HANDLE FILENAME ?-key CODEC-KEY?" 2N/A "HANDLE FILENAME ?MODE?" 2N/A /* The return value is the value of the sqlite* pointer 2N/A /* If compiled with SQLITE_TEST turned on, then register the "md5sum" 2N/A** Provide a dummy Tcl_InitStubs if we are using this as a static 2N/A** Initialize this module. 2N/A** This Tcl module contains only a single new Tcl command named "sqlite". 2N/A** (Hence there is no namespace. There is no point in using a namespace 2N/A** if the extension only supplies one new name!) The "sqlite" command is 2N/A** used to open a new SQLite database. See the DbMain() routine above 2N/A** for additional information. 2N/A** If compiled using mktclapp, this routine runs to initialize 2N/A/*************************************************************************** 2N/A** The remaining code is only included if the TCLSH macro is defined to 2N/A** be an integer greater than 0 2N/A** If the macro TCLSH is defined and is one, then put in code for the 2N/A** "main" routine that implement a interactive shell into which the user 2N/A** can type TCL commands. 2N/A "while {![eof stdin]} {\n" 2N/A "if {$line!=\"\"} {\n" 2N/A "puts -nonewline \"> \"\n" 2N/A "puts -nonewline \"% \"\n" 2N/A "append line [gets stdin]\n" 2N/A "if {[info complete $line]} {\n" 2N/A "if {[catch {uplevel #0 $line} result]} {\n" 2N/A "puts stderr \"Error: $result\"\n" 2N/A "} elseif {$result!=\"\"} {\n" 2N/A#
endif /* TCLSH==1 */ 2N/A#
endif /* TCL_THREADS */ 2N/A#
endif /* TCLSH==1 */ 2N/A** If the macro TCLSH is set to 2, then implement a space analysis tool. 2N/A#
endif /* TCLSH==2 */