Fossil SCM

Assorted minor improvements to the gitusers doc.

wyoung 2020-11-02 08:52 trunk
Commit 52bf1c0c34766ac7dc312d3be7ca942be9eaab6a7d3a61d65883a23cd916519b
1 file changed +56 -35
+56 -35
--- www/gitusers.md
+++ www/gitusers.md
@@ -17,11 +17,11 @@
1717
only pidgin Git, who may often have questions of the form, “Now how do I
1818
do X in Git again?”
1919
2020
This document’s authors are intimately familiar with Fossil, so it is
2121
difficult for us to anticipate the perspective of people who are
22
-initimately familiar with Git. If you have a lot of prior Git
22
+intimately familiar with Git. If you have a lot of prior Git
2323
experience, we welcome your contributions and questions on the [Fossil
2424
Forum][ffor].
2525
2626
While we do try to explain Fossil-specific terminology inline here
2727
as-needed, you may find it helpful to skim [the Fossil glossary][gloss].
@@ -132,11 +132,11 @@
132132
and do without the subdirectory scheme, for example.
133133
134134
135135
#### <a id="close" name="dotfile"></a> Closing A Check-Out
136136
137
-The [`fossil close`][close] command dissaociates a check-out directory from the
137
+The [`fossil close`][close] command dissociates a check-out directory from the
138138
Fossil repository database, nondestructively inverting [`fossil open`][open]. It
139139
won’t remove the managed files, and unless you give the `--force`
140140
option, it won’t let you close the check-out with uncommitted changes to
141141
those managed files.
142142
@@ -286,14 +286,14 @@
286286
287287
Fossil parses a huge amount of information out of commits that allow it
288288
to produce its [timeline CLI][tlc] and [its `/timeline` web view][tlw]
289289
using indexed SQL lookups, which generally have the info you would have
290290
to manually extract from `git log`, produced much more quickly than Git
291
-can, all else being equal: [SQLite’s B-tree data structures][btree]
291
+can, all else being equal: operations over [SQLite’s B-tree data structures][btree]
292292
generally run in O(log n) time, faster than O(n) for equal *n* when the
293293
constants are equal. Yet the constants are *not* equal because Fossil
294
-reads read from a single disk file rather than visit potentially many
294
+reads from a single disk file rather than visit potentially many
295295
files in sequence as Git must, so the OS’s buffer cache can result in
296296
[still better performance][35pct].
297297
298298
Unlike Git’s log, Fossil’s timeline shows info across branches by
299299
default, a feature for maintaining better situational awareness. The
@@ -329,12 +329,12 @@
329329
output with `git log --name-status`.
330330
331331
332332
#### <a id="whatchanged"></a> What Changed?
333333
334
-A related command is `git whatchanged`, which gives results similar to
335
-`git log --raw`.
334
+A related — though deprecated — command is `git whatchanged`, which gives results similar to
335
+`git log --raw`, so we cover it here.
336336
337337
Though there is no `fossil whatchanged` command, the same sort of
338338
information is available. For example, to pull the current changes from
339339
the remote repository and then inspect them before updating the local
340340
working directory, you might say this in Git:
@@ -346,11 +346,13 @@
346346
347347
fossil pull
348348
fossil up -n
349349
fossil diff --from tip
350350
351
-To invert the direction of the `diff`, say instead:
351
+To invert the `diff` to show a more natural patch, the command needs to
352
+be a bit more complicated, since you can’t currently give `--to`
353
+without `--from`.
352354
353355
fossil diff --from current --to tip
354356
355357
Rather than use the “dry run” form of [the `update` command][up], you can
356358
say:
@@ -402,11 +404,11 @@
402404
403405
alias f=fossil
404406
f tim d c
405407
406408
Granted, that’s rather obscure, but you you can also choose something
407
-intermediate like “`f time desc curr`”.
409
+intermediate like “`f time desc curr`”, which is reasonably clear.
408410
409411
[35pct]: https://www.sqlite.org/fasterthanfs.html
410412
[btree]: https://sqlite.org/btreemodule.html
411413
[gcn]: https://git-scm.com/docs/gitrevisions
412414
[infoc]: /help?cmd=info
@@ -450,10 +452,15 @@
450452
If you only want to commit _some_ of the changes, list the names
451453
of the files or directories you want to commit as arguments, like this:
452454
453455
fossil commit src/feature.c doc/feature.md examples/feature
454456
457
+There are currently no interactive patching features in Fossil like
458
+`git add --patch/-p` or `git commit -p`. [Contributions welcome!][ctrb]
459
+
460
+[ctrb]: https://fossil-scm.org/fossil/doc/trunk/www/contribute.wiki
461
+
455462
456463
<a id="bneed"></a>
457464
## Create Branches At Point Of Need, Rather Than Ahead of Need
458465
459466
Fossil prefers that you create new branches as part of the first commit
@@ -467,10 +474,14 @@
467474
adding commits to the tip of that branch.
468475
469476
To switch back to the parent branch, say something like:
470477
471478
fossil update trunk # ≅ git checkout master
479
+
480
+(There is also `fossil checkout trunk`, but it’s a 2nd-tier command
481
+meant for more specialized purposes. Almost always, you want to use
482
+`update` instead.)
472483
473484
Fossil does also support the Git style, creating the branch ahead of
474485
need:
475486
476487
fossil branch new my-new-branch
@@ -523,11 +534,11 @@
523534
2. It provides immediate off-machine backup of your commits. Unlike
524535
centralized version control, though, you can still work while
525536
disconnected; your changes will sync up with the remote once you get
526537
back online.
527538
528
-3. Because there is little distinction betwen the clones in the Fossil
539
+3. Because there is little distinction between the clones in the Fossil
529540
model — unlike in Git, where clones often quickly diverge from each
530541
other, quite possibly on purpose — the backup advantage applies in inverse
531542
as well: if the remote server falls over dead, one of those with a
532543
clone of that repository can stand it back up, and everyone can get
533544
back to work simply by re-pointing their local repo at the new
@@ -554,11 +565,11 @@
554565
Furthermore, branch *names* sync automatically in Fossil, not just the
555566
content of those branches. That means this common Git command:
556567
557568
git push origin master
558569
559
-is simply this in Fossil:
570
+…is simply this in Fossil:
560571
561572
fossil push
562573
563574
Fossil doesn’t need to be told what to push or where to push it: it just
564575
keeps using the same remote server URL you gave it last
@@ -628,12 +639,12 @@
628639
…gives much the same output as
629640
630641
fossil diff --checkin COMMIT_ID
631642
632643
…only without the patch email header. Git comes out of the [LKML] world,
633
-where emailing a patch is a normal thing to do. Fossil is designed for
634
-[more cohesive teams][devorg] where such drive-by patches are rarer.
644
+where emailing a patch is a normal thing to do. Fossil is [designed for
645
+cohesive teams][devorg] where such drive-by patches are rarer.
635646
636647
You can use any of [Fossil’s special check-in names][scin] in place of
637648
the `COMMIT_ID` in this and later examples. Fossil docs usually say
638649
“`VERSION`” or “`NAME`” where this is allowed, since the version string
639650
or name might not refer to a commit ID, but instead to a forum post, a
@@ -653,16 +664,16 @@
653664
654665
…is
655666
656667
fossil time -n 1 COMMIT_ID
657668
658
-…or with a shorter, more obvious command with more verbose output:
669
+…or with a shorter, more obvious command, though with more verbose output:
659670
660671
fossil info COMMIT_ID
661672
662673
The `fossil info` command isn’t otherwise a good equivalent to
663
-`git show`. It just overlaps its functionality in some areas. Much of
674
+`git show`; it just overlaps its functionality in some areas. Much of
664675
what’s missing is present in the corresponding [`/info` web
665676
view][infow], though.
666677
667678
668679
#### <a name="dstat"></a> Diff Statistics
@@ -691,16 +702,18 @@
691702
in mind if you plan on [mirroring your Fossil repository to GitHub][mirgh].
692703
693704
Fossil does not require tag and branch names to be unique. It is
694705
common, for example, to put a "`release`" tag on every release for a
695706
Fossil-hosted project. This does not create a conflict in Fossil, since
696
-Fossil resolves such conflicts in a predictable way: the newest match
707
+Fossil resolves the ambiguity in a predictable way: the newest match
697708
wins. Therefore, “`fossil up release`” always gets you the current
698709
release in a project that uses this tagging convention.
699710
700711
[The `fossil git export` command][fge] squashes repeated tags down to a
701
-single instance to avoid confusing Git, exporting only the newest tag.
712
+single instance to avoid confusing Git, exporting only the newest tag,
713
+emulating Fossil’s own ambiguity resolution rule as best it can within
714
+Git’s limitations.
702715
703716
[fge]: /help?cmd=git
704717
[gcrf]: https://git-scm.com/docs/git-check-ref-format
705718
706719
@@ -756,22 +769,22 @@
756769
A common thing to need to do in a version control system is to check out
757770
a version by date. Perhaps this is because your customer gave you a
758771
vague bug report — “I think it broke on a Wednesday… Yes, there was a
759772
full moon, and the Dodgers were playing in Boston…” — or perhaps you’re
760773
poking semi-randomly through history to find a “good” version to set up
761
-a [`bisect`][bis] operation.
774
+the start point of a [`bisect`][bis] operation.
762775
763776
Because Git doesn’t maintain comprehensive lookup tables into its log —
764777
[as detailed above](#log) — you will find pages online recommending
765
-horrorshow commands like this:
778
+horror-show commands like this:
766779
767780
git checkout $(git rev-list -n 1 --first-parent --before="2020-04-12" master)
768781
769782
That’s [the top answer on Stack Overflow][gcod] for the first hit on
770783
“git checkout by date” in the web search engine I used.
771784
772
-We believe you get such answers for requests for help with Git in part
785
+We believe you get such answers to Git help requests in part
773786
because of its lack of an always-up-to-date index into its log and in
774787
part because of its “small tools loosely joined” design philosophy. This
775788
sort of command is therefore composed piece by piece:
776789
777790
<center>◆  ◆  ◆</center>
@@ -822,16 +835,21 @@
822835
823836
And too bad if you’re a Windows user who doesn’t want to use [Git
824837
Bash][gbash], since neither of the stock OS command shells have a
825838
command interpolation feature needed to run that horrid command.
826839
827
-(By the way, if you think the bit about “a commit from 2019-12-15” in my
840
+By the way, congratulations, you just created a [detached head][gdh]
841
+along with all of its attendant risks. There’s no such state in Fossil
842
+due to its robust commit history indexing.
843
+
844
+If you think the bit about “a commit from 2019-12-15” in my
828845
little story above is made up, try `git rev-parse master@{2020-04-12}`
829
-on [Git’s own repository][gitgh]: it gives [this commit][grpgh]! Oddly,
830
-GitHub shows the date we asked for, unlike the `git show` command above.
831
-It’s success, of a sort, though it leaves us wondering why there’s a
832
-discrepancy.)
846
+on [Git’s own repository][gitgh]: it gives [this commit][grpgh]! Though
847
+GitHub shows the date we asked for, the `git show` command above gives
848
+the confusing result referenced in the story.
849
+This fixup within GitHub is success, of a sort, though it leaves us wondering why there’s a
850
+discrepancy.
833851
834852
But hark! The same Stack Overflow answer gives a much simpler
835853
alternative based on Git’s [`rev-parse` feature][grp]:
836854
837855
git checkout master@{2020-04-12}
@@ -846,12 +864,13 @@
846864
this, it happily gave me a commit from 2019-07-19 until I nuked the
847865
repository and re-cloned, after which it at least warned me that the
848866
reflog didn’t go back that far… But it still gave me an answer: a wrong
849867
one!
850868
851
-Why? Because Git lacks comprehensive up-to-date indices into its log.
852
-When I nuked my clone and re-cloned, I also nuked my stale reflog, so my
869
+Why? Because Git lacks comprehensive up-to-date indices into its log,
870
+and my clone was stale.
871
+When I nuked my stale clone and re-cloned, my
853872
command above started giving me today’s latest commit, that being as far
854873
back in history as it could dig. Who wants this behavior?
855874
856875
Well, at least it works on Windows! That’s something!
857876
@@ -866,10 +885,11 @@
866885
…and the commit will *always* be the one closest to the 12th of April, 2020, no matter
867886
whether it’s a fresh clone or a stale one, praise be Ritchie!
868887
869888
[gbash]: https://appuals.com/what-is-git-bash/
870889
[gcod]: https://stackoverflow.com/a/6990682/142454
890
+[gdh]: https://www.git-tower.com/learn/git/faq/detached-head-when-checkout-commit/
871891
[gitgh]: https://github.com/git/git/
872892
[grp]: https://git-scm.com/docs/git-rev-parse
873893
[grpgh]: https://github.com/git/git/commit/a99bc27aec74071aa1
874894
[reflog]: https://git-scm.com/docs/git-reflog
875895
@@ -909,20 +929,20 @@
909929
910930
ssh my-nas.local 'git init --bare /SHARES/dayjob/repo.git'
911931
git push --all ssh://my-nas.local//SHARES/dayjob/repo.git
912932
913933
Realize that this is carefully optimized down to these two long
914
-commands. In practice, typing these commands by hand, from memory, we’d
915
-expect a normal user to need to give four or more commands here instead.
934
+commands. In practice, we’d expect a user typing these commands by hand from memory
935
+to need to give four or more commands here instead.
916936
Packing the “`git init`” call into the “`ssh`” call is something more
917937
often done in scripts and documentation examples than done interactively,
918938
which then necessitates a third command before the push, “`exit`”.
919939
There’s also a good chance that you’ll forget the need for the `--bare`
920940
option here to avoid a fatal complaint from Git that the laptop can’t
921941
push into a non-empty repo. If you fall into this trap, among the many
922942
that Git lays for newbies, you have to nuke the incorrectly initted
923
-repo, search the web and docs to find out about `--bare`, and try again.
943
+repo, search the web or Git man pages to find out about `--bare`, and try again.
924944
925945
Having navigated that little minefield,
926946
we can tell Git that there is a second origin, a “home” repo in
927947
addition to the named “work” repo we set up earlier:
928948
@@ -930,11 +950,11 @@
930950
git config master.remote home
931951
932952
We don’t have to push or pull because the remote repo is a complete
933953
clone of the repo on the laptop at this point, so we can just get to
934954
work now, committing along the way to get our work safely off-machine
935
-and onto the NAS, like so:
955
+and onto our home NAS, like so:
936956
937957
git add
938958
git commit
939959
git push
940960
@@ -954,17 +974,18 @@
954974
that when returning home, you’d have to manually reset the upstream
955975
again.
956976
957977
This example also shows a consequence of that fact that
958978
[Git doesn’t sync branch names](#syncall): you have to keep repeating
959
-yourself, “master, master.”
979
+yourself like an obsequious supplicant: “Master, master.” Didn’t we
980
+invent computers to serve humans, rather than the other way around?
960981
961982
962983
#### Fossil Method
963984
964
-Now we’re going to do the same thing as above using Fossil. We’ve broken
965
-the commands up into blocks corresponding to those above for comparison.
985
+Now we’re going to do the same thing using Fossil, with
986
+the commands arranged in blocks corresponding to those above for comparison.
966987
967988
We start the same way, cloning the work repo down to the laptop:
968989
969990
fossil clone https://dev-server.example.com/repo
970991
cd repo
@@ -972,19 +993,19 @@
972993
973994
We’ve chosen the new “`fossil clone URI`” syntax added in Fossil 2.14 rather than separate
974995
`clone` and `open` commands to make the parallel with Git clearer. [See
975996
above](#mwd) for more on that topic.
976997
977
-Fossil’s equivalent [`remote` command][rem] is longer than the Git equivalent because
998
+Our [`remote` command][rem] is longer than the Git equivalent because
978999
Fossil currently has no short command
9791000
to rename an existing remote. Worse, unlike with Git, we can’t just keep
9801001
using the default remote name because Fossil uses that slot in its
9811002
configuration database to store the *current* remote name, so on
9821003
switching from work to home, the home URL will overwrite the work URL if
9831004
we don’t give it an explicit name first.
9841005
985
-So far, the Fossil commands are longer, but keep these costs in perspective:
1006
+Although the Fossil commands are longer, so far, keep it in perspective:
9861007
they’re one-time setup costs,
9871008
easily amortized to insignificance by the shorter day-to-day commands
9881009
below.
9891010
9901011
On first beginning to work from home, we reverse-clone the Fossil repo
9911012
--- www/gitusers.md
+++ www/gitusers.md
@@ -17,11 +17,11 @@
17 only pidgin Git, who may often have questions of the form, “Now how do I
18 do X in Git again?”
19
20 This document’s authors are intimately familiar with Fossil, so it is
21 difficult for us to anticipate the perspective of people who are
22 initimately familiar with Git. If you have a lot of prior Git
23 experience, we welcome your contributions and questions on the [Fossil
24 Forum][ffor].
25
26 While we do try to explain Fossil-specific terminology inline here
27 as-needed, you may find it helpful to skim [the Fossil glossary][gloss].
@@ -132,11 +132,11 @@
132 and do without the subdirectory scheme, for example.
133
134
135 #### <a id="close" name="dotfile"></a> Closing A Check-Out
136
137 The [`fossil close`][close] command dissaociates a check-out directory from the
138 Fossil repository database, nondestructively inverting [`fossil open`][open]. It
139 won’t remove the managed files, and unless you give the `--force`
140 option, it won’t let you close the check-out with uncommitted changes to
141 those managed files.
142
@@ -286,14 +286,14 @@
286
287 Fossil parses a huge amount of information out of commits that allow it
288 to produce its [timeline CLI][tlc] and [its `/timeline` web view][tlw]
289 using indexed SQL lookups, which generally have the info you would have
290 to manually extract from `git log`, produced much more quickly than Git
291 can, all else being equal: [SQLite’s B-tree data structures][btree]
292 generally run in O(log n) time, faster than O(n) for equal *n* when the
293 constants are equal. Yet the constants are *not* equal because Fossil
294 reads read from a single disk file rather than visit potentially many
295 files in sequence as Git must, so the OS’s buffer cache can result in
296 [still better performance][35pct].
297
298 Unlike Git’s log, Fossil’s timeline shows info across branches by
299 default, a feature for maintaining better situational awareness. The
@@ -329,12 +329,12 @@
329 output with `git log --name-status`.
330
331
332 #### <a id="whatchanged"></a> What Changed?
333
334 A related command is `git whatchanged`, which gives results similar to
335 `git log --raw`.
336
337 Though there is no `fossil whatchanged` command, the same sort of
338 information is available. For example, to pull the current changes from
339 the remote repository and then inspect them before updating the local
340 working directory, you might say this in Git:
@@ -346,11 +346,13 @@
346
347 fossil pull
348 fossil up -n
349 fossil diff --from tip
350
351 To invert the direction of the `diff`, say instead:
 
 
352
353 fossil diff --from current --to tip
354
355 Rather than use the “dry run” form of [the `update` command][up], you can
356 say:
@@ -402,11 +404,11 @@
402
403 alias f=fossil
404 f tim d c
405
406 Granted, that’s rather obscure, but you you can also choose something
407 intermediate like “`f time desc curr`”.
408
409 [35pct]: https://www.sqlite.org/fasterthanfs.html
410 [btree]: https://sqlite.org/btreemodule.html
411 [gcn]: https://git-scm.com/docs/gitrevisions
412 [infoc]: /help?cmd=info
@@ -450,10 +452,15 @@
450 If you only want to commit _some_ of the changes, list the names
451 of the files or directories you want to commit as arguments, like this:
452
453 fossil commit src/feature.c doc/feature.md examples/feature
454
 
 
 
 
 
455
456 <a id="bneed"></a>
457 ## Create Branches At Point Of Need, Rather Than Ahead of Need
458
459 Fossil prefers that you create new branches as part of the first commit
@@ -467,10 +474,14 @@
467 adding commits to the tip of that branch.
468
469 To switch back to the parent branch, say something like:
470
471 fossil update trunk # ≅ git checkout master
 
 
 
 
472
473 Fossil does also support the Git style, creating the branch ahead of
474 need:
475
476 fossil branch new my-new-branch
@@ -523,11 +534,11 @@
523 2. It provides immediate off-machine backup of your commits. Unlike
524 centralized version control, though, you can still work while
525 disconnected; your changes will sync up with the remote once you get
526 back online.
527
528 3. Because there is little distinction betwen the clones in the Fossil
529 model — unlike in Git, where clones often quickly diverge from each
530 other, quite possibly on purpose — the backup advantage applies in inverse
531 as well: if the remote server falls over dead, one of those with a
532 clone of that repository can stand it back up, and everyone can get
533 back to work simply by re-pointing their local repo at the new
@@ -554,11 +565,11 @@
554 Furthermore, branch *names* sync automatically in Fossil, not just the
555 content of those branches. That means this common Git command:
556
557 git push origin master
558
559 is simply this in Fossil:
560
561 fossil push
562
563 Fossil doesn’t need to be told what to push or where to push it: it just
564 keeps using the same remote server URL you gave it last
@@ -628,12 +639,12 @@
628 …gives much the same output as
629
630 fossil diff --checkin COMMIT_ID
631
632 …only without the patch email header. Git comes out of the [LKML] world,
633 where emailing a patch is a normal thing to do. Fossil is designed for
634 [more cohesive teams][devorg] where such drive-by patches are rarer.
635
636 You can use any of [Fossil’s special check-in names][scin] in place of
637 the `COMMIT_ID` in this and later examples. Fossil docs usually say
638 “`VERSION`” or “`NAME`” where this is allowed, since the version string
639 or name might not refer to a commit ID, but instead to a forum post, a
@@ -653,16 +664,16 @@
653
654 …is
655
656 fossil time -n 1 COMMIT_ID
657
658 …or with a shorter, more obvious command with more verbose output:
659
660 fossil info COMMIT_ID
661
662 The `fossil info` command isn’t otherwise a good equivalent to
663 `git show`. It just overlaps its functionality in some areas. Much of
664 what’s missing is present in the corresponding [`/info` web
665 view][infow], though.
666
667
668 #### <a name="dstat"></a> Diff Statistics
@@ -691,16 +702,18 @@
691 in mind if you plan on [mirroring your Fossil repository to GitHub][mirgh].
692
693 Fossil does not require tag and branch names to be unique. It is
694 common, for example, to put a "`release`" tag on every release for a
695 Fossil-hosted project. This does not create a conflict in Fossil, since
696 Fossil resolves such conflicts in a predictable way: the newest match
697 wins. Therefore, “`fossil up release`” always gets you the current
698 release in a project that uses this tagging convention.
699
700 [The `fossil git export` command][fge] squashes repeated tags down to a
701 single instance to avoid confusing Git, exporting only the newest tag.
 
 
702
703 [fge]: /help?cmd=git
704 [gcrf]: https://git-scm.com/docs/git-check-ref-format
705
706
@@ -756,22 +769,22 @@
756 A common thing to need to do in a version control system is to check out
757 a version by date. Perhaps this is because your customer gave you a
758 vague bug report — “I think it broke on a Wednesday… Yes, there was a
759 full moon, and the Dodgers were playing in Boston…” — or perhaps you’re
760 poking semi-randomly through history to find a “good” version to set up
761 a [`bisect`][bis] operation.
762
763 Because Git doesn’t maintain comprehensive lookup tables into its log —
764 [as detailed above](#log) — you will find pages online recommending
765 horrorshow commands like this:
766
767 git checkout $(git rev-list -n 1 --first-parent --before="2020-04-12" master)
768
769 That’s [the top answer on Stack Overflow][gcod] for the first hit on
770 “git checkout by date” in the web search engine I used.
771
772 We believe you get such answers for requests for help with Git in part
773 because of its lack of an always-up-to-date index into its log and in
774 part because of its “small tools loosely joined” design philosophy. This
775 sort of command is therefore composed piece by piece:
776
777 <center>◆  ◆  ◆</center>
@@ -822,16 +835,21 @@
822
823 And too bad if you’re a Windows user who doesn’t want to use [Git
824 Bash][gbash], since neither of the stock OS command shells have a
825 command interpolation feature needed to run that horrid command.
826
827 (By the way, if you think the bit about “a commit from 2019-12-15” in my
 
 
 
 
828 little story above is made up, try `git rev-parse master@{2020-04-12}`
829 on [Git’s own repository][gitgh]: it gives [this commit][grpgh]! Oddly,
830 GitHub shows the date we asked for, unlike the `git show` command above.
831 It’s success, of a sort, though it leaves us wondering why there’s a
832 discrepancy.)
 
833
834 But hark! The same Stack Overflow answer gives a much simpler
835 alternative based on Git’s [`rev-parse` feature][grp]:
836
837 git checkout master@{2020-04-12}
@@ -846,12 +864,13 @@
846 this, it happily gave me a commit from 2019-07-19 until I nuked the
847 repository and re-cloned, after which it at least warned me that the
848 reflog didn’t go back that far… But it still gave me an answer: a wrong
849 one!
850
851 Why? Because Git lacks comprehensive up-to-date indices into its log.
852 When I nuked my clone and re-cloned, I also nuked my stale reflog, so my
 
853 command above started giving me today’s latest commit, that being as far
854 back in history as it could dig. Who wants this behavior?
855
856 Well, at least it works on Windows! That’s something!
857
@@ -866,10 +885,11 @@
866 …and the commit will *always* be the one closest to the 12th of April, 2020, no matter
867 whether it’s a fresh clone or a stale one, praise be Ritchie!
868
869 [gbash]: https://appuals.com/what-is-git-bash/
870 [gcod]: https://stackoverflow.com/a/6990682/142454
 
871 [gitgh]: https://github.com/git/git/
872 [grp]: https://git-scm.com/docs/git-rev-parse
873 [grpgh]: https://github.com/git/git/commit/a99bc27aec74071aa1
874 [reflog]: https://git-scm.com/docs/git-reflog
875
@@ -909,20 +929,20 @@
909
910 ssh my-nas.local 'git init --bare /SHARES/dayjob/repo.git'
911 git push --all ssh://my-nas.local//SHARES/dayjob/repo.git
912
913 Realize that this is carefully optimized down to these two long
914 commands. In practice, typing these commands by hand, from memory, we’d
915 expect a normal user to need to give four or more commands here instead.
916 Packing the “`git init`” call into the “`ssh`” call is something more
917 often done in scripts and documentation examples than done interactively,
918 which then necessitates a third command before the push, “`exit`”.
919 There’s also a good chance that you’ll forget the need for the `--bare`
920 option here to avoid a fatal complaint from Git that the laptop can’t
921 push into a non-empty repo. If you fall into this trap, among the many
922 that Git lays for newbies, you have to nuke the incorrectly initted
923 repo, search the web and docs to find out about `--bare`, and try again.
924
925 Having navigated that little minefield,
926 we can tell Git that there is a second origin, a “home” repo in
927 addition to the named “work” repo we set up earlier:
928
@@ -930,11 +950,11 @@
930 git config master.remote home
931
932 We don’t have to push or pull because the remote repo is a complete
933 clone of the repo on the laptop at this point, so we can just get to
934 work now, committing along the way to get our work safely off-machine
935 and onto the NAS, like so:
936
937 git add
938 git commit
939 git push
940
@@ -954,17 +974,18 @@
954 that when returning home, you’d have to manually reset the upstream
955 again.
956
957 This example also shows a consequence of that fact that
958 [Git doesn’t sync branch names](#syncall): you have to keep repeating
959 yourself, “master, master.”
 
960
961
962 #### Fossil Method
963
964 Now we’re going to do the same thing as above using Fossil. We’ve broken
965 the commands up into blocks corresponding to those above for comparison.
966
967 We start the same way, cloning the work repo down to the laptop:
968
969 fossil clone https://dev-server.example.com/repo
970 cd repo
@@ -972,19 +993,19 @@
972
973 We’ve chosen the new “`fossil clone URI`” syntax added in Fossil 2.14 rather than separate
974 `clone` and `open` commands to make the parallel with Git clearer. [See
975 above](#mwd) for more on that topic.
976
977 Fossil’s equivalent [`remote` command][rem] is longer than the Git equivalent because
978 Fossil currently has no short command
979 to rename an existing remote. Worse, unlike with Git, we can’t just keep
980 using the default remote name because Fossil uses that slot in its
981 configuration database to store the *current* remote name, so on
982 switching from work to home, the home URL will overwrite the work URL if
983 we don’t give it an explicit name first.
984
985 So far, the Fossil commands are longer, but keep these costs in perspective:
986 they’re one-time setup costs,
987 easily amortized to insignificance by the shorter day-to-day commands
988 below.
989
990 On first beginning to work from home, we reverse-clone the Fossil repo
991
--- www/gitusers.md
+++ www/gitusers.md
@@ -17,11 +17,11 @@
17 only pidgin Git, who may often have questions of the form, “Now how do I
18 do X in Git again?”
19
20 This document’s authors are intimately familiar with Fossil, so it is
21 difficult for us to anticipate the perspective of people who are
22 intimately familiar with Git. If you have a lot of prior Git
23 experience, we welcome your contributions and questions on the [Fossil
24 Forum][ffor].
25
26 While we do try to explain Fossil-specific terminology inline here
27 as-needed, you may find it helpful to skim [the Fossil glossary][gloss].
@@ -132,11 +132,11 @@
132 and do without the subdirectory scheme, for example.
133
134
135 #### <a id="close" name="dotfile"></a> Closing A Check-Out
136
137 The [`fossil close`][close] command dissociates a check-out directory from the
138 Fossil repository database, nondestructively inverting [`fossil open`][open]. It
139 won’t remove the managed files, and unless you give the `--force`
140 option, it won’t let you close the check-out with uncommitted changes to
141 those managed files.
142
@@ -286,14 +286,14 @@
286
287 Fossil parses a huge amount of information out of commits that allow it
288 to produce its [timeline CLI][tlc] and [its `/timeline` web view][tlw]
289 using indexed SQL lookups, which generally have the info you would have
290 to manually extract from `git log`, produced much more quickly than Git
291 can, all else being equal: operations over [SQLite’s B-tree data structures][btree]
292 generally run in O(log n) time, faster than O(n) for equal *n* when the
293 constants are equal. Yet the constants are *not* equal because Fossil
294 reads from a single disk file rather than visit potentially many
295 files in sequence as Git must, so the OS’s buffer cache can result in
296 [still better performance][35pct].
297
298 Unlike Git’s log, Fossil’s timeline shows info across branches by
299 default, a feature for maintaining better situational awareness. The
@@ -329,12 +329,12 @@
329 output with `git log --name-status`.
330
331
332 #### <a id="whatchanged"></a> What Changed?
333
334 A related — though deprecated — command is `git whatchanged`, which gives results similar to
335 `git log --raw`, so we cover it here.
336
337 Though there is no `fossil whatchanged` command, the same sort of
338 information is available. For example, to pull the current changes from
339 the remote repository and then inspect them before updating the local
340 working directory, you might say this in Git:
@@ -346,11 +346,13 @@
346
347 fossil pull
348 fossil up -n
349 fossil diff --from tip
350
351 To invert the `diff` to show a more natural patch, the command needs to
352 be a bit more complicated, since you can’t currently give `--to`
353 without `--from`.
354
355 fossil diff --from current --to tip
356
357 Rather than use the “dry run” form of [the `update` command][up], you can
358 say:
@@ -402,11 +404,11 @@
404
405 alias f=fossil
406 f tim d c
407
408 Granted, that’s rather obscure, but you you can also choose something
409 intermediate like “`f time desc curr`”, which is reasonably clear.
410
411 [35pct]: https://www.sqlite.org/fasterthanfs.html
412 [btree]: https://sqlite.org/btreemodule.html
413 [gcn]: https://git-scm.com/docs/gitrevisions
414 [infoc]: /help?cmd=info
@@ -450,10 +452,15 @@
452 If you only want to commit _some_ of the changes, list the names
453 of the files or directories you want to commit as arguments, like this:
454
455 fossil commit src/feature.c doc/feature.md examples/feature
456
457 There are currently no interactive patching features in Fossil like
458 `git add --patch/-p` or `git commit -p`. [Contributions welcome!][ctrb]
459
460 [ctrb]: https://fossil-scm.org/fossil/doc/trunk/www/contribute.wiki
461
462
463 <a id="bneed"></a>
464 ## Create Branches At Point Of Need, Rather Than Ahead of Need
465
466 Fossil prefers that you create new branches as part of the first commit
@@ -467,10 +474,14 @@
474 adding commits to the tip of that branch.
475
476 To switch back to the parent branch, say something like:
477
478 fossil update trunk # ≅ git checkout master
479
480 (There is also `fossil checkout trunk`, but it’s a 2nd-tier command
481 meant for more specialized purposes. Almost always, you want to use
482 `update` instead.)
483
484 Fossil does also support the Git style, creating the branch ahead of
485 need:
486
487 fossil branch new my-new-branch
@@ -523,11 +534,11 @@
534 2. It provides immediate off-machine backup of your commits. Unlike
535 centralized version control, though, you can still work while
536 disconnected; your changes will sync up with the remote once you get
537 back online.
538
539 3. Because there is little distinction between the clones in the Fossil
540 model — unlike in Git, where clones often quickly diverge from each
541 other, quite possibly on purpose — the backup advantage applies in inverse
542 as well: if the remote server falls over dead, one of those with a
543 clone of that repository can stand it back up, and everyone can get
544 back to work simply by re-pointing their local repo at the new
@@ -554,11 +565,11 @@
565 Furthermore, branch *names* sync automatically in Fossil, not just the
566 content of those branches. That means this common Git command:
567
568 git push origin master
569
570 …is simply this in Fossil:
571
572 fossil push
573
574 Fossil doesn’t need to be told what to push or where to push it: it just
575 keeps using the same remote server URL you gave it last
@@ -628,12 +639,12 @@
639 …gives much the same output as
640
641 fossil diff --checkin COMMIT_ID
642
643 …only without the patch email header. Git comes out of the [LKML] world,
644 where emailing a patch is a normal thing to do. Fossil is [designed for
645 cohesive teams][devorg] where such drive-by patches are rarer.
646
647 You can use any of [Fossil’s special check-in names][scin] in place of
648 the `COMMIT_ID` in this and later examples. Fossil docs usually say
649 “`VERSION`” or “`NAME`” where this is allowed, since the version string
650 or name might not refer to a commit ID, but instead to a forum post, a
@@ -653,16 +664,16 @@
664
665 …is
666
667 fossil time -n 1 COMMIT_ID
668
669 …or with a shorter, more obvious command, though with more verbose output:
670
671 fossil info COMMIT_ID
672
673 The `fossil info` command isn’t otherwise a good equivalent to
674 `git show`; it just overlaps its functionality in some areas. Much of
675 what’s missing is present in the corresponding [`/info` web
676 view][infow], though.
677
678
679 #### <a name="dstat"></a> Diff Statistics
@@ -691,16 +702,18 @@
702 in mind if you plan on [mirroring your Fossil repository to GitHub][mirgh].
703
704 Fossil does not require tag and branch names to be unique. It is
705 common, for example, to put a "`release`" tag on every release for a
706 Fossil-hosted project. This does not create a conflict in Fossil, since
707 Fossil resolves the ambiguity in a predictable way: the newest match
708 wins. Therefore, “`fossil up release`” always gets you the current
709 release in a project that uses this tagging convention.
710
711 [The `fossil git export` command][fge] squashes repeated tags down to a
712 single instance to avoid confusing Git, exporting only the newest tag,
713 emulating Fossil’s own ambiguity resolution rule as best it can within
714 Git’s limitations.
715
716 [fge]: /help?cmd=git
717 [gcrf]: https://git-scm.com/docs/git-check-ref-format
718
719
@@ -756,22 +769,22 @@
769 A common thing to need to do in a version control system is to check out
770 a version by date. Perhaps this is because your customer gave you a
771 vague bug report — “I think it broke on a Wednesday… Yes, there was a
772 full moon, and the Dodgers were playing in Boston…” — or perhaps you’re
773 poking semi-randomly through history to find a “good” version to set up
774 the start point of a [`bisect`][bis] operation.
775
776 Because Git doesn’t maintain comprehensive lookup tables into its log —
777 [as detailed above](#log) — you will find pages online recommending
778 horror-show commands like this:
779
780 git checkout $(git rev-list -n 1 --first-parent --before="2020-04-12" master)
781
782 That’s [the top answer on Stack Overflow][gcod] for the first hit on
783 “git checkout by date” in the web search engine I used.
784
785 We believe you get such answers to Git help requests in part
786 because of its lack of an always-up-to-date index into its log and in
787 part because of its “small tools loosely joined” design philosophy. This
788 sort of command is therefore composed piece by piece:
789
790 <center>◆  ◆  ◆</center>
@@ -822,16 +835,21 @@
835
836 And too bad if you’re a Windows user who doesn’t want to use [Git
837 Bash][gbash], since neither of the stock OS command shells have a
838 command interpolation feature needed to run that horrid command.
839
840 By the way, congratulations, you just created a [detached head][gdh]
841 along with all of its attendant risks. There’s no such state in Fossil
842 due to its robust commit history indexing.
843
844 If you think the bit about “a commit from 2019-12-15” in my
845 little story above is made up, try `git rev-parse master@{2020-04-12}`
846 on [Git’s own repository][gitgh]: it gives [this commit][grpgh]! Though
847 GitHub shows the date we asked for, the `git show` command above gives
848 the confusing result referenced in the story.
849 This fixup within GitHub is success, of a sort, though it leaves us wondering why there’s a
850 discrepancy.
851
852 But hark! The same Stack Overflow answer gives a much simpler
853 alternative based on Git’s [`rev-parse` feature][grp]:
854
855 git checkout master@{2020-04-12}
@@ -846,12 +864,13 @@
864 this, it happily gave me a commit from 2019-07-19 until I nuked the
865 repository and re-cloned, after which it at least warned me that the
866 reflog didn’t go back that far… But it still gave me an answer: a wrong
867 one!
868
869 Why? Because Git lacks comprehensive up-to-date indices into its log,
870 and my clone was stale.
871 When I nuked my stale clone and re-cloned, my
872 command above started giving me today’s latest commit, that being as far
873 back in history as it could dig. Who wants this behavior?
874
875 Well, at least it works on Windows! That’s something!
876
@@ -866,10 +885,11 @@
885 …and the commit will *always* be the one closest to the 12th of April, 2020, no matter
886 whether it’s a fresh clone or a stale one, praise be Ritchie!
887
888 [gbash]: https://appuals.com/what-is-git-bash/
889 [gcod]: https://stackoverflow.com/a/6990682/142454
890 [gdh]: https://www.git-tower.com/learn/git/faq/detached-head-when-checkout-commit/
891 [gitgh]: https://github.com/git/git/
892 [grp]: https://git-scm.com/docs/git-rev-parse
893 [grpgh]: https://github.com/git/git/commit/a99bc27aec74071aa1
894 [reflog]: https://git-scm.com/docs/git-reflog
895
@@ -909,20 +929,20 @@
929
930 ssh my-nas.local 'git init --bare /SHARES/dayjob/repo.git'
931 git push --all ssh://my-nas.local//SHARES/dayjob/repo.git
932
933 Realize that this is carefully optimized down to these two long
934 commands. In practice, we’d expect a user typing these commands by hand from memory
935 to need to give four or more commands here instead.
936 Packing the “`git init`” call into the “`ssh`” call is something more
937 often done in scripts and documentation examples than done interactively,
938 which then necessitates a third command before the push, “`exit`”.
939 There’s also a good chance that you’ll forget the need for the `--bare`
940 option here to avoid a fatal complaint from Git that the laptop can’t
941 push into a non-empty repo. If you fall into this trap, among the many
942 that Git lays for newbies, you have to nuke the incorrectly initted
943 repo, search the web or Git man pages to find out about `--bare`, and try again.
944
945 Having navigated that little minefield,
946 we can tell Git that there is a second origin, a “home” repo in
947 addition to the named “work” repo we set up earlier:
948
@@ -930,11 +950,11 @@
950 git config master.remote home
951
952 We don’t have to push or pull because the remote repo is a complete
953 clone of the repo on the laptop at this point, so we can just get to
954 work now, committing along the way to get our work safely off-machine
955 and onto our home NAS, like so:
956
957 git add
958 git commit
959 git push
960
@@ -954,17 +974,18 @@
974 that when returning home, you’d have to manually reset the upstream
975 again.
976
977 This example also shows a consequence of that fact that
978 [Git doesn’t sync branch names](#syncall): you have to keep repeating
979 yourself like an obsequious supplicant: “Master, master.” Didn’t we
980 invent computers to serve humans, rather than the other way around?
981
982
983 #### Fossil Method
984
985 Now we’re going to do the same thing using Fossil, with
986 the commands arranged in blocks corresponding to those above for comparison.
987
988 We start the same way, cloning the work repo down to the laptop:
989
990 fossil clone https://dev-server.example.com/repo
991 cd repo
@@ -972,19 +993,19 @@
993
994 We’ve chosen the new “`fossil clone URI`” syntax added in Fossil 2.14 rather than separate
995 `clone` and `open` commands to make the parallel with Git clearer. [See
996 above](#mwd) for more on that topic.
997
998 Our [`remote` command][rem] is longer than the Git equivalent because
999 Fossil currently has no short command
1000 to rename an existing remote. Worse, unlike with Git, we can’t just keep
1001 using the default remote name because Fossil uses that slot in its
1002 configuration database to store the *current* remote name, so on
1003 switching from work to home, the home URL will overwrite the work URL if
1004 we don’t give it an explicit name first.
1005
1006 Although the Fossil commands are longer, so far, keep it in perspective:
1007 they’re one-time setup costs,
1008 easily amortized to insignificance by the shorter day-to-day commands
1009 below.
1010
1011 On first beginning to work from home, we reverse-clone the Fossil repo
1012

Keyboard Shortcuts

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