]> git.ipfire.org Git - thirdparty/sqlite.git/commitdiff
More doc tweaks, one teensy enhancement, and a new feature bug fix
authorlarrybr <larrybr@noemail.net>
Fri, 16 Jun 2023 02:18:59 +0000 (02:18 +0000)
committerlarrybr <larrybr@noemail.net>
Fri, 16 Jun 2023 02:18:59 +0000 (02:18 +0000)
FossilOrigin-Name: 1073ef0629921dbb74719045a742d68d2bb4e28fc5fa6463e725ddd1d9e6e651

doc/extensible_shell.md
doc/tcl_extension_intro.md
ext/misc/tclshext.c.in
manifest
manifest.uuid
src/shell.c.in

index 2547d1201366aecc5fed1d7888f75432123d98e2..c75d710911bc8640c73244528fec158f522be5f6 100644 (file)
@@ -32,14 +32,16 @@ subcommands will store or retrieve all or named parameters into/from a file.
 
 **.shxopts** either shows or alters extended shell features. Presently,
 this allows shell input parsing to be enhanced as described below or to be
-reverted to the traditional rule where dot-commands always occupy one line.
+reverted to the traditional rule where dot-commands always occupy one line
+and neither dot-commands nor #-prefixed comments may have leading whitespace.
 
 **.tables** has new options to show only tables, views, or system tables.
 
 **.vars** is used to create or modify "shell" variables. These are
 key/value pairs which are associated with the shell session rather than
 a specific database such as .databases would list. These variables may
-be the subject of "edit", "set", "save" and "load" subcommands.
+be the subject of "edit", "set", "save" and "load" subcommands with
+effect similar to what they do with the .parameter dot-command.
 
 **.x** is a general purpose, "run these" command. By default, its arguments
 are treated as shell variable names, values of which are interpreted as
@@ -52,10 +54,20 @@ Other new shell features are:
 By default, when invoked as "sqlite3x", or after ".shxopts +parsing" is run,
 the shell effects enhanced command parsing whereby quoted dot-command arguments
 may span multiple lines or dot-command input lines may be spliced together
-with trailing backslash.
+with trailing backslash, and all shell input may have leading whitespace.
 
 When not invoked as "sqlite3x", or after ".shxopts -parsing" is run, any
 dot-command arguments and the dot-command itself end at the first newline.
+Also, input lines with leading whitespace will not be accepted as dot-commands
+or #-prefixed comments.
 This might be needed to run legacy shell scripts having some dot-command(s)
 with a final argument that has an initial quote but no closing quote or
 which happen to end with backslash.
+
+The shell's handling of certain fatal conditions has been changed to make
+it more suitable being embedded into other applications. It no longer calls
+exit() for OOM conditions or -safe mode violations. This feature has not
+yet been fully tested; work remains to be sure that the shell can be called,
+then return to its caller, repeatedly without leaking resources or leaving
+the console in an odd state. But the infrastructure is in place to make
+that all work with only minor (or possibly no) revisions.
index 8d6e0a95aa6c6ca7c5c5a54b636573390b0534eb..15962188136cd00634498f741e47345218451b19 100644 (file)
@@ -57,7 +57,10 @@ On Windows systems, using MSVC, with suitable environment setup,
 it may be built by running "nmake -f Makefile.msc sqlite3x.exe".
 
 The Tcl extension for sqlite3x, called "tclshext" here,
