Names and IDs in Git
Systems that hold git repos, like github.com, or gitbox.a.o, each have their own way of
logging in and authenticating. For github.com, 2 factor authentication is required in order
to write to Apache repos - see
When "pushing" to github.com, you need to use a "Personal Access Token" when it asks for a password.
Set one up if needed, by logging into your github.com account, and clicking on your user picture
in the upper right corner -> Settings -> Developer settings -> Personal Access Tokens.
The name used for logging in is separate from the name used to identify each commit in
git. The credentials used to identify each commit are called your "identity" and are
the combination of a username and "email". These can be set globally for all repos
in your local machine, or locally, per repository.
Using multiple git identities
You may work with different organizations, and want to have different identities for each
repository, depending. You can do this; just use the local git configuration for the repo to
Recent GIT changes
June 2019: git 2.23 release - has new switch/restore
commands, to be used in place of git checkout; see
GIT vs SVN
Note in this table, that the various commands usually have many options (especially git)
which can change their behavior substantially. This table frequently is only showing
one of the main uses of the git commands. When in doubt, please google the command
git branch) to see all the other things a git command can do.
|Goal / Task
||svn checkout <url-of-a-branch>
git clone <repo-url>
git clone <repo-url> -branch <branch-name>
- making a working tree of the contents of some (usually remote) repository
- updating an existing working tree to the "head" level of the repository, to
catch up with any changes made by others.
Git has distributed repositories; to get a local working tree, you first need to have a local
clone of a (usually remote) repository.
The clone operation creates a full (all branches, tags, etc.) copy of the remote repository
onto the local machine.
Subsequently, the default branch (or a specific branch) is checked out into the working tree.
|update to current
Update makes the working tree have the same level as the remote.
SVN update may cause merging to occur, and merge conflicts which are resolved by hand.
git pull does this in a 2 step process:
- In step 1 it does a
git fetch which updates the part of the local git repo that
are tracking the remote, to matching the current data at the remote
(by default, it does this for all branches).
- In step 2, it does a
git merge which merges the remote-tracking branch(s) which changed with
any corresponding local branch(s).
This may result in merge conflicts which will need manual resolving.
If there are conflicting changes, then there are two options:
- stash the changes, pull, then apply the stash, then resolve conflicts
- commit the local changes, pull, resolve conflicts
SVN commit uploads changes from the working tree to the remote repo.
It fails if the remote repo's files are beyond the working-tree's checkout level;
in this case an svn update is needed first before the commit can be done.
- The update may create merge conflicts which will need to be resolved before the commit can happen.
A git commit commits the (staged) changes in the working tree to the local repository branch.
- Eclipse team plugin for git allows you to
stage any unstaged items before doing the commit.
git push transfer the changes from the local repository up to the
the remote one, provided that those changes can be done using fast-forward.
Otherwise, like SVN, this operation fails. Fix this the same way, by doing a git pull
and addressing any merge issues.
- Note that protected branches (such as master) cannot be "pushed" to. Instead, you must create a
"pull request" and then later merge that pull request with the protected branch.
The local repo can be configured to talk to any number of other local or remote repositories
to sync with them.
However, most of the time, it is only configured to sync with a single canonical remote repo,
e.g. on GitHub.
||svn copy <url>/trunk <url>/tags/<tag-name>
||git tag <tag-name>
Tags are first-class citizens in git and represent a state of the repository.
In SVN, tags are just another folder and a manifestation of a folder naming convention.
||svn copy <url>/trunk <url>/branches/<branch-namel>
||git branch <branch-name>
||Creating a branch does not "switch" the current checkout to the branch. See switch.
||svn switch <url>
||git switch <branch>
SVN switch updates the local working tree (or portions of it) to some remote repo spot.
git switch is at the granularity of a branch.
The working tree and the git "index" of to-be-committed things are updated to match the new branch.
switch command is a refactoring of the git checkout command; see
Switch updates the local checkout to a different branch, preserving any changes not yet checked (maybe showing conflict editor), and changing where a commit will go with the same SVN repo.
git switch replaces the checkout tree (except for untracked things) with the branch/tag/revision.
If this would lose data (because you have uncommitted changes), the checkout is not done (error msg).
|reset back to prev commit
git reset --hard hash-of-commit
git push -f origin branch-name
|The "-f" is needed to move the remote HEAD backwards. This method is only used when no one has cloned the branch-name. Typical use: when
a release:prepare has been done which needs to be rolled back.
|remove a tag
|| use tortiseSVN tool
git tag to list the tags
git tag -d uimaj-x.y.z to remove the tag locally
git push origin :refs/tags/uimaj-x.y.z to remove the tag remotely
|If you have a failed release:prepare and want to roll back, you can use this to delete the tag.
|relocate (when the URL of the remote repo has changed)
||svn relocate <from-url> <to-url>
||git remote set-url origin <remote-url>
The git remote set-url associates a remote with a name, such as origin, which
by convention is used by default for many operations involving remotes.
|change the commit message
||svn propset, eclipse: in team history view
||git commit amend - changes the last commit message
In SVN, it is easy to update the properties (commit messages) of any past commit.
In git, this is possible but intentionally difficult.
The version history in git is covered by cryptographic hashes.
In order for the distributed version control to work well,
it is essential that the hashes are consistent across all clones of the repositories.
If they are not, manual intervention is necessary.
Rewriting the commit message is fine, as long as the commit is only to your private
local repo. But it will cause problems if it has been "published" (that is, pushed to a
remote repo, where others might have downloaded it). Because of this,
it is highly discouraged to re-write git histories and only possible using a "force push".
For this reason, shared branches such as the "master" branch or maintenance branches
are usually "protected", meaning that force-pushes are rejected.
But since it is not uncommon that things need to be rewritten,
it is usually accepted that people force-push changes into feature branches they work on.
But it should still be avoided, in particular if there are others
contributing to the same feature branch.
|submitting a patch
Create a Jira issue
attach that diff to Jira issue
Create a Jira issue
Create a branch following naming convention:
commit any changes for the patch to that branch
push the branch to remote
create a pull request via GitHub site
wait for the CI (Continuous Integration) process to
finish any checking/testing of the pull request
ask for a review (if you are not a committer)
make changes (if needed) and repeat review
merge the pull request (or ask a committer to do it)
With the SVN-based infrastructure that is in place at te ASF, diffs need to be handled manually.
I.e. contributors need to create them,
committers need to apply them, review them, run test builds,
and the process repeats if changes need to be made.
In GitHub contributions are made through pull requests;
these are required (vs just doing git push) when the branch being pushed to is
marked as "protected". By convention, the release branches and tags, and the "master" are
marked this way. This is changed/managed by filing a Jira issue with INFRA.
While working on a feature or bug fix in a separate branch, simple pushes can be used.
A pull request provides the ability to
discuss changes in pull requests, perform reviews, and run automated checks.
The ASF Jenkins is already set up to automatically monitor pull requests
and to run automated checks on them. For security reasons,
pull requests from non-committers are not built automatically but must be triggered by a committer
by posting a comment such as "Jenkins, can you test this please."
to the discussion thread of the pull request on the GitHub website.