Fossil SCM

Merge versionable settings and empty-dirs setting from versionable-settings branch

ben 2011-06-02 19:38 ben-testing merge
Commit 30ebed190319313eb4c45ea10b1022387e144603
+3 -3
--- src/add.c
+++ src/add.c
@@ -60,11 +60,11 @@
6060
"manifest.uuid",
6161
};
6262
6363
if( N>=0 && N<count(azName) ) return azName[N];
6464
if( N>=count(azName) && N<count(azName)+count(azManifest)
65
- && db_get_boolean("manifest",0) ){
65
+ && db_get_versionable_setting_boolean("manifest",0) ){
6666
return azManifest[N-count(azName)];
6767
}
6868
return 0;
6969
}
7070
@@ -185,11 +185,11 @@
185185
186186
zIgnoreFlag = find_option("ignore",0,1);
187187
includeDotFiles = find_option("dotfiles",0,0)!=0;
188188
db_must_be_within_tree();
189189
if( zIgnoreFlag==0 ){
190
- zIgnoreFlag = db_get("ignore-glob", 0);
190
+ zIgnoreFlag = db_get_versionable_setting("ignore-glob", 0);
191191
}
192192
vid = db_lget_int("checkout",0);
193193
if( vid==0 ){
194194
fossil_panic("no checkout to add to");
195195
}
@@ -337,11 +337,11 @@
337337
int nDelete = 0;
338338
Glob *pIgnore;
339339
340340
db_must_be_within_tree();
341341
if( zIgnoreFlag==0 ){
342
- zIgnoreFlag = db_get("ignore-glob", 0);
342
+ zIgnoreFlag = db_get_versionable_setting("ignore-glob", 0);
343343
}
344344
vid = db_lget_int("checkout",0);
345345
if( vid==0 ){
346346
fossil_panic("no checkout to add to");
347347
}
348348
--- src/add.c
+++ src/add.c
@@ -60,11 +60,11 @@
60 "manifest.uuid",
61 };
62
63 if( N>=0 && N<count(azName) ) return azName[N];
64 if( N>=count(azName) && N<count(azName)+count(azManifest)
65 && db_get_boolean("manifest",0) ){
66 return azManifest[N-count(azName)];
67 }
68 return 0;
69 }
70
@@ -185,11 +185,11 @@
185
186 zIgnoreFlag = find_option("ignore",0,1);
187 includeDotFiles = find_option("dotfiles",0,0)!=0;
188 db_must_be_within_tree();
189 if( zIgnoreFlag==0 ){
190 zIgnoreFlag = db_get("ignore-glob", 0);
191 }
192 vid = db_lget_int("checkout",0);
193 if( vid==0 ){
194 fossil_panic("no checkout to add to");
195 }
@@ -337,11 +337,11 @@
337 int nDelete = 0;
338 Glob *pIgnore;
339
340 db_must_be_within_tree();
341 if( zIgnoreFlag==0 ){
342 zIgnoreFlag = db_get("ignore-glob", 0);
343 }
344 vid = db_lget_int("checkout",0);
345 if( vid==0 ){
346 fossil_panic("no checkout to add to");
347 }
348
--- src/add.c
+++ src/add.c
@@ -60,11 +60,11 @@
60 "manifest.uuid",
61 };
62
63 if( N>=0 && N<count(azName) ) return azName[N];
64 if( N>=count(azName) && N<count(azName)+count(azManifest)
65 && db_get_versionable_setting_boolean("manifest",0) ){
66 return azManifest[N-count(azName)];
67 }
68 return 0;
69 }
70
@@ -185,11 +185,11 @@
185
186 zIgnoreFlag = find_option("ignore",0,1);
187 includeDotFiles = find_option("dotfiles",0,0)!=0;
188 db_must_be_within_tree();
189 if( zIgnoreFlag==0 ){
190 zIgnoreFlag = db_get_versionable_setting("ignore-glob", 0);
191 }
192 vid = db_lget_int("checkout",0);
193 if( vid==0 ){
194 fossil_panic("no checkout to add to");
195 }
@@ -337,11 +337,11 @@
337 int nDelete = 0;
338 Glob *pIgnore;
339
340 db_must_be_within_tree();
341 if( zIgnoreFlag==0 ){
342 zIgnoreFlag = db_get_versionable_setting("ignore-glob", 0);
343 }
344 vid = db_lget_int("checkout",0);
345 if( vid==0 ){
346 fossil_panic("no checkout to add to");
347 }
348
+5 -5
--- src/checkin.c
+++ src/checkin.c
@@ -224,16 +224,16 @@
224224
int allFlag = find_option("dotfiles",0,0)!=0;
225225
int outputManifest;
226226
Glob *pIgnore;
227227
228228
db_must_be_within_tree();
229
- outputManifest = db_get_boolean("manifest",0);
229
+ outputManifest = db_get_versionable_setting_boolean("manifest",0);
230230
db_multi_exec("CREATE TEMP TABLE sfile(x TEXT PRIMARY KEY)");
231231
n = strlen(g.zLocalRoot);
232232
blob_init(&path, g.zLocalRoot, n-1);
233233
if( zIgnoreFlag==0 ){
234
- zIgnoreFlag = db_get("ignore-glob", 0);
234
+ zIgnoreFlag = db_get_versionable_setting("ignore-glob", 0);
235235
}
236236
pIgnore = glob_create(zIgnoreFlag);
237237
vfile_scan(&path, blob_size(&path), allFlag, pIgnore);
238238
glob_free(pIgnore);
239239
db_prepare(&q,
@@ -283,11 +283,11 @@
283283
allFlag = find_option("force","f",0)!=0;
284284
dotfilesFlag = find_option("dotfiles",0,0)!=0;
285285
zIgnoreFlag = find_option("ignore",0,1);
286286
db_must_be_within_tree();
287287
if( zIgnoreFlag==0 ){
288
- zIgnoreFlag = db_get("ignore-glob", 0);
288
+ zIgnoreFlag = db_get_versionable_setting("ignore-glob", 0);
289289
}
290290
db_multi_exec("CREATE TEMP TABLE sfile(x TEXT PRIMARY KEY)");
291291
n = strlen(g.zLocalRoot);
292292
blob_init(&path, g.zLocalRoot, n-1);
293293
pIgnore = glob_create(zIgnoreFlag);
@@ -831,11 +831,11 @@
831831
zUserOvrd = find_option("user-override",0,1);
832832
db_must_be_within_tree();
833833
noSign = db_get_boolean("omitsign", 0)|noSign;
834834
if( db_get_boolean("clearsign", 0)==0 ){ noSign = 1; }
835835
useCksum = db_get_boolean("repo-cksum", 1);
836
- outputManifest = db_get_boolean("manifest", 0);
836
+ outputManifest = db_get_versionable_setting_boolean("manifest", 0);
837837
verify_all_options();
838838
839839
/* So that older versions of Fossil (that do not understand delta-
840840
** manifest) can continue to use this repository, do not create a new
841841
** delta-manifest unless this repository already contains one or more
@@ -972,11 +972,11 @@
972972
** the identified fils are inserted (if they have been modified).
973973
*/
974974
db_prepare(&q,
975975
"SELECT id, %Q || pathname, mrid, %s FROM vfile "
976976
"WHERE chnged==1 AND NOT deleted AND file_is_selected(id)",
977
- g.zLocalRoot, glob_expr("pathname", db_get("crnl-glob",""))
977
+ g.zLocalRoot, glob_expr("pathname", db_get_versionable_setting("crnl-glob",""))
978978
);
979979
while( db_step(&q)==SQLITE_ROW ){
980980
int id, rid;
981981
const char *zFullname;
982982
Blob content;
983983
--- src/checkin.c
+++ src/checkin.c
@@ -224,16 +224,16 @@
224 int allFlag = find_option("dotfiles",0,0)!=0;
225 int outputManifest;
226 Glob *pIgnore;
227
228 db_must_be_within_tree();
229 outputManifest = db_get_boolean("manifest",0);
230 db_multi_exec("CREATE TEMP TABLE sfile(x TEXT PRIMARY KEY)");
231 n = strlen(g.zLocalRoot);
232 blob_init(&path, g.zLocalRoot, n-1);
233 if( zIgnoreFlag==0 ){
234 zIgnoreFlag = db_get("ignore-glob", 0);
235 }
236 pIgnore = glob_create(zIgnoreFlag);
237 vfile_scan(&path, blob_size(&path), allFlag, pIgnore);
238 glob_free(pIgnore);
239 db_prepare(&q,
@@ -283,11 +283,11 @@
283 allFlag = find_option("force","f",0)!=0;
284 dotfilesFlag = find_option("dotfiles",0,0)!=0;
285 zIgnoreFlag = find_option("ignore",0,1);
286 db_must_be_within_tree();
287 if( zIgnoreFlag==0 ){
288 zIgnoreFlag = db_get("ignore-glob", 0);
289 }
290 db_multi_exec("CREATE TEMP TABLE sfile(x TEXT PRIMARY KEY)");
291 n = strlen(g.zLocalRoot);
292 blob_init(&path, g.zLocalRoot, n-1);
293 pIgnore = glob_create(zIgnoreFlag);
@@ -831,11 +831,11 @@
831 zUserOvrd = find_option("user-override",0,1);
832 db_must_be_within_tree();
833 noSign = db_get_boolean("omitsign", 0)|noSign;
834 if( db_get_boolean("clearsign", 0)==0 ){ noSign = 1; }
835 useCksum = db_get_boolean("repo-cksum", 1);
836 outputManifest = db_get_boolean("manifest", 0);
837 verify_all_options();
838
839 /* So that older versions of Fossil (that do not understand delta-
840 ** manifest) can continue to use this repository, do not create a new
841 ** delta-manifest unless this repository already contains one or more
@@ -972,11 +972,11 @@
972 ** the identified fils are inserted (if they have been modified).
973 */
974 db_prepare(&q,
975 "SELECT id, %Q || pathname, mrid, %s FROM vfile "
976 "WHERE chnged==1 AND NOT deleted AND file_is_selected(id)",
977 g.zLocalRoot, glob_expr("pathname", db_get("crnl-glob",""))
978 );
979 while( db_step(&q)==SQLITE_ROW ){
980 int id, rid;
981 const char *zFullname;
982 Blob content;
983
--- src/checkin.c
+++ src/checkin.c
@@ -224,16 +224,16 @@
224 int allFlag = find_option("dotfiles",0,0)!=0;
225 int outputManifest;
226 Glob *pIgnore;
227
228 db_must_be_within_tree();
229 outputManifest = db_get_versionable_setting_boolean("manifest",0);
230 db_multi_exec("CREATE TEMP TABLE sfile(x TEXT PRIMARY KEY)");
231 n = strlen(g.zLocalRoot);
232 blob_init(&path, g.zLocalRoot, n-1);
233 if( zIgnoreFlag==0 ){
234 zIgnoreFlag = db_get_versionable_setting("ignore-glob", 0);
235 }
236 pIgnore = glob_create(zIgnoreFlag);
237 vfile_scan(&path, blob_size(&path), allFlag, pIgnore);
238 glob_free(pIgnore);
239 db_prepare(&q,
@@ -283,11 +283,11 @@
283 allFlag = find_option("force","f",0)!=0;
284 dotfilesFlag = find_option("dotfiles",0,0)!=0;
285 zIgnoreFlag = find_option("ignore",0,1);
286 db_must_be_within_tree();
287 if( zIgnoreFlag==0 ){
288 zIgnoreFlag = db_get_versionable_setting("ignore-glob", 0);
289 }
290 db_multi_exec("CREATE TEMP TABLE sfile(x TEXT PRIMARY KEY)");
291 n = strlen(g.zLocalRoot);
292 blob_init(&path, g.zLocalRoot, n-1);
293 pIgnore = glob_create(zIgnoreFlag);
@@ -831,11 +831,11 @@
831 zUserOvrd = find_option("user-override",0,1);
832 db_must_be_within_tree();
833 noSign = db_get_boolean("omitsign", 0)|noSign;
834 if( db_get_boolean("clearsign", 0)==0 ){ noSign = 1; }
835 useCksum = db_get_boolean("repo-cksum", 1);
836 outputManifest = db_get_versionable_setting_boolean("manifest", 0);
837 verify_all_options();
838
839 /* So that older versions of Fossil (that do not understand delta-
840 ** manifest) can continue to use this repository, do not create a new
841 ** delta-manifest unless this repository already contains one or more
@@ -972,11 +972,11 @@
972 ** the identified fils are inserted (if they have been modified).
973 */
974 db_prepare(&q,
975 "SELECT id, %Q || pathname, mrid, %s FROM vfile "
976 "WHERE chnged==1 AND NOT deleted AND file_is_selected(id)",
977 g.zLocalRoot, glob_expr("pathname", db_get_versionable_setting("crnl-glob",""))
978 );
979 while( db_step(&q)==SQLITE_ROW ){
980 int id, rid;
981 const char *zFullname;
982 Blob content;
983
+2 -1
--- src/checkout.c
+++ src/checkout.c
@@ -141,11 +141,11 @@
141141
void manifest_to_disk(int vid){
142142
char *zManFile;
143143
Blob manifest;
144144
Blob hash;
145145
146
- if( db_get_boolean("manifest",0) ){
146
+ if( db_get_versionable_setting_boolean("manifest",0) ){
147147
blob_zero(&manifest);
148148
content_get(vid, &manifest);
149149
zManFile = mprintf("%smanifest", g.zLocalRoot);
150150
blob_write_to_file(&manifest, zManFile);
151151
free(zManFile);
@@ -242,10 +242,11 @@
242242
if( !keepFlag ){
243243
vfile_to_disk(vid, 0, 1, promptFlag);
244244
}
245245
checkout_set_all_exe(vid);
246246
manifest_to_disk(vid);
247
+ ensure_empty_dirs_created();
247248
db_lset_int("checkout", vid);
248249
undo_reset();
249250
db_multi_exec("DELETE FROM vmerge");
250251
if( !keepFlag && db_get_boolean("repo-cksum",1) ){
251252
vfile_aggregate_checksum_manifest(vid, &cksum1, &cksum1b);
252253
--- src/checkout.c
+++ src/checkout.c
@@ -141,11 +141,11 @@
141 void manifest_to_disk(int vid){
142 char *zManFile;
143 Blob manifest;
144 Blob hash;
145
146 if( db_get_boolean("manifest",0) ){
147 blob_zero(&manifest);
148 content_get(vid, &manifest);
149 zManFile = mprintf("%smanifest", g.zLocalRoot);
150 blob_write_to_file(&manifest, zManFile);
151 free(zManFile);
@@ -242,10 +242,11 @@
242 if( !keepFlag ){
243 vfile_to_disk(vid, 0, 1, promptFlag);
244 }
245 checkout_set_all_exe(vid);
246 manifest_to_disk(vid);
 
247 db_lset_int("checkout", vid);
248 undo_reset();
249 db_multi_exec("DELETE FROM vmerge");
250 if( !keepFlag && db_get_boolean("repo-cksum",1) ){
251 vfile_aggregate_checksum_manifest(vid, &cksum1, &cksum1b);
252
--- src/checkout.c
+++ src/checkout.c
@@ -141,11 +141,11 @@
141 void manifest_to_disk(int vid){
142 char *zManFile;
143 Blob manifest;
144 Blob hash;
145
146 if( db_get_versionable_setting_boolean("manifest",0) ){
147 blob_zero(&manifest);
148 content_get(vid, &manifest);
149 zManFile = mprintf("%smanifest", g.zLocalRoot);
150 blob_write_to_file(&manifest, zManFile);
151 free(zManFile);
@@ -242,10 +242,11 @@
242 if( !keepFlag ){
243 vfile_to_disk(vid, 0, 1, promptFlag);
244 }
245 checkout_set_all_exe(vid);
246 manifest_to_disk(vid);
247 ensure_empty_dirs_created();
248 db_lset_int("checkout", vid);
249 undo_reset();
250 db_multi_exec("DELETE FROM vmerge");
251 if( !keepFlag && db_get_boolean("repo-cksum",1) ){
252 vfile_aggregate_checksum_manifest(vid, &cksum1, &cksum1b);
253
+2 -1
--- src/checkout.c
+++ src/checkout.c
@@ -141,11 +141,11 @@
141141
void manifest_to_disk(int vid){
142142
char *zManFile;
143143
Blob manifest;
144144
Blob hash;
145145
146
- if( db_get_boolean("manifest",0) ){
146
+ if( db_get_versionable_setting_boolean("manifest",0) ){
147147
blob_zero(&manifest);
148148
content_get(vid, &manifest);
149149
zManFile = mprintf("%smanifest", g.zLocalRoot);
150150
blob_write_to_file(&manifest, zManFile);
151151
free(zManFile);
@@ -242,10 +242,11 @@
242242
if( !keepFlag ){
243243
vfile_to_disk(vid, 0, 1, promptFlag);
244244
}
245245
checkout_set_all_exe(vid);
246246
manifest_to_disk(vid);
247
+ ensure_empty_dirs_created();
247248
db_lset_int("checkout", vid);
248249
undo_reset();
249250
db_multi_exec("DELETE FROM vmerge");
250251
if( !keepFlag && db_get_boolean("repo-cksum",1) ){
251252
vfile_aggregate_checksum_manifest(vid, &cksum1, &cksum1b);
252253
--- src/checkout.c
+++ src/checkout.c
@@ -141,11 +141,11 @@
141 void manifest_to_disk(int vid){
142 char *zManFile;
143 Blob manifest;
144 Blob hash;
145
146 if( db_get_boolean("manifest",0) ){
147 blob_zero(&manifest);
148 content_get(vid, &manifest);
149 zManFile = mprintf("%smanifest", g.zLocalRoot);
150 blob_write_to_file(&manifest, zManFile);
151 free(zManFile);
@@ -242,10 +242,11 @@
242 if( !keepFlag ){
243 vfile_to_disk(vid, 0, 1, promptFlag);
244 }
245 checkout_set_all_exe(vid);
246 manifest_to_disk(vid);
 
247 db_lset_int("checkout", vid);
248 undo_reset();
249 db_multi_exec("DELETE FROM vmerge");
250 if( !keepFlag && db_get_boolean("repo-cksum",1) ){
251 vfile_aggregate_checksum_manifest(vid, &cksum1, &cksum1b);
252
--- src/checkout.c
+++ src/checkout.c
@@ -141,11 +141,11 @@
141 void manifest_to_disk(int vid){
142 char *zManFile;
143 Blob manifest;
144 Blob hash;
145
146 if( db_get_versionable_setting_boolean("manifest",0) ){
147 blob_zero(&manifest);
148 content_get(vid, &manifest);
149 zManFile = mprintf("%smanifest", g.zLocalRoot);
150 blob_write_to_file(&manifest, zManFile);
151 free(zManFile);
@@ -242,10 +242,11 @@
242 if( !keepFlag ){
243 vfile_to_disk(vid, 0, 1, promptFlag);
244 }
245 checkout_set_all_exe(vid);
246 manifest_to_disk(vid);
247 ensure_empty_dirs_created();
248 db_lset_int("checkout", vid);
249 undo_reset();
250 db_multi_exec("DELETE FROM vmerge");
251 if( !keepFlag && db_get_boolean("repo-cksum",1) ){
252 vfile_aggregate_checksum_manifest(vid, &cksum1, &cksum1b);
253
--- src/configure.c
+++ src/configure.c
@@ -81,10 +81,11 @@
8181
{ "project-name", CONFIGSET_PROJ },
8282
{ "project-description", CONFIGSET_PROJ },
8383
{ "manifest", CONFIGSET_PROJ },
8484
{ "ignore-glob", CONFIGSET_PROJ },
8585
{ "crnl-glob", CONFIGSET_PROJ },
86
+ { "empty-dirs", CONFIGSET_PROJ },
8687
{ "index-page", CONFIGSET_SKIN },
8788
{ "timeline-block-markup", CONFIGSET_SKIN },
8889
{ "timeline-max-comment", CONFIGSET_SKIN },
8990
{ "ticket-table", CONFIGSET_TKT },
9091
{ "ticket-common", CONFIGSET_TKT },
9192
--- src/configure.c
+++ src/configure.c
@@ -81,10 +81,11 @@
81 { "project-name", CONFIGSET_PROJ },
82 { "project-description", CONFIGSET_PROJ },
83 { "manifest", CONFIGSET_PROJ },
84 { "ignore-glob", CONFIGSET_PROJ },
85 { "crnl-glob", CONFIGSET_PROJ },
 
86 { "index-page", CONFIGSET_SKIN },
87 { "timeline-block-markup", CONFIGSET_SKIN },
88 { "timeline-max-comment", CONFIGSET_SKIN },
89 { "ticket-table", CONFIGSET_TKT },
90 { "ticket-common", CONFIGSET_TKT },
91
--- src/configure.c
+++ src/configure.c
@@ -81,10 +81,11 @@
81 { "project-name", CONFIGSET_PROJ },
82 { "project-description", CONFIGSET_PROJ },
83 { "manifest", CONFIGSET_PROJ },
84 { "ignore-glob", CONFIGSET_PROJ },
85 { "crnl-glob", CONFIGSET_PROJ },
86 { "empty-dirs", CONFIGSET_PROJ },
87 { "index-page", CONFIGSET_SKIN },
88 { "timeline-block-markup", CONFIGSET_SKIN },
89 { "timeline-max-comment", CONFIGSET_SKIN },
90 { "ticket-table", CONFIGSET_TKT },
91 { "ticket-common", CONFIGSET_TKT },
92
--- src/configure.c
+++ src/configure.c
@@ -81,10 +81,11 @@
8181
{ "project-name", CONFIGSET_PROJ },
8282
{ "project-description", CONFIGSET_PROJ },
8383
{ "manifest", CONFIGSET_PROJ },
8484
{ "ignore-glob", CONFIGSET_PROJ },
8585
{ "crnl-glob", CONFIGSET_PROJ },
86
+ { "empty-dirs", CONFIGSET_PROJ },
8687
{ "index-page", CONFIGSET_SKIN },
8788
{ "timeline-block-markup", CONFIGSET_SKIN },
8889
{ "timeline-max-comment", CONFIGSET_SKIN },
8990
{ "ticket-table", CONFIGSET_TKT },
9091
{ "ticket-common", CONFIGSET_TKT },
9192
--- src/configure.c
+++ src/configure.c
@@ -81,10 +81,11 @@
81 { "project-name", CONFIGSET_PROJ },
82 { "project-description", CONFIGSET_PROJ },
83 { "manifest", CONFIGSET_PROJ },
84 { "ignore-glob", CONFIGSET_PROJ },
85 { "crnl-glob", CONFIGSET_PROJ },
 
86 { "index-page", CONFIGSET_SKIN },
87 { "timeline-block-markup", CONFIGSET_SKIN },
88 { "timeline-max-comment", CONFIGSET_SKIN },
89 { "ticket-table", CONFIGSET_TKT },
90 { "ticket-common", CONFIGSET_TKT },
91
--- src/configure.c
+++ src/configure.c
@@ -81,10 +81,11 @@
81 { "project-name", CONFIGSET_PROJ },
82 { "project-description", CONFIGSET_PROJ },
83 { "manifest", CONFIGSET_PROJ },
84 { "ignore-glob", CONFIGSET_PROJ },
85 { "crnl-glob", CONFIGSET_PROJ },
86 { "empty-dirs", CONFIGSET_PROJ },
87 { "index-page", CONFIGSET_SKIN },
88 { "timeline-block-markup", CONFIGSET_SKIN },
89 { "timeline-max-comment", CONFIGSET_SKIN },
90 { "ticket-table", CONFIGSET_TKT },
91 { "ticket-common", CONFIGSET_TKT },
92
+113 -45
--- src/db.c
+++ src/db.c
@@ -1392,10 +1392,57 @@
13921392
sqlite3 *dbTemp = g.db;
13931393
g.db = g.dbConfig;
13941394
g.dbConfig = dbTemp;
13951395
}
13961396
}
1397
+
1398
+/*
1399
+** Get a potentially versioned setting - either from .fossil-settings/<name>
1400
+*/
1401
+char *db_get_versionable_setting(const char *zName, char *zDefault){
1402
+ /* Attempt to load the versioned setting from a checked out file */
1403
+ char *zVersionedSetting = 0;
1404
+ int noWarn = 0;
1405
+ if( db_open_local() ){
1406
+ Blob versionedPathname;
1407
+ blob_zero(&versionedPathname);
1408
+ blob_appendf(&versionedPathname, "%s/.fossil-settings/%s", g.zLocalRoot, zName);
1409
+ char *zVersionedPathname = blob_str(&versionedPathname);
1410
+ if( file_size(zVersionedPathname)>=0 ){
1411
+ /* File exists, and contains the value for this setting. Load from the file. */
1412
+ Blob setting;
1413
+ blob_zero(&setting);
1414
+ if( blob_read_from_file(&setting, zVersionedPathname) >= 0 ){
1415
+ blob_trim(&setting); /* Avoid non-obvious problems with line endings on boolean properties */
1416
+ zVersionedSetting = strdup(blob_str(&setting));
1417
+ }
1418
+ blob_reset(&setting);
1419
+ /* See if there's a no-warn flag */
1420
+ blob_append(&versionedPathname, ".no-warn", -1);
1421
+ if( file_size(blob_str(&versionedPathname))>=0 ){
1422
+ noWarn = 1;
1423
+ }
1424
+ }
1425
+ blob_reset(&versionedPathname);
1426
+ }
1427
+ /* Load the normal, non-versioned setting */
1428
+ char *zSetting = db_get(zName, zDefault);
1429
+ /* Display a warning? */
1430
+ if( zVersionedSetting!=0 && zSetting!=0 && zSetting[0]!='\0' && zSetting!=zDefault && !noWarn ){
1431
+ /* There's a versioned setting, and a non-versioned setting. Tell the user about the conflict */
1432
+ fossil_warning("Setting %s has both versioned and non-versioned values: using versioned value from file .fossil-settings/%s (To silence this warning, either create an empty file named .fossil-settings/%s.no-warn or delete the non-versioned setting with \"fossil unset %s\")", zName, zName, zName, zName);
1433
+ }
1434
+ /* Prefer the versioned setting */
1435
+ return ( zVersionedSetting!=0 ) ? zVersionedSetting : zSetting;
1436
+}
1437
+int db_get_versionable_setting_boolean(const char *zName, int dflt){
1438
+ char *zVal = db_get_versionable_setting(zName, dflt ? "on" : "off");
1439
+ if( is_truth(zVal) ) return 1;
1440
+ if( is_false(zVal) ) return 0;
1441
+ return dflt;
1442
+}
1443
+
13971444
13981445
/*
13991446
** Get and set values from the CONFIG, GLOBAL_CONFIG and VVAR table in the
14001447
** repository and local databases.
14011448
*/
@@ -1596,30 +1643,39 @@
15961643
}
15971644
15981645
/*
15991646
** Print the value of a setting named zName
16001647
*/
1601
-static void print_setting(const char *zName){
1648
+static void print_setting(const struct stControlSettings *ctrlSetting, int localOpen){
16021649
Stmt q;
16031650
if( g.repositoryOpen ){
16041651
db_prepare(&q,
16051652
"SELECT '(local)', value FROM config WHERE name=%Q"
16061653
" UNION ALL "
16071654
"SELECT '(global)', value FROM global_config WHERE name=%Q",
1608
- zName, zName
1655
+ ctrlSetting->name, ctrlSetting->name
16091656
);
16101657
}else{
16111658
db_prepare(&q,
16121659
"SELECT '(global)', value FROM global_config WHERE name=%Q",
1613
- zName
1660
+ ctrlSetting->name
16141661
);
16151662
}
16161663
if( db_step(&q)==SQLITE_ROW ){
1617
- fossil_print("%-20s %-8s %s\n", zName, db_column_text(&q, 0),
1664
+ fossil_print("%-20s %-8s %s\n", ctrlSetting->name, db_column_text(&q, 0),
16181665
db_column_text(&q, 1));
16191666
}else{
1620
- fossil_print("%-20s\n", zName);
1667
+ fossil_print("%-20s\n", ctrlSetting->name);
1668
+ }
1669
+ if( ctrlSetting->versionable && localOpen ){
1670
+ /* Check to see if this is overridden by a versionable settings file */
1671
+ Blob versionedPathname;
1672
+ blob_zero(&versionedPathname);
1673
+ blob_appendf(&versionedPathname, "%s/.fossil-settings/%s", g.zLocalRoot, ctrlSetting->name);
1674
+ if( file_size(blob_str(&versionedPathname))>=0 ){
1675
+ fossil_print(" (overridden by contents of file .fossil-settings/%s)\n", ctrlSetting->name);
1676
+ }
16211677
}
16221678
db_finalize(&q);
16231679
}
16241680
16251681
@@ -1635,43 +1691,45 @@
16351691
#if INTERFACE
16361692
struct stControlSettings {
16371693
char const *name; /* Name of the setting */
16381694
char const *var; /* Internal variable name used by db_set() */
16391695
int width; /* Width of display. 0 for boolean values */
1696
+ int versionable; /* Is this setting versionable? */
16401697
char const *def; /* Default value */
16411698
};
16421699
#endif /* INTERFACE */
16431700
struct stControlSettings const ctrlSettings[] = {
1644
- { "access-log", 0, 0, "off" },
1645
- { "auto-captcha", "autocaptcha", 0, "on" },
1646
- { "auto-shun", 0, 0, "on" },
1647
- { "autosync", 0, 0, "on" },
1648
- { "binary-glob", 0, 32, "" },
1649
- { "clearsign", 0, 0, "off" },
1650
- { "crnl-glob", 0, 16, "" },
1651
- { "default-perms", 0, 16, "u" },
1652
- { "diff-command", 0, 16, "" },
1653
- { "dont-push", 0, 0, "off" },
1654
- { "editor", 0, 16, "" },
1655
- { "gdiff-command", 0, 16, "gdiff" },
1656
- { "gmerge-command",0, 40, "" },
1657
- { "https-login", 0, 0, "off" },
1658
- { "ignore-glob", 0, 40, "" },
1659
- { "http-port", 0, 16, "8080" },
1660
- { "localauth", 0, 0, "off" },
1661
- { "main-branch", 0, 40, "trunk" },
1662
- { "manifest", 0, 0, "off" },
1663
- { "max-upload", 0, 25, "250000" },
1664
- { "mtime-changes", 0, 0, "on" },
1665
- { "pgp-command", 0, 32, "gpg --clearsign -o " },
1666
- { "proxy", 0, 32, "off" },
1667
- { "repo-cksum", 0, 0, "on" },
1668
- { "self-register", 0, 0, "off" },
1669
- { "ssl-identity", 0, 40, "" },
1670
- { "ssh-command", 0, 32, "" },
1671
- { "web-browser", 0, 32, "" },
1672
- { 0,0,0,0 }
1701
+ { "access-log", 0, 0, 0, "off" },
1702
+ { "auto-captcha", "autocaptcha", 0, 0, "on" },
1703
+ { "auto-shun", 0, 0, 0, "on" },
1704
+ { "autosync", 0, 0, 0, "on" },
1705
+ { "binary-glob", 0, 32, 1, "" },
1706
+ { "clearsign", 0, 0, 0, "off" },
1707
+ { "crnl-glob", 0, 16, 1, "" },
1708
+ { "default-perms", 0, 16, 0, "u" },
1709
+ { "diff-command", 0, 16, 0, "" },
1710
+ { "dont-push", 0, 0, 0, "off" },
1711
+ { "editor", 0, 16, 0, "" },
1712
+ { "gdiff-command", 0, 16, 0, "gdiff" },
1713
+ { "gmerge-command",0, 40, 0, "" },
1714
+ { "https-login", 0, 0, 0, "off" },
1715
+ { "ignore-glob", 0, 40, 1, "" },
1716
+ { "empty-dirs", 0, 40, 1, "" },
1717
+ { "http-port", 0, 16, 0, "8080" },
1718
+ { "localauth", 0, 0, 0, "off" },
1719
+ { "main-branch", 0, 40, 0, "trunk" },
1720
+ { "manifest", 0, 0, 1, "off" },
1721
+ { "max-upload", 0, 25, 0, "250000" },
1722
+ { "mtime-changes", 0, 0, 0, "on" },
1723
+ { "pgp-command", 0, 32, 0, "gpg --clearsign -o " },
1724
+ { "proxy", 0, 32, 0, "off" },
1725
+ { "repo-cksum", 0, 0, 0, "on" },
1726
+ { "self-register", 0, 0, 0, "off" },
1727
+ { "ssl-identity", 0, 40, 0, "" },
1728
+ { "ssh-command", 0, 32, 0, "" },
1729
+ { "web-browser", 0, 32, 0, "" },
1730
+ { 0,0,0,0,0 }
16731731
};
16741732
16751733
/*
16761734
** COMMAND: settings
16771735
** COMMAND: unset
@@ -1680,10 +1738,14 @@
16801738
** %fossil unset PROPERTY ?-global?
16811739
**
16821740
** The "settings" command with no arguments lists all properties and their
16831741
** values. With just a property name it shows the value of that property.
16841742
** With a value argument it changes the property for the current repository.
1743
+**
1744
+** Settings marked as versionable are overridden by the contents of the
1745
+** file named .fossil-settings/PROPERTY in the checked out files, if that
1746
+** file exists.
16851747
**
16861748
** The "unset" command clears a property setting.
16871749
**
16881750
**
16891751
** auto-captcha If enabled, the Login page provides a button to
@@ -1697,20 +1759,20 @@
16971759
** or update and automatically push after commit or
16981760
** tag or branch creation. If the value is "pullonly"
16991761
** then only pull operations occur automatically.
17001762
** Default: on
17011763
**
1702
-** binary-glob The VALUE is a comma-separated list of GLOB patterns
1703
-** that should be treated as binary files for merging
1704
-** purposes. Example: *.xml
1764
+** binary-glob The VALUE is a comma or newline-separated list of
1765
+** (versionable) GLOB patterns that should be treated as binary files
1766
+** for merging purposes. Example: *.xml
17051767
**
17061768
** clearsign When enabled, fossil will attempt to sign all commits
17071769
** with gpg. When disabled (the default), commits will
17081770
** be unsigned. Default: off
17091771
**
1710
-** crnl-glob A comma-separated list of GLOB patterns for text files
1711
-** in which it is ok to have CR+NL line endings.
1772
+** crnl-glob A comma or newline-separated list of GLOB patterns for
1773
+** (versionable) text files in which it is ok to have CR+NL line endings.
17121774
** Set to "*" to disable CR+NL checking.
17131775
**
17141776
** default-perms Permissions given automatically to new users. For more
17151777
** information on permissions see Users page in Server
17161778
** Administration of the HTTP UI. Default: u.
@@ -1718,10 +1780,15 @@
17181780
** diff-command External command to run when performing a diff.
17191781
** If undefined, the internal text diff will be used.
17201782
**
17211783
** dont-push Prevent this repository from pushing from client to
17221784
** server. Useful when setting up a private branch.
1785
+**
1786
+** empty-dirs A comma or newline-separated list of pathnames. On
1787
+** (versionable) update and checkout commands, if no file or directory
1788
+** exists with that name, an empty directory will be
1789
+** created.
17231790
**
17241791
** editor Text editor command used for check-in comments.
17251792
**
17261793
** gdiff-command External command to run when performing a graphical
17271794
** diff. If undefined, text diff will be used.
@@ -1736,23 +1803,23 @@
17361803
** and "ui" commands. Default: 8080
17371804
**
17381805
** https-login Send login creditials using HTTPS instead of HTTP
17391806
** even if the login page request came via HTTP.
17401807
**
1741
-** ignore-glob The VALUE is a comma-separated list of GLOB patterns
1742
-** specifying files that the "extra" command will ignore.
1743
-** Example: *.o,*.obj,*.exe
1808
+** ignore-glob The VALUE is a comma or newline-separated list of GLOB
1809
+** (versionable) patterns specifying files that the "extra" command will
1810
+** ignore. Example: *.o,*.obj,*.exe
17441811
**
17451812
** localauth If enabled, require that HTTP connections from
17461813
** 127.0.0.1 be authenticated by password. If
17471814
** false, all HTTP requests from localhost have
17481815
** unrestricted access to the repository.
17491816
**
17501817
** main-branch The primary branch for the project. Default: trunk
17511818
**
17521819
** manifest If enabled, automatically create files "manifest" and
1753
-** "manifest.uuid" in every checkout. The SQLite and
1820
+** (versionable) "manifest.uuid" in every checkout. The SQLite and
17541821
** Fossil repositories both require this. Default: off.
17551822
**
17561823
** max-upload A limit on the size of uplink HTTP requests. The
17571824
** default is 250000 bytes.
17581825
**
@@ -1805,12 +1872,13 @@
18051872
}
18061873
if( unsetFlag && g.argc!=3 ){
18071874
usage("PROPERTY ?-global?");
18081875
}
18091876
if( g.argc==2 ){
1877
+ int openLocal = db_open_local();
18101878
for(i=0; ctrlSettings[i].name; i++){
1811
- print_setting(ctrlSettings[i].name);
1879
+ print_setting(&ctrlSettings[i], openLocal);
18121880
}
18131881
}else if( g.argc==3 || g.argc==4 ){
18141882
const char *zName = g.argv[2];
18151883
int isManifest;
18161884
int n = strlen(zName);
@@ -1828,11 +1896,11 @@
18281896
db_unset(ctrlSettings[i].name, globalFlag);
18291897
}else if( g.argc==4 ){
18301898
db_set(ctrlSettings[i].name, g.argv[3], globalFlag);
18311899
}else{
18321900
isManifest = 0;
1833
- print_setting(ctrlSettings[i].name);
1901
+ print_setting(&ctrlSettings[i], db_open_local());
18341902
}
18351903
if( isManifest ){
18361904
manifest_to_disk(db_lget_int("checkout", 0));
18371905
}
18381906
}else{
18391907
--- src/db.c
+++ src/db.c
@@ -1392,10 +1392,57 @@
1392 sqlite3 *dbTemp = g.db;
1393 g.db = g.dbConfig;
1394 g.dbConfig = dbTemp;
1395 }
1396 }
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1397
1398 /*
1399 ** Get and set values from the CONFIG, GLOBAL_CONFIG and VVAR table in the
1400 ** repository and local databases.
1401 */
@@ -1596,30 +1643,39 @@
1596 }
1597
1598 /*
1599 ** Print the value of a setting named zName
1600 */
1601 static void print_setting(const char *zName){
1602 Stmt q;
1603 if( g.repositoryOpen ){
1604 db_prepare(&q,
1605 "SELECT '(local)', value FROM config WHERE name=%Q"
1606 " UNION ALL "
1607 "SELECT '(global)', value FROM global_config WHERE name=%Q",
1608 zName, zName
1609 );
1610 }else{
1611 db_prepare(&q,
1612 "SELECT '(global)', value FROM global_config WHERE name=%Q",
1613 zName
1614 );
1615 }
1616 if( db_step(&q)==SQLITE_ROW ){
1617 fossil_print("%-20s %-8s %s\n", zName, db_column_text(&q, 0),
1618 db_column_text(&q, 1));
1619 }else{
1620 fossil_print("%-20s\n", zName);
 
 
 
 
 
 
 
 
 
1621 }
1622 db_finalize(&q);
1623 }
1624
1625
@@ -1635,43 +1691,45 @@
1635 #if INTERFACE
1636 struct stControlSettings {
1637 char const *name; /* Name of the setting */
1638 char const *var; /* Internal variable name used by db_set() */
1639 int width; /* Width of display. 0 for boolean values */
 
1640 char const *def; /* Default value */
1641 };
1642 #endif /* INTERFACE */
1643 struct stControlSettings const ctrlSettings[] = {
1644 { "access-log", 0, 0, "off" },
1645 { "auto-captcha", "autocaptcha", 0, "on" },
1646 { "auto-shun", 0, 0, "on" },
1647 { "autosync", 0, 0, "on" },
1648 { "binary-glob", 0, 32, "" },
1649 { "clearsign", 0, 0, "off" },
1650 { "crnl-glob", 0, 16, "" },
1651 { "default-perms", 0, 16, "u" },
1652 { "diff-command", 0, 16, "" },
1653 { "dont-push", 0, 0, "off" },
1654 { "editor", 0, 16, "" },
1655 { "gdiff-command", 0, 16, "gdiff" },
1656 { "gmerge-command",0, 40, "" },
1657 { "https-login", 0, 0, "off" },
1658 { "ignore-glob", 0, 40, "" },
1659 { "http-port", 0, 16, "8080" },
1660 { "localauth", 0, 0, "off" },
1661 { "main-branch", 0, 40, "trunk" },
1662 { "manifest", 0, 0, "off" },
1663 { "max-upload", 0, 25, "250000" },
1664 { "mtime-changes", 0, 0, "on" },
1665 { "pgp-command", 0, 32, "gpg --clearsign -o " },
1666 { "proxy", 0, 32, "off" },
1667 { "repo-cksum", 0, 0, "on" },
1668 { "self-register", 0, 0, "off" },
1669 { "ssl-identity", 0, 40, "" },
1670 { "ssh-command", 0, 32, "" },
1671 { "web-browser", 0, 32, "" },
1672 { 0,0,0,0 }
 
1673 };
1674
1675 /*
1676 ** COMMAND: settings
1677 ** COMMAND: unset
@@ -1680,10 +1738,14 @@
1680 ** %fossil unset PROPERTY ?-global?
1681 **
1682 ** The "settings" command with no arguments lists all properties and their
1683 ** values. With just a property name it shows the value of that property.
1684 ** With a value argument it changes the property for the current repository.
 
 
 
 
1685 **
1686 ** The "unset" command clears a property setting.
1687 **
1688 **
1689 ** auto-captcha If enabled, the Login page provides a button to
@@ -1697,20 +1759,20 @@
1697 ** or update and automatically push after commit or
1698 ** tag or branch creation. If the value is "pullonly"
1699 ** then only pull operations occur automatically.
1700 ** Default: on
1701 **
1702 ** binary-glob The VALUE is a comma-separated list of GLOB patterns
1703 ** that should be treated as binary files for merging
1704 ** purposes. Example: *.xml
1705 **
1706 ** clearsign When enabled, fossil will attempt to sign all commits
1707 ** with gpg. When disabled (the default), commits will
1708 ** be unsigned. Default: off
1709 **
1710 ** crnl-glob A comma-separated list of GLOB patterns for text files
1711 ** in which it is ok to have CR+NL line endings.
1712 ** Set to "*" to disable CR+NL checking.
1713 **
1714 ** default-perms Permissions given automatically to new users. For more
1715 ** information on permissions see Users page in Server
1716 ** Administration of the HTTP UI. Default: u.
@@ -1718,10 +1780,15 @@
1718 ** diff-command External command to run when performing a diff.
1719 ** If undefined, the internal text diff will be used.
1720 **
1721 ** dont-push Prevent this repository from pushing from client to
1722 ** server. Useful when setting up a private branch.
 
 
 
 
 
1723 **
1724 ** editor Text editor command used for check-in comments.
1725 **
1726 ** gdiff-command External command to run when performing a graphical
1727 ** diff. If undefined, text diff will be used.
@@ -1736,23 +1803,23 @@
1736 ** and "ui" commands. Default: 8080
1737 **
1738 ** https-login Send login creditials using HTTPS instead of HTTP
1739 ** even if the login page request came via HTTP.
1740 **
1741 ** ignore-glob The VALUE is a comma-separated list of GLOB patterns
1742 ** specifying files that the "extra" command will ignore.
1743 ** Example: *.o,*.obj,*.exe
1744 **
1745 ** localauth If enabled, require that HTTP connections from
1746 ** 127.0.0.1 be authenticated by password. If
1747 ** false, all HTTP requests from localhost have
1748 ** unrestricted access to the repository.
1749 **
1750 ** main-branch The primary branch for the project. Default: trunk
1751 **
1752 ** manifest If enabled, automatically create files "manifest" and
1753 ** "manifest.uuid" in every checkout. The SQLite and
1754 ** Fossil repositories both require this. Default: off.
1755 **
1756 ** max-upload A limit on the size of uplink HTTP requests. The
1757 ** default is 250000 bytes.
1758 **
@@ -1805,12 +1872,13 @@
1805 }
1806 if( unsetFlag && g.argc!=3 ){
1807 usage("PROPERTY ?-global?");
1808 }
1809 if( g.argc==2 ){
 
1810 for(i=0; ctrlSettings[i].name; i++){
1811 print_setting(ctrlSettings[i].name);
1812 }
1813 }else if( g.argc==3 || g.argc==4 ){
1814 const char *zName = g.argv[2];
1815 int isManifest;
1816 int n = strlen(zName);
@@ -1828,11 +1896,11 @@
1828 db_unset(ctrlSettings[i].name, globalFlag);
1829 }else if( g.argc==4 ){
1830 db_set(ctrlSettings[i].name, g.argv[3], globalFlag);
1831 }else{
1832 isManifest = 0;
1833 print_setting(ctrlSettings[i].name);
1834 }
1835 if( isManifest ){
1836 manifest_to_disk(db_lget_int("checkout", 0));
1837 }
1838 }else{
1839
--- src/db.c
+++ src/db.c
@@ -1392,10 +1392,57 @@
1392 sqlite3 *dbTemp = g.db;
1393 g.db = g.dbConfig;
1394 g.dbConfig = dbTemp;
1395 }
1396 }
1397
1398 /*
1399 ** Get a potentially versioned setting - either from .fossil-settings/<name>
1400 */
1401 char *db_get_versionable_setting(const char *zName, char *zDefault){
1402 /* Attempt to load the versioned setting from a checked out file */
1403 char *zVersionedSetting = 0;
1404 int noWarn = 0;
1405 if( db_open_local() ){
1406 Blob versionedPathname;
1407 blob_zero(&versionedPathname);
1408 blob_appendf(&versionedPathname, "%s/.fossil-settings/%s", g.zLocalRoot, zName);
1409 char *zVersionedPathname = blob_str(&versionedPathname);
1410 if( file_size(zVersionedPathname)>=0 ){
1411 /* File exists, and contains the value for this setting. Load from the file. */
1412 Blob setting;
1413 blob_zero(&setting);
1414 if( blob_read_from_file(&setting, zVersionedPathname) >= 0 ){
1415 blob_trim(&setting); /* Avoid non-obvious problems with line endings on boolean properties */
1416 zVersionedSetting = strdup(blob_str(&setting));
1417 }
1418 blob_reset(&setting);
1419 /* See if there's a no-warn flag */
1420 blob_append(&versionedPathname, ".no-warn", -1);
1421 if( file_size(blob_str(&versionedPathname))>=0 ){
1422 noWarn = 1;
1423 }
1424 }
1425 blob_reset(&versionedPathname);
1426 }
1427 /* Load the normal, non-versioned setting */
1428 char *zSetting = db_get(zName, zDefault);
1429 /* Display a warning? */
1430 if( zVersionedSetting!=0 && zSetting!=0 && zSetting[0]!='\0' && zSetting!=zDefault && !noWarn ){
1431 /* There's a versioned setting, and a non-versioned setting. Tell the user about the conflict */
1432 fossil_warning("Setting %s has both versioned and non-versioned values: using versioned value from file .fossil-settings/%s (To silence this warning, either create an empty file named .fossil-settings/%s.no-warn or delete the non-versioned setting with \"fossil unset %s\")", zName, zName, zName, zName);
1433 }
1434 /* Prefer the versioned setting */
1435 return ( zVersionedSetting!=0 ) ? zVersionedSetting : zSetting;
1436 }
1437 int db_get_versionable_setting_boolean(const char *zName, int dflt){
1438 char *zVal = db_get_versionable_setting(zName, dflt ? "on" : "off");
1439 if( is_truth(zVal) ) return 1;
1440 if( is_false(zVal) ) return 0;
1441 return dflt;
1442 }
1443
1444
1445 /*
1446 ** Get and set values from the CONFIG, GLOBAL_CONFIG and VVAR table in the
1447 ** repository and local databases.
1448 */
@@ -1596,30 +1643,39 @@
1643 }
1644
1645 /*
1646 ** Print the value of a setting named zName
1647 */
1648 static void print_setting(const struct stControlSettings *ctrlSetting, int localOpen){
1649 Stmt q;
1650 if( g.repositoryOpen ){
1651 db_prepare(&q,
1652 "SELECT '(local)', value FROM config WHERE name=%Q"
1653 " UNION ALL "
1654 "SELECT '(global)', value FROM global_config WHERE name=%Q",
1655 ctrlSetting->name, ctrlSetting->name
1656 );
1657 }else{
1658 db_prepare(&q,
1659 "SELECT '(global)', value FROM global_config WHERE name=%Q",
1660 ctrlSetting->name
1661 );
1662 }
1663 if( db_step(&q)==SQLITE_ROW ){
1664 fossil_print("%-20s %-8s %s\n", ctrlSetting->name, db_column_text(&q, 0),
1665 db_column_text(&q, 1));
1666 }else{
1667 fossil_print("%-20s\n", ctrlSetting->name);
1668 }
1669 if( ctrlSetting->versionable && localOpen ){
1670 /* Check to see if this is overridden by a versionable settings file */
1671 Blob versionedPathname;
1672 blob_zero(&versionedPathname);
1673 blob_appendf(&versionedPathname, "%s/.fossil-settings/%s", g.zLocalRoot, ctrlSetting->name);
1674 if( file_size(blob_str(&versionedPathname))>=0 ){
1675 fossil_print(" (overridden by contents of file .fossil-settings/%s)\n", ctrlSetting->name);
1676 }
1677 }
1678 db_finalize(&q);
1679 }
1680
1681
@@ -1635,43 +1691,45 @@
1691 #if INTERFACE
1692 struct stControlSettings {
1693 char const *name; /* Name of the setting */
1694 char const *var; /* Internal variable name used by db_set() */
1695 int width; /* Width of display. 0 for boolean values */
1696 int versionable; /* Is this setting versionable? */
1697 char const *def; /* Default value */
1698 };
1699 #endif /* INTERFACE */
1700 struct stControlSettings const ctrlSettings[] = {
1701 { "access-log", 0, 0, 0, "off" },
1702 { "auto-captcha", "autocaptcha", 0, 0, "on" },
1703 { "auto-shun", 0, 0, 0, "on" },
1704 { "autosync", 0, 0, 0, "on" },
1705 { "binary-glob", 0, 32, 1, "" },
1706 { "clearsign", 0, 0, 0, "off" },
1707 { "crnl-glob", 0, 16, 1, "" },
1708 { "default-perms", 0, 16, 0, "u" },
1709 { "diff-command", 0, 16, 0, "" },
1710 { "dont-push", 0, 0, 0, "off" },
1711 { "editor", 0, 16, 0, "" },
1712 { "gdiff-command", 0, 16, 0, "gdiff" },
1713 { "gmerge-command",0, 40, 0, "" },
1714 { "https-login", 0, 0, 0, "off" },
1715 { "ignore-glob", 0, 40, 1, "" },
1716 { "empty-dirs", 0, 40, 1, "" },
1717 { "http-port", 0, 16, 0, "8080" },
1718 { "localauth", 0, 0, 0, "off" },
1719 { "main-branch", 0, 40, 0, "trunk" },
1720 { "manifest", 0, 0, 1, "off" },
1721 { "max-upload", 0, 25, 0, "250000" },
1722 { "mtime-changes", 0, 0, 0, "on" },
1723 { "pgp-command", 0, 32, 0, "gpg --clearsign -o " },
1724 { "proxy", 0, 32, 0, "off" },
1725 { "repo-cksum", 0, 0, 0, "on" },
1726 { "self-register", 0, 0, 0, "off" },
1727 { "ssl-identity", 0, 40, 0, "" },
1728 { "ssh-command", 0, 32, 0, "" },
1729 { "web-browser", 0, 32, 0, "" },
1730 { 0,0,0,0,0 }
1731 };
1732
1733 /*
1734 ** COMMAND: settings
1735 ** COMMAND: unset
@@ -1680,10 +1738,14 @@
1738 ** %fossil unset PROPERTY ?-global?
1739 **
1740 ** The "settings" command with no arguments lists all properties and their
1741 ** values. With just a property name it shows the value of that property.
1742 ** With a value argument it changes the property for the current repository.
1743 **
1744 ** Settings marked as versionable are overridden by the contents of the
1745 ** file named .fossil-settings/PROPERTY in the checked out files, if that
1746 ** file exists.
1747 **
1748 ** The "unset" command clears a property setting.
1749 **
1750 **
1751 ** auto-captcha If enabled, the Login page provides a button to
@@ -1697,20 +1759,20 @@
1759 ** or update and automatically push after commit or
1760 ** tag or branch creation. If the value is "pullonly"
1761 ** then only pull operations occur automatically.
1762 ** Default: on
1763 **
1764 ** binary-glob The VALUE is a comma or newline-separated list of
1765 ** (versionable) GLOB patterns that should be treated as binary files
1766 ** for merging purposes. Example: *.xml
1767 **
1768 ** clearsign When enabled, fossil will attempt to sign all commits
1769 ** with gpg. When disabled (the default), commits will
1770 ** be unsigned. Default: off
1771 **
1772 ** crnl-glob A comma or newline-separated list of GLOB patterns for
1773 ** (versionable) text files in which it is ok to have CR+NL line endings.
1774 ** Set to "*" to disable CR+NL checking.
1775 **
1776 ** default-perms Permissions given automatically to new users. For more
1777 ** information on permissions see Users page in Server
1778 ** Administration of the HTTP UI. Default: u.
@@ -1718,10 +1780,15 @@
1780 ** diff-command External command to run when performing a diff.
1781 ** If undefined, the internal text diff will be used.
1782 **
1783 ** dont-push Prevent this repository from pushing from client to
1784 ** server. Useful when setting up a private branch.
1785 **
1786 ** empty-dirs A comma or newline-separated list of pathnames. On
1787 ** (versionable) update and checkout commands, if no file or directory
1788 ** exists with that name, an empty directory will be
1789 ** created.
1790 **
1791 ** editor Text editor command used for check-in comments.
1792 **
1793 ** gdiff-command External command to run when performing a graphical
1794 ** diff. If undefined, text diff will be used.
@@ -1736,23 +1803,23 @@
1803 ** and "ui" commands. Default: 8080
1804 **
1805 ** https-login Send login creditials using HTTPS instead of HTTP
1806 ** even if the login page request came via HTTP.
1807 **
1808 ** ignore-glob The VALUE is a comma or newline-separated list of GLOB
1809 ** (versionable) patterns specifying files that the "extra" command will
1810 ** ignore. Example: *.o,*.obj,*.exe
1811 **
1812 ** localauth If enabled, require that HTTP connections from
1813 ** 127.0.0.1 be authenticated by password. If
1814 ** false, all HTTP requests from localhost have
1815 ** unrestricted access to the repository.
1816 **
1817 ** main-branch The primary branch for the project. Default: trunk
1818 **
1819 ** manifest If enabled, automatically create files "manifest" and
1820 ** (versionable) "manifest.uuid" in every checkout. The SQLite and
1821 ** Fossil repositories both require this. Default: off.
1822 **
1823 ** max-upload A limit on the size of uplink HTTP requests. The
1824 ** default is 250000 bytes.
1825 **
@@ -1805,12 +1872,13 @@
1872 }
1873 if( unsetFlag && g.argc!=3 ){
1874 usage("PROPERTY ?-global?");
1875 }
1876 if( g.argc==2 ){
1877 int openLocal = db_open_local();
1878 for(i=0; ctrlSettings[i].name; i++){
1879 print_setting(&ctrlSettings[i], openLocal);
1880 }
1881 }else if( g.argc==3 || g.argc==4 ){
1882 const char *zName = g.argv[2];
1883 int isManifest;
1884 int n = strlen(zName);
@@ -1828,11 +1896,11 @@
1896 db_unset(ctrlSettings[i].name, globalFlag);
1897 }else if( g.argc==4 ){
1898 db_set(ctrlSettings[i].name, g.argv[3], globalFlag);
1899 }else{
1900 isManifest = 0;
1901 print_setting(&ctrlSettings[i], db_open_local());
1902 }
1903 if( isManifest ){
1904 manifest_to_disk(db_lget_int("checkout", 0));
1905 }
1906 }else{
1907
+113 -45
--- src/db.c
+++ src/db.c
@@ -1392,10 +1392,57 @@
13921392
sqlite3 *dbTemp = g.db;
13931393
g.db = g.dbConfig;
13941394
g.dbConfig = dbTemp;
13951395
}
13961396
}
1397
+
1398
+/*
1399
+** Get a potentially versioned setting - either from .fossil-settings/<name>
1400
+*/
1401
+char *db_get_versionable_setting(const char *zName, char *zDefault){
1402
+ /* Attempt to load the versioned setting from a checked out file */
1403
+ char *zVersionedSetting = 0;
1404
+ int noWarn = 0;
1405
+ if( db_open_local() ){
1406
+ Blob versionedPathname;
1407
+ blob_zero(&versionedPathname);
1408
+ blob_appendf(&versionedPathname, "%s/.fossil-settings/%s", g.zLocalRoot, zName);
1409
+ char *zVersionedPathname = blob_str(&versionedPathname);
1410
+ if( file_size(zVersionedPathname)>=0 ){
1411
+ /* File exists, and contains the value for this setting. Load from the file. */
1412
+ Blob setting;
1413
+ blob_zero(&setting);
1414
+ if( blob_read_from_file(&setting, zVersionedPathname) >= 0 ){
1415
+ blob_trim(&setting); /* Avoid non-obvious problems with line endings on boolean properties */
1416
+ zVersionedSetting = strdup(blob_str(&setting));
1417
+ }
1418
+ blob_reset(&setting);
1419
+ /* See if there's a no-warn flag */
1420
+ blob_append(&versionedPathname, ".no-warn", -1);
1421
+ if( file_size(blob_str(&versionedPathname))>=0 ){
1422
+ noWarn = 1;
1423
+ }
1424
+ }
1425
+ blob_reset(&versionedPathname);
1426
+ }
1427
+ /* Load the normal, non-versioned setting */
1428
+ char *zSetting = db_get(zName, zDefault);
1429
+ /* Display a warning? */
1430
+ if( zVersionedSetting!=0 && zSetting!=0 && zSetting[0]!='\0' && zSetting!=zDefault && !noWarn ){
1431
+ /* There's a versioned setting, and a non-versioned setting. Tell the user about the conflict */
1432
+ fossil_warning("Setting %s has both versioned and non-versioned values: using versioned value from file .fossil-settings/%s (To silence this warning, either create an empty file named .fossil-settings/%s.no-warn or delete the non-versioned setting with \"fossil unset %s\")", zName, zName, zName, zName);
1433
+ }
1434
+ /* Prefer the versioned setting */
1435
+ return ( zVersionedSetting!=0 ) ? zVersionedSetting : zSetting;
1436
+}
1437
+int db_get_versionable_setting_boolean(const char *zName, int dflt){
1438
+ char *zVal = db_get_versionable_setting(zName, dflt ? "on" : "off");
1439
+ if( is_truth(zVal) ) return 1;
1440
+ if( is_false(zVal) ) return 0;
1441
+ return dflt;
1442
+}
1443
+
13971444
13981445
/*
13991446
** Get and set values from the CONFIG, GLOBAL_CONFIG and VVAR table in the
14001447
** repository and local databases.
14011448
*/
@@ -1596,30 +1643,39 @@
15961643
}
15971644
15981645
/*
15991646
** Print the value of a setting named zName
16001647
*/
1601
-static void print_setting(const char *zName){
1648
+static void print_setting(const struct stControlSettings *ctrlSetting, int localOpen){
16021649
Stmt q;
16031650
if( g.repositoryOpen ){
16041651
db_prepare(&q,
16051652
"SELECT '(local)', value FROM config WHERE name=%Q"
16061653
" UNION ALL "
16071654
"SELECT '(global)', value FROM global_config WHERE name=%Q",
1608
- zName, zName
1655
+ ctrlSetting->name, ctrlSetting->name
16091656
);
16101657
}else{
16111658
db_prepare(&q,
16121659
"SELECT '(global)', value FROM global_config WHERE name=%Q",
1613
- zName
1660
+ ctrlSetting->name
16141661
);
16151662
}
16161663
if( db_step(&q)==SQLITE_ROW ){
1617
- fossil_print("%-20s %-8s %s\n", zName, db_column_text(&q, 0),
1664
+ fossil_print("%-20s %-8s %s\n", ctrlSetting->name, db_column_text(&q, 0),
16181665
db_column_text(&q, 1));
16191666
}else{
1620
- fossil_print("%-20s\n", zName);
1667
+ fossil_print("%-20s\n", ctrlSetting->name);
1668
+ }
1669
+ if( ctrlSetting->versionable && localOpen ){
1670
+ /* Check to see if this is overridden by a versionable settings file */
1671
+ Blob versionedPathname;
1672
+ blob_zero(&versionedPathname);
1673
+ blob_appendf(&versionedPathname, "%s/.fossil-settings/%s", g.zLocalRoot, ctrlSetting->name);
1674
+ if( file_size(blob_str(&versionedPathname))>=0 ){
1675
+ fossil_print(" (overridden by contents of file .fossil-settings/%s)\n", ctrlSetting->name);
1676
+ }
16211677
}
16221678
db_finalize(&q);
16231679
}
16241680
16251681
@@ -1635,43 +1691,45 @@
16351691
#if INTERFACE
16361692
struct stControlSettings {
16371693
char const *name; /* Name of the setting */
16381694
char const *var; /* Internal variable name used by db_set() */
16391695
int width; /* Width of display. 0 for boolean values */
1696
+ int versionable; /* Is this setting versionable? */
16401697
char const *def; /* Default value */
16411698
};
16421699
#endif /* INTERFACE */
16431700
struct stControlSettings const ctrlSettings[] = {
1644
- { "access-log", 0, 0, "off" },
1645
- { "auto-captcha", "autocaptcha", 0, "on" },
1646
- { "auto-shun", 0, 0, "on" },
1647
- { "autosync", 0, 0, "on" },
1648
- { "binary-glob", 0, 32, "" },
1649
- { "clearsign", 0, 0, "off" },
1650
- { "crnl-glob", 0, 16, "" },
1651
- { "default-perms", 0, 16, "u" },
1652
- { "diff-command", 0, 16, "" },
1653
- { "dont-push", 0, 0, "off" },
1654
- { "editor", 0, 16, "" },
1655
- { "gdiff-command", 0, 16, "gdiff" },
1656
- { "gmerge-command",0, 40, "" },
1657
- { "https-login", 0, 0, "off" },
1658
- { "ignore-glob", 0, 40, "" },
1659
- { "http-port", 0, 16, "8080" },
1660
- { "localauth", 0, 0, "off" },
1661
- { "main-branch", 0, 40, "trunk" },
1662
- { "manifest", 0, 0, "off" },
1663
- { "max-upload", 0, 25, "250000" },
1664
- { "mtime-changes", 0, 0, "on" },
1665
- { "pgp-command", 0, 32, "gpg --clearsign -o " },
1666
- { "proxy", 0, 32, "off" },
1667
- { "repo-cksum", 0, 0, "on" },
1668
- { "self-register", 0, 0, "off" },
1669
- { "ssl-identity", 0, 40, "" },
1670
- { "ssh-command", 0, 32, "" },
1671
- { "web-browser", 0, 32, "" },
1672
- { 0,0,0,0 }
1701
+ { "access-log", 0, 0, 0, "off" },
1702
+ { "auto-captcha", "autocaptcha", 0, 0, "on" },
1703
+ { "auto-shun", 0, 0, 0, "on" },
1704
+ { "autosync", 0, 0, 0, "on" },
1705
+ { "binary-glob", 0, 32, 1, "" },
1706
+ { "clearsign", 0, 0, 0, "off" },
1707
+ { "crnl-glob", 0, 16, 1, "" },
1708
+ { "default-perms", 0, 16, 0, "u" },
1709
+ { "diff-command", 0, 16, 0, "" },
1710
+ { "dont-push", 0, 0, 0, "off" },
1711
+ { "editor", 0, 16, 0, "" },
1712
+ { "gdiff-command", 0, 16, 0, "gdiff" },
1713
+ { "gmerge-command",0, 40, 0, "" },
1714
+ { "https-login", 0, 0, 0, "off" },
1715
+ { "ignore-glob", 0, 40, 1, "" },
1716
+ { "empty-dirs", 0, 40, 1, "" },
1717
+ { "http-port", 0, 16, 0, "8080" },
1718
+ { "localauth", 0, 0, 0, "off" },
1719
+ { "main-branch", 0, 40, 0, "trunk" },
1720
+ { "manifest", 0, 0, 1, "off" },
1721
+ { "max-upload", 0, 25, 0, "250000" },
1722
+ { "mtime-changes", 0, 0, 0, "on" },
1723
+ { "pgp-command", 0, 32, 0, "gpg --clearsign -o " },
1724
+ { "proxy", 0, 32, 0, "off" },
1725
+ { "repo-cksum", 0, 0, 0, "on" },
1726
+ { "self-register", 0, 0, 0, "off" },
1727
+ { "ssl-identity", 0, 40, 0, "" },
1728
+ { "ssh-command", 0, 32, 0, "" },
1729
+ { "web-browser", 0, 32, 0, "" },
1730
+ { 0,0,0,0,0 }
16731731
};
16741732
16751733
/*
16761734
** COMMAND: settings
16771735
** COMMAND: unset
@@ -1680,10 +1738,14 @@
16801738
** %fossil unset PROPERTY ?-global?
16811739
**
16821740
** The "settings" command with no arguments lists all properties and their
16831741
** values. With just a property name it shows the value of that property.
16841742
** With a value argument it changes the property for the current repository.
1743
+**
1744
+** Settings marked as versionable are overridden by the contents of the
1745
+** file named .fossil-settings/PROPERTY in the checked out files, if that
1746
+** file exists.
16851747
**
16861748
** The "unset" command clears a property setting.
16871749
**
16881750
**
16891751
** auto-captcha If enabled, the Login page provides a button to
@@ -1697,20 +1759,20 @@
16971759
** or update and automatically push after commit or
16981760
** tag or branch creation. If the value is "pullonly"
16991761
** then only pull operations occur automatically.
17001762
** Default: on
17011763
**
1702
-** binary-glob The VALUE is a comma-separated list of GLOB patterns
1703
-** that should be treated as binary files for merging
1704
-** purposes. Example: *.xml
1764
+** binary-glob The VALUE is a comma or newline-separated list of
1765
+** (versionable) GLOB patterns that should be treated as binary files
1766
+** for merging purposes. Example: *.xml
17051767
**
17061768
** clearsign When enabled, fossil will attempt to sign all commits
17071769
** with gpg. When disabled (the default), commits will
17081770
** be unsigned. Default: off
17091771
**
1710
-** crnl-glob A comma-separated list of GLOB patterns for text files
1711
-** in which it is ok to have CR+NL line endings.
1772
+** crnl-glob A comma or newline-separated list of GLOB patterns for
1773
+** (versionable) text files in which it is ok to have CR+NL line endings.
17121774
** Set to "*" to disable CR+NL checking.
17131775
**
17141776
** default-perms Permissions given automatically to new users. For more
17151777
** information on permissions see Users page in Server
17161778
** Administration of the HTTP UI. Default: u.
@@ -1718,10 +1780,15 @@
17181780
** diff-command External command to run when performing a diff.
17191781
** If undefined, the internal text diff will be used.
17201782
**
17211783
** dont-push Prevent this repository from pushing from client to
17221784
** server. Useful when setting up a private branch.
1785
+**
1786
+** empty-dirs A comma or newline-separated list of pathnames. On
1787
+** (versionable) update and checkout commands, if no file or directory
1788
+** exists with that name, an empty directory will be
1789
+** created.
17231790
**
17241791
** editor Text editor command used for check-in comments.
17251792
**
17261793
** gdiff-command External command to run when performing a graphical
17271794
** diff. If undefined, text diff will be used.
@@ -1736,23 +1803,23 @@
17361803
** and "ui" commands. Default: 8080
17371804
**
17381805
** https-login Send login creditials using HTTPS instead of HTTP
17391806
** even if the login page request came via HTTP.
17401807
**
1741
-** ignore-glob The VALUE is a comma-separated list of GLOB patterns
1742
-** specifying files that the "extra" command will ignore.
1743
-** Example: *.o,*.obj,*.exe
1808
+** ignore-glob The VALUE is a comma or newline-separated list of GLOB
1809
+** (versionable) patterns specifying files that the "extra" command will
1810
+** ignore. Example: *.o,*.obj,*.exe
17441811
**
17451812
** localauth If enabled, require that HTTP connections from
17461813
** 127.0.0.1 be authenticated by password. If
17471814
** false, all HTTP requests from localhost have
17481815
** unrestricted access to the repository.
17491816
**
17501817
** main-branch The primary branch for the project. Default: trunk
17511818
**
17521819
** manifest If enabled, automatically create files "manifest" and
1753
-** "manifest.uuid" in every checkout. The SQLite and
1820
+** (versionable) "manifest.uuid" in every checkout. The SQLite and
17541821
** Fossil repositories both require this. Default: off.
17551822
**
17561823
** max-upload A limit on the size of uplink HTTP requests. The
17571824
** default is 250000 bytes.
17581825
**
@@ -1805,12 +1872,13 @@
18051872
}
18061873
if( unsetFlag && g.argc!=3 ){
18071874
usage("PROPERTY ?-global?");
18081875
}
18091876
if( g.argc==2 ){
1877
+ int openLocal = db_open_local();
18101878
for(i=0; ctrlSettings[i].name; i++){
1811
- print_setting(ctrlSettings[i].name);
1879
+ print_setting(&ctrlSettings[i], openLocal);
18121880
}
18131881
}else if( g.argc==3 || g.argc==4 ){
18141882
const char *zName = g.argv[2];
18151883
int isManifest;
18161884
int n = strlen(zName);
@@ -1828,11 +1896,11 @@
18281896
db_unset(ctrlSettings[i].name, globalFlag);
18291897
}else if( g.argc==4 ){
18301898
db_set(ctrlSettings[i].name, g.argv[3], globalFlag);
18311899
}else{
18321900
isManifest = 0;
1833
- print_setting(ctrlSettings[i].name);
1901
+ print_setting(&ctrlSettings[i], db_open_local());
18341902
}
18351903
if( isManifest ){
18361904
manifest_to_disk(db_lget_int("checkout", 0));
18371905
}
18381906
}else{
18391907
--- src/db.c
+++ src/db.c
@@ -1392,10 +1392,57 @@
1392 sqlite3 *dbTemp = g.db;
1393 g.db = g.dbConfig;
1394 g.dbConfig = dbTemp;
1395 }
1396 }
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1397
1398 /*
1399 ** Get and set values from the CONFIG, GLOBAL_CONFIG and VVAR table in the
1400 ** repository and local databases.
1401 */
@@ -1596,30 +1643,39 @@
1596 }
1597
1598 /*
1599 ** Print the value of a setting named zName
1600 */
1601 static void print_setting(const char *zName){
1602 Stmt q;
1603 if( g.repositoryOpen ){
1604 db_prepare(&q,
1605 "SELECT '(local)', value FROM config WHERE name=%Q"
1606 " UNION ALL "
1607 "SELECT '(global)', value FROM global_config WHERE name=%Q",
1608 zName, zName
1609 );
1610 }else{
1611 db_prepare(&q,
1612 "SELECT '(global)', value FROM global_config WHERE name=%Q",
1613 zName
1614 );
1615 }
1616 if( db_step(&q)==SQLITE_ROW ){
1617 fossil_print("%-20s %-8s %s\n", zName, db_column_text(&q, 0),
1618 db_column_text(&q, 1));
1619 }else{
1620 fossil_print("%-20s\n", zName);
 
 
 
 
 
 
 
 
 
1621 }
1622 db_finalize(&q);
1623 }
1624
1625
@@ -1635,43 +1691,45 @@
1635 #if INTERFACE
1636 struct stControlSettings {
1637 char const *name; /* Name of the setting */
1638 char const *var; /* Internal variable name used by db_set() */
1639 int width; /* Width of display. 0 for boolean values */
 
1640 char const *def; /* Default value */
1641 };
1642 #endif /* INTERFACE */
1643 struct stControlSettings const ctrlSettings[] = {
1644 { "access-log", 0, 0, "off" },
1645 { "auto-captcha", "autocaptcha", 0, "on" },
1646 { "auto-shun", 0, 0, "on" },
1647 { "autosync", 0, 0, "on" },
1648 { "binary-glob", 0, 32, "" },
1649 { "clearsign", 0, 0, "off" },
1650 { "crnl-glob", 0, 16, "" },
1651 { "default-perms", 0, 16, "u" },
1652 { "diff-command", 0, 16, "" },
1653 { "dont-push", 0, 0, "off" },
1654 { "editor", 0, 16, "" },
1655 { "gdiff-command", 0, 16, "gdiff" },
1656 { "gmerge-command",0, 40, "" },
1657 { "https-login", 0, 0, "off" },
1658 { "ignore-glob", 0, 40, "" },
1659 { "http-port", 0, 16, "8080" },
1660 { "localauth", 0, 0, "off" },
1661 { "main-branch", 0, 40, "trunk" },
1662 { "manifest", 0, 0, "off" },
1663 { "max-upload", 0, 25, "250000" },
1664 { "mtime-changes", 0, 0, "on" },
1665 { "pgp-command", 0, 32, "gpg --clearsign -o " },
1666 { "proxy", 0, 32, "off" },
1667 { "repo-cksum", 0, 0, "on" },
1668 { "self-register", 0, 0, "off" },
1669 { "ssl-identity", 0, 40, "" },
1670 { "ssh-command", 0, 32, "" },
1671 { "web-browser", 0, 32, "" },
1672 { 0,0,0,0 }
 
1673 };
1674
1675 /*
1676 ** COMMAND: settings
1677 ** COMMAND: unset
@@ -1680,10 +1738,14 @@
1680 ** %fossil unset PROPERTY ?-global?
1681 **
1682 ** The "settings" command with no arguments lists all properties and their
1683 ** values. With just a property name it shows the value of that property.
1684 ** With a value argument it changes the property for the current repository.
 
 
 
 
1685 **
1686 ** The "unset" command clears a property setting.
1687 **
1688 **
1689 ** auto-captcha If enabled, the Login page provides a button to
@@ -1697,20 +1759,20 @@
1697 ** or update and automatically push after commit or
1698 ** tag or branch creation. If the value is "pullonly"
1699 ** then only pull operations occur automatically.
1700 ** Default: on
1701 **
1702 ** binary-glob The VALUE is a comma-separated list of GLOB patterns
1703 ** that should be treated as binary files for merging
1704 ** purposes. Example: *.xml
1705 **
1706 ** clearsign When enabled, fossil will attempt to sign all commits
1707 ** with gpg. When disabled (the default), commits will
1708 ** be unsigned. Default: off
1709 **
1710 ** crnl-glob A comma-separated list of GLOB patterns for text files
1711 ** in which it is ok to have CR+NL line endings.
1712 ** Set to "*" to disable CR+NL checking.
1713 **
1714 ** default-perms Permissions given automatically to new users. For more
1715 ** information on permissions see Users page in Server
1716 ** Administration of the HTTP UI. Default: u.
@@ -1718,10 +1780,15 @@
1718 ** diff-command External command to run when performing a diff.
1719 ** If undefined, the internal text diff will be used.
1720 **
1721 ** dont-push Prevent this repository from pushing from client to
1722 ** server. Useful when setting up a private branch.
 
 
 
 
 
1723 **
1724 ** editor Text editor command used for check-in comments.
1725 **
1726 ** gdiff-command External command to run when performing a graphical
1727 ** diff. If undefined, text diff will be used.
@@ -1736,23 +1803,23 @@
1736 ** and "ui" commands. Default: 8080
1737 **
1738 ** https-login Send login creditials using HTTPS instead of HTTP
1739 ** even if the login page request came via HTTP.
1740 **
1741 ** ignore-glob The VALUE is a comma-separated list of GLOB patterns
1742 ** specifying files that the "extra" command will ignore.
1743 ** Example: *.o,*.obj,*.exe
1744 **
1745 ** localauth If enabled, require that HTTP connections from
1746 ** 127.0.0.1 be authenticated by password. If
1747 ** false, all HTTP requests from localhost have
1748 ** unrestricted access to the repository.
1749 **
1750 ** main-branch The primary branch for the project. Default: trunk
1751 **
1752 ** manifest If enabled, automatically create files "manifest" and
1753 ** "manifest.uuid" in every checkout. The SQLite and
1754 ** Fossil repositories both require this. Default: off.
1755 **
1756 ** max-upload A limit on the size of uplink HTTP requests. The
1757 ** default is 250000 bytes.
1758 **
@@ -1805,12 +1872,13 @@
1805 }
1806 if( unsetFlag && g.argc!=3 ){
1807 usage("PROPERTY ?-global?");
1808 }
1809 if( g.argc==2 ){
 
1810 for(i=0; ctrlSettings[i].name; i++){
1811 print_setting(ctrlSettings[i].name);
1812 }
1813 }else if( g.argc==3 || g.argc==4 ){
1814 const char *zName = g.argv[2];
1815 int isManifest;
1816 int n = strlen(zName);
@@ -1828,11 +1896,11 @@
1828 db_unset(ctrlSettings[i].name, globalFlag);
1829 }else if( g.argc==4 ){
1830 db_set(ctrlSettings[i].name, g.argv[3], globalFlag);
1831 }else{
1832 isManifest = 0;
1833 print_setting(ctrlSettings[i].name);
1834 }
1835 if( isManifest ){
1836 manifest_to_disk(db_lget_int("checkout", 0));
1837 }
1838 }else{
1839
--- src/db.c
+++ src/db.c
@@ -1392,10 +1392,57 @@
1392 sqlite3 *dbTemp = g.db;
1393 g.db = g.dbConfig;
1394 g.dbConfig = dbTemp;
1395 }
1396 }
1397
1398 /*
1399 ** Get a potentially versioned setting - either from .fossil-settings/<name>
1400 */
1401 char *db_get_versionable_setting(const char *zName, char *zDefault){
1402 /* Attempt to load the versioned setting from a checked out file */
1403 char *zVersionedSetting = 0;
1404 int noWarn = 0;
1405 if( db_open_local() ){
1406 Blob versionedPathname;
1407 blob_zero(&versionedPathname);
1408 blob_appendf(&versionedPathname, "%s/.fossil-settings/%s", g.zLocalRoot, zName);
1409 char *zVersionedPathname = blob_str(&versionedPathname);
1410 if( file_size(zVersionedPathname)>=0 ){
1411 /* File exists, and contains the value for this setting. Load from the file. */
1412 Blob setting;
1413 blob_zero(&setting);
1414 if( blob_read_from_file(&setting, zVersionedPathname) >= 0 ){
1415 blob_trim(&setting); /* Avoid non-obvious problems with line endings on boolean properties */
1416 zVersionedSetting = strdup(blob_str(&setting));
1417 }
1418 blob_reset(&setting);
1419 /* See if there's a no-warn flag */
1420 blob_append(&versionedPathname, ".no-warn", -1);
1421 if( file_size(blob_str(&versionedPathname))>=0 ){
1422 noWarn = 1;
1423 }
1424 }
1425 blob_reset(&versionedPathname);
1426 }
1427 /* Load the normal, non-versioned setting */
1428 char *zSetting = db_get(zName, zDefault);
1429 /* Display a warning? */
1430 if( zVersionedSetting!=0 && zSetting!=0 && zSetting[0]!='\0' && zSetting!=zDefault && !noWarn ){
1431 /* There's a versioned setting, and a non-versioned setting. Tell the user about the conflict */
1432 fossil_warning("Setting %s has both versioned and non-versioned values: using versioned value from file .fossil-settings/%s (To silence this warning, either create an empty file named .fossil-settings/%s.no-warn or delete the non-versioned setting with \"fossil unset %s\")", zName, zName, zName, zName);
1433 }
1434 /* Prefer the versioned setting */
1435 return ( zVersionedSetting!=0 ) ? zVersionedSetting : zSetting;
1436 }
1437 int db_get_versionable_setting_boolean(const char *zName, int dflt){
1438 char *zVal = db_get_versionable_setting(zName, dflt ? "on" : "off");
1439 if( is_truth(zVal) ) return 1;
1440 if( is_false(zVal) ) return 0;
1441 return dflt;
1442 }
1443
1444
1445 /*
1446 ** Get and set values from the CONFIG, GLOBAL_CONFIG and VVAR table in the
1447 ** repository and local databases.
1448 */
@@ -1596,30 +1643,39 @@
1643 }
1644
1645 /*
1646 ** Print the value of a setting named zName
1647 */
1648 static void print_setting(const struct stControlSettings *ctrlSetting, int localOpen){
1649 Stmt q;
1650 if( g.repositoryOpen ){
1651 db_prepare(&q,
1652 "SELECT '(local)', value FROM config WHERE name=%Q"
1653 " UNION ALL "
1654 "SELECT '(global)', value FROM global_config WHERE name=%Q",
1655 ctrlSetting->name, ctrlSetting->name
1656 );
1657 }else{
1658 db_prepare(&q,
1659 "SELECT '(global)', value FROM global_config WHERE name=%Q",
1660 ctrlSetting->name
1661 );
1662 }
1663 if( db_step(&q)==SQLITE_ROW ){
1664 fossil_print("%-20s %-8s %s\n", ctrlSetting->name, db_column_text(&q, 0),
1665 db_column_text(&q, 1));
1666 }else{
1667 fossil_print("%-20s\n", ctrlSetting->name);
1668 }
1669 if( ctrlSetting->versionable && localOpen ){
1670 /* Check to see if this is overridden by a versionable settings file */
1671 Blob versionedPathname;
1672 blob_zero(&versionedPathname);
1673 blob_appendf(&versionedPathname, "%s/.fossil-settings/%s", g.zLocalRoot, ctrlSetting->name);
1674 if( file_size(blob_str(&versionedPathname))>=0 ){
1675 fossil_print(" (overridden by contents of file .fossil-settings/%s)\n", ctrlSetting->name);
1676 }
1677 }
1678 db_finalize(&q);
1679 }
1680
1681
@@ -1635,43 +1691,45 @@
1691 #if INTERFACE
1692 struct stControlSettings {
1693 char const *name; /* Name of the setting */
1694 char const *var; /* Internal variable name used by db_set() */
1695 int width; /* Width of display. 0 for boolean values */
1696 int versionable; /* Is this setting versionable? */
1697 char const *def; /* Default value */
1698 };
1699 #endif /* INTERFACE */
1700 struct stControlSettings const ctrlSettings[] = {
1701 { "access-log", 0, 0, 0, "off" },
1702 { "auto-captcha", "autocaptcha", 0, 0, "on" },
1703 { "auto-shun", 0, 0, 0, "on" },
1704 { "autosync", 0, 0, 0, "on" },
1705 { "binary-glob", 0, 32, 1, "" },
1706 { "clearsign", 0, 0, 0, "off" },
1707 { "crnl-glob", 0, 16, 1, "" },
1708 { "default-perms", 0, 16, 0, "u" },
1709 { "diff-command", 0, 16, 0, "" },
1710 { "dont-push", 0, 0, 0, "off" },
1711 { "editor", 0, 16, 0, "" },
1712 { "gdiff-command", 0, 16, 0, "gdiff" },
1713 { "gmerge-command",0, 40, 0, "" },
1714 { "https-login", 0, 0, 0, "off" },
1715 { "ignore-glob", 0, 40, 1, "" },
1716 { "empty-dirs", 0, 40, 1, "" },
1717 { "http-port", 0, 16, 0, "8080" },
1718 { "localauth", 0, 0, 0, "off" },
1719 { "main-branch", 0, 40, 0, "trunk" },
1720 { "manifest", 0, 0, 1, "off" },
1721 { "max-upload", 0, 25, 0, "250000" },
1722 { "mtime-changes", 0, 0, 0, "on" },
1723 { "pgp-command", 0, 32, 0, "gpg --clearsign -o " },
1724 { "proxy", 0, 32, 0, "off" },
1725 { "repo-cksum", 0, 0, 0, "on" },
1726 { "self-register", 0, 0, 0, "off" },
1727 { "ssl-identity", 0, 40, 0, "" },
1728 { "ssh-command", 0, 32, 0, "" },
1729 { "web-browser", 0, 32, 0, "" },
1730 { 0,0,0,0,0 }
1731 };
1732
1733 /*
1734 ** COMMAND: settings
1735 ** COMMAND: unset
@@ -1680,10 +1738,14 @@
1738 ** %fossil unset PROPERTY ?-global?
1739 **
1740 ** The "settings" command with no arguments lists all properties and their
1741 ** values. With just a property name it shows the value of that property.
1742 ** With a value argument it changes the property for the current repository.
1743 **
1744 ** Settings marked as versionable are overridden by the contents of the
1745 ** file named .fossil-settings/PROPERTY in the checked out files, if that
1746 ** file exists.
1747 **
1748 ** The "unset" command clears a property setting.
1749 **
1750 **
1751 ** auto-captcha If enabled, the Login page provides a button to
@@ -1697,20 +1759,20 @@
1759 ** or update and automatically push after commit or
1760 ** tag or branch creation. If the value is "pullonly"
1761 ** then only pull operations occur automatically.
1762 ** Default: on
1763 **
1764 ** binary-glob The VALUE is a comma or newline-separated list of
1765 ** (versionable) GLOB patterns that should be treated as binary files
1766 ** for merging purposes. Example: *.xml
1767 **
1768 ** clearsign When enabled, fossil will attempt to sign all commits
1769 ** with gpg. When disabled (the default), commits will
1770 ** be unsigned. Default: off
1771 **
1772 ** crnl-glob A comma or newline-separated list of GLOB patterns for
1773 ** (versionable) text files in which it is ok to have CR+NL line endings.
1774 ** Set to "*" to disable CR+NL checking.
1775 **
1776 ** default-perms Permissions given automatically to new users. For more
1777 ** information on permissions see Users page in Server
1778 ** Administration of the HTTP UI. Default: u.
@@ -1718,10 +1780,15 @@
1780 ** diff-command External command to run when performing a diff.
1781 ** If undefined, the internal text diff will be used.
1782 **
1783 ** dont-push Prevent this repository from pushing from client to
1784 ** server. Useful when setting up a private branch.
1785 **
1786 ** empty-dirs A comma or newline-separated list of pathnames. On
1787 ** (versionable) update and checkout commands, if no file or directory
1788 ** exists with that name, an empty directory will be
1789 ** created.
1790 **
1791 ** editor Text editor command used for check-in comments.
1792 **
1793 ** gdiff-command External command to run when performing a graphical
1794 ** diff. If undefined, text diff will be used.
@@ -1736,23 +1803,23 @@
1803 ** and "ui" commands. Default: 8080
1804 **
1805 ** https-login Send login creditials using HTTPS instead of HTTP
1806 ** even if the login page request came via HTTP.
1807 **
1808 ** ignore-glob The VALUE is a comma or newline-separated list of GLOB
1809 ** (versionable) patterns specifying files that the "extra" command will
1810 ** ignore. Example: *.o,*.obj,*.exe
1811 **
1812 ** localauth If enabled, require that HTTP connections from
1813 ** 127.0.0.1 be authenticated by password. If
1814 ** false, all HTTP requests from localhost have
1815 ** unrestricted access to the repository.
1816 **
1817 ** main-branch The primary branch for the project. Default: trunk
1818 **
1819 ** manifest If enabled, automatically create files "manifest" and
1820 ** (versionable) "manifest.uuid" in every checkout. The SQLite and
1821 ** Fossil repositories both require this. Default: off.
1822 **
1823 ** max-upload A limit on the size of uplink HTTP requests. The
1824 ** default is 250000 bytes.
1825 **
@@ -1805,12 +1872,13 @@
1872 }
1873 if( unsetFlag && g.argc!=3 ){
1874 usage("PROPERTY ?-global?");
1875 }
1876 if( g.argc==2 ){
1877 int openLocal = db_open_local();
1878 for(i=0; ctrlSettings[i].name; i++){
1879 print_setting(&ctrlSettings[i], openLocal);
1880 }
1881 }else if( g.argc==3 || g.argc==4 ){
1882 const char *zName = g.argv[2];
1883 int isManifest;
1884 int n = strlen(zName);
@@ -1828,11 +1896,11 @@
1896 db_unset(ctrlSettings[i].name, globalFlag);
1897 }else if( g.argc==4 ){
1898 db_set(ctrlSettings[i].name, g.argv[3], globalFlag);
1899 }else{
1900 isManifest = 0;
1901 print_setting(&ctrlSettings[i], db_open_local());
1902 }
1903 if( isManifest ){
1904 manifest_to_disk(db_lget_int("checkout", 0));
1905 }
1906 }else{
1907
+4 -4
--- src/glob.c
+++ src/glob.c
@@ -110,24 +110,24 @@
110110
p = fossil_malloc( sizeof(*p) + nList+1 );
111111
memset(p, 0, sizeof(*p));
112112
z = (char*)&p[1];
113113
memcpy(z, zPatternList, nList+1);
114114
while( z[0] ){
115
- while( z[0]==',' || z[0]==' ' ) z++; /* Skip leading spaces */
115
+ while( z[0]==',' || z[0]==' ' || z[0]=='\n' || z[0]=='\r' ) z++; /* Skip leading spaces and newlines */
116116
if( z[0]=='\'' || z[0]=='"' ){
117117
delimiter = z[0];
118118
z++;
119119
}else{
120120
delimiter = ',';
121121
}
122122
if( z[0]==0 ) break;
123123
p->azPattern = fossil_realloc(p->azPattern, (p->nPattern+1)*sizeof(char*) );
124124
p->azPattern[p->nPattern++] = z;
125
- for(i=0; z[i] && z[i]!=delimiter; i++){}
125
+ for(i=0; z[i] && z[i]!=delimiter && z[i]!='\n' && z[i]!='\r'; i++){}
126126
if( delimiter==',' ){
127
- /* Remove trailing spaces on a comma-delimited pattern */
128
- for(j=i; j>1 && z[j-1]==' '; j--){}
127
+ /* Remove trailing spaces / newlines on a comma-delimited pattern */
128
+ for(j=i; j>1 && (z[j-1]==' ' || z[j-1]=='\n' || z[j-1]=='\r'); j--){}
129129
if( j<i ) z[j] = 0;
130130
}
131131
if( z[i]==0 ) break;
132132
z[i] = 0;
133133
z += i+1;
134134
--- src/glob.c
+++ src/glob.c
@@ -110,24 +110,24 @@
110 p = fossil_malloc( sizeof(*p) + nList+1 );
111 memset(p, 0, sizeof(*p));
112 z = (char*)&p[1];
113 memcpy(z, zPatternList, nList+1);
114 while( z[0] ){
115 while( z[0]==',' || z[0]==' ' ) z++; /* Skip leading spaces */
116 if( z[0]=='\'' || z[0]=='"' ){
117 delimiter = z[0];
118 z++;
119 }else{
120 delimiter = ',';
121 }
122 if( z[0]==0 ) break;
123 p->azPattern = fossil_realloc(p->azPattern, (p->nPattern+1)*sizeof(char*) );
124 p->azPattern[p->nPattern++] = z;
125 for(i=0; z[i] && z[i]!=delimiter; i++){}
126 if( delimiter==',' ){
127 /* Remove trailing spaces on a comma-delimited pattern */
128 for(j=i; j>1 && z[j-1]==' '; j--){}
129 if( j<i ) z[j] = 0;
130 }
131 if( z[i]==0 ) break;
132 z[i] = 0;
133 z += i+1;
134
--- src/glob.c
+++ src/glob.c
@@ -110,24 +110,24 @@
110 p = fossil_malloc( sizeof(*p) + nList+1 );
111 memset(p, 0, sizeof(*p));
112 z = (char*)&p[1];
113 memcpy(z, zPatternList, nList+1);
114 while( z[0] ){
115 while( z[0]==',' || z[0]==' ' || z[0]=='\n' || z[0]=='\r' ) z++; /* Skip leading spaces and newlines */
116 if( z[0]=='\'' || z[0]=='"' ){
117 delimiter = z[0];
118 z++;
119 }else{
120 delimiter = ',';
121 }
122 if( z[0]==0 ) break;
123 p->azPattern = fossil_realloc(p->azPattern, (p->nPattern+1)*sizeof(char*) );
124 p->azPattern[p->nPattern++] = z;
125 for(i=0; z[i] && z[i]!=delimiter && z[i]!='\n' && z[i]!='\r'; i++){}
126 if( delimiter==',' ){
127 /* Remove trailing spaces / newlines on a comma-delimited pattern */
128 for(j=i; j>1 && (z[j-1]==' ' || z[j-1]=='\n' || z[j-1]=='\r'); j--){}
129 if( j<i ) z[j] = 0;
130 }
131 if( z[i]==0 ) break;
132 z[i] = 0;
133 z += i+1;
134
+4 -4
--- src/glob.c
+++ src/glob.c
@@ -110,24 +110,24 @@
110110
p = fossil_malloc( sizeof(*p) + nList+1 );
111111
memset(p, 0, sizeof(*p));
112112
z = (char*)&p[1];
113113
memcpy(z, zPatternList, nList+1);
114114
while( z[0] ){
115
- while( z[0]==',' || z[0]==' ' ) z++; /* Skip leading spaces */
115
+ while( z[0]==',' || z[0]==' ' || z[0]=='\n' || z[0]=='\r' ) z++; /* Skip leading spaces and newlines */
116116
if( z[0]=='\'' || z[0]=='"' ){
117117
delimiter = z[0];
118118
z++;
119119
}else{
120120
delimiter = ',';
121121
}
122122
if( z[0]==0 ) break;
123123
p->azPattern = fossil_realloc(p->azPattern, (p->nPattern+1)*sizeof(char*) );
124124
p->azPattern[p->nPattern++] = z;
125
- for(i=0; z[i] && z[i]!=delimiter; i++){}
125
+ for(i=0; z[i] && z[i]!=delimiter && z[i]!='\n' && z[i]!='\r'; i++){}
126126
if( delimiter==',' ){
127
- /* Remove trailing spaces on a comma-delimited pattern */
128
- for(j=i; j>1 && z[j-1]==' '; j--){}
127
+ /* Remove trailing spaces / newlines on a comma-delimited pattern */
128
+ for(j=i; j>1 && (z[j-1]==' ' || z[j-1]=='\n' || z[j-1]=='\r'); j--){}
129129
if( j<i ) z[j] = 0;
130130
}
131131
if( z[i]==0 ) break;
132132
z[i] = 0;
133133
z += i+1;
134134
--- src/glob.c
+++ src/glob.c
@@ -110,24 +110,24 @@
110 p = fossil_malloc( sizeof(*p) + nList+1 );
111 memset(p, 0, sizeof(*p));
112 z = (char*)&p[1];
113 memcpy(z, zPatternList, nList+1);
114 while( z[0] ){
115 while( z[0]==',' || z[0]==' ' ) z++; /* Skip leading spaces */
116 if( z[0]=='\'' || z[0]=='"' ){
117 delimiter = z[0];
118 z++;
119 }else{
120 delimiter = ',';
121 }
122 if( z[0]==0 ) break;
123 p->azPattern = fossil_realloc(p->azPattern, (p->nPattern+1)*sizeof(char*) );
124 p->azPattern[p->nPattern++] = z;
125 for(i=0; z[i] && z[i]!=delimiter; i++){}
126 if( delimiter==',' ){
127 /* Remove trailing spaces on a comma-delimited pattern */
128 for(j=i; j>1 && z[j-1]==' '; j--){}
129 if( j<i ) z[j] = 0;
130 }
131 if( z[i]==0 ) break;
132 z[i] = 0;
133 z += i+1;
134
--- src/glob.c
+++ src/glob.c
@@ -110,24 +110,24 @@
110 p = fossil_malloc( sizeof(*p) + nList+1 );
111 memset(p, 0, sizeof(*p));
112 z = (char*)&p[1];
113 memcpy(z, zPatternList, nList+1);
114 while( z[0] ){
115 while( z[0]==',' || z[0]==' ' || z[0]=='\n' || z[0]=='\r' ) z++; /* Skip leading spaces and newlines */
116 if( z[0]=='\'' || z[0]=='"' ){
117 delimiter = z[0];
118 z++;
119 }else{
120 delimiter = ',';
121 }
122 if( z[0]==0 ) break;
123 p->azPattern = fossil_realloc(p->azPattern, (p->nPattern+1)*sizeof(char*) );
124 p->azPattern[p->nPattern++] = z;
125 for(i=0; z[i] && z[i]!=delimiter && z[i]!='\n' && z[i]!='\r'; i++){}
126 if( delimiter==',' ){
127 /* Remove trailing spaces / newlines on a comma-delimited pattern */
128 for(j=i; j>1 && (z[j-1]==' ' || z[j-1]=='\n' || z[j-1]=='\r'); j--){}
129 if( j<i ) z[j] = 0;
130 }
131 if( z[i]==0 ) break;
132 z[i] = 0;
133 z += i+1;
134
+1 -1
--- src/merge.c
+++ src/merge.c
@@ -91,11 +91,11 @@
9191
zPivot = find_option("baseline",0,1);
9292
if( g.argc!=3 ){
9393
usage("VERSION");
9494
}
9595
db_must_be_within_tree();
96
- if( zBinGlob==0 ) zBinGlob = db_get("binary-glob",0);
96
+ if( zBinGlob==0 ) zBinGlob = db_get_versionable_setting("binary-glob",0);
9797
vid = db_lget_int("checkout", 0);
9898
if( vid==0 ){
9999
fossil_fatal("nothing is checked out");
100100
}
101101
mid = name_to_typed_rid(g.argv[2], "ci");
102102
--- src/merge.c
+++ src/merge.c
@@ -91,11 +91,11 @@
91 zPivot = find_option("baseline",0,1);
92 if( g.argc!=3 ){
93 usage("VERSION");
94 }
95 db_must_be_within_tree();
96 if( zBinGlob==0 ) zBinGlob = db_get("binary-glob",0);
97 vid = db_lget_int("checkout", 0);
98 if( vid==0 ){
99 fossil_fatal("nothing is checked out");
100 }
101 mid = name_to_typed_rid(g.argv[2], "ci");
102
--- src/merge.c
+++ src/merge.c
@@ -91,11 +91,11 @@
91 zPivot = find_option("baseline",0,1);
92 if( g.argc!=3 ){
93 usage("VERSION");
94 }
95 db_must_be_within_tree();
96 if( zBinGlob==0 ) zBinGlob = db_get_versionable_setting("binary-glob",0);
97 vid = db_lget_int("checkout", 0);
98 if( vid==0 ){
99 fossil_fatal("nothing is checked out");
100 }
101 mid = name_to_typed_rid(g.argv[2], "ci");
102
+1 -1
--- src/merge.c
+++ src/merge.c
@@ -91,11 +91,11 @@
9191
zPivot = find_option("baseline",0,1);
9292
if( g.argc!=3 ){
9393
usage("VERSION");
9494
}
9595
db_must_be_within_tree();
96
- if( zBinGlob==0 ) zBinGlob = db_get("binary-glob",0);
96
+ if( zBinGlob==0 ) zBinGlob = db_get_versionable_setting("binary-glob",0);
9797
vid = db_lget_int("checkout", 0);
9898
if( vid==0 ){
9999
fossil_fatal("nothing is checked out");
100100
}
101101
mid = name_to_typed_rid(g.argv[2], "ci");
102102
--- src/merge.c
+++ src/merge.c
@@ -91,11 +91,11 @@
91 zPivot = find_option("baseline",0,1);
92 if( g.argc!=3 ){
93 usage("VERSION");
94 }
95 db_must_be_within_tree();
96 if( zBinGlob==0 ) zBinGlob = db_get("binary-glob",0);
97 vid = db_lget_int("checkout", 0);
98 if( vid==0 ){
99 fossil_fatal("nothing is checked out");
100 }
101 mid = name_to_typed_rid(g.argv[2], "ci");
102
--- src/merge.c
+++ src/merge.c
@@ -91,11 +91,11 @@
91 zPivot = find_option("baseline",0,1);
92 if( g.argc!=3 ){
93 usage("VERSION");
94 }
95 db_must_be_within_tree();
96 if( zBinGlob==0 ) zBinGlob = db_get_versionable_setting("binary-glob",0);
97 vid = db_lget_int("checkout", 0);
98 if( vid==0 ){
99 fossil_fatal("nothing is checked out");
100 }
101 mid = name_to_typed_rid(g.argv[2], "ci");
102
+11 -2
--- src/setup.c
+++ src/setup.c
@@ -1062,25 +1062,34 @@
10621062
for(pSet=ctrlSettings; pSet->name!=0; pSet++){
10631063
if( pSet->width==0 ){
10641064
onoff_attribute(pSet->name, pSet->name,
10651065
pSet->var!=0 ? pSet->var : pSet->name,
10661066
is_truth(pSet->def));
1067
- @ <br />
1067
+ if( pSet->versionable ){
1068
+ @ (v)<br />
1069
+ } else {
1070
+ @ <br />
1071
+ }
10681072
}
10691073
}
10701074
@ </td><td style="width: 30;"></td><td valign="top">
10711075
for(pSet=ctrlSettings; pSet->name!=0; pSet++){
10721076
if( pSet->width!=0 ){
10731077
entry_attribute(pSet->name, /*pSet->width*/ 40, pSet->name,
10741078
pSet->var!=0 ? pSet->var : pSet->name,
10751079
(char*)pSet->def);
1076
- @ <br />
1080
+ if( pSet->versionable ){
1081
+ @ (v)<br />
1082
+ } else {
1083
+ @ <br />
1084
+ }
10771085
}
10781086
}
10791087
@ </td></tr></table>
10801088
@ <p><input type="submit" name="submit" value="Apply Changes" /></p>
10811089
@ </div></form>
1090
+ @ <p>Settings marked with (v) are 'versionable' and will be overridden by the contents of files named <tt>.fossil-settings/PROPERTY</tt>.</p>
10821091
@ <hr /><p>
10831092
@ These settings work in the same way, as the <kbd>set</kbd> commandline:<br />
10841093
@ </p><pre>%s(zHelp_setting_cmd)</pre>
10851094
db_end_transaction(0);
10861095
style_footer();
10871096
--- src/setup.c
+++ src/setup.c
@@ -1062,25 +1062,34 @@
1062 for(pSet=ctrlSettings; pSet->name!=0; pSet++){
1063 if( pSet->width==0 ){
1064 onoff_attribute(pSet->name, pSet->name,
1065 pSet->var!=0 ? pSet->var : pSet->name,
1066 is_truth(pSet->def));
1067 @ <br />
 
 
 
 
1068 }
1069 }
1070 @ </td><td style="width: 30;"></td><td valign="top">
1071 for(pSet=ctrlSettings; pSet->name!=0; pSet++){
1072 if( pSet->width!=0 ){
1073 entry_attribute(pSet->name, /*pSet->width*/ 40, pSet->name,
1074 pSet->var!=0 ? pSet->var : pSet->name,
1075 (char*)pSet->def);
1076 @ <br />
 
 
 
 
1077 }
1078 }
1079 @ </td></tr></table>
1080 @ <p><input type="submit" name="submit" value="Apply Changes" /></p>
1081 @ </div></form>
 
1082 @ <hr /><p>
1083 @ These settings work in the same way, as the <kbd>set</kbd> commandline:<br />
1084 @ </p><pre>%s(zHelp_setting_cmd)</pre>
1085 db_end_transaction(0);
1086 style_footer();
1087
--- src/setup.c
+++ src/setup.c
@@ -1062,25 +1062,34 @@
1062 for(pSet=ctrlSettings; pSet->name!=0; pSet++){
1063 if( pSet->width==0 ){
1064 onoff_attribute(pSet->name, pSet->name,
1065 pSet->var!=0 ? pSet->var : pSet->name,
1066 is_truth(pSet->def));
1067 if( pSet->versionable ){
1068 @ (v)<br />
1069 } else {
1070 @ <br />
1071 }
1072 }
1073 }
1074 @ </td><td style="width: 30;"></td><td valign="top">
1075 for(pSet=ctrlSettings; pSet->name!=0; pSet++){
1076 if( pSet->width!=0 ){
1077 entry_attribute(pSet->name, /*pSet->width*/ 40, pSet->name,
1078 pSet->var!=0 ? pSet->var : pSet->name,
1079 (char*)pSet->def);
1080 if( pSet->versionable ){
1081 @ (v)<br />
1082 } else {
1083 @ <br />
1084 }
1085 }
1086 }
1087 @ </td></tr></table>
1088 @ <p><input type="submit" name="submit" value="Apply Changes" /></p>
1089 @ </div></form>
1090 @ <p>Settings marked with (v) are 'versionable' and will be overridden by the contents of files named <tt>.fossil-settings/PROPERTY</tt>.</p>
1091 @ <hr /><p>
1092 @ These settings work in the same way, as the <kbd>set</kbd> commandline:<br />
1093 @ </p><pre>%s(zHelp_setting_cmd)</pre>
1094 db_end_transaction(0);
1095 style_footer();
1096
+11 -2
--- src/setup.c
+++ src/setup.c
@@ -1062,25 +1062,34 @@
10621062
for(pSet=ctrlSettings; pSet->name!=0; pSet++){
10631063
if( pSet->width==0 ){
10641064
onoff_attribute(pSet->name, pSet->name,
10651065
pSet->var!=0 ? pSet->var : pSet->name,
10661066
is_truth(pSet->def));
1067
- @ <br />
1067
+ if( pSet->versionable ){
1068
+ @ (v)<br />
1069
+ } else {
1070
+ @ <br />
1071
+ }
10681072
}
10691073
}
10701074
@ </td><td style="width: 30;"></td><td valign="top">
10711075
for(pSet=ctrlSettings; pSet->name!=0; pSet++){
10721076
if( pSet->width!=0 ){
10731077
entry_attribute(pSet->name, /*pSet->width*/ 40, pSet->name,
10741078
pSet->var!=0 ? pSet->var : pSet->name,
10751079
(char*)pSet->def);
1076
- @ <br />
1080
+ if( pSet->versionable ){
1081
+ @ (v)<br />
1082
+ } else {
1083
+ @ <br />
1084
+ }
10771085
}
10781086
}
10791087
@ </td></tr></table>
10801088
@ <p><input type="submit" name="submit" value="Apply Changes" /></p>
10811089
@ </div></form>
1090
+ @ <p>Settings marked with (v) are 'versionable' and will be overridden by the contents of files named <tt>.fossil-settings/PROPERTY</tt>.</p>
10821091
@ <hr /><p>
10831092
@ These settings work in the same way, as the <kbd>set</kbd> commandline:<br />
10841093
@ </p><pre>%s(zHelp_setting_cmd)</pre>
10851094
db_end_transaction(0);
10861095
style_footer();
10871096
--- src/setup.c
+++ src/setup.c
@@ -1062,25 +1062,34 @@
1062 for(pSet=ctrlSettings; pSet->name!=0; pSet++){
1063 if( pSet->width==0 ){
1064 onoff_attribute(pSet->name, pSet->name,
1065 pSet->var!=0 ? pSet->var : pSet->name,
1066 is_truth(pSet->def));
1067 @ <br />
 
 
 
 
1068 }
1069 }
1070 @ </td><td style="width: 30;"></td><td valign="top">
1071 for(pSet=ctrlSettings; pSet->name!=0; pSet++){
1072 if( pSet->width!=0 ){
1073 entry_attribute(pSet->name, /*pSet->width*/ 40, pSet->name,
1074 pSet->var!=0 ? pSet->var : pSet->name,
1075 (char*)pSet->def);
1076 @ <br />
 
 
 
 
1077 }
1078 }
1079 @ </td></tr></table>
1080 @ <p><input type="submit" name="submit" value="Apply Changes" /></p>
1081 @ </div></form>
 
1082 @ <hr /><p>
1083 @ These settings work in the same way, as the <kbd>set</kbd> commandline:<br />
1084 @ </p><pre>%s(zHelp_setting_cmd)</pre>
1085 db_end_transaction(0);
1086 style_footer();
1087
--- src/setup.c
+++ src/setup.c
@@ -1062,25 +1062,34 @@
1062 for(pSet=ctrlSettings; pSet->name!=0; pSet++){
1063 if( pSet->width==0 ){
1064 onoff_attribute(pSet->name, pSet->name,
1065 pSet->var!=0 ? pSet->var : pSet->name,
1066 is_truth(pSet->def));
1067 if( pSet->versionable ){
1068 @ (v)<br />
1069 } else {
1070 @ <br />
1071 }
1072 }
1073 }
1074 @ </td><td style="width: 30;"></td><td valign="top">
1075 for(pSet=ctrlSettings; pSet->name!=0; pSet++){
1076 if( pSet->width!=0 ){
1077 entry_attribute(pSet->name, /*pSet->width*/ 40, pSet->name,
1078 pSet->var!=0 ? pSet->var : pSet->name,
1079 (char*)pSet->def);
1080 if( pSet->versionable ){
1081 @ (v)<br />
1082 } else {
1083 @ <br />
1084 }
1085 }
1086 }
1087 @ </td></tr></table>
1088 @ <p><input type="submit" name="submit" value="Apply Changes" /></p>
1089 @ </div></form>
1090 @ <p>Settings marked with (v) are 'versionable' and will be overridden by the contents of files named <tt>.fossil-settings/PROPERTY</tt>.</p>
1091 @ <hr /><p>
1092 @ These settings work in the same way, as the <kbd>set</kbd> commandline:<br />
1093 @ </p><pre>%s(zHelp_setting_cmd)</pre>
1094 db_end_transaction(0);
1095 style_footer();
1096
+1 -1
--- src/tar.c
+++ src/tar.c
@@ -215,11 +215,11 @@
215215
nPrefix = blob_size(&filename);
216216
217217
pManifest = manifest_get(rid, CFTYPE_MANIFEST);
218218
if( pManifest ){
219219
mTime = (pManifest->rDate - 2440587.5)*86400.0;
220
- if( db_get_boolean("manifest", 0) ){
220
+ if( db_get_versionable_setting_boolean("manifest", 0) ){
221221
blob_append(&filename, "manifest", -1);
222222
zName = blob_str(&filename);
223223
tar_add_file(zName, &mfile, 0, mTime);
224224
sha1sum_blob(&mfile, &hash);
225225
blob_reset(&mfile);
226226
--- src/tar.c
+++ src/tar.c
@@ -215,11 +215,11 @@
215 nPrefix = blob_size(&filename);
216
217 pManifest = manifest_get(rid, CFTYPE_MANIFEST);
218 if( pManifest ){
219 mTime = (pManifest->rDate - 2440587.5)*86400.0;
220 if( db_get_boolean("manifest", 0) ){
221 blob_append(&filename, "manifest", -1);
222 zName = blob_str(&filename);
223 tar_add_file(zName, &mfile, 0, mTime);
224 sha1sum_blob(&mfile, &hash);
225 blob_reset(&mfile);
226
--- src/tar.c
+++ src/tar.c
@@ -215,11 +215,11 @@
215 nPrefix = blob_size(&filename);
216
217 pManifest = manifest_get(rid, CFTYPE_MANIFEST);
218 if( pManifest ){
219 mTime = (pManifest->rDate - 2440587.5)*86400.0;
220 if( db_get_versionable_setting_boolean("manifest", 0) ){
221 blob_append(&filename, "manifest", -1);
222 zName = blob_str(&filename);
223 tar_add_file(zName, &mfile, 0, mTime);
224 sha1sum_blob(&mfile, &hash);
225 blob_reset(&mfile);
226
+1 -1
--- src/tar.c
+++ src/tar.c
@@ -215,11 +215,11 @@
215215
nPrefix = blob_size(&filename);
216216
217217
pManifest = manifest_get(rid, CFTYPE_MANIFEST);
218218
if( pManifest ){
219219
mTime = (pManifest->rDate - 2440587.5)*86400.0;
220
- if( db_get_boolean("manifest", 0) ){
220
+ if( db_get_versionable_setting_boolean("manifest", 0) ){
221221
blob_append(&filename, "manifest", -1);
222222
zName = blob_str(&filename);
223223
tar_add_file(zName, &mfile, 0, mTime);
224224
sha1sum_blob(&mfile, &hash);
225225
blob_reset(&mfile);
226226
--- src/tar.c
+++ src/tar.c
@@ -215,11 +215,11 @@
215 nPrefix = blob_size(&filename);
216
217 pManifest = manifest_get(rid, CFTYPE_MANIFEST);
218 if( pManifest ){
219 mTime = (pManifest->rDate - 2440587.5)*86400.0;
220 if( db_get_boolean("manifest", 0) ){
221 blob_append(&filename, "manifest", -1);
222 zName = blob_str(&filename);
223 tar_add_file(zName, &mfile, 0, mTime);
224 sha1sum_blob(&mfile, &hash);
225 blob_reset(&mfile);
226
--- src/tar.c
+++ src/tar.c
@@ -215,11 +215,11 @@
215 nPrefix = blob_size(&filename);
216
217 pManifest = manifest_get(rid, CFTYPE_MANIFEST);
218 if( pManifest ){
219 mTime = (pManifest->rDate - 2440587.5)*86400.0;
220 if( db_get_versionable_setting_boolean("manifest", 0) ){
221 blob_append(&filename, "manifest", -1);
222 zName = blob_str(&filename);
223 tar_add_file(zName, &mfile, 0, mTime);
224 sha1sum_blob(&mfile, &hash);
225 blob_reset(&mfile);
226
+52
--- src/update.c
+++ src/update.c
@@ -115,10 +115,13 @@
115115
}
116116
if( !nochangeFlag && db_exists("SELECT 1 FROM vmerge") ){
117117
fossil_fatal("cannot update an uncommitted merge");
118118
}
119119
if( !nochangeFlag && !internalUpdate ) autosync(AUTOSYNC_PULL);
120
+
121
+ /* Create any empty directories now, as well as after the update, so changes in settings are reflected now */
122
+ ensure_empty_dirs_created();
120123
121124
if( internalUpdate ){
122125
tid = internalUpdate;
123126
}else if( g.argc>=3 ){
124127
if( fossil_strcmp(g.argv[2], "current")==0 ){
@@ -440,10 +443,11 @@
440443
** Clean up the mid and pid VFILE entries. Then commit the changes.
441444
*/
442445
if( nochangeFlag ){
443446
db_end_transaction(1); /* With --nochange, rollback changes */
444447
}else{
448
+ ensure_empty_dirs_created();
445449
if( g.argc<=3 ){
446450
/* All files updated. Shift the current checkout to the target. */
447451
db_multi_exec("DELETE FROM vfile WHERE vid!=%d", tid);
448452
checkout_set_all_exe(vid);
449453
manifest_to_disk(tid);
@@ -455,10 +459,58 @@
455459
}
456460
if( !internalUpdate ) undo_finish();
457461
db_end_transaction(0);
458462
}
459463
}
464
+
465
+/*
466
+** Make sure empty directories are created
467
+*/
468
+void ensure_empty_dirs_created()
469
+{
470
+ /* Make empty directories? */
471
+ char *zEmptyDirs = db_get_versionable_setting("empty-dirs", 0);
472
+ if( zEmptyDirs!=0 ){
473
+ Blob dirsList;
474
+ blob_zero(&dirsList);
475
+ blob_init(&dirsList, zEmptyDirs, strlen(zEmptyDirs));
476
+ /* Replace commas by spaces */
477
+ char *bc = blob_str(&dirsList);
478
+ while( (*bc)!='\0' ){
479
+ if( (*bc)==',' ) { *bc = ' '; }
480
+ ++bc;
481
+ }
482
+ /* Make directories */
483
+ Blob dirName;
484
+ blob_zero(&dirName);
485
+ while( blob_token(&dirsList, &dirName) ){
486
+ const char *zDir = blob_str(&dirName);
487
+ /* Make full pathname of the directory */
488
+ Blob path;
489
+ blob_zero(&path);
490
+ blob_appendf(&path, "%s/%s", g.zLocalRoot, zDir);
491
+ const char *zPath = blob_str(&path);
492
+ /* Handle various cases of existence of the directory */
493
+ switch( file_isdir(zPath) ){
494
+ case 0: { /* doesn't exist */
495
+ if( file_mkdir(zPath, 0)!=0 ) {
496
+ fossil_warning("couldn't create directory %s as required by empty-dirs setting", zDir);
497
+ }
498
+ break;
499
+ }
500
+ case 1: { /* exists, and is a directory */
501
+ /* do nothing - required directory exists already */
502
+ break;
503
+ }
504
+ case 2: { /* exists, but isn't a directory */
505
+ fossil_warning("file %s found, but a directory is required by empty-dirs setting", zDir);
506
+ }
507
+ }
508
+ blob_reset(&path);
509
+ }
510
+ }
511
+}
460512
461513
462514
/*
463515
** Get the contents of a file within the checking "revision". If
464516
** revision==NULL then get the file content for the current checkout.
465517
--- src/update.c
+++ src/update.c
@@ -115,10 +115,13 @@
115 }
116 if( !nochangeFlag && db_exists("SELECT 1 FROM vmerge") ){
117 fossil_fatal("cannot update an uncommitted merge");
118 }
119 if( !nochangeFlag && !internalUpdate ) autosync(AUTOSYNC_PULL);
 
 
 
120
121 if( internalUpdate ){
122 tid = internalUpdate;
123 }else if( g.argc>=3 ){
124 if( fossil_strcmp(g.argv[2], "current")==0 ){
@@ -440,10 +443,11 @@
440 ** Clean up the mid and pid VFILE entries. Then commit the changes.
441 */
442 if( nochangeFlag ){
443 db_end_transaction(1); /* With --nochange, rollback changes */
444 }else{
 
445 if( g.argc<=3 ){
446 /* All files updated. Shift the current checkout to the target. */
447 db_multi_exec("DELETE FROM vfile WHERE vid!=%d", tid);
448 checkout_set_all_exe(vid);
449 manifest_to_disk(tid);
@@ -455,10 +459,58 @@
455 }
456 if( !internalUpdate ) undo_finish();
457 db_end_transaction(0);
458 }
459 }
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
460
461
462 /*
463 ** Get the contents of a file within the checking "revision". If
464 ** revision==NULL then get the file content for the current checkout.
465
--- src/update.c
+++ src/update.c
@@ -115,10 +115,13 @@
115 }
116 if( !nochangeFlag && db_exists("SELECT 1 FROM vmerge") ){
117 fossil_fatal("cannot update an uncommitted merge");
118 }
119 if( !nochangeFlag && !internalUpdate ) autosync(AUTOSYNC_PULL);
120
121 /* Create any empty directories now, as well as after the update, so changes in settings are reflected now */
122 ensure_empty_dirs_created();
123
124 if( internalUpdate ){
125 tid = internalUpdate;
126 }else if( g.argc>=3 ){
127 if( fossil_strcmp(g.argv[2], "current")==0 ){
@@ -440,10 +443,11 @@
443 ** Clean up the mid and pid VFILE entries. Then commit the changes.
444 */
445 if( nochangeFlag ){
446 db_end_transaction(1); /* With --nochange, rollback changes */
447 }else{
448 ensure_empty_dirs_created();
449 if( g.argc<=3 ){
450 /* All files updated. Shift the current checkout to the target. */
451 db_multi_exec("DELETE FROM vfile WHERE vid!=%d", tid);
452 checkout_set_all_exe(vid);
453 manifest_to_disk(tid);
@@ -455,10 +459,58 @@
459 }
460 if( !internalUpdate ) undo_finish();
461 db_end_transaction(0);
462 }
463 }
464
465 /*
466 ** Make sure empty directories are created
467 */
468 void ensure_empty_dirs_created()
469 {
470 /* Make empty directories? */
471 char *zEmptyDirs = db_get_versionable_setting("empty-dirs", 0);
472 if( zEmptyDirs!=0 ){
473 Blob dirsList;
474 blob_zero(&dirsList);
475 blob_init(&dirsList, zEmptyDirs, strlen(zEmptyDirs));
476 /* Replace commas by spaces */
477 char *bc = blob_str(&dirsList);
478 while( (*bc)!='\0' ){
479 if( (*bc)==',' ) { *bc = ' '; }
480 ++bc;
481 }
482 /* Make directories */
483 Blob dirName;
484 blob_zero(&dirName);
485 while( blob_token(&dirsList, &dirName) ){
486 const char *zDir = blob_str(&dirName);
487 /* Make full pathname of the directory */
488 Blob path;
489 blob_zero(&path);
490 blob_appendf(&path, "%s/%s", g.zLocalRoot, zDir);
491 const char *zPath = blob_str(&path);
492 /* Handle various cases of existence of the directory */
493 switch( file_isdir(zPath) ){
494 case 0: { /* doesn't exist */
495 if( file_mkdir(zPath, 0)!=0 ) {
496 fossil_warning("couldn't create directory %s as required by empty-dirs setting", zDir);
497 }
498 break;
499 }
500 case 1: { /* exists, and is a directory */
501 /* do nothing - required directory exists already */
502 break;
503 }
504 case 2: { /* exists, but isn't a directory */
505 fossil_warning("file %s found, but a directory is required by empty-dirs setting", zDir);
506 }
507 }
508 blob_reset(&path);
509 }
510 }
511 }
512
513
514 /*
515 ** Get the contents of a file within the checking "revision". If
516 ** revision==NULL then get the file content for the current checkout.
517
+52
--- src/update.c
+++ src/update.c
@@ -115,10 +115,13 @@
115115
}
116116
if( !nochangeFlag && db_exists("SELECT 1 FROM vmerge") ){
117117
fossil_fatal("cannot update an uncommitted merge");
118118
}
119119
if( !nochangeFlag && !internalUpdate ) autosync(AUTOSYNC_PULL);
120
+
121
+ /* Create any empty directories now, as well as after the update, so changes in settings are reflected now */
122
+ ensure_empty_dirs_created();
120123
121124
if( internalUpdate ){
122125
tid = internalUpdate;
123126
}else if( g.argc>=3 ){
124127
if( fossil_strcmp(g.argv[2], "current")==0 ){
@@ -440,10 +443,11 @@
440443
** Clean up the mid and pid VFILE entries. Then commit the changes.
441444
*/
442445
if( nochangeFlag ){
443446
db_end_transaction(1); /* With --nochange, rollback changes */
444447
}else{
448
+ ensure_empty_dirs_created();
445449
if( g.argc<=3 ){
446450
/* All files updated. Shift the current checkout to the target. */
447451
db_multi_exec("DELETE FROM vfile WHERE vid!=%d", tid);
448452
checkout_set_all_exe(vid);
449453
manifest_to_disk(tid);
@@ -455,10 +459,58 @@
455459
}
456460
if( !internalUpdate ) undo_finish();
457461
db_end_transaction(0);
458462
}
459463
}
464
+
465
+/*
466
+** Make sure empty directories are created
467
+*/
468
+void ensure_empty_dirs_created()
469
+{
470
+ /* Make empty directories? */
471
+ char *zEmptyDirs = db_get_versionable_setting("empty-dirs", 0);
472
+ if( zEmptyDirs!=0 ){
473
+ Blob dirsList;
474
+ blob_zero(&dirsList);
475
+ blob_init(&dirsList, zEmptyDirs, strlen(zEmptyDirs));
476
+ /* Replace commas by spaces */
477
+ char *bc = blob_str(&dirsList);
478
+ while( (*bc)!='\0' ){
479
+ if( (*bc)==',' ) { *bc = ' '; }
480
+ ++bc;
481
+ }
482
+ /* Make directories */
483
+ Blob dirName;
484
+ blob_zero(&dirName);
485
+ while( blob_token(&dirsList, &dirName) ){
486
+ const char *zDir = blob_str(&dirName);
487
+ /* Make full pathname of the directory */
488
+ Blob path;
489
+ blob_zero(&path);
490
+ blob_appendf(&path, "%s/%s", g.zLocalRoot, zDir);
491
+ const char *zPath = blob_str(&path);
492
+ /* Handle various cases of existence of the directory */
493
+ switch( file_isdir(zPath) ){
494
+ case 0: { /* doesn't exist */
495
+ if( file_mkdir(zPath, 0)!=0 ) {
496
+ fossil_warning("couldn't create directory %s as required by empty-dirs setting", zDir);
497
+ }
498
+ break;
499
+ }
500
+ case 1: { /* exists, and is a directory */
501
+ /* do nothing - required directory exists already */
502
+ break;
503
+ }
504
+ case 2: { /* exists, but isn't a directory */
505
+ fossil_warning("file %s found, but a directory is required by empty-dirs setting", zDir);
506
+ }
507
+ }
508
+ blob_reset(&path);
509
+ }
510
+ }
511
+}
460512
461513
462514
/*
463515
** Get the contents of a file within the checking "revision". If
464516
** revision==NULL then get the file content for the current checkout.
465517
--- src/update.c
+++ src/update.c
@@ -115,10 +115,13 @@
115 }
116 if( !nochangeFlag && db_exists("SELECT 1 FROM vmerge") ){
117 fossil_fatal("cannot update an uncommitted merge");
118 }
119 if( !nochangeFlag && !internalUpdate ) autosync(AUTOSYNC_PULL);
 
 
 
120
121 if( internalUpdate ){
122 tid = internalUpdate;
123 }else if( g.argc>=3 ){
124 if( fossil_strcmp(g.argv[2], "current")==0 ){
@@ -440,10 +443,11 @@
440 ** Clean up the mid and pid VFILE entries. Then commit the changes.
441 */
442 if( nochangeFlag ){
443 db_end_transaction(1); /* With --nochange, rollback changes */
444 }else{
 
445 if( g.argc<=3 ){
446 /* All files updated. Shift the current checkout to the target. */
447 db_multi_exec("DELETE FROM vfile WHERE vid!=%d", tid);
448 checkout_set_all_exe(vid);
449 manifest_to_disk(tid);
@@ -455,10 +459,58 @@
455 }
456 if( !internalUpdate ) undo_finish();
457 db_end_transaction(0);
458 }
459 }
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
460
461
462 /*
463 ** Get the contents of a file within the checking "revision". If
464 ** revision==NULL then get the file content for the current checkout.
465
--- src/update.c
+++ src/update.c
@@ -115,10 +115,13 @@
115 }
116 if( !nochangeFlag && db_exists("SELECT 1 FROM vmerge") ){
117 fossil_fatal("cannot update an uncommitted merge");
118 }
119 if( !nochangeFlag && !internalUpdate ) autosync(AUTOSYNC_PULL);
120
121 /* Create any empty directories now, as well as after the update, so changes in settings are reflected now */
122 ensure_empty_dirs_created();
123
124 if( internalUpdate ){
125 tid = internalUpdate;
126 }else if( g.argc>=3 ){
127 if( fossil_strcmp(g.argv[2], "current")==0 ){
@@ -440,10 +443,11 @@
443 ** Clean up the mid and pid VFILE entries. Then commit the changes.
444 */
445 if( nochangeFlag ){
446 db_end_transaction(1); /* With --nochange, rollback changes */
447 }else{
448 ensure_empty_dirs_created();
449 if( g.argc<=3 ){
450 /* All files updated. Shift the current checkout to the target. */
451 db_multi_exec("DELETE FROM vfile WHERE vid!=%d", tid);
452 checkout_set_all_exe(vid);
453 manifest_to_disk(tid);
@@ -455,10 +459,58 @@
459 }
460 if( !internalUpdate ) undo_finish();
461 db_end_transaction(0);
462 }
463 }
464
465 /*
466 ** Make sure empty directories are created
467 */
468 void ensure_empty_dirs_created()
469 {
470 /* Make empty directories? */
471 char *zEmptyDirs = db_get_versionable_setting("empty-dirs", 0);
472 if( zEmptyDirs!=0 ){
473 Blob dirsList;
474 blob_zero(&dirsList);
475 blob_init(&dirsList, zEmptyDirs, strlen(zEmptyDirs));
476 /* Replace commas by spaces */
477 char *bc = blob_str(&dirsList);
478 while( (*bc)!='\0' ){
479 if( (*bc)==',' ) { *bc = ' '; }
480 ++bc;
481 }
482 /* Make directories */
483 Blob dirName;
484 blob_zero(&dirName);
485 while( blob_token(&dirsList, &dirName) ){
486 const char *zDir = blob_str(&dirName);
487 /* Make full pathname of the directory */
488 Blob path;
489 blob_zero(&path);
490 blob_appendf(&path, "%s/%s", g.zLocalRoot, zDir);
491 const char *zPath = blob_str(&path);
492 /* Handle various cases of existence of the directory */
493 switch( file_isdir(zPath) ){
494 case 0: { /* doesn't exist */
495 if( file_mkdir(zPath, 0)!=0 ) {
496 fossil_warning("couldn't create directory %s as required by empty-dirs setting", zDir);
497 }
498 break;
499 }
500 case 1: { /* exists, and is a directory */
501 /* do nothing - required directory exists already */
502 break;
503 }
504 case 2: { /* exists, but isn't a directory */
505 fossil_warning("file %s found, but a directory is required by empty-dirs setting", zDir);
506 }
507 }
508 blob_reset(&path);
509 }
510 }
511 }
512
513
514 /*
515 ** Get the contents of a file within the checking "revision". If
516 ** revision==NULL then get the file content for the current checkout.
517
+1 -1
--- src/zip.c
+++ src/zip.c
@@ -337,11 +337,11 @@
337337
338338
pManifest = manifest_get(rid, CFTYPE_MANIFEST);
339339
if( pManifest ){
340340
char *zName;
341341
zip_set_timedate(pManifest->rDate);
342
- if( db_get_boolean("manifest", 0) ){
342
+ if( db_get_versionable_setting_boolean("manifest", 0) ){
343343
blob_append(&filename, "manifest", -1);
344344
zName = blob_str(&filename);
345345
zip_add_folders(zName);
346346
zip_add_file(zName, &mfile, 0);
347347
sha1sum_blob(&mfile, &hash);
348348
--- src/zip.c
+++ src/zip.c
@@ -337,11 +337,11 @@
337
338 pManifest = manifest_get(rid, CFTYPE_MANIFEST);
339 if( pManifest ){
340 char *zName;
341 zip_set_timedate(pManifest->rDate);
342 if( db_get_boolean("manifest", 0) ){
343 blob_append(&filename, "manifest", -1);
344 zName = blob_str(&filename);
345 zip_add_folders(zName);
346 zip_add_file(zName, &mfile, 0);
347 sha1sum_blob(&mfile, &hash);
348
--- src/zip.c
+++ src/zip.c
@@ -337,11 +337,11 @@
337
338 pManifest = manifest_get(rid, CFTYPE_MANIFEST);
339 if( pManifest ){
340 char *zName;
341 zip_set_timedate(pManifest->rDate);
342 if( db_get_versionable_setting_boolean("manifest", 0) ){
343 blob_append(&filename, "manifest", -1);
344 zName = blob_str(&filename);
345 zip_add_folders(zName);
346 zip_add_file(zName, &mfile, 0);
347 sha1sum_blob(&mfile, &hash);
348
+1 -1
--- src/zip.c
+++ src/zip.c
@@ -337,11 +337,11 @@
337337
338338
pManifest = manifest_get(rid, CFTYPE_MANIFEST);
339339
if( pManifest ){
340340
char *zName;
341341
zip_set_timedate(pManifest->rDate);
342
- if( db_get_boolean("manifest", 0) ){
342
+ if( db_get_versionable_setting_boolean("manifest", 0) ){
343343
blob_append(&filename, "manifest", -1);
344344
zName = blob_str(&filename);
345345
zip_add_folders(zName);
346346
zip_add_file(zName, &mfile, 0);
347347
sha1sum_blob(&mfile, &hash);
348348
--- src/zip.c
+++ src/zip.c
@@ -337,11 +337,11 @@
337
338 pManifest = manifest_get(rid, CFTYPE_MANIFEST);
339 if( pManifest ){
340 char *zName;
341 zip_set_timedate(pManifest->rDate);
342 if( db_get_boolean("manifest", 0) ){
343 blob_append(&filename, "manifest", -1);
344 zName = blob_str(&filename);
345 zip_add_folders(zName);
346 zip_add_file(zName, &mfile, 0);
347 sha1sum_blob(&mfile, &hash);
348
--- src/zip.c
+++ src/zip.c
@@ -337,11 +337,11 @@
337
338 pManifest = manifest_get(rid, CFTYPE_MANIFEST);
339 if( pManifest ){
340 char *zName;
341 zip_set_timedate(pManifest->rDate);
342 if( db_get_versionable_setting_boolean("manifest", 0) ){
343 blob_append(&filename, "manifest", -1);
344 zName = blob_str(&filename);
345 zip_add_folders(zName);
346 zip_add_file(zName, &mfile, 0);
347 sha1sum_blob(&mfile, &hash);
348

Keyboard Shortcuts

Open search /
Next entry (timeline) j
Previous entry (timeline) k
Open focused entry Enter
Show this help ?
Toggle theme Top nav button