-may be built for Unix-like systems,
+may be built from the top directory of a SQLite project checkout.
+(See [Obtaining Code ...](https://sqlite.org/getthecode.html#obtaining_code_directly_from_the_version_control_system).)
+
+Build the extension for Unix-like systems,
 after configure is run with a "--enable-tcl" option
 (and a "--with-tcl=..." option if necessary),
 by invoking make with "tcl_shell_extension" as a target.
@@ -67,7 +70,7 @@ appropriately, it may be built by running
 
 It may be necessary to first install the Tcl development package or library
 in order for configure to find the Tcl interpreter
-and specify how get it as a library to be linked into the extension.
+and specify how to locate it as a library to be linked with the extension.
 
 To manually get a Tcl-extended-shell started,
 (assuming the above-mentioned images were built and have
@@ -79,12 +82,12 @@ either of these inputs is needed:<br>
     .shxload tclshext
  or
   At shell invocation:
-    sqlite3x -cmd '.shxload tclshext'
+    sqlite3x -cmd ".shxload tclshext"
 ```
 [^loader]: A directory path may need to be prepended to the extension's
   name for the OS loader to find it unless it is in one of the locations
   designated to the loader as a candidate for dynamic libraries. How such
-  designation is made is beyond the scope of this introduction.)
+  designation is made is beyond the scope of this introduction.
 
 Provided this results in another prompt without any error message(s),
 the Tcl-extended shell is ready to go.
@@ -92,9 +95,12 @@ For brevity, the shell in this state will be called "sqlite3xt".
 
 ## Yet Another Prompt -- Now What? ##
 
-When sqlite3xt is ready, it acts very much like the sqlite3 shell.
+When sqlite3xt is ready for input, it acts very much like the sqlite3 shell.
+(^ The sqlite3x shell passes a test suite which is substantially
+identical to that used for the traditional shell, differing only
+in the content and format of error messages.)
 When given sensible inputs (as discussed below in "Parsing"),
-that are recognized by sqlite3,
+that are recognized by and valid for the sqlite3 shell,
 the same outputs and effects will occur as would with sqlite3.
 This condition,
 where SQL and dot commands recognized by sqlite3 may be input
@@ -106,9 +112,10 @@ For sqlite3xt, that is just the beginning.
 
 The effect of loading tclshext can be briefly summarized as
 the introduction of an alternative "execution environment",
+together with a way of entering and leaving it,
 explication of which follows this on the primary "execution environment":
 
-### shell execution environment ###
+### Shell execution environment ###
 
 The "shell execution environment", in effect upon sqlite3xt startup,
 has these characteristics pertinent here:
@@ -126,9 +133,10 @@ then submitted to the SQL execution (prepare/step) engine.
 
 * Whitespace-delimited arguments after the leading token
 are parsed according to the section on "Dot-command arguments"
-[here](https://sqlite.org/cli.html), with one exception as noted next.
+[here](https://sqlite.org/cli.html#rules_for_dot_commands_sql_and_more),
+with exceptions as noted next.
 
-The exception to legacy argument parsing is that open quote
+The main exception to legacy argument parsing is that open quote
 constructs are not auto-closed by the end of an input line.
 (This legacy behavior may be reinstated if desired by: entering
 ".shxopts -parsing" at the prompt; renaming the sqlite3x image
@@ -138,18 +146,19 @@ Instead, arguments are collected, potentially across multiple lines,
 until an input line ends outside of any open quote construct.
 (Input which does not depend on the legacy, auto-close-on-newline
 behavior is what the term "sensible inputs" means as used above.)
-As examples, this would not be sensible input to sqlite3:<br>
+For example, this would not be sensible input to sqlite3:<br>
 ```
    .print 'Hello.
    This was entered as multi-line input.'
 ```
-as it would result in an error, while this input:<br>
+as it would result in an error, (malformed SQL), while this input:<br>
 ```
-   .print "I'm not fond of closing my quotations.
+   .print &quot;I'm not fond of closing my quotations.
 ```
-is acceptable to sqlite3, but deemed not "sensible" here.
+is acceptable to sqlite3, but deemed "not sensible" here.
 When either is input to sqlite3x, a continuation prompt will be issued
-(in interactive mode.)
+(in interactive mode) and the rest of the multi-line input
+will be taken as part of the .print dot-command.
 
 Of course, this is (mostly) review to those familiar with the sqlite3 shell.
 
@@ -164,13 +173,15 @@ In this alternative execution environment, these critical differences exist:
 * An expanded set of command words is available and readily expanded further.
 
 * The available command words generally do not begin with '.'.
+(^In the Tcl execution environment, enter
+"info&nbsp;commands" to see the available command words.)
 
 * When in interactive mode, commands whose
 initial token is not defined as a Tcl command,
-but can be found as an executable
-in directories named in the PATH environment variable,
+but which can be found as an executable
+in a directory named in the PATH environment variable,
 will be executed in a sub-process
-(unless blocked by auto_noexec having been set.)
+(unless blocked by Tcl global variable auto_noexec having been set.)
 
 * The command word and arguments are collected,
 parsed and expanded according to the usual
@@ -184,23 +195,23 @@ and [variables can be set](https://www.tcl.tk/man/tcl8.6/TclCmd/set.html),
 either of which may affect argument expansion
 per the usual Tcl rules.
 
-This environment will be quite familiar to those who use Tcl.
+This environment will be familiar to those who use Tcl.
 There are a few differences however. These are:<br>
 
 * A single '.' on an input line which is not inside of an incomplete
 Tcl line group is treated as a (momentary) end-of-input by the REPL.
-(^ "REPL" is short for "Read, Evaluate, Print Loop.)
+(^ "REPL" is an acronym for "Read, Evaluate, Print Loop".)
 
 * The shell's dot commands, while not visible via \[info commands\],
 are discoverable by the "unknown" command and will be executed
 if their names (with the '.' prefix) would be found and resolved
 unambiguously in the shell execution environment.
-Commands whose names begin with '.' which are not found uniquely in the
+Commands whose names begin with '.' which are not found as unique in the
 shell execution environment produce an "invalid command name" error.
 Except for that treatment, the unknown command in effect
 acts like the standard Tcl version.
-(footnote: That version remains available as _original_unkown,
-to which non-dot commands are delegated .)
+(That standard version remains available as _original_unkown,
+to which handling of non-dot-prefixed commands is delegated.)
 
 * A few non-standard-Tcl commands are available. In particular:
 
@@ -231,7 +242,9 @@ evident below. With no arguments,
 it does nothing, quietly and successfully, with the empty result.
 
 * The present implementation does not run the event loop processing
-that Tcl often uses for certain functionality (such as sockets.)
+that the standard Tcl REPL uses to support certain functionality
+(such as sockets, asynchronous I/O and the Tk GUI subsystem.)
+A future enhancement is to support use of event loop and Tk.
 
 ## Switching Execution Environments ##
 
@@ -278,9 +291,8 @@ becomes part of the shell's repertoire.
 When entered without any argument(s)
 from the shell execution environment,
 the .tcl command has the same effect as .. by itself.
-(footnote:
-When run from the Tcl execution environment with no arguments,
-it acts as a no-op rather than entering a recursive REPL.)
+(^When run from the Tcl execution environment with no arguments,
+.tcl acts as a no-op rather than entering a recursive REPL.)
 With arguments, it will read file content into the Tcl interpreter
 just as Tcl's source command would.
 This may be useful for getting the Tcl execution environment
@@ -314,9 +326,8 @@ the shell execution environment remains in effect afterward.
 
 This temporary use of the Tcl interpreter serves two purposes.
 One is to exploit the more powerful capabilities of Tcl for argument processing.
-Within the text of arguments as provided, 
-variables can be accessed,
-computations can be done,
+Within the text of arguments as provided,
+variables can be accessed, computations can be done,
 and Tcl commands can be invoked to yield results (or produce side effects),
 all of which can affect what the expanded arguments finally contain.
 The other (miniscule) effect is to avoid the need for extra
@@ -350,11 +361,11 @@ in the namespace(s) searched by the interpreter, it is
 passed to the Tcl command named "unknown".
 In the tclshext-augmented Tcl environment,
 that procedure is implemented by C code which treats
-a purported command with a leading '.' specially, 
+a purported command with a leading '.' specially,
 by attempting to find it in the shell's repertoire of dot commands.
 If found (unambiguously), it is then executed
 and the result (such as it is) returned to the caller.
-(footnote: The sqlite3 dot commands return the empty result on success.)
+(The sqlite3 shell dot-commands return the empty result on success.)
 So, assuming there is a dot command invokable as .dotcmd,
 (which there could be if another extension provided it),
 it can be found and executed from the Tcl execution environment
@@ -409,7 +420,7 @@ execution environment. For example:<br>
 
 It should be noted, for those new to Tcl, that brace-quoting in Tcl
 means "Whatever is between these matching braces is the (single) value."
-It can be used for nearly any content, except for mismatched braces.
+It can be used for nearly any content, excepting explicit mismatched braces.
 
 ## Summary, More to Come ##
 
index 3aa7fd2261c8b4e2138e27acf216076dc9b5f4e6..2a0a2469bd7ff611ce283d5c71ce1af0e8a93802 100644 (file)
@@ -1046,7 +1046,7 @@ static int UserDbObjCmd(void *cd, Tcl_Interp *interp,
   UserDb *pudb = (UserDb*)cd;
   static const char *azDoHere[] = { "close", 0 };
   enum DbDoWhat { DDW_Close };
-  int doWhat;
+  int doWhat = -1;
   int whichDb = -1;
   const char *zMoan;
 
@@ -1057,12 +1057,13 @@ static int UserDbObjCmd(void *cd, Tcl_Interp *interp,
   }
   if( whichDb>0 ) whichDb = pudb->ixuSdb;
   /* Delegate all subcommands except above to the now-visible SqliteDb. */
-  if( objc>=2 && !Tcl_GetIndexFromObj(interp, objv[1], azDoHere,
-                                      "subcommand", 0, &doWhat)){
+  if( objc>=2
+      && TCL_OK==Tcl_GetIndexFromObj(0, objv[1], azDoHere, "", 0, &doWhat)){
     switch( doWhat ){
     case DDW_Close:
-      zMoan = " close is disallowd. It is a wrapped DB.\n";
+      zMoan = " close disallowed. It is a wrapped DB belonging to the shell.";
       goto complain_fail;
+    default: ; /* Fine */
     }
   }
   if( pudb->numSdb==0 || whichDb<0 ){
index 162b29a4327aab1410402d671972870bb62d2055..0781a282d0439ae9985caa064f32748495d3b872 100644 (file)
--- a/manifest
+++ b/manifest
@@ -1,5 +1,5 @@
-C Improve\sand\sadd\sdocs\sfor\sextensible\sshell.
-D 2023-06-13T23:04:34.322
+C More\sdoc\stweaks,\sone\steensy\senhancement,\sand\sa\snew\sfeature\sbug\sfix
+D 2023-06-16T02:18:59.017
 F .fossil-settings/empty-dirs dbb81e8fc0401ac46a1491ab34a7f2c7c0452f2f06b54ebb845d024ca8283ef1
 F .fossil-settings/ignore-glob 35175cdfcf539b2318cb04a9901442804be81cd677d8b889fcc9149c21f239ea
 F LICENSE.md df5091916dbb40e6e9686186587125e1b2ff51f022cc334e886c19a0e9982724
@@ -37,12 +37,12 @@ F configure 697e926af786eb6ddb94ade8aace9f42814902d939ddc6a7bc5f11c3eca7dd51 x
 F configure.ac 510be9293c7efca69c0cc7f427f223b0597f82dda214af7491887db25fa4e237
 F contrib/sqlitecon.tcl 210a913ad63f9f991070821e599d600bd913e0ad
 F doc/F2FS.txt c1d4a0ae9711cfe0e1d8b019d154f1c29e0d3abfe820787ba1e9ed7691160fcd
-F doc/extensible_shell.md 478e40a4b06032eb4bd626bf576a0ff4b3058ffb8da4d3fc9f49a94d3eb0654b
+F doc/extensible_shell.md 3a32ed1d6f9d59d9cd8c94d149a33c448cfdfcff20aaa9031681699f9e82710e
 F doc/json-enhancements.md e356fc834781f1f1aa22ee300027a270b2c960122468499bf347bb123ce1ea4f
 F doc/lemon.html d2862dbef72496e87f7996f37e814b146848190a742c12161d13fd15346051b0
 F doc/pager-invariants.txt 27fed9a70ddad2088750c4a2b493b63853da2710
 F doc/shell_extend.html 61e649726612004ae6efb07507301c120969426c052024dd21550606657ecb9b
-F doc/tcl_extension_intro.md 552277491082f7c286c04b75b5a2d8e1fa675201b28c6c571f7a0a7ed557c2b3
+F doc/tcl_extension_intro.md 4c0505365c6a37dbfb93c66e72e228c517947e9daa9f3040ef4390461cb5740b
 F doc/trusted-schema.md 33625008620e879c7bcfbbfa079587612c434fa094d338b08242288d358c3e8a
 F doc/vdbesort-memory.md 4da2639c14cd24a31e0af694b1a8dd37eaf277aff3867e9a8cc14046bc49df56
 F doc/vfs-shm.txt e101f27ea02a8387ce46a05be2b1a902a021d37a
@@ -319,7 +319,7 @@ F ext/misc/showauth.c 732578f0fe4ce42d577e1c86dc89dd14a006ab52
 F ext/misc/spellfix.c 94df9bbfa514a563c1484f684a2df3d128a2f7209a84ca3ca100c68a0163e29f
 F ext/misc/sqlar.c 53e7d48f68d699a24f1a92e68e71eca8b3a9ff991fe9588c2a05bde103c6e7b7
 F ext/misc/stmt.c bc30d60d55e70d0133f10ac6103fe9336543f673740b73946f98758a2bb16dd7
-F ext/misc/tclshext.c.in 1a49bd7d9e2e06f7ed5f409dab829724b9e91a5c766275313fc142e30d441012
+F ext/misc/tclshext.c.in 066f3b5cb386244167aeb03d7a46b5974b50ac72d17d6546649a66ceb7614613
 F ext/misc/templatevtab.c 8a16a91a5ceaccfcbd6aaaa56d46828806e460dd194965b3f77bf38f14b942c4
 F ext/misc/totype.c fa4aedeb07f66169005dffa8de3b0a2b621779fd44f85c103228a42afa71853b
 F ext/misc/uint.c 053fed3bce2e89583afcd4bf804d75d659879bbcedac74d0fa9ed548839a030b
@@ -644,7 +644,7 @@ F src/resmanage.h eb801fdd1d49ed6c44bb103d6e077a2835d7592cf0c20af6b2f0d8eaeb42b3
 F src/resolve.c c1457b920aeb33ed106bf478fad31b7473a8950a755ea898980c428928f3a514
 F src/rowset.c 8432130e6c344b3401a8874c3cb49fefe6873fec593294de077afea2dce5ec97
 F src/select.c 1ddfe4450101c3d4890ecb2d6b97ab80b78764d5a3e7022b171721df1620c419
-F src/shell.c.in a1cca1616759d744de488f9592a86557b85caf65ff5aa7fe5fb2aa75f14bad75
+F src/shell.c.in 188945e30d1688970ca853c07a4a5bd95657381d01a6b6150e0a9e11fce221c8
 F src/shext_linkage.h 4a686427844d5d2b71f2095cb032280fb262490795f0710487ebbedb3732f1cb
 F src/sqlite.h.in 3076d78836b6dac53b3ab0875fc8fd15bca8077aad4d33c85336e05af6aef8c7
 F src/sqlite3.rc 5121c9e10c3964d5755191c80dd1180c122fc3a8
@@ -2052,8 +2052,8 @@ F vsixtest/vsixtest.tcl 6a9a6ab600c25a91a7acc6293828957a386a8a93
 F vsixtest/vsixtest.vcxproj.data 2ed517e100c66dc455b492e1a33350c1b20fbcdc
 F vsixtest/vsixtest.vcxproj.filters 37e51ffedcdb064aad6ff33b6148725226cd608e
 F vsixtest/vsixtest_TemporaryKey.pfx e5b1b036facdb453873e7084e1cae9102ccc67a0
-P bbbdb864f087e806f8fb73618dd769cba5450252e33e938dac0630dd0abb8d43
-R 63bf2e0465b9d20f01f16674055aac03
+P 1a57af86da17a3da6bb343001c779d4d9d2ff2c1937ded4d6370d6a951c3cda4
+R b6513344e2855361b63c6f2e2dc46ceb
 U larrybr
-Z 69f9a194b6b656a29ffe037db91af732
+Z 29b4d969b0d35ef65e922c1adb2b29af
 # Remove this line to create a well-formed Fossil manifest.
index 2edd6e851a5c2048c3dae68f231920bf79919efb..a5218114e14caecea17383cf1c1ebd840931f7b7 100644 (file)
@@ -1 +1 @@
-1a57af86da17a3da6bb343001c779d4d9d2ff2c1937ded4d6370d6a951c3cda4
\ No newline at end of file
+1073ef0629921dbb74719045a742d68d2bb4e28fc5fa6463e725ddd1d9e6e651
\ No newline at end of file
index 93fdcf7e5bb40377a8cf1c1cc9bf7800222eb942..47eea62a4b1aaa2bdeceff0701b7555f334b1308 100644 (file)
@@ -13536,6 +13536,7 @@ DISPATCHABLE_COMMAND( shxload 4 2 0 ){
   }
   if( zFile==0 ) return DCR_Missing;
   if( pzExtArgs==0 ) pzExtArgs = azArg + ai;
+  open_db(p, 0);
   rc = load_shell_extension(p, zFile, zProc, pzErr, nArg-ai, pzExtArgs);
   return DCR_Ok|(rc!=SQLITE_OK);
 }
@@ -13595,6 +13596,14 @@ DISPATCHABLE_COMMAND( shxopts 3 0 0 ){
   return DCR_CmdErred;
 }
 
+static void showWidths(ShellExState *p){
+  int i = 0;
+  while( i < p->numWidths ){
+    raw_printf(ISS(p)->out," %d",p->pSpecWidths[i++]);
+  }
+  raw_printf(ISS(p)->out,"\n");
+}
+
 DISPATCHABLE_COMMAND( show ? 1 1 ){
   static const char *azBool[] = { "off", "on", "trigger", "full"};
   const char *zOut;
@@ -13651,11 +13660,8 @@ DISPATCHABLE_COMMAND( show ? 1 1 ){
   case 3:  zOut = "vmstep";  break;
   }
   utf8_printf(out, "%12.12s: %s\n","stats", zOut);
-  utf8_printf(out, "%12.12s: ", "width");
-  for (i=0;i<p->numWidths;i++) {
-    raw_printf(out, "%d ", p->pSpecWidths[i]);
-  }
-  raw_printf(out, "\n");
+  utf8_printf(out, "%12.12s:", "width");
+  showWidths(p);
   utf8_printf(out, "%12.12s: %s\n", "filename",
               psi->pAuxDb->zDbFilename ? psi->pAuxDb->zDbFilename : "");
   return DCR_Ok;
@@ -14573,10 +14579,11 @@ static void setColumnWidths(ShellExState *p, char *azWidths[], int nWidths){
 }
 COLLECT_HELP_TEXT[
   ".width NUM1 NUM2 ...     Set minimum column widths for columnar output",
-  "   Negative values right-justify",
+  "   Negative values right-justify. A lone ? shows the current values.",
 ];
 DISPATCHABLE_COMMAND( width ? 1 0 ){
-  setColumnWidths(p, azArg+1, nArg-1);
+  if( nArg==2 && cli_strcmp(azArg[1],"?")==0 ) showWidths(p);
+  else setColumnWidths(p, azArg+1, nArg-1);
   return DCR_Ok;
 }