# git
## intro
`git` is a mature, actively maintained open source project originally developed in 2005 by Linus Torvalds, the famous creator of the Linux operating system kernel. A staggering number of software projects rely on `git` for version control, including commercial projects as well as open source. Developers who have worked with `git` are well represented in the pool of available software development talent and it works well on a wide range of operating systems and IDEs (Integrated Development Environments).
Having a distributed architecture, `git` is an example of a DVCS (hence Distributed Version Control System). Rather than have only one single place for the full version history of the software as is common in once-popular version control systems like CVS or Subversion (also known as SVN), in `git`, every developer's working copy of the code is also a repository that can contain the full history of all changes.
In addition to being distributed,`git` has been designed with performance, security and flexibility in mind.

It's probably best to read [git - the simple guide](https://rogerdudler.github.io/git-guide/) as git can be used by professionals as a very deep and complex tool, as well as novices using just commands like `git add .`, `git commit`, `git clone`, `git pull`, `git push` .
A repository can look like this the (commits are circles, the arrows point to important branches in the sequence of commits)

A `branch` simply is a *ordering* of commits. So checking out a `branch` simply means all your files will change to this *odering* of commits the `ref` holds.
**example:** ffmpeg (software for video encoding, transcoding, decoding)

**example**: relion


</p>
if you `git clone https://github.com/3dem/relion` you will get the full repo, including all the older and beta branches. Feel free to play around. Nothing is changed, as in `git` there is no single point of truth - everybody hold their own complete copy of the repo.
As a single contributor to a repo, generally the `git diff` is extremely useful:

---
## start a repository
git init
This command creates an empty Git repository - basically a .git directory with subdirectories for objects, refs/heads, refs/tags, and template files. An initial HEAD file that references the HEAD of the master branch is also created.
In order to begin tracking a new file, you use the command `git add`. To begin tracking the `README` file, you can run this:
`$ git add README`
If you run your status command again, you can see that your `README` file is now tracked and staged to be committed:
```git status```
On branch master
Your branch is up-to-date with 'origin/master'.
Changes to be committed: (use "git reset HEAD <file>..." to unstage) new file: README`
You can tell that it’s staged because it’s under the “Changes to be committed” heading. If you commit at this point, the version of the file at the time you ran `git add` is what will be in the subsequent historical snapshot. You may recall that when you ran `git init` earlier, you then ran `git add <files>` — that was to begin tracking files in your directory. The `git add` command takes a path name for either a file or a directory; if it’s a directory, the command adds all the files in that directory recursively
---
## show tree of commits
git log --oneline --decorate --all --graph

---
## glossary
**commit**
As a noun: A single point in the Git history; the entire history of a project is represented as a set of interrelated commits. The word "commit" is often used by Git in the same places other revision control systems use the words "revision" or "version". Also used as a short hand for [commit object](https://git-scm.com/docs/gitglossary#def_commit_object).As a verb: The action of storing a new snapshot of the project’s state in the Git history, by creating a new commit representing the current state of the [index](https://git-scm.com/docs/gitglossary#def_index) and advancing [HEAD](https://git-scm.com/docs/gitglossary#def_HEAD) to point at the new commit.
**branch**
A "branch" is an active line of development. The most recent [commit](https://git-scm.com/docs/gitglossary#def_commit) on a branch is referred to as the tip of that branch. The tip of the branch is referenced by a branch [head](https://git-scm.com/docs/gitglossary#def_head), which moves forward as additional development is done on the branch. A single Git [repository](https://git-scm.com/docs/gitglossary#def_repository) can track an arbitrary number of branches, but your [working tree](https://git-scm.com/docs/gitglossary#def_working_tree) is associated with just one of them (the "current" or "checked out" branch), and [HEAD](https://git-scm.com/docs/gitglossary#def_HEAD) points to that branch.
**HEAD**
The current [branch](https://git-scm.com/docs/gitglossary#def_branch). In more detail: Your [working tree](https://git-scm.com/docs/gitglossary#def_working_tree) is normally derived from the state of the tree referred to by HEAD. HEAD is a reference to one of the [heads](https://git-scm.com/docs/gitglossary#def_head) in your repository, except when using a [detached HEAD](https://git-scm.com/docs/gitglossary#def_detached_HEAD), in which case it directly references an arbitrary commit.
**origin**
The default upstream [repository](https://git-scm.com/docs/gitglossary#def_repository). Most projects have at least one upstream project which they track. By default ***origin*** is used for that purpose. New upstream updates will be fetched into [remote-tracking branches](https://git-scm.com/docs/gitglossary#def_remote_tracking_branch) named origin/name-of-upstream-branch, which you can see using `git branch -r`.
**pull**
Pulling a [branch](https://git-scm.com/docs/gitglossary#def_branch) means to [fetch](https://git-scm.com/docs/gitglossary#def_fetch) it and [merge](https://git-scm.com/docs/gitglossary#def_merge) it. See also [git-pull[1]](https://git-scm.com/docs/git-pull).
**push**
Pushing a [branch](https://git-scm.com/docs/gitglossary#def_branch) means to get the branch’s [head ref](https://git-scm.com/docs/gitglossary#def_head_ref) from a remote [repository](https://git-scm.com/docs/gitglossary#def_repository), find out if it is an ancestor to the branch’s local head ref, and in that case, putting all objects, which are [reachable](https://git-scm.com/docs/gitglossary#def_reachable) from the local head ref, and which are missing from the remote repository, into the remote [object database](https://git-scm.com/docs/gitglossary#def_object_database), and updating the remote head ref. If the remote [head](https://git-scm.com/docs/gitglossary#def_head) is not an ancestor to the local head, the push fails.
**rebase**
To reapply a series of changes from a [branch](https://git-scm.com/docs/gitglossary#def_branch) to a different base, and reset the [head](https://git-scm.com/docs/gitglossary#def_head) of that branch to the result.
**ref**
A name that begins with `refs/` (e.g. `refs/heads/master`) that points to an [object name](https://git-scm.com/docs/gitglossary#def_object_name) or another ref (the latter is called a [symbolic ref](https://git-scm.com/docs/gitglossary#def_symref)). For convenience, a ref can sometimes be abbreviated when used as an argument to a Git command; see [gitrevisions[7]](https://git-scm.com/docs/gitrevisions) for details. Refs are stored in the [repository](https://git-scm.com/docs/gitglossary#def_repository).The ref namespace is hierarchical. Different subhierarchies are used for different purposes (e.g. the `refs/heads/` hierarchy is used to represent local branches).There are a few special-purpose refs that do not begin with `refs/`. The most notable example is `HEAD`.
---
## more
does some viz to help understand, generally amazing.
[git-school/visualizing-git](https://github.com/git-school/visualizing-git)