Fossil SCM
Added safemerge option to commit, update and settings
Commit
41561125cd744d8b1adbc7a7fb6f0cb0a32571a1
Parent
8d55aa3597e4969…
4 files changed
+1
-1
+18
-6
+12
-3
+13
-3
+1
-1
| --- src/branch.c | ||
| +++ src/branch.c | ||
| @@ -37,11 +37,11 @@ | ||
| 37 | 37 | Blob cksum1, cksum2; /* Before and after commit checksums */ |
| 38 | 38 | Blob cksum1b; /* Checksum recorded in the manifest */ |
| 39 | 39 | |
| 40 | 40 | noSign = find_option("nosign","",0)!=0; |
| 41 | 41 | db_must_be_within_tree(); |
| 42 | - noSign = db_get_int("omit-ci-sig", 0)|noSign; | |
| 42 | + noSign = db_get_int("omit-sign", 0)|noSign; | |
| 43 | 43 | zColor = find_option("bgcolor","c",1); |
| 44 | 44 | |
| 45 | 45 | verify_all_options(); |
| 46 | 46 | |
| 47 | 47 | /* fossil branch new name */ |
| 48 | 48 |
| --- src/branch.c | |
| +++ src/branch.c | |
| @@ -37,11 +37,11 @@ | |
| 37 | Blob cksum1, cksum2; /* Before and after commit checksums */ |
| 38 | Blob cksum1b; /* Checksum recorded in the manifest */ |
| 39 | |
| 40 | noSign = find_option("nosign","",0)!=0; |
| 41 | db_must_be_within_tree(); |
| 42 | noSign = db_get_int("omit-ci-sig", 0)|noSign; |
| 43 | zColor = find_option("bgcolor","c",1); |
| 44 | |
| 45 | verify_all_options(); |
| 46 | |
| 47 | /* fossil branch new name */ |
| 48 |
| --- src/branch.c | |
| +++ src/branch.c | |
| @@ -37,11 +37,11 @@ | |
| 37 | Blob cksum1, cksum2; /* Before and after commit checksums */ |
| 38 | Blob cksum1b; /* Checksum recorded in the manifest */ |
| 39 | |
| 40 | noSign = find_option("nosign","",0)!=0; |
| 41 | db_must_be_within_tree(); |
| 42 | noSign = db_get_int("omit-sign", 0)|noSign; |
| 43 | zColor = find_option("bgcolor","c",1); |
| 44 | |
| 45 | verify_all_options(); |
| 46 | |
| 47 | /* fossil branch new name */ |
| 48 |
+18
-6
| --- src/checkin.c | ||
| +++ src/checkin.c | ||
| @@ -315,11 +315,11 @@ | ||
| 315 | 315 | ** changed will be committed unless some subset of files is specified |
| 316 | 316 | ** on the command line. |
| 317 | 317 | */ |
| 318 | 318 | void commit_cmd(void){ |
| 319 | 319 | int rc; |
| 320 | - int vid, nrid, nvid; | |
| 320 | + int vid, nrid, nvid, wouldFork=0; | |
| 321 | 321 | Blob comment; |
| 322 | 322 | const char *zComment; |
| 323 | 323 | Stmt q; |
| 324 | 324 | Stmt q2; |
| 325 | 325 | char *zUuid, *zDate; |
| @@ -335,11 +335,11 @@ | ||
| 335 | 335 | |
| 336 | 336 | noSign = find_option("nosign","",0)!=0; |
| 337 | 337 | zComment = find_option("comment","m",1); |
| 338 | 338 | forceFlag = find_option("force", "r", 0)!=0; |
| 339 | 339 | db_must_be_within_tree(); |
| 340 | - noSign = db_get_int("omit-ci-sig", 0)|noSign; | |
| 340 | + noSign = db_get_int("omit-sign", 0)|noSign; | |
| 341 | 341 | verify_all_options(); |
| 342 | 342 | |
| 343 | 343 | /* |
| 344 | 344 | ** Autosync if requested. |
| 345 | 345 | */ |
| @@ -382,12 +382,15 @@ | ||
| 382 | 382 | fossil_panic("file %s has not changed", blob_str(&unmodified)); |
| 383 | 383 | } |
| 384 | 384 | } |
| 385 | 385 | |
| 386 | 386 | vid = db_lget_int("checkout", 0); |
| 387 | - if( !forceFlag && db_exists("SELECT 1 FROM plink WHERE pid=%d", vid) ){ | |
| 388 | - fossil_fatal("would fork. use -f or --force"); | |
| 387 | + if( db_exists("SELECT 1 FROM plink WHERE pid=%d", vid) ){ | |
| 388 | + wouldFork=1; | |
| 389 | + if( forceFlag==0 && db_get_int("safemerge", 0)==0 ){ | |
| 390 | + fossil_fatal("would fork. use -f or --force"); | |
| 391 | + } | |
| 389 | 392 | } |
| 390 | 393 | vfile_aggregate_checksum_disk(vid, &cksum1); |
| 391 | 394 | if( zComment ){ |
| 392 | 395 | blob_zero(&comment); |
| 393 | 396 | blob_append(&comment, zComment, -1); |
| @@ -534,8 +537,17 @@ | ||
| 534 | 537 | undo_reset(); |
| 535 | 538 | |
| 536 | 539 | /* Commit */ |
| 537 | 540 | db_end_transaction(0); |
| 538 | 541 | |
| 539 | - /* Do an autosync push if requested */ | |
| 540 | - autosync(0); | |
| 542 | + if( wouldFork==0 ){ | |
| 543 | + /* Do an autosync push if requested. If wouldFork == 1, then they either | |
| 544 | + ** forced this commit or safe merge is on, and this commit did indeed | |
| 545 | + ** create a fork. In this case, we want the user to merge before sending | |
| 546 | + ** their new commit back to the rest of the world, so do not auto-push. | |
| 547 | + */ | |
| 548 | + autosync(0); | |
| 549 | + }else{ | |
| 550 | + printf("Warning: commit caused a fork to occur. Please merge and push\n"); | |
| 551 | + printf(" your changes as soon as possible.\n"); | |
| 552 | + } | |
| 541 | 553 | } |
| 542 | 554 |
| --- src/checkin.c | |
| +++ src/checkin.c | |
| @@ -315,11 +315,11 @@ | |
| 315 | ** changed will be committed unless some subset of files is specified |
| 316 | ** on the command line. |
| 317 | */ |
| 318 | void commit_cmd(void){ |
| 319 | int rc; |
| 320 | int vid, nrid, nvid; |
| 321 | Blob comment; |
| 322 | const char *zComment; |
| 323 | Stmt q; |
| 324 | Stmt q2; |
| 325 | char *zUuid, *zDate; |
| @@ -335,11 +335,11 @@ | |
| 335 | |
| 336 | noSign = find_option("nosign","",0)!=0; |
| 337 | zComment = find_option("comment","m",1); |
| 338 | forceFlag = find_option("force", "r", 0)!=0; |
| 339 | db_must_be_within_tree(); |
| 340 | noSign = db_get_int("omit-ci-sig", 0)|noSign; |
| 341 | verify_all_options(); |
| 342 | |
| 343 | /* |
| 344 | ** Autosync if requested. |
| 345 | */ |
| @@ -382,12 +382,15 @@ | |
| 382 | fossil_panic("file %s has not changed", blob_str(&unmodified)); |
| 383 | } |
| 384 | } |
| 385 | |
| 386 | vid = db_lget_int("checkout", 0); |
| 387 | if( !forceFlag && db_exists("SELECT 1 FROM plink WHERE pid=%d", vid) ){ |
| 388 | fossil_fatal("would fork. use -f or --force"); |
| 389 | } |
| 390 | vfile_aggregate_checksum_disk(vid, &cksum1); |
| 391 | if( zComment ){ |
| 392 | blob_zero(&comment); |
| 393 | blob_append(&comment, zComment, -1); |
| @@ -534,8 +537,17 @@ | |
| 534 | undo_reset(); |
| 535 | |
| 536 | /* Commit */ |
| 537 | db_end_transaction(0); |
| 538 | |
| 539 | /* Do an autosync push if requested */ |
| 540 | autosync(0); |
| 541 | } |
| 542 |
| --- src/checkin.c | |
| +++ src/checkin.c | |
| @@ -315,11 +315,11 @@ | |
| 315 | ** changed will be committed unless some subset of files is specified |
| 316 | ** on the command line. |
| 317 | */ |
| 318 | void commit_cmd(void){ |
| 319 | int rc; |
| 320 | int vid, nrid, nvid, wouldFork=0; |
| 321 | Blob comment; |
| 322 | const char *zComment; |
| 323 | Stmt q; |
| 324 | Stmt q2; |
| 325 | char *zUuid, *zDate; |
| @@ -335,11 +335,11 @@ | |
| 335 | |
| 336 | noSign = find_option("nosign","",0)!=0; |
| 337 | zComment = find_option("comment","m",1); |
| 338 | forceFlag = find_option("force", "r", 0)!=0; |
| 339 | db_must_be_within_tree(); |
| 340 | noSign = db_get_int("omit-sign", 0)|noSign; |
| 341 | verify_all_options(); |
| 342 | |
| 343 | /* |
| 344 | ** Autosync if requested. |
| 345 | */ |
| @@ -382,12 +382,15 @@ | |
| 382 | fossil_panic("file %s has not changed", blob_str(&unmodified)); |
| 383 | } |
| 384 | } |
| 385 | |
| 386 | vid = db_lget_int("checkout", 0); |
| 387 | if( db_exists("SELECT 1 FROM plink WHERE pid=%d", vid) ){ |
| 388 | wouldFork=1; |
| 389 | if( forceFlag==0 && db_get_int("safemerge", 0)==0 ){ |
| 390 | fossil_fatal("would fork. use -f or --force"); |
| 391 | } |
| 392 | } |
| 393 | vfile_aggregate_checksum_disk(vid, &cksum1); |
| 394 | if( zComment ){ |
| 395 | blob_zero(&comment); |
| 396 | blob_append(&comment, zComment, -1); |
| @@ -534,8 +537,17 @@ | |
| 537 | undo_reset(); |
| 538 | |
| 539 | /* Commit */ |
| 540 | db_end_transaction(0); |
| 541 | |
| 542 | if( wouldFork==0 ){ |
| 543 | /* Do an autosync push if requested. If wouldFork == 1, then they either |
| 544 | ** forced this commit or safe merge is on, and this commit did indeed |
| 545 | ** create a fork. In this case, we want the user to merge before sending |
| 546 | ** their new commit back to the rest of the world, so do not auto-push. |
| 547 | */ |
| 548 | autosync(0); |
| 549 | }else{ |
| 550 | printf("Warning: commit caused a fork to occur. Please merge and push\n"); |
| 551 | printf(" your changes as soon as possible.\n"); |
| 552 | } |
| 553 | } |
| 554 |
M
src/db.c
+12
-3
| --- src/db.c | ||
| +++ src/db.c | ||
| @@ -682,11 +682,11 @@ | ||
| 682 | 682 | void db_initial_setup (int makeInitialVersion, int makeServerCodes){ |
| 683 | 683 | char *zDate; |
| 684 | 684 | char *zUser; |
| 685 | 685 | Blob hash; |
| 686 | 686 | Blob manifest; |
| 687 | - | |
| 687 | + | |
| 688 | 688 | db_set("content-schema", CONTENT_SCHEMA); |
| 689 | 689 | db_set("aux-schema", AUX_SCHEMA); |
| 690 | 690 | if( makeServerCodes ){ |
| 691 | 691 | db_multi_exec( |
| 692 | 692 | "INSERT INTO config(name,value)" |
| @@ -694,10 +694,11 @@ | ||
| 694 | 694 | "INSERT INTO config(name,value)" |
| 695 | 695 | " VALUES('project-code', lower(hex(randomblob(20))));" |
| 696 | 696 | ); |
| 697 | 697 | } |
| 698 | 698 | db_set_int("autosync", 1); |
| 699 | + db_set_int("safemerge", 0); | |
| 699 | 700 | db_set_int("localauth", 0); |
| 700 | 701 | zUser = db_global_get("default-user", 0); |
| 701 | 702 | if( zUser==0 ){ |
| 702 | 703 | zUser = getenv("USER"); |
| 703 | 704 | } |
| @@ -918,10 +919,13 @@ | ||
| 918 | 919 | ** |
| 919 | 920 | ** editor Text editor command used for check-in comments. |
| 920 | 921 | ** |
| 921 | 922 | ** clear-sign Command used to clear-sign manifests at check-in. |
| 922 | 923 | ** The default is "gpg --clearsign -o ". |
| 924 | +** | |
| 925 | +** omit-sign When enabled, fossil will not attempt to sign any | |
| 926 | +** commit with gpg. All commits will be unsigned. | |
| 923 | 927 | */ |
| 924 | 928 | void cmd_config(void){ |
| 925 | 929 | db_open_config(); |
| 926 | 930 | if( g.argc>2 ){ |
| 927 | 931 | int i; |
| @@ -974,19 +978,24 @@ | ||
| 974 | 978 | ** |
| 975 | 979 | ** autosync If enabled, automatically pull prior to |
| 976 | 980 | ** commit or update and automatically push |
| 977 | 981 | ** after commit or tag or branch creation. |
| 978 | 982 | ** |
| 979 | -** localauth If true, require that HTTP connections from | |
| 983 | +** localauth If enabled, require that HTTP connections from | |
| 980 | 984 | ** 127.0.0.1 be authenticated by password. If |
| 981 | 985 | ** false, all HTTP requests from localhost have |
| 982 | 986 | ** unrestricted access to the repository. |
| 987 | +** | |
| 988 | +** safemerge If enabled, when commit will cause a fork, the | |
| 989 | +** commit will not abort with warning. Also update | |
| 990 | +** will not be allowed if local changes exist. | |
| 983 | 991 | */ |
| 984 | 992 | void setting_cmd(void){ |
| 985 | 993 | static const char *azName[] = { |
| 986 | 994 | "autosync", |
| 987 | - "localauth" | |
| 995 | + "localauth", | |
| 996 | + "safemerge", | |
| 988 | 997 | }; |
| 989 | 998 | int i; |
| 990 | 999 | db_find_and_open_repository(); |
| 991 | 1000 | if( g.argc==2 ){ |
| 992 | 1001 | for(i=0; i<sizeof(azName)/sizeof(azName[0]); i++){ |
| 993 | 1002 |
| --- src/db.c | |
| +++ src/db.c | |
| @@ -682,11 +682,11 @@ | |
| 682 | void db_initial_setup (int makeInitialVersion, int makeServerCodes){ |
| 683 | char *zDate; |
| 684 | char *zUser; |
| 685 | Blob hash; |
| 686 | Blob manifest; |
| 687 | |
| 688 | db_set("content-schema", CONTENT_SCHEMA); |
| 689 | db_set("aux-schema", AUX_SCHEMA); |
| 690 | if( makeServerCodes ){ |
| 691 | db_multi_exec( |
| 692 | "INSERT INTO config(name,value)" |
| @@ -694,10 +694,11 @@ | |
| 694 | "INSERT INTO config(name,value)" |
| 695 | " VALUES('project-code', lower(hex(randomblob(20))));" |
| 696 | ); |
| 697 | } |
| 698 | db_set_int("autosync", 1); |
| 699 | db_set_int("localauth", 0); |
| 700 | zUser = db_global_get("default-user", 0); |
| 701 | if( zUser==0 ){ |
| 702 | zUser = getenv("USER"); |
| 703 | } |
| @@ -918,10 +919,13 @@ | |
| 918 | ** |
| 919 | ** editor Text editor command used for check-in comments. |
| 920 | ** |
| 921 | ** clear-sign Command used to clear-sign manifests at check-in. |
| 922 | ** The default is "gpg --clearsign -o ". |
| 923 | */ |
| 924 | void cmd_config(void){ |
| 925 | db_open_config(); |
| 926 | if( g.argc>2 ){ |
| 927 | int i; |
| @@ -974,19 +978,24 @@ | |
| 974 | ** |
| 975 | ** autosync If enabled, automatically pull prior to |
| 976 | ** commit or update and automatically push |
| 977 | ** after commit or tag or branch creation. |
| 978 | ** |
| 979 | ** localauth If true, require that HTTP connections from |
| 980 | ** 127.0.0.1 be authenticated by password. If |
| 981 | ** false, all HTTP requests from localhost have |
| 982 | ** unrestricted access to the repository. |
| 983 | */ |
| 984 | void setting_cmd(void){ |
| 985 | static const char *azName[] = { |
| 986 | "autosync", |
| 987 | "localauth" |
| 988 | }; |
| 989 | int i; |
| 990 | db_find_and_open_repository(); |
| 991 | if( g.argc==2 ){ |
| 992 | for(i=0; i<sizeof(azName)/sizeof(azName[0]); i++){ |
| 993 |
| --- src/db.c | |
| +++ src/db.c | |
| @@ -682,11 +682,11 @@ | |
| 682 | void db_initial_setup (int makeInitialVersion, int makeServerCodes){ |
| 683 | char *zDate; |
| 684 | char *zUser; |
| 685 | Blob hash; |
| 686 | Blob manifest; |
| 687 | |
| 688 | db_set("content-schema", CONTENT_SCHEMA); |
| 689 | db_set("aux-schema", AUX_SCHEMA); |
| 690 | if( makeServerCodes ){ |
| 691 | db_multi_exec( |
| 692 | "INSERT INTO config(name,value)" |
| @@ -694,10 +694,11 @@ | |
| 694 | "INSERT INTO config(name,value)" |
| 695 | " VALUES('project-code', lower(hex(randomblob(20))));" |
| 696 | ); |
| 697 | } |
| 698 | db_set_int("autosync", 1); |
| 699 | db_set_int("safemerge", 0); |
| 700 | db_set_int("localauth", 0); |
| 701 | zUser = db_global_get("default-user", 0); |
| 702 | if( zUser==0 ){ |
| 703 | zUser = getenv("USER"); |
| 704 | } |
| @@ -918,10 +919,13 @@ | |
| 919 | ** |
| 920 | ** editor Text editor command used for check-in comments. |
| 921 | ** |
| 922 | ** clear-sign Command used to clear-sign manifests at check-in. |
| 923 | ** The default is "gpg --clearsign -o ". |
| 924 | ** |
| 925 | ** omit-sign When enabled, fossil will not attempt to sign any |
| 926 | ** commit with gpg. All commits will be unsigned. |
| 927 | */ |
| 928 | void cmd_config(void){ |
| 929 | db_open_config(); |
| 930 | if( g.argc>2 ){ |
| 931 | int i; |
| @@ -974,19 +978,24 @@ | |
| 978 | ** |
| 979 | ** autosync If enabled, automatically pull prior to |
| 980 | ** commit or update and automatically push |
| 981 | ** after commit or tag or branch creation. |
| 982 | ** |
| 983 | ** localauth If enabled, require that HTTP connections from |
| 984 | ** 127.0.0.1 be authenticated by password. If |
| 985 | ** false, all HTTP requests from localhost have |
| 986 | ** unrestricted access to the repository. |
| 987 | ** |
| 988 | ** safemerge If enabled, when commit will cause a fork, the |
| 989 | ** commit will not abort with warning. Also update |
| 990 | ** will not be allowed if local changes exist. |
| 991 | */ |
| 992 | void setting_cmd(void){ |
| 993 | static const char *azName[] = { |
| 994 | "autosync", |
| 995 | "localauth", |
| 996 | "safemerge", |
| 997 | }; |
| 998 | int i; |
| 999 | db_find_and_open_repository(); |
| 1000 | if( g.argc==2 ){ |
| 1001 | for(i=0; i<sizeof(azName)/sizeof(azName[0]); i++){ |
| 1002 |
+13
-3
| --- src/update.c | ||
| +++ src/update.c | ||
| @@ -65,10 +65,13 @@ | ||
| 65 | 65 | fossil_fatal("cannot find current version"); |
| 66 | 66 | } |
| 67 | 67 | if( db_exists("SELECT 1 FROM vmerge") ){ |
| 68 | 68 | fossil_fatal("cannot update an uncommitted merge"); |
| 69 | 69 | } |
| 70 | + if( unsaved_changes() && db_get_int("safemerge", 0) ){ | |
| 71 | + fossil_fatal("you have uncommitted changes and safemerge is enabled"); | |
| 72 | + } | |
| 70 | 73 | |
| 71 | 74 | if( g.argc==3 ){ |
| 72 | 75 | tid = name_to_rid(g.argv[2]); |
| 73 | 76 | if( tid==0 ){ |
| 74 | 77 | fossil_fatal("not a version: %s", g.argv[2]); |
| @@ -76,13 +79,20 @@ | ||
| 76 | 79 | if( !is_a_version(tid) ){ |
| 77 | 80 | fossil_fatal("not a version: %s", g.argv[2]); |
| 78 | 81 | } |
| 79 | 82 | } |
| 80 | 83 | |
| 81 | - /* Do an autosync pull prior to the update, if autosync is on */ | |
| 82 | - autosync(1); | |
| 83 | - | |
| 84 | + if( tid==0 ){ | |
| 85 | + /* | |
| 86 | + ** Do an autosync pull prior to the update, if autosync is on and they | |
| 87 | + ** did not want a specific version (i.e. another branch, a past revision). | |
| 88 | + ** By not giving a specific version, they are asking for the latest, thus | |
| 89 | + ** pull to get the latest, then update. | |
| 90 | + */ | |
| 91 | + autosync(1); | |
| 92 | + } | |
| 93 | + | |
| 84 | 94 | if( tid==0 ){ |
| 85 | 95 | compute_leaves(vid); |
| 86 | 96 | if( !latestFlag && db_int(0, "SELECT count(*) FROM leaves")>1 ){ |
| 87 | 97 | db_prepare(&q, |
| 88 | 98 | "%s " |
| 89 | 99 |
| --- src/update.c | |
| +++ src/update.c | |
| @@ -65,10 +65,13 @@ | |
| 65 | fossil_fatal("cannot find current version"); |
| 66 | } |
| 67 | if( db_exists("SELECT 1 FROM vmerge") ){ |
| 68 | fossil_fatal("cannot update an uncommitted merge"); |
| 69 | } |
| 70 | |
| 71 | if( g.argc==3 ){ |
| 72 | tid = name_to_rid(g.argv[2]); |
| 73 | if( tid==0 ){ |
| 74 | fossil_fatal("not a version: %s", g.argv[2]); |
| @@ -76,13 +79,20 @@ | |
| 76 | if( !is_a_version(tid) ){ |
| 77 | fossil_fatal("not a version: %s", g.argv[2]); |
| 78 | } |
| 79 | } |
| 80 | |
| 81 | /* Do an autosync pull prior to the update, if autosync is on */ |
| 82 | autosync(1); |
| 83 | |
| 84 | if( tid==0 ){ |
| 85 | compute_leaves(vid); |
| 86 | if( !latestFlag && db_int(0, "SELECT count(*) FROM leaves")>1 ){ |
| 87 | db_prepare(&q, |
| 88 | "%s " |
| 89 |
| --- src/update.c | |
| +++ src/update.c | |
| @@ -65,10 +65,13 @@ | |
| 65 | fossil_fatal("cannot find current version"); |
| 66 | } |
| 67 | if( db_exists("SELECT 1 FROM vmerge") ){ |
| 68 | fossil_fatal("cannot update an uncommitted merge"); |
| 69 | } |
| 70 | if( unsaved_changes() && db_get_int("safemerge", 0) ){ |
| 71 | fossil_fatal("you have uncommitted changes and safemerge is enabled"); |
| 72 | } |
| 73 | |
| 74 | if( g.argc==3 ){ |
| 75 | tid = name_to_rid(g.argv[2]); |
| 76 | if( tid==0 ){ |
| 77 | fossil_fatal("not a version: %s", g.argv[2]); |
| @@ -76,13 +79,20 @@ | |
| 79 | if( !is_a_version(tid) ){ |
| 80 | fossil_fatal("not a version: %s", g.argv[2]); |
| 81 | } |
| 82 | } |
| 83 | |
| 84 | if( tid==0 ){ |
| 85 | /* |
| 86 | ** Do an autosync pull prior to the update, if autosync is on and they |
| 87 | ** did not want a specific version (i.e. another branch, a past revision). |
| 88 | ** By not giving a specific version, they are asking for the latest, thus |
| 89 | ** pull to get the latest, then update. |
| 90 | */ |
| 91 | autosync(1); |
| 92 | } |
| 93 | |
| 94 | if( tid==0 ){ |
| 95 | compute_leaves(vid); |
| 96 | if( !latestFlag && db_int(0, "SELECT count(*) FROM leaves")>1 ){ |
| 97 | db_prepare(&q, |
| 98 | "%s " |
| 99 |