Skip to content

Commit

Permalink
Minor edits.
Browse files Browse the repository at this point in the history
  • Loading branch information
blynn committed Mar 26, 2010
1 parent f392970 commit 839f7e0
Show file tree
Hide file tree
Showing 8 changed files with 109 additions and 83 deletions.
3 changes: 2 additions & 1 deletion book.css
Expand Up @@ -13,7 +13,8 @@ pre {
}

ul li p {
margin-bottom:0;
margin: 0;
padding: 0;
}

/* Based on http://phrogz.net/CSS/columns3.html */
Expand Down
6 changes: 3 additions & 3 deletions en/basic.txt
Expand Up @@ -23,7 +23,7 @@ To save the state again:

=== Add, Delete, Rename ===

The above will only keep track of the files that were present when you first ran *git add*. If you add new files or subdirectories, you'll have to tell Git:
The above only keeps track of the files that were present when you first ran *git add*. If you add new files or subdirectories, you'll have to tell Git:

$ git add readme.txt Documentation

Expand Down Expand Up @@ -164,7 +164,7 @@ and your users can upgrade their version by changing to the directory containing

$ git pull

Your users will never end up with a version of your script you don't want them to see. Obviously this trick works for anything, not just scripts.
Your users will never end up with a version of your script you don't want them to see.

=== What Have I Done? ===

Expand Down Expand Up @@ -193,7 +193,7 @@ fire up any web browser.

=== Exercise ===

Let A, B, C, D be four successive commits where B is the same as A except some files have been removed. We want to add the files back at D and not at B. How can we do this?
Let A, B, C, D be four successive commits where B is the same as A except some files have been removed. We want to add the files back at D. How can we do this?

There are at least three solutions. Assuming we are at D:

Expand Down
30 changes: 15 additions & 15 deletions en/branch.txt
Expand Up @@ -82,7 +82,7 @@ Then once you've fixed the bug:

and resume work on your original task.

You can even merge in the bugfix you just made, either by typing:
You can even 'merge' in the bugfix you just made, either by typing:

$ git merge fixes

Expand All @@ -94,38 +94,38 @@ since you have already pushed the bugfix to the main repository.

=== Merging ===

With many version control systems, creating branches is easy but merging them
With some version control systems, creating branches is easy but merging them
back together is tough. With Git, merging is so trivial that you might be
unaware of it happening.

Indeed, though we have just introduced *git merge*, we encountered merging long ago. The *pull* command in fact fetches commits and then merges them into your current branch. If you have no local changes, then the merge is a 'fast forward', a degenerate case akin to fetching the latest version in a centralized version control system. But if you do have local changes, Git will automatically merge, and report any conflicts.

Ordinarily, a commit has exactly one parent, namely, the previous commit.
Merging other branches creates a commit with at least two parents. This begs
the question: what commit does `HEAD~10` really refer to? A commit could have
multiple parents, so which one do we follow?
Ordinarily, a commit has exactly one 'parent commit', namely, the previous
commit. Merging branches together produces a commit with at least two parents.
This begs the question: what commit does `HEAD~10` really refer to? A commit
could have multiple parents, so which one do we follow?

It turns out we follow the first parent at every step. This is usually desired,
because commits in the current branch always become first parents in a *git
merge*; frequently you're only concerned with the changes you made in the
It turns out this notation chooses the first parent every time. This is
desirable because commits in the current branch become the first parents during
a merge; frequently you're only concerned with the changes you made in the
current branch, as opposed to changes merged in from other branches.

You can refer to a specific parent with a caret. For example, to show
the logs from the second parent:

$ git log HEAD^2

If you want the first parent, you can leave out the number. For example, to
show the differences with the first parent:
You may omit the number for the first parent. For example, to show the
differences with the first parent:

$ git diff HEAD^

You can combine this notation with other types. For example:

$ git checkout 1bd6^^2~10 -b ancient
$ git checkout 1b6d^^2~10 -b ancient

starts a new branch ``ancient'' representing the state 10 commits back from the
second parent of the first parent of the commit starting with 1bd6.
second parent of the first parent of the commit starting with 1b6d.

=== Uninterrupted Workflow ===

Expand Down Expand Up @@ -230,14 +230,14 @@ You can have multiple stashes, and manipulate them in various ways. See
=== Work How You Want ===

You might wonder if branches are worth the bother. After all, clones are almost
as fast, and you can use *cd* to switch between them, instead of esoteric Git
as fast, and you can switch between them with *cd* instead of esoteric Git
commands.

Consider web browsers. Why support multiple tabs as well as multiple windows?
Because allowing both accommodates a wide variety of styles. Some users like to
keep only one browser window open, and use tabs for multiple webpages. Others
might insist on the other extreme: multiple windows with no extra tabs anywhere.
Yet others prefer something in between.
Others still prefer something in between.

