The ".ar" command deduces whether or not the target file is
a ZIP or SQLAR and does the appropropriate thing. The "-z" option is omitted. The "--append" option is added to open auxiliary databases using apndvfs. FossilOrigin-Name: 430d1a7daa823ae53606b7a158af4e7c16f62ff9b072b90606524e7c3f6131df
This commit is contained in:
parent
a82c95b47d
commit
a5676c4d2d
14
manifest
14
manifest
@ -1,5 +1,5 @@
|
||||
C Allow\sthe\suse\sof\s".ar\s-t"\swithout\sspecifying\san\sarchive\sfile\sor\sthe\s"-z"\noption\swhen\sthe\scommand-line\sshell\sis\sopened\son\sa\sZIP\sarchive.
|
||||
D 2018-01-10T14:00:00.949
|
||||
C The\s".ar"\scommand\sdeduces\swhether\sor\snot\sthe\starget\sfile\sis\na\sZIP\sor\sSQLAR\sand\sdoes\sthe\sappropropriate\sthing.\s\sThe\s"-z"\soption\sis\somitted.\nThe\s"--append"\soption\sis\sadded\sto\sopen\sauxiliary\sdatabases\susing\sapndvfs.
|
||||
D 2018-01-10T15:17:34.832
|
||||
F .fossil-settings/empty-dirs dbb81e8fc0401ac46a1491ab34a7f2c7c0452f2f06b54ebb845d024ca8283ef1
|
||||
F .fossil-settings/ignore-glob 35175cdfcf539b2318cb04a9901442804be81cd677d8b889fcc9149c21f239ea
|
||||
F Makefile.in 12b6daa4bdb03fa87da27cbc205ff88ace645475b5be79414a3038b68ade14cb
|
||||
@ -484,7 +484,7 @@ F src/random.c 80f5d666f23feb3e6665a6ce04c7197212a88384
|
||||
F src/resolve.c bbee7e31d369a18a2f4836644769882e9c5d40ef4a3af911db06410b65cb3730
|
||||
F src/rowset.c 7b7e7e479212e65b723bf40128c7b36dc5afdfac
|
||||
F src/select.c 8b22abe193e4d8243befa2038e4ae2405802fed1c446e5e502d11f652e09ba74
|
||||
F src/shell.c.in aae06c143e7c70cfe616a96af8b5656f3891916beee172c7a40b084dab221b79
|
||||
F src/shell.c.in 7d49ed78c6d8298d38d4733c3cc24f3a4230cd2f151564b7c11ab2e280007f9c
|
||||
F src/sqlite.h.in 1f1a2da222ec57465794e8984d77f32d0bd0da80cdc136beadda461a0be9d80c
|
||||
F src/sqlite3.rc 5121c9e10c3964d5755191c80dd1180c122fc3a8
|
||||
F src/sqlite3ext.h c02d628cca67f3889c689d82d25c3eb45e2c155db08e4c6089b5840d64687d34
|
||||
@ -1225,7 +1225,7 @@ F test/shell4.test 89ad573879a745974ff2df20ff97c5d6ffffbd5d
|
||||
F test/shell5.test 23939a4c51f0421330ea61dbd3c74f9c215f5f8d3d1a94846da6ffc777a35458
|
||||
F test/shell6.test 1ceb51b2678c472ba6cf1e5da96679ce8347889fe2c3bf93a0e0fa73f00b00d3
|
||||
F test/shell7.test 115132f66d0463417f408562cc2cf534f6bbc6d83a6d50f0072a9eb171bae97f
|
||||
F test/shell8.test 5a1f2c6d5cc11e7c7d69e960972f447a9b01e80c419ff9ebaf059f94fe5b3ab9
|
||||
F test/shell8.test c836470ccde867e1f438a7acad7560805cc04f9dbab84cb55d92925942b76247
|
||||
F test/shortread1.test bb591ef20f0fd9ed26d0d12e80eee6d7ac8897a3
|
||||
F test/show_speedtest1_rtree.tcl 32e6c5f073d7426148a6936a0408f4b5b169aba5
|
||||
F test/shrink.test 1b4330b1fd9e818c04726d45cb28db73087535ce
|
||||
@ -1697,7 +1697,7 @@ F vsixtest/vsixtest.tcl 6a9a6ab600c25a91a7acc6293828957a386a8a93
|
||||
F vsixtest/vsixtest.vcxproj.data 2ed517e100c66dc455b492e1a33350c1b20fbcdc
|
||||
F vsixtest/vsixtest.vcxproj.filters 37e51ffedcdb064aad6ff33b6148725226cd608e
|
||||
F vsixtest/vsixtest_TemporaryKey.pfx e5b1b036facdb453873e7084e1cae9102ccc67a0
|
||||
P a2baada429e84dc4b7243173a056e3c8bc042682f7efb01fdf8d2cc452c97e04
|
||||
R 870698cbfc790bad8e7df783afd6e385
|
||||
P 9340a2c145bcb4b38d19276a16264a37341c617f0554d66e1da653f1d9f85163
|
||||
R 9764fa4832552c458077bab9b9143a51
|
||||
U drh
|
||||
Z 6cb4ecc388fb1e11ac7a5d118227df45
|
||||
Z fa68d24d45da969d4d63bf64e8c4f030
|
||||
|
@ -1 +1 @@
|
||||
9340a2c145bcb4b38d19276a16264a37341c617f0554d66e1da653f1d9f85163
|
||||
430d1a7daa823ae53606b7a158af4e7c16f62ff9b072b90606524e7c3f6131df
|
103
src/shell.c.in
103
src/shell.c.in
@ -4505,10 +4505,11 @@ typedef struct ArCommand ArCommand;
|
||||
struct ArCommand {
|
||||
u8 eCmd; /* An AR_CMD_* value */
|
||||
u8 bVerbose; /* True if --verbose */
|
||||
u8 bZip; /* True if --zip */
|
||||
u8 bZip; /* True if the archive is a ZIP */
|
||||
u8 bDryRun; /* True if --dry-run */
|
||||
u8 bAppend; /* True if --append */
|
||||
int nArg; /* Number of command arguments */
|
||||
const char *zSrcTable; /* "sqlar", "zipfile($file)" or "zip" */
|
||||
char *zSrcTable; /* "sqlar", "zipfile($file)" or "zip" */
|
||||
const char *zFile; /* --file argument, or NULL */
|
||||
const char *zDir; /* --directory argument, or NULL */
|
||||
char **azArg; /* Array of command arguments */
|
||||
@ -4541,7 +4542,7 @@ static int arUsage(FILE *f){
|
||||
" -f FILE, --file FILE Operate on archive FILE (default is current db)\n"
|
||||
" -C DIR, --directory DIR Change to directory DIR to read/extract files\n"
|
||||
" -n, --dryrun Show the SQL that would have occurred\n"
|
||||
" -z, --zip Operate on a ZIP archive instead of an SQLAR\n"
|
||||
" -a, --append Append the SQLAR to an existing file\n"
|
||||
"\n"
|
||||
"See also: http://sqlite.org/cli.html#sqlar_archive_support\n"
|
||||
"\n"
|
||||
@ -4579,7 +4580,7 @@ static int arErrorMsg(const char *zFmt, ...){
|
||||
#define AR_SWITCH_VERBOSE 6
|
||||
#define AR_SWITCH_FILE 7
|
||||
#define AR_SWITCH_DIRECTORY 8
|
||||
#define AR_SWITCH_ZIP 9
|
||||
#define AR_SWITCH_APPEND 9
|
||||
#define AR_SWITCH_DRYRUN 10
|
||||
|
||||
static int arProcessSwitch(ArCommand *pAr, int eSwitch, const char *zArg){
|
||||
@ -4601,8 +4602,8 @@ static int arProcessSwitch(ArCommand *pAr, int eSwitch, const char *zArg){
|
||||
case AR_SWITCH_VERBOSE:
|
||||
pAr->bVerbose = 1;
|
||||
break;
|
||||
case AR_SWITCH_ZIP:
|
||||
pAr->bZip = 1;
|
||||
case AR_SWITCH_APPEND:
|
||||
pAr->bAppend = 1;
|
||||
break;
|
||||
|
||||
case AR_SWITCH_FILE:
|
||||
@ -4641,7 +4642,7 @@ static int arParseCommand(
|
||||
{ "verbose", 'v', AR_SWITCH_VERBOSE, 0 },
|
||||
{ "file", 'f', AR_SWITCH_FILE, 1 },
|
||||
{ "directory", 'C', AR_SWITCH_DIRECTORY, 1 },
|
||||
{ "zip", 'z', AR_SWITCH_ZIP, 0 },
|
||||
{ "append", 'a', AR_SWITCH_APPEND, 0 },
|
||||
{ "dryrun", 'n', AR_SWITCH_DRYRUN, 0 },
|
||||
};
|
||||
int nSwitch = sizeof(aSwitch) / sizeof(struct ArSwitch);
|
||||
@ -4779,11 +4780,6 @@ static int arCheckEntries(ArCommand *pAr){
|
||||
"SELECT name FROM %s WHERE name=$name",
|
||||
pAr->zSrcTable
|
||||
);
|
||||
if( rc==SQLITE_OK
|
||||
&& (j = sqlite3_bind_parameter_index(pTest, "$archiveFile"))>0
|
||||
){
|
||||
sqlite3_bind_text(pTest, j, pAr->zFile, -1, SQLITE_TRANSIENT);
|
||||
}
|
||||
j = sqlite3_bind_parameter_index(pTest, "$name");
|
||||
for(i=0; i<pAr->nArg && rc==SQLITE_OK; i++){
|
||||
char *z = pAr->azArg[i];
|
||||
@ -4882,18 +4878,12 @@ static int arListCommand(ArCommand *pAr){
|
||||
char *zWhere = 0;
|
||||
sqlite3_stmt *pSql = 0;
|
||||
int rc;
|
||||
int j;
|
||||
|
||||
rc = arCheckEntries(pAr);
|
||||
arWhereClause(&rc, pAr, &zWhere);
|
||||
|
||||
shellPreparePrintf(pAr->db, &rc, &pSql, zSql, azCols[pAr->bVerbose],
|
||||
pAr->zSrcTable, zWhere);
|
||||
if( rc==SQLITE_OK
|
||||
&& (j = sqlite3_bind_parameter_index(pSql, "$archiveFile"))>0
|
||||
){
|
||||
sqlite3_bind_text(pSql, j, pAr->zFile, -1, SQLITE_TRANSIENT);
|
||||
}
|
||||
if( pAr->bDryRun ){
|
||||
utf8_printf(pAr->p->out, "%s\n", sqlite3_sql(pSql));
|
||||
}else{
|
||||
@ -4960,10 +4950,6 @@ static int arExtractCommand(ArCommand *pAr){
|
||||
if( rc==SQLITE_OK ){
|
||||
j = sqlite3_bind_parameter_index(pSql, "$dir");
|
||||
sqlite3_bind_text(pSql, j, zDir, -1, SQLITE_STATIC);
|
||||
j = sqlite3_bind_parameter_index(pSql, "$archiveFile");
|
||||
if( j ){
|
||||
sqlite3_bind_text(pSql, j, pAr->zFile, -1, SQLITE_STATIC);
|
||||
}
|
||||
|
||||
/* Run the SELECT statement twice. The first time, writefile() is called
|
||||
** for all archive members that should be extracted. The second time,
|
||||
@ -5022,7 +5008,7 @@ static int arCreateOrUpdateCommand(
|
||||
ArCommand *pAr, /* Command arguments and options */
|
||||
int bUpdate /* true for a --create. false for --update */
|
||||
){
|
||||
const char *zSql = "SELECT name, mode, mtime, data FROM fsdir(?, ?)";
|
||||
const char *zSql = "SELECT name, mode, mtime, data FROM fsdir($name, $dir)";
|
||||
const char *zCreate =
|
||||
"CREATE TABLE IF NOT EXISTS sqlar(\n"
|
||||
" name TEXT PRIMARY KEY, -- name of the file\n"
|
||||
@ -5037,6 +5023,7 @@ static int arCreateOrUpdateCommand(
|
||||
sqlite3_stmt *pStmt = 0; /* Directory traverser */
|
||||
sqlite3_stmt *pInsert = 0; /* Compilation of zInsert */
|
||||
int i; /* For iterating through azFile[] */
|
||||
int j; /* Parameter index */
|
||||
int rc; /* Return code */
|
||||
|
||||
assert( pAr->bZip==0 );
|
||||
@ -5050,12 +5037,19 @@ static int arCreateOrUpdateCommand(
|
||||
}
|
||||
|
||||
rc = arExecSql(pAr, zCreate);
|
||||
shellPrepare(pAr->db, &rc, zInsert, &pInsert);
|
||||
if( !pAr->bDryRun ){
|
||||
shellPrepare(pAr->db, &rc, zInsert, &pInsert);
|
||||
}
|
||||
shellPrepare(pAr->db, &rc, zSql, &pStmt);
|
||||
sqlite3_bind_text(pStmt, 2, pAr->zDir, -1, SQLITE_STATIC);
|
||||
j = sqlite3_bind_parameter_index(pStmt, "$dir");
|
||||
sqlite3_bind_text(pStmt, j, pAr->zDir, -1, SQLITE_STATIC);
|
||||
if( pAr->bDryRun ){
|
||||
utf8_printf(pAr->p->out, "%s;\n", sqlite3_sql(pStmt));
|
||||
}
|
||||
|
||||
for(i=0; i<pAr->nArg && rc==SQLITE_OK; i++){
|
||||
sqlite3_bind_text(pStmt, 1, pAr->azArg[i], -1, SQLITE_STATIC);
|
||||
j = sqlite3_bind_parameter_index(pStmt, "$name");
|
||||
sqlite3_bind_text(pStmt, j, pAr->azArg[i], -1, SQLITE_STATIC);
|
||||
while( rc==SQLITE_OK && SQLITE_ROW==sqlite3_step(pStmt) ){
|
||||
int sz;
|
||||
const char *zName = (const char*)sqlite3_column_text(pStmt, 0);
|
||||
@ -5065,6 +5059,10 @@ static int arCreateOrUpdateCommand(
|
||||
if( pAr->bVerbose ){
|
||||
utf8_printf(pAr->p->out, "%s\n", zName);
|
||||
}
|
||||
if( pAr->bDryRun ){
|
||||
utf8_printf(pAr->p->out, "%s;\n", zInsert);
|
||||
continue;
|
||||
}
|
||||
|
||||
sqlite3_bind_text(pInsert, 1, zName, -1, SQLITE_STATIC);
|
||||
sqlite3_bind_int(pInsert, 2, mode);
|
||||
@ -5115,45 +5113,61 @@ static int arDotCommand(
|
||||
int rc;
|
||||
rc = arParseCommand(azArg, nArg, &cmd);
|
||||
if( rc==SQLITE_OK ){
|
||||
int eDbType = SHELL_OPEN_UNSPEC;
|
||||
cmd.p = pState;
|
||||
cmd.db = pState->db;
|
||||
cmd.zSrcTable = "sqlar";
|
||||
if( cmd.bZip || pState->openMode==SHELL_OPEN_ZIPFILE ){
|
||||
if( cmd.zFile==0
|
||||
&& sqlite3_table_column_metadata(cmd.db,0,"zip","name",0,0,0,0,0)==SQLITE_OK
|
||||
){
|
||||
cmd.zSrcTable = "zip";
|
||||
}else if( cmd.zFile!=0 ){
|
||||
cmd.zSrcTable = "zipfile($archiveFile)";
|
||||
cmd.zSrcTable = 0;
|
||||
if( cmd.zFile ){
|
||||
eDbType = deduceDatabaseType(cmd.zFile);
|
||||
}else{
|
||||
eDbType = pState->openMode;
|
||||
}
|
||||
if( eDbType==SHELL_OPEN_ZIPFILE ){
|
||||
if( cmd.zFile==0 ){
|
||||
cmd.zSrcTable = sqlite3_mprintf("zip");
|
||||
}else{
|
||||
utf8_printf(stderr, "no zip archive file specified\n");
|
||||
return SQLITE_ERROR;
|
||||
cmd.zSrcTable = sqlite3_mprintf("zipfile(%Q)", cmd.zFile);
|
||||
}
|
||||
if( cmd.eCmd==AR_CMD_CREATE || cmd.eCmd==AR_CMD_UPDATE ){
|
||||
utf8_printf(stderr, "zip archives are read-only\n");
|
||||
return SQLITE_ERROR;
|
||||
rc = SQLITE_ERROR;
|
||||
goto end_ar_command;
|
||||
}
|
||||
cmd.bZip = 1;
|
||||
}else if( cmd.zFile ){
|
||||
int flags;
|
||||
if( cmd.bAppend ) eDbType = SHELL_OPEN_APPENDVFS;
|
||||
if( cmd.eCmd==AR_CMD_CREATE || cmd.eCmd==AR_CMD_UPDATE ){
|
||||
flags = SQLITE_OPEN_READWRITE|SQLITE_OPEN_CREATE;
|
||||
}else{
|
||||
flags = SQLITE_OPEN_READONLY;
|
||||
}
|
||||
cmd.db = 0;
|
||||
rc = sqlite3_open_v2(cmd.zFile, &cmd.db, flags, 0);
|
||||
if( cmd.bDryRun ){
|
||||
utf8_printf(pState->out, "-- open database '%s'%s\n", cmd.zFile,
|
||||
eDbType==SHELL_OPEN_APPENDVFS ? " using 'apndvfs'" : "");
|
||||
}
|
||||
rc = sqlite3_open_v2(cmd.zFile, &cmd.db, flags,
|
||||
eDbType==SHELL_OPEN_APPENDVFS ? "apndvfs" : 0);
|
||||
if( rc!=SQLITE_OK ){
|
||||
utf8_printf(stderr, "cannot open file: %s (%s)\n",
|
||||
cmd.zFile, sqlite3_errmsg(cmd.db)
|
||||
);
|
||||
sqlite3_close(cmd.db);
|
||||
return rc;
|
||||
goto end_ar_command;
|
||||
}
|
||||
sqlite3_fileio_init(cmd.db, 0, 0);
|
||||
#ifdef SQLITE_HAVE_ZLIB
|
||||
sqlite3_sqlar_init(cmd.db, 0, 0);
|
||||
#endif
|
||||
}
|
||||
if( cmd.zSrcTable==0 ){
|
||||
if( sqlite3_table_column_metadata(cmd.db,0,"sqlar","name",0,0,0,0,0) ){
|
||||
utf8_printf(stderr, "database does not contain an 'sqlar' table\n");
|
||||
rc = SQLITE_ERROR;
|
||||
goto end_ar_command;
|
||||
}
|
||||
cmd.zSrcTable = sqlite3_mprintf("sqlar");
|
||||
}
|
||||
|
||||
switch( cmd.eCmd ){
|
||||
case AR_CMD_CREATE:
|
||||
@ -5177,11 +5191,12 @@ static int arDotCommand(
|
||||
rc = arCreateOrUpdateCommand(&cmd, 1);
|
||||
break;
|
||||
}
|
||||
|
||||
if( cmd.db!=pState->db ){
|
||||
sqlite3_close(cmd.db);
|
||||
}
|
||||
}
|
||||
end_ar_command:
|
||||
if( cmd.db!=pState->db ){
|
||||
sqlite3_close(cmd.db);
|
||||
}
|
||||
sqlite3_free(cmd.zSrcTable);
|
||||
|
||||
return rc;
|
||||
}
|
||||
|
@ -101,7 +101,7 @@ foreach {tn tcl} {
|
||||
set x2 ".ar --extract --dir ar3"
|
||||
|
||||
set c3 ".ar --creat --dir ar1 --file test_xyz.db ."
|
||||
set x3 ".ar --e --d ar3 --f test_xyz.db"
|
||||
set x3 ".ar --e --dir ar3 --f test_xyz.db"
|
||||
}
|
||||
|
||||
4 {
|
||||
@ -169,4 +169,3 @@ finish_test
|
||||
|
||||
|
||||
finish_test
|
||||
|
||||
|
Loading…
x
Reference in New Issue
Block a user