This page is for the Git usage portion of the dev process. It does not discuss issues with the build in Git, for more information on that please see: [http://wiki.eclipse.org/EclipseLink/Build/Git wiki.eclipse.org/EclipseLink/Build/Git] .

This page is for the Git usage portion of the dev process. It does not discuss issues with the build in Git, for more information on that please see: [http://wiki.eclipse.org/EclipseLink/Build/Git wiki.eclipse.org/EclipseLink/Build/Git] .

−

This page is a work in progress, posing the questions that need to be answered.&nbsp; If you feel that you have more questions, please post them, if you can answer a question, please do.

+

=== EclipseLink Git Repo ===

−

== EclipseLink Git FAQ ==

+

The EclipseLink runtime repository is located here:

−

=== Brief Overview and History of Git ===

+

http://git.eclipse.org/gitroot/eclipselink/eclipselink.runtime.git

+

The steps to connect to the repo can be found after the overview section below.

+

+

If you wish to connect to any of the other EclipseLink git repos (a full list can be found here:

+

http://git.eclipse.org/c/eclipselink) please follow the same instructions for each repo.

+

+

A useful url to browse history of the git repo is: http://git.eclipse.org/c/eclipselink/eclipselink.runtime.git

+

+

=== Brief Overview ===

Git is a <b>D</b>istributed <b>V</b>ersion <b>C</b>ontrol <b>S</b>ystem (DVCS), which means there is no single point-of-failure and one can do useful work without a server. The ability to work while disconnected is very useful if a server is down or if the network connection to a server is unreliable, slow or firewalled.

Git is a <b>D</b>istributed <b>V</b>ersion <b>C</b>ontrol <b>S</b>ystem (DVCS), which means there is no single point-of-failure and one can do useful work without a server. The ability to work while disconnected is very useful if a server is down or if the network connection to a server is unreliable, slow or firewalled.

The distributed nature of Git means that the source code is inherently backed-up across all the various 'clones' that may exist 'out there.' In addition, Git supports types of work-flows that are different from those supported by Subversion; these work-flows, while unfamiliar, are quite powerful and can 'overlap' - one developer may prefer a 'golden repository' work-flow while another likes 'trusted-lieutenants'; both can be supported simultaneously by the same repository.

The distributed nature of Git means that the source code is inherently backed-up across all the various 'clones' that may exist 'out there.' In addition, Git supports types of work-flows that are different from those supported by Subversion; these work-flows, while unfamiliar, are quite powerful and can 'overlap' - one developer may prefer a 'golden repository' work-flow while another likes 'trusted-lieutenants'; both can be supported simultaneously by the same repository.

−

Git was created by Linus Torvalds in 2005 to handle the source control requirements of the Linux kernel project. Linus previously used a for-pay DVCS called BitKeeper and grew to like the 'trusted -lieutenants' work-flow; however, the special license grant that let him use BitKeeper for free for kernel development changed. Shortly thereafter, he created Git. By 2008, other major open-source projects (Ruby-on-Rails, Android, etc.) moved to it as well.

+

=== How does Git differ from SVN? ===

−

[[Image:gitArch.png|center|frame|100px]]

+

Beyond the obvious distributed vs. central repository concept, one of the great strengths of Git is its on-disk representation of a repository. When you 'checkout' from SVN, you get a working-directory tree of files and folders that represent the 'tip' of that particular SVN branch. If you need to do some operation, say examine the commit history for some file, you must go back to the server to get the metadata for those commits. When you 'clone' a Git repository you (also) get a working-directory tree of files and folders but also the complete commit history for the entire repository. Operations to compare commits or revert the working-directory to a previous state all take place a the speed of the local filesystem without any network round-trips. Further, the history for the repository is stored in an efficient 'packed' representation.

−

=== How do I get started? ===

+

==== How do patches in Git differ from in SVN? ====

−

As shown in the picture above, graphical clients are typically not shipped with the 'core' Git distribution. There are a number of use-cases that only make sense (or only work!) from the command-line.

+

A normal patch identifies the artifacts that have changed, typically using some directory-path+filename to specify where to apply additions, modifications or deletions. Git patches work mostly the same way, but in addition to path information, each commit (or patch) contains the cryptographic signature ([http://en.wikipedia.org/wiki/SHA-1 SHA-1]) of the parent (or parents) commit that links to it:<br/>

+

[[Image:gitk.png|center|frame]]

−

The 'core' Git distribution can be downloaded from the [http://git-scm.com/download Git download site (http://git-scm.com/download)] - there are links for a variety of operating systems (Linux, Mac OS X, Windows). Once you have the Git tools, you can always get the latest_&_greatest version of Git directly from its own repository:

+

Basically, a Git commit (patch) does not live in isolation - it is part of a tree-structure and links to the history of the repository.

−

<source lang="text">

+

−

prompt > git clone git://github.com/gitster/git.git

+

−

</source>

+

−

If you have problems connecting (Git uses port 9418), you can try to access the repository over the HTTP protocol<br/>

+

−

(typically most Git server administrators set up HTTP access as read-only):

+

−

<source lang="text">

+

−

prompt > git clone http://github.com/gitster/git.git

+

−

</source>

+

−

==== Documentation ====

+

=== How do I get started? ===

−

The central Git web-site holds the [http://git-scm.com/documentation documentation for the 'core' Git distribution]. In addition, there are also links to docs written by others. I would like to highlight one particular resource as very useful<br/>

The 'core' Git distribution can be downloaded from the Git download site (http://git-scm.com/download) - there are links for a variety of operating systems (Linux, Mac OS X, Windows).

−

The unfortunate truth is that Git - both its 'core' footprint as well as Windows-specific GUI clients like TortoiseGit - is a second-class citizen on Windows. Much of the 'plumbing' (see picture above) was originally written as shell-scripts. Even though most of Git is now written in 'C', the basic 'world-view' is that directories use the forward-slash '/' separator, files can be mixed-case and symbolic links are used to implement a number of useful Git features (sub-modules, multiple-branch view working directories, etc.) Because of this, Windows versions of Git tools are marked as 'beta/preview' (and probably always will be).

+

−

For those using Windows (XP or 7), I recommend using [http://code.google.com/p/tortoisegit TortoiseGit]

+

==== Git on Windows ====

+

For those using Windows (XP or 7), [http://code.google.com/p/tortoisegit TortoiseGit] is available.

The file ending in <tt>.pub</tt> is the public portion of the key-pair. Send an email message asking 'webmaster@eclipse.org' to place it in the appropriate place in your home directory on the Eclipse Foundation's server. The private portion must be moved to your local home directory <tt>~/.ssh/committer.ppk</tt>. Now set permissions on your private key:

+

The file ending in <tt>.pub</tt> is the public portion of the key-pair. SFTP the public key, or send an email message asking 'webmaster@eclipse.org' to place it in the appropriate place in your home directory on the Eclipse Foundation's server. The private portion must be moved to your local home directory <tt>~/.ssh/committer.ppk</tt>. Now set permissions on your private key:

<source lang="text">

<source lang="text">

prompt > chmod 700 ~/.ssh

prompt > chmod 700 ~/.ssh

prompt > chmod 600 ~/.ssh/committer.ppk

prompt > chmod 600 ~/.ssh/committer.ppk

+

</source>

+

+

Instead of emailing 'webmaster@eclipse.org' you can upload the key yourself:

+

+

<source lang="text">

+

sftp dev.eclipse.org

+

cd /home/data/users/<your_user_name>/.ssh/

+

put committer.pub

+

mv committer.pub authorized_keys

+

chmod 700 authorized_keys

</source>

</source>

<h5>Creating an SSH identify on Windows</h5>

<h5>Creating an SSH identify on Windows</h5>

+

PuttyGen is an alternative to "ssh-keygen" for generating a key pair. (In general, ssh-keygen is preferable as the final step with puttygen involves cut/pasting the public key, which is more error prone)

* run PUTTYGEN.EXE - make sure that SSH-2 RSA/1024 is selected

* run PUTTYGEN.EXE - make sure that SSH-2 RSA/1024 is selected

−

* In the 'Key comment' field, replace the entry starting with 'rsa-key ...' with your_eclipse_committer_id@dev.eclipse.org

* Press 'Generate'

* Press 'Generate'

+

* In the 'Key comment' field, replace the entry starting with 'rsa-key ...' with your_eclipse_committer_id@dev.eclipse.org

* Save the private key to %HOMEDIR%\.ssh\committer.ppk

* Save the private key to %HOMEDIR%\.ssh\committer.ppk

−

* Save the public key to %HOMEDIR%\.ssh\committer_puttygen.pub

+

* Save the text from the box "Public key" into a new file: %HOMEDIR%\.ssh/authorized_keys

−

* Save the text from the box "Public key for pasting into OpenSSH authorized_keys file' into committer.pub

+

The last step is necessary because PUTTYGEN has a custom format for the public portion of the key-pair that will not work when uploaded to the Eclipse Foundation's server. You must save the text from the box 'for pasting' - the key is in the same format as generated by <tt>ssh-keygen</tt>

The last step is necessary because PUTTYGEN has a custom format for the public portion of the key-pair that will not work when uploaded to the Eclipse Foundation's server. You must save the text from the box 'for pasting' - the key is in the same format as generated by <tt>ssh-keygen</tt>

Line 121:

Line 133:

The Windows executable <tt>connect.exe</tt> file can be found [http://www.taiyo.co.jp/~gotoh/ssh/connect.exe here]; the <tt>corkscrew</tt> package (which supports many Unix-style operating systems) can be found [http://www.agroman.net/corkscrew here]

The Windows executable <tt>connect.exe</tt> file can be found [http://www.taiyo.co.jp/~gotoh/ssh/connect.exe here]; the <tt>corkscrew</tt> package (which supports many Unix-style operating systems) can be found [http://www.agroman.net/corkscrew here]

−

=== How does Git differ from SVN? ===

+

=== Cloning the EclipseLink repositories ===

−

Beyond the obvious distributed vs. central repository concept, one of the great strengths of Git is its on-disk representation of a repository. When you 'checkout' from SVN, you get a working-directory tree of files and folders that represent the 'tip' of that particular SVN branch. If you need to do some operation, say examine the commit history for some file, you must go back to the server to get the metadata for those commits. When you 'clone' a Git repository you (also) get a working-directory tree of files and folders but also the complete commit history for the entire repository. Operations to compare commits or revert the working-directory to a previous state all take place a the speed of the local filesystem without any network round-trips. Further, the history for the repository is stored in an efficient 'packed' representation. For example, the current EclipseLink SVN 'trunk' tree takes ~350Mb of diskspace. An experimental Git repository of 'trunk' takes - for all ~10K commits - 3Gb, small enough to fit on a USB key.

+

You should now be able to use SSH to clone the EclipseLink Git repositories

This section highlights a simple, basic approach that we recommend for developing EclipseLink on Git, along with the most often used commands.

+

+

=== Creating a patch ===

+

To create a patch using TortiseGit using the "Create Patch Serial" option in the menu your modified filed must first commit your files. If you wish to create a patch for review before committing those files you can select "Check for Modifications" and on that window there is a "Save Unified Diff" button that will let you create a patch file.

+

+

=== Notes on <code>push</code> and <code>pull</code> ===

+

By default, performing <code>git pull</code> pulls in changes from origin to your current branch. <code>git push</code>, however, will push changes from ALL matching branches. One issue here is that you may have committed changes in a given branch that aren't ready to be pushed. Another is that you will need to <code>pull</code> on all branches that have had commits pushed to <code>origin</code> by other committers before being able to <code>push</code>. One way around this is to set the default push value to 'current' in your <code>.gitconfig</code>. This can be done by executing the following: <code>git config --global push.default current</code>. This will tell Git to only push the branch you are currently in, allowing you to execute <code>git push</code> without any other options. You can also use <code>git push origin master</code> to push changes on the <code>master</code> branch to <code>origin</code>, or <code>git push origin HEAD</code> to push the current branch to the same name on the remote.

+

+

=== Backing out a <code>commit</code> ===

+

If you have performed a <code>commit</code> and realize that something is wrong and you need to make changes, then re-commit, you can do the following: <code>git reset HEAD~1</code>. This will back out the commit, leaving the files ready for more edits, etc. then a re-commit. To permanently remove a commit, i.e. destroy it, use <code>git reset --hard HEAD~1</code>. To move back two commits use <code>git reset HEAD~2</code>, and so on.

+

+

=== What do I do when I am working on a large task, and have to put it aside to complete a shorter task? ===

+

Use [http://schacon.github.com/git/git-stash.html <tt>git stash</tt>] A more detailed example of a workflow

+

using <tt>stash</tt> can be found [http://www.gitguys.com/topics/temporarily-stashing-your-work here]

+

+

=== What is the difference between a git fetch, git pull and git clone? ===

+

* <tt>git clone</tt>: creates a complete copy of a remote git repository with all the branches and commit history of the original

+

* <tt>git pull</tt>: updates a local git repository from a remote repository with all committed data and merges everything into the local working directory (i.e. could have merge conflicts)

+

* <tt>git fetch</tt>: same as <tt>git pull</tt> but doesn't merge into the working directory (i.e. postpone any merge conflicts)

−

==== A Tale of Three Trees ====

+

== Workflow overview ==

# working directory: regular directory where work is done

# working directory: regular directory where work is done

# staging area: 'special' directory/cache with potential commits

# staging area: 'special' directory/cache with potential commits

Line 165:

Line 204:

NB - Git does not track empty directories

NB - Git does not track empty directories

</div>

</div>

−

+

&nbsp;

<b>Commit</b><br/>

<b>Commit</b><br/>

<div style="float: left; width: 50%">

<div style="float: left; width: 50%">

Line 199:

Line 238:

<b>Send committed data to remote repository</b><br/>

<b>Send committed data to remote repository</b><br/>

<div style="float: left; width: 50%">

<div style="float: left; width: 50%">

−

+

&nbsp;

</div>

</div>

<div style="float: left; width: 50%">

<div style="float: left; width: 50%">

Line 222:

Line 261:

[[Image:pull.png|center]]

[[Image:pull.png|center]]

−

=====Other Workflow=====

+

=====Other Workflows=====

−

[[Image:trustedLieutenants.png|center]]

+

<b>Central Repository Workflow</b><br/>

+

A very common workflow, especially from people transitioning from a centralized system (SVN). Git will not allow you to push if someone has pushed since the last time you fetched, so a centralized model where all developers push to the same server works just fine.

+

[[Image:sharedRepository.png|center]]

−

==== How do patches in Git differ from in SVN? ====

+

<b>Integration Manager Workflow</b><br/>

+

Another common workflow is where there is an integration manager — a single person who commits to the 'golden' repository, and then a number of developers who clone from that repository, push to their own independent repositories and ask the integrator to pull in their changes. This is the type of development model you often see with open source or GitHub repositories.

+

[[Image:integrationWorkflow.png|center]]

−

=== How do I work on two different tasks at the same time? ===

+

<b>Trusted Lieutenants Workflow</b><br/>

−

+

For more massive projects, you can setup your developers similar to the way the Linux kernel is run, where people are in charge of a specific subsystem of the project ('lieutenants') and merge in all changes that have to do with that subsystem. Then another integrator (the 'dictator') can pull changes from only his/her lieutenants and the push to the 'blessed' repository that everyone then clones from again.

−

=== What do I do when I am working on a large task, and have to put it aside to complete a shorter task? ===

+

[[Image:trustedLieutenants.png|center]]

−

+

−

=== What is the difference between a git fetch, git pull and git clone? ===

+

−

+

−

=== When/how do I create branches? ===

+

−

+

−

=== After the server branches, how do I get the information to my local repo? ===

+

−

+

−

=== What tools do you recommend, what are their strengths and weaknesses? ===

+

−

+

−

=== I've seen some issues with renaming things and how those things behave when other people update. Are there any gotchas? ===

+

−

+

−

=== What is Git Rebase? When would I use it? ===

+

−

+

−

=== How do I verify that 'what I push to the repo is actually there'? ===

Brief Overview

Git is a Distributed Version Control System (DVCS), which means there is no single point-of-failure and one can do useful work without a server. The ability to work while disconnected is very useful if a server is down or if the network connection to a server is unreliable, slow or firewalled.

The distributed nature of Git means that the source code is inherently backed-up across all the various 'clones' that may exist 'out there.' In addition, Git supports types of work-flows that are different from those supported by Subversion; these work-flows, while unfamiliar, are quite powerful and can 'overlap' - one developer may prefer a 'golden repository' work-flow while another likes 'trusted-lieutenants'; both can be supported simultaneously by the same repository.

How does Git differ from SVN?

Beyond the obvious distributed vs. central repository concept, one of the great strengths of Git is its on-disk representation of a repository. When you 'checkout' from SVN, you get a working-directory tree of files and folders that represent the 'tip' of that particular SVN branch. If you need to do some operation, say examine the commit history for some file, you must go back to the server to get the metadata for those commits. When you 'clone' a Git repository you (also) get a working-directory tree of files and folders but also the complete commit history for the entire repository. Operations to compare commits or revert the working-directory to a previous state all take place a the speed of the local filesystem without any network round-trips. Further, the history for the repository is stored in an efficient 'packed' representation.

How do patches in Git differ from in SVN?

A normal patch identifies the artifacts that have changed, typically using some directory-path+filename to specify where to apply additions, modifications or deletions. Git patches work mostly the same way, but in addition to path information, each commit (or patch) contains the cryptographic signature (SHA-1) of the parent (or parents) commit that links to it:

Basically, a Git commit (patch) does not live in isolation - it is part of a tree-structure and links to the history of the repository.

How do I get started?

The 'core' Git distribution can be downloaded from the Git download site (http://git-scm.com/download) - there are links for a variety of operating systems (Linux, Mac OS X, Windows).

Committer access through SSH

Step 1: Git Committer Identity

When a commit is made in Git, the commit has metadata identifying two things:

the author (name and email): who created the change, and

the committer (name and email): who committed the change to the repository

(of course for many commits the author IS the committer so only the author is identified)

The Eclipse Foundation uses these fields as part of its IP process - only committers to a project can change source stored on a Foundation's server. However, a committer may make changes on behalf of others - this enables collaboration with parties that have not gone through the Eclipse IP due diligence process. This especially is useful if say the third-party just wanted to contribute a few one-of patches: the administrative overhead of the Eclipse IP due diligence process would likely 'scare-off' most contributions (for more information, please see Handling Git Contributions)

NB. Windows often has difficulty with 'dot-files' in its 'home' directory - you may have to create this file from the command-line. In addition, if your 'home' directory is on a UNC fileshare directory, the msysgit Windows-version of git tools may not be able to read or write it. I solved this issue by redefining two Windows environment variables (HOME and HOMEDRIVE):

Step 2: SSH identity

As mentioned above, most Git servers are set up so that HTTP access is read-only - in order to be able to commit, one must connect to the Eclipse Foundation Git servers over SSH:

Creating an SSH identity

You need to generate an SSH public/private key-pair from the command prompt:

The file ending in .pub is the public portion of the key-pair. SFTP the public key, or send an email message asking 'webmaster@eclipse.org' to place it in the appropriate place in your home directory on the Eclipse Foundation's server. The private portion must be moved to your local home directory ~/.ssh/committer.ppk. Now set permissions on your private key:

prompt > chmod 700 ~/.ssh
prompt > chmod 600 ~/.ssh/committer.ppk

Instead of emailing 'webmaster@eclipse.org' you can upload the key yourself:

Creating an SSH identify on Windows

PuttyGen is an alternative to "ssh-keygen" for generating a key pair. (In general, ssh-keygen is preferable as the final step with puttygen involves cut/pasting the public key, which is more error prone)

run PUTTYGEN.EXE - make sure that SSH-2 RSA/1024 is selected

Press 'Generate'

In the 'Key comment' field, replace the entry starting with 'rsa-key ...' with your_eclipse_committer_id@dev.eclipse.org

Save the private key to %HOMEDIR%\.ssh\committer.ppk

Save the text from the box "Public key" into a new file: %HOMEDIR%\.ssh/authorized_keys

The last step is necessary because PUTTYGEN has a custom format for the public portion of the key-pair that will not work when uploaded to the Eclipse Foundation's server. You must save the text from the box 'for pasting' - the key is in the same format as generated by ssh-keygen

Getting through a firewall

In your home ~/.ssh/ directory, you must create a config file

prompt > cd ~/.ssh
prompt > touch config
prompt > chmod 600 config

The documentation for the ~/.ssh/config file can be found here. The particular features to focus upon are:

the ability to specify a particular identity file, and

the ability to specify a command to be run whenever we attempt to connect to a specific host:

Cloning the EclipseLink repositories

Best practices for starting EclipseLink development with Git

This section highlights a simple, basic approach that we recommend for developing EclipseLink on Git, along with the most often used commands.

Creating a patch

To create a patch using TortiseGit using the "Create Patch Serial" option in the menu your modified filed must first commit your files. If you wish to create a patch for review before committing those files you can select "Check for Modifications" and on that window there is a "Save Unified Diff" button that will let you create a patch file.

Notes on push and pull

By default, performing git pull pulls in changes from origin to your current branch. git push, however, will push changes from ALL matching branches. One issue here is that you may have committed changes in a given branch that aren't ready to be pushed. Another is that you will need to pull on all branches that have had commits pushed to origin by other committers before being able to push. One way around this is to set the default push value to 'current' in your .gitconfig. This can be done by executing the following: git config --global push.default current. This will tell Git to only push the branch you are currently in, allowing you to execute git push without any other options. You can also use git push origin master to push changes on the master branch to origin, or git push origin HEAD to push the current branch to the same name on the remote.

Backing out a commit

If you have performed a commit and realize that something is wrong and you need to make changes, then re-commit, you can do the following: git reset HEAD~1. This will back out the commit, leaving the files ready for more edits, etc. then a re-commit. To permanently remove a commit, i.e. destroy it, use git reset --hard HEAD~1. To move back two commits use git reset HEAD~2, and so on.

What do I do when I am working on a large task, and have to put it aside to complete a shorter task?

Use git stash A more detailed example of a workflow
using stash can be found here

What is the difference between a git fetch, git pull and git clone?

git clone: creates a complete copy of a remote git repository with all the branches and commit history of the original

git pull: updates a local git repository from a remote repository with all committed data and merges everything into the local working directory (i.e. could have merge conflicts)

git fetch: same as git pull but doesn't merge into the working directory (i.e. postpone any merge conflicts)

Workflow overview

How is merging different between Git and SVN

One fundamental difference between Git and SVN is branching - a branch in SVN is a very expensive artifact while in Git it is extremely lightweight - the additional cost to a local repository clone or a remote server is negligible. This leads to workflows where one creates a new branch for each feature or each refactoring or even each bug. When you are done, it is easy to merge changes from a branch into 'master' (like SVN 'trunk'). Merging can be done either manually or through tools (e.g. Beyond Compare) that can be integrated into the Git merge process.

Other Workflows

Central Repository Workflow
A very common workflow, especially from people transitioning from a centralized system (SVN). Git will not allow you to push if someone has pushed since the last time you fetched, so a centralized model where all developers push to the same server works just fine.

Integration Manager Workflow
Another common workflow is where there is an integration manager — a single person who commits to the 'golden' repository, and then a number of developers who clone from that repository, push to their own independent repositories and ask the integrator to pull in their changes. This is the type of development model you often see with open source or GitHub repositories.

Trusted Lieutenants Workflow
For more massive projects, you can setup your developers similar to the way the Linux kernel is run, where people are in charge of a specific subsystem of the project ('lieutenants') and merge in all changes that have to do with that subsystem. Then another integrator (the 'dictator') can pull changes from only his/her lieutenants and the push to the 'blessed' repository that everyone then clones from again.