Branching is like tabs for your working directory, and cloning is like opening
a new browser window. These operations are fast and local, so why not
Expand Down
53 changes: 38 additions & 15 deletions en/clone.txt
Expand Up @@ -2,11 +2,11 @@

In older version control systems, checkout is the standard operation to get files. You retrieve a bunch of files in the requested saved state.

In Git and other distributed version control systems, cloning is the standard operation. To get files you create a clone of the entire repository. In other words, you practically mirror the central server. Anything the main repository can do, you can do.
In Git and other distributed version control systems, cloning is the standard operation. To get files, you create a 'clone' of the entire repository. In other words, you practically mirror the central server. Anything the main repository can do, you can do.

=== Sync Computers ===

This is the reason I first used Git. I can tolerate making tarballs or using *rsync* for backups and basic syncing. But sometimes I edit on my laptop, other times on my desktop, and the two may not have talked to each other in between.
I can tolerate making tarballs or using *rsync* for backups and basic syncing. But sometimes I edit on my laptop, other times on my desktop, and the two may not have talked to each other in between. This situation drove me to learn Git in the first place.

Initialize a Git repository and commit your files on one machine. Then on the other:

Expand All @@ -17,7 +17,7 @@ to create a second copy of the files and Git repository. From now on,
$ git commit -a
$ git pull other.computer:/path/to/files HEAD

will pull in the state of the files on the other computer into the one you're working on. If you've recently made conflicting edits in the same file, Git will let you know and you should commit again after resolving them.
will 'pull' in the state of the files on the other computer into the one you're working on. If you've recently made conflicting edits in the same file, Git will let you know and you should commit again after resolving them.

=== Classic Source Control ===

Expand All @@ -27,38 +27,61 @@ Initialize a Git repository for your files:
$ git add .
$ git commit -m "Initial commit"

On the central server, initialize an empty Git repository with some name,
and start the Git daemon if necessary:
On the central server, initialize a 'bare repository' in some directory:

$ GIT_DIR=proj.git git init
$ git daemon --detach # it might already be running
$ mkdir proj.git
$ cd proj.git
$ git init --bare
$ # one-liner alternative: GIT_DIR=proj.git git init

Start the Git daemon if necessary:

$ git daemon --detach # it may already be running

For Git hosting services, follow the instructions to setup the initially
empty Git repository. Typically one fills in a form on a webpage.

Push your project to the central server with:
'Push' your project to the central server with:

$ git push git://central.server/path/to/proj.git HEAD

The central server now holds a 'bare repository': a repository with no working directory. In other words, the central server has the history of your project, but never contains a snapshot of it. To check out the source, a developer types:
The bare repository is so named because it contains no working directory and exposes files that are hidden away in the `.git` subdirectory of a normal Git repository. In other words, the central server maintains the history of your project, and never carries a snapshot of any given version.

To check out the source, a developer types:

$ git clone git://central.server/path/to/proj.git

After making changes, the code is checked in to the main server by:
After making changes, the developer saves changes locally:

$ git commit -a
$ git push

If the main server has been updated, the latest version needs to be checked out before the push. To sync to the latest version:
To update to the latest version:

$ git commit -a
$ git pull

Any merge conflicts should be resolved then committed:

$ git commit -a

To check in local changes into the central repository:

$ git push

If the main server has new changes due to activity by other developers, the
push fails, and the developer should pull the latest version, resolve any merge
conflicts, then try again.

=== Push versus pull ===

A push is more convenient than a pull in the above example. If we pulled from the server, we would have to login to the server first, and give the pull command the network address of the machine we're pulling from. Firewalls may interfere, and we might not even have shell access to the server.
A push is more convenient than a pull in the above example. Firstly, pull fails
on bare repositories (you must 'fetch' instead; we discuss this in a later
chapter). But even if we kept a normal repository on the central server,
pulling into it is still cumbersome. Each time, we would have to login to the
server first, and give the pull command the network address of the machine
we're pulling from. Firewalls may interfere, and we might not even have shell
access to the server.

However, we usually avoid pushing into a repository, because confusion can ensue if the destination has a working directory with changes. But since a bare repository by definition has no working directory, pushing to a bare repository is a straightforward operation.
However, apart from this case, we discourage pushing into a repository, because confusion can ensue when the destination has a working directory.

In short, while learning Git, only push when the target is a bare repository; otherwise pull.

Expand Down
18 changes: 10 additions & 8 deletions en/grandmaster.txt
Expand Up @@ -86,9 +86,9 @@ But how can you go back to the future? The past commits know nothing of the futu

