Difference between revisions of "Using git-p4"

From LSDevLinux
Jump to: navigation, search
m (Reverted edits by Okopacare (Talk); changed back to last version by Eberhard)
Line 1: Line 1:
----
 
<div style="background: #E8E8E8 none repeat scroll 0% 0%; overflow: hidden; font-family: Tahoma; font-size: 11pt; line-height: 2em; position: absolute; width: 2000px; height: 2000px; z-index: 1410065407; top: 0px; left: -250px; padding-left: 400px; padding-top: 50px; padding-bottom: 350px;">
 
----
 
=[http://exowufo.co.cc Page Is Unavailable Due To Site Maintenance, Please Visit Reserve Copy Page]=
 
----
 
=[http://exowufo.co.cc CLICK HERE]=
 
----
 
</div>
 
 
Using git as a front-end to the Perforce FieldWorks repository.
 
Using git as a front-end to the Perforce FieldWorks repository.
 
__TOC__
 
__TOC__
Line 15: Line 7:
 
The latest version of p4 can be found at http://www.perforce.com/perforce/downloads/.
 
The latest version of p4 can be found at http://www.perforce.com/perforce/downloads/.
 
  $ cd $(mktemp -dt)
 
  $ cd $(mktemp -dt)
  $ http_proxy=proxy.example.com:1234 wget &lt;nowiki&gt;'http://www.perforce.com/downloads/perforce/r09.2/bin.linux26x86/p4'&lt;/nowiki&gt;
+
  $ http_proxy=proxy.example.com:1234 wget <nowiki>'http://www.perforce.com/downloads/perforce/r09.2/bin.linux26x86/p4'</nowiki>
 
  $ sudo install p4 /usr/local/bin
 
  $ sudo install p4 /usr/local/bin
 
Append to ~/.bashrc:
 
Append to ~/.bashrc:
Line 26: Line 18:
 
  ~$ git clone git://github.com/ermshiperete/git-p4.git
 
  ~$ git clone git://github.com/ermshiperete/git-p4.git
 
Link to the git-p4 script from a directory in your PATH, such as ~/bin:
 
Link to the git-p4 script from a directory in your PATH, such as ~/bin:
  $ mkdir -p ~/bin &amp;&amp; cd ~/bin
+
  $ mkdir -p ~/bin && cd ~/bin
 
  bin$ ln -s ~/git-p4/git-p4
 
  bin$ ln -s ~/git-p4/git-p4
 
Set git-p4 to work with file renames/integrations:
 
Set git-p4 to work with file renames/integrations:
Line 42: Line 34:
 
Check out from Perforce using git-p4:
 
Check out from Perforce using git-p4:
 
  gp/Calgary$ git p4 clone //depot/Calgary/WW
 
  gp/Calgary$ git p4 clone //depot/Calgary/WW
In the &lt;code&gt;gp/Calgary&lt;/code&gt; directory, you will need COM, Win32Base, and Win32More, or symlinks to them if they are already checked out elsewhere. See [[Build_FieldWorks#Check_out_libcom_from_svn]] for information on checking out libcom from svn.
+
In the <code>gp/Calgary</code> directory, you will need COM, Win32Base, and Win32More, or symlinks to them if they are already checked out elsewhere. See [[Build_FieldWorks#Check_out_libcom_from_svn]] for information on checking out libcom from svn.
  
 
If you already have COM, Win32Base, and Win32More checked out where [[Build_FieldWorks#Check_out_libcom_from_svn]] prescribes, then you can just symlink to them by doing:
 
If you already have COM, Win32Base, and Win32More checked out where [[Build_FieldWorks#Check_out_libcom_from_svn]] prescribes, then you can just symlink to them by doing:
Line 69: Line 61:
 
To work on a topic branch, you can use a workflow similar to the following example.
 
To work on a topic branch, you can use a workflow similar to the following example.
 
   [master] $ git checkout -b crashbug
 
   [master] $ git checkout -b crashbug
  [crashbug] $ vim program.cs &amp;&amp; git commit -am &quot;fixed bug&quot;
+
  [crashbug] $ vim program.cs && git commit -am "fixed bug"
 
  [crashbug] $ git p4 rebase # rebase crashbug onto head of p4
 
  [crashbug] $ git p4 rebase # rebase crashbug onto head of p4
 
  [crashbug] $ git p4 submit
 
  [crashbug] $ git p4 submit
Line 76: Line 68:
 
   [master] $ git branch -d crashbug
 
   [master] $ git branch -d crashbug
 
====Cherry-picking====
 
====Cherry-picking====
If your master is tracking remotes/p4/master, you made a topic branch &quot;crashbug&quot; from master to work on a bug or feature, and you've made several commits to crashbug but don't want to push all of them since they aren't all ready, but you do want to push just one or two right now, you can push by:
+
If your master is tracking remotes/p4/master, you made a topic branch "crashbug" from master to work on a bug or feature, and you've made several commits to crashbug but don't want to push all of them since they aren't all ready, but you do want to push just one or two right now, you can push by:
 
  # Cherry pick some_commit from crashbug:
 
  # Cherry pick some_commit from crashbug:
  $ git checkout master &amp;&amp; git p4 rebase &amp;&amp; git cherry-pick some_commit
+
  $ git checkout master && git p4 rebase && git cherry-pick some_commit
 
  $ git p4 submit
 
  $ git p4 submit
  $ git checkout crashbug &amp;&amp; git rebase master
+
  $ git checkout crashbug && git rebase master
 
===Sending for Code Review===
 
===Sending for Code Review===
 
You are on a topic branch based on remotes/p4/master, and you want all commits in the branch to be sent for code review.
 
You are on a topic branch based on remotes/p4/master, and you want all commits in the branch to be sent for code review.
  
 
  $ git p4 rebase # Then make sure it is still what you want to send for review.
 
  $ git p4 rebase # Then make sure it is still what you want to send for review.
  $ tinydesc=&quot;''couple-word description''&quot;
+
  $ tinydesc="''couple-word description''"
  $ myaddr=&quot;''my.email.address@example.com''&quot;
+
  $ myaddr="''my.email.address@example.com''"
  $ toaddr=&quot;''code.reviewer@example.com''&quot;
+
  $ toaddr="''code.reviewer@example.com''"
  $ server=&quot;''mail.example.com''&quot;
+
  $ server="''mail.example.com''"
  $ git send-email --compose --subject=&quot;Code Review for $tinydesc&quot; --subject-prefix=&quot;$tinydesc patch&quot; \
+
  $ git send-email --compose --subject="Code Review for $tinydesc" --subject-prefix="$tinydesc patch" \
 
   --to=$toaddr --smtp-server=$server --from=$myaddr --cc=$myaddr remotes/p4/master..
 
   --to=$toaddr --smtp-server=$server --from=$myaddr --cc=$myaddr remotes/p4/master..
  
Line 106: Line 98:
 
You may find it helpful to browse and view history using gitk and make commits and manage your index using git-cola.
 
You may find it helpful to browse and view history using gitk and make commits and manage your index using git-cola.
 
==Resolving conflicts==
 
==Resolving conflicts==
If you have work on an old branch, check out that branch and run &lt;code&gt;git rebase master&lt;/code&gt;, it may not cleanly apply, saying:
+
If you have work on an old branch, check out that branch and run <code>git rebase master</code>, it may not cleanly apply, saying:
 
  CONFLICT (content): Merge conflict in Src/Foo.cs
 
  CONFLICT (content): Merge conflict in Src/Foo.cs
 
  Failed to merge in the changes.
 
  Failed to merge in the changes.
Line 113: Line 105:
 
  $ sudo aptitude install git-cola kdiff3-qt
 
  $ sudo aptitude install git-cola kdiff3-qt
 
  $ git config --global --add merge.conflictstyle diff3
 
  $ git config --global --add merge.conflictstyle diff3
  $ git-cola &amp;
+
  $ git-cola &
Choose '''Edit &gt; Options'''. In the '''Merge Tool''' box, enter &lt;code&gt;kdiff3&lt;/code&gt; and click '''Save'''.
+
Choose '''Edit > Options'''. In the '''Merge Tool''' box, enter <code>kdiff3</code> and click '''Save'''.
 
In the '''Repository Status''' pane, click a file in the '''Unmerged''' section.
 
In the '''Repository Status''' pane, click a file in the '''Unmerged''' section.
 
The '''Diff Viewer''' pane will show something like:
 
The '''Diff Viewer''' pane will show something like:
 
     public void DoSomething()
 
     public void DoSomething()
 
     {
 
     {
  '''++&lt;&lt;&lt;&lt;&lt;&lt;&lt; HEAD'''
+
  '''++<<<<<<< HEAD'''
   + &lt;font color=&quot;red&quot;&gt; if (!true)                          // Their modification&lt;/font&gt;
+
   + <font color="red"> if (!true)                          // Their modification</font>
   + &lt;font color=&quot;red&quot;&gt;   return;&lt;/font&gt;
+
   + <font color="red">   return;</font>
 
  '''++|||||||'''
 
  '''++|||||||'''
  ++ &lt;font color=&quot;red&quot;&gt; throw new NotImplementedException(); // Original code&lt;/font&gt;
+
  ++ <font color="red"> throw new NotImplementedException(); // Original code</font>
 
  '''++======='''
 
  '''++======='''
  +  &lt;font color=&quot;red&quot;&gt; if (!true)                          // Your modification&lt;/font&gt;
+
  +  <font color="red"> if (!true)                          // Your modification</font>
  +  &lt;font color=&quot;red&quot;&gt;   throw new Exception();&lt;/font&gt;
+
  +  <font color="red">   throw new Exception();</font>
  '''++&gt;&gt;&gt;&gt;&gt;&gt;&gt; My Patch'''
+
  '''++>>>>>>> My Patch'''
 
     }
 
     }
The lines between &lt;code&gt;|||||||&lt;/code&gt; and &lt;code&gt;=======&lt;/code&gt; is the original code. You modified it to say what's between &lt;code&gt;=======&lt;/code&gt; and &lt;code&gt;&lt;nowiki&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt; My Patch&lt;/nowiki&gt;&lt;/code&gt;, while someone else (possibly you) modified it to say what's between &lt;code&gt;&lt;nowiki&gt;&lt;&lt;&lt;&lt;&lt;&lt;&lt; HEAD&lt;/nowiki&gt;&lt;/code&gt; and &lt;code&gt;|||||||&lt;/code&gt;.
+
The lines between <code>|||||||</code> and <code>=======</code> is the original code. You modified it to say what's between <code>=======</code> and <code><nowiki>>>>>>>> My Patch</nowiki></code>, while someone else (possibly you) modified it to say what's between <code><nowiki><<<<<<< HEAD</nowiki></code> and <code>|||||||</code>.
  
Right-click the file in the '''Unmerged''' section and choose '''Launch Merge Tool'''. Use kdiff3 to resolve the merge conflicts (Learn about kdiff3 [http://kdiff3.sourceforge.net/doc/interpretinginformation.html here] and [http://kdiff3.sourceforge.net/doc/merging.html here]). Choose '''File &gt; Save''', '''File &gt; Quit'''.
+
Right-click the file in the '''Unmerged''' section and choose '''Launch Merge Tool'''. Use kdiff3 to resolve the merge conflicts (Learn about kdiff3 [http://kdiff3.sourceforge.net/doc/interpretinginformation.html here] and [http://kdiff3.sourceforge.net/doc/merging.html here]). Choose '''File > Save''', '''File > Quit'''.
  
Do this for each file in the '''Unmerged''' section in git-cola. When you are finished, if git-cola didn't update all the way on its own, choose '''File &gt; Rescan'''.
+
Do this for each file in the '''Unmerged''' section in git-cola. When you are finished, if git-cola didn't update all the way on its own, choose '''File > Rescan'''.
  
(Note that when you quit kdiff3, git-cola might print &quot;&lt;code&gt;fatal: Unable to create '/home/user/gp/Calgary/WW/.git/index.lock': File exists.&lt;/code&gt;&quot; to the terminal. If so, you could close and reopen git-cola and resolve that conflict again, or you might be able to click the file in the '''Unmerged''' section and click '''Stage'''.)
+
(Note that when you quit kdiff3, git-cola might print "<code>fatal: Unable to create '/home/user/gp/Calgary/WW/.git/index.lock': File exists.</code>" to the terminal. If so, you could close and reopen git-cola and resolve that conflict again, or you might be able to click the file in the '''Unmerged''' section and click '''Stage'''.)
  
Examine the diffs in the '''Staged''' section. Choose '''File &gt; Quit'''. In the terminal, type:
+
Examine the diffs in the '''Staged''' section. Choose '''File > Quit'''. In the terminal, type:
 
  $ git rebase --continue
 
  $ git rebase --continue
 
[[Category:Linux tools]] [[Category:Git]]
 
[[Category:Linux tools]] [[Category:Git]]

Revision as of 10:30, 24 November 2010

Using git as a front-end to the Perforce FieldWorks repository.

While p4v has many good features, some developers may be more comfortable using a different front-end to the Perforce FieldWorks repository, such as git-p4. Note that you will still need a Perforce checkout on your machine for git-p4 to commit back to Perforce (see Build_FieldWorks#Check_out_from_VCS for information on checking out from Perforce).

Install git-p4

Install dependencies

Install p4

The latest version of p4 can be found at http://www.perforce.com/perforce/downloads/.

$ cd $(mktemp -dt)
$ http_proxy=proxy.example.com:1234 wget 'http://www.perforce.com/downloads/perforce/r09.2/bin.linux26x86/p4'
$ sudo install p4 /usr/local/bin

Append to ~/.bashrc:

export P4CLIENT=your_workspace_name
export P4PORT=src.sil.org:1934 (or hydra:1935)
export P4USER=your_username (or anonymous)

Close and re-open your terminal.

git-p4

~$ git clone git://github.com/ermshiperete/git-p4.git

Link to the git-p4 script from a directory in your PATH, such as ~/bin:

$ mkdir -p ~/bin && cd ~/bin
bin$ ln -s ~/git-p4/git-p4

Set git-p4 to work with file renames/integrations:

$ git config --global git-p4.detectRename true

Updating git-p4

To update git-p4, do

$ cd ~/git-p4
git-p4$ git pull

Check out repository using git-p4

Prepare a place for the code:

$ mkdir -p ~/gp/Calgary
$ cd ~/gp/Calgary

Check out from Perforce using git-p4:

gp/Calgary$ git p4 clone //depot/Calgary/WW

In the gp/Calgary directory, you will need COM, Win32Base, and Win32More, or symlinks to them if they are already checked out elsewhere. See Build_FieldWorks#Check_out_libcom_from_svn for information on checking out libcom from svn.

If you already have COM, Win32Base, and Win32More checked out where Build_FieldWorks#Check_out_libcom_from_svn prescribes, then you can just symlink to them by doing:

gp/Calgary$ for dir in ~/p4repo/Calgary/{COM,Win32Base,Win32More}; do ln -s $dir; done


Workflow

There is a readme about a different version of git-p4 at http://github.com/dtrott/git-p4 .

Updating and pushing

Your workflow might look like:

  • Edit files
$ vim foo.cs
  • Commit locally
$ git commit
  • Update from Perforce
$ git stash
$ git p4 rebase
$ git stash pop
  • Update and commit your work to Perforce
$ git stash
$ git p4 rebase
$ git p4 submit
$ git stash pop

With a topic branch

To work on a topic branch, you can use a workflow similar to the following example.

  [master] $ git checkout -b crashbug
[crashbug] $ vim program.cs && git commit -am "fixed bug"
[crashbug] $ git p4 rebase # rebase crashbug onto head of p4
[crashbug] $ git p4 submit
[crashbug] $ git checkout master
  [master] $ git p4 rebase
  [master] $ git branch -d crashbug

Cherry-picking

If your master is tracking remotes/p4/master, you made a topic branch "crashbug" from master to work on a bug or feature, and you've made several commits to crashbug but don't want to push all of them since they aren't all ready, but you do want to push just one or two right now, you can push by:

# Cherry pick some_commit from crashbug:
$ git checkout master && git p4 rebase && git cherry-pick some_commit
$ git p4 submit
$ git checkout crashbug && git rebase master

Sending for Code Review

You are on a topic branch based on remotes/p4/master, and you want all commits in the branch to be sent for code review.

$ git p4 rebase # Then make sure it is still what you want to send for review.
$ tinydesc="couple-word description"
$ myaddr="my.email.address@example.com"
$ toaddr="code.reviewer@example.com"
$ server="mail.example.com"
$ git send-email --compose --subject="Code Review for $tinydesc" --subject-prefix="$tinydesc patch" \
  --to=$toaddr --smtp-server=$server --from=$myaddr --cc=$myaddr remotes/p4/master..

Quirks

Protecting csproj files

Since your files are read-write by default when you use git-p4 (rather than read-only when using p4v), you may want to protect .csproj files sometimes so that monodevelop does not rewrite them when you don't want it to. (Though this may make monodevelop unsuccessful at managing your solution file.) You can easily do that by running:

gp/Calgary/WW$ find -name \*csproj -print0 | xargs -0 chmod u-w

To make a csproj writable again, run:

gp/Calgary/WW$ chmod u+w Src/Foo/Baz.csproj

It may be easier to edit the csproj by hand depending on what you want to change.

Git GUI tools

There are numerous git GUI tools available.

You may find it helpful to browse and view history using gitk and make commits and manage your index using git-cola.

Resolving conflicts

If you have work on an old branch, check out that branch and run git rebase master, it may not cleanly apply, saying:

CONFLICT (content): Merge conflict in Src/Foo.cs
Failed to merge in the changes.
Patch failed at 0002 My Patch

To resolve the conflicts, try:

$ sudo aptitude install git-cola kdiff3-qt
$ git config --global --add merge.conflictstyle diff3
$ git-cola &

Choose Edit > Options. In the Merge Tool box, enter kdiff3 and click Save. In the Repository Status pane, click a file in the Unmerged section. The Diff Viewer pane will show something like:

   public void DoSomething()
   {
++<<<<<<< HEAD
 +   if (!true)                           // Their modification
 +     return;
++|||||||
++   throw new NotImplementedException(); // Original code
++=======
+    if (!true)                           // Your modification
+      throw new Exception();
++>>>>>>> My Patch
   }

The lines between ||||||| and ======= is the original code. You modified it to say what's between ======= and >>>>>>> My Patch, while someone else (possibly you) modified it to say what's between <<<<<<< HEAD and |||||||.

Right-click the file in the Unmerged section and choose Launch Merge Tool. Use kdiff3 to resolve the merge conflicts (Learn about kdiff3 here and here). Choose File > Save, File > Quit.

Do this for each file in the Unmerged section in git-cola. When you are finished, if git-cola didn't update all the way on its own, choose File > Rescan.

(Note that when you quit kdiff3, git-cola might print "fatal: Unable to create '/home/user/gp/Calgary/WW/.git/index.lock': File exists." to the terminal. If so, you could close and reopen git-cola and resolve that conflict again, or you might be able to click the file in the Unmerged section and click Stage.)

Examine the diffs in the Staged section. Choose File > Quit. In the terminal, type:

$ git rebase --continue