If you have the SHA1 of the original HEAD then:

$ git reset 1bd6
$ git reset 1b6d

But suppose you never took it down? Don't worry, for commands like these, Git saves the original HEAD as a tag called ORIG_HEAD, and you can return safe and sound with:
But suppose you never took it down? Don't worry: for commands like these, Git saves the original HEAD as a tag called ORIG_HEAD, and you can return safe and sound with:

$ git reset ORIG_HEAD

Expand Down Expand Up @@ -161,7 +161,7 @@ One popular resident is +workdir/git-new-workdir+. Via clever symlinking, this s

$ git-new-workdir an/existing/repo new/directory

The new directory and files within can be thought of as a clone, except since the history is shared, the two trees automatically stay in sync. There's no need to merge, push or pull.
The new directory and the files within can be thought of as a clone, except since the history is shared, the two trees automatically stay in sync. There's no need to merge, push or pull.

=== Daring Stunts ===

Expand All @@ -177,7 +177,7 @@ On the other hand, if you specify particular paths for checkout, then there are

*Reset*: Reset also fails in the presence of uncommitted changes. To force it through, run:

$ git reset --hard 1bd6
$ git reset --hard 1b6d

*Branch*: Deleting branches fails if this causes changes to be lost. To force a deletion, type:

Expand All @@ -200,10 +200,10 @@ directories are expendable, then delete them mercilessly with:

Next time, that pesky command will work!

=== Improve Your Public Image ===
=== Preventing Bad Commits ===

Stupid mistakes abound in the histories of many of my projects. The most
frightening are missing files due to forgetting to run *git add*. Luckily I
frightening are missing files due to a forgotten *git add*. Luckily I
have yet to lose crucial data though accidental omission because I rarely
delete original working directories. I typically notice the error a few commits
later, so the only damage is a bit of missing history and a sheepish admission
Expand Down Expand Up @@ -238,5 +238,7 @@ Several git operations support hooks; see *git help hooks*. One can write hooks
to complain about spelling mistakes in commit messages, add new files, indent
paragraphs, append an entry to a webpage, play a sound, and so on.

We encountered the *post-update* hook earlier when discussing Git over
HTTP. This hook updates a few files Git needs for non-native communication.
We activated the sample *post-update* hook earlier when discussing Git over
HTTP; this causes Git to run this script whenever the head has moved. The
sample post-update script updates a few files Git needs for communication over
Git-agnostic transports such as HTTP.
23 changes: 11 additions & 12 deletions en/history.txt
Expand Up @@ -6,9 +6,6 @@ history which you alone possess. Just as nations forever argue over who
committed what atrocity, if someone else has a clone whose version of history
differs to yours, you will have trouble reconciling when your trees interact.

Of course, if you control all the other trees too, you can simply overwrite
them.

Some developers strongly feel history should be immutable, warts and all.
Others feel trees should be made presentable before they are unleashed in
public. Git accommodates both viewpoints. Like cloning, branching and merging,
Expand Down Expand Up @@ -44,20 +41,22 @@ Then:

- Remove commits by deleting lines.
- Reorder commits by reordering lines.
- Replace "pick" with "edit" to mark a commit for amending.
- Replace "pick" with "reword" to change the log message.
- Replace "pick" with "squash" to merge a commit with the previous one.
- Replace "pick" with "fixup" to merge a commit with the previous one and discard the log message.
- Replace `pick` with:
* `edit` to mark a commit for amending.
* `reword` to change the log message.
* `squash` to merge a commit with the previous one.
* `fixup` to merge a commit with the previous one and discard the log message.

If you marked a commit for editing, then run:
Save and quit. If you marked a commit for editing, then
run:

$ git commit --amend

Otherwise, run:

$ git rebase --continue

So commit early and commit often: you can easily tidy up later with rebase.
So commit early and commit often: you can tidy up later with rebase.

=== Local Changes Last ===

Expand Down Expand Up @@ -147,9 +146,9 @@ You can checkout the latest version of the project with:

$ git checkout master .

The *git fast-export* command converts any git repository to the
The *git fast-export* command converts any repository to the
*git fast-import* format, whose output you can study for writing exporters,
and also to transport git repositories in a human-readable format. Indeed,
and also to transport repositories in a human-readable format. Indeed,
these commands can send repositories of text files over text-only channels.

=== Where Did It All Go Wrong? ===
Expand All @@ -161,7 +160,7 @@ can pinpoint the problem:

$ git bisect start
$ git bisect bad HEAD
$ git bisect good 1bd6
$ git bisect good 1b6d

Git checks out a state halfway in between. Test the feature, and if it's still broken:

Expand Down

0 comments on commit 839f7e0

Please sign in to comment.