3

My workplace started using Gerrit to manage all of our projects. I've never used Gerrit before. I'm trying to figure out a good workflow for using it for submitting code for review.

I created a branch foo. I made a commit on it, and pushed it to Gerrit. Then I started a branch bar starting from foo, and made another commit on it. I pushed the branch bar to Gerrit as well.

I am now on branch bar:

$ git branch
* bar
foo

Now I wanted to start a code review for a merge from bar to foo. I was told that this command should do it:

$ git push gerrit HEAD:refs/for/foo
Total 0 (delta 0), reused 0 (delta 0)
remote:
remote: Processing changes: refs: 1, done
To ssh://ram@gerrit/acme/my_project
 ! [remote rejected] HEAD -> refs/for/foo (no new changes)
error: failed to push some refs to 'ssh://ram@gerrit/acme/my_project' 

As you can see, I'm getting the error (no new changes). I asked our local Gerrit champion why, and he says that as far as he knows, you can't push for code review code that's already on Gerrit, even if that code is on a different branch.

It looks like if I'd avoid pushing the branch bar to Gerrit, my problem would go away and the code review would work. But I would prefer to be able to push whatever the %&@# I want without it interfering with code reviews. I like pushing branches. I like having my branches on Gerrit, because then I can also send them to other people to see on the web interface.

Is it possible to make code reviews in Gerrit work without forbidding me from pushing my branches to Gerrit?

Ram Rachum
  • 84,019
  • 84
  • 236
  • 374
  • One workaround that comes to my mind is to ammend your commit, remove the change-id (so that your hook creates a new one) and try pushing again. Let me know if that works – Dunno Sep 01 '16 at 15:48
  • @Dunno Thanks for the creativity, but I'm looking for a good workflow, and that workaround is too hacky to my taste. (I'd rather have a separate remote to push to if I can't find a better solution.) – Ram Rachum Sep 01 '16 at 15:59
  • 1
    The thing is, change-ids to gerrit are basically what commit ids are to git. Once you push a commit with one change-id, you can't push it again unless it's changed. I doubt there is a non-hacky solution but I'll try to find one. Btw, my workaround works, I just checked it myself. – Dunno Sep 01 '16 at 16:05
  • @Dunno is right, the solution is not a hacky workaround, this is about Gerrit process: you can't have 2 different changes with the same Change-Id. You just need to change the Change-Id. – Marcelo Ávila de Oliveira Sep 01 '16 at 16:40
  • As far as I know, you have to amend the merge commit to make git to add a new change-id. The default behavior of gerrit hook is to not add a change-id to a git merge. If I understood well, your merge commit is not yet pushed onto gerrit but you would like to ? Is it possible for you to **rebase** `bar` onto `foo` instead of a merge ? If yes, I will explain it on an answer. – Flows Sep 01 '16 at 16:42
  • Have all the changes for `foo` been submitted? According to what you described, it was expected to be a fast forward push. But it failed. – ElpieKay Sep 01 '16 at 22:22

3 Answers3

0

Gerrit will not allow you to push the same commit with the same change-id twice. That leaves you with two options:

  1. Amend the existing commit to change the change-id
  2. Create a new commit that will have a different change-id, and contain all changes from branch foo.

Either way, you'll have to change the commit's change-id, in option 1 using git commit --amend or in option 2 using git rebase foo bar -i, squashing all commits into 1 and then changing it's message.

This is actually a reasonable behavior - Gerrit is a code review tool, so it doesn't make sense to push commits directly to branches.

If you really need a remote just to show your code to others, then you'll have to make a new one for that purpose.

Larry B.
  • 753
  • 6
  • 21
Dunno
  • 3,632
  • 3
  • 28
  • 43
  • "This is actually a reasonable behavior - Gerrit is a code review tool, so it doesn't make sense to push commits directly to branches." - If Gerrit didn't handle merging for you, your argument might make sense. But the way that Gerrit works, means that all merging ends up going through Gerrit so you should have options to do that sanely. – Steven Byks Apr 06 '17 at 16:36
  • "If you really need a remote just to show your code to others, then you'll have to make a new one for that purpose." You basically just said, "don't use gerrit for code review". Showing your code to other people is most of what a code review is. If you can't do that with Gerrit, then it's kinda useless as a code review tool. – Steven Byks Apr 06 '17 at 16:37
0

I think you need to do the merge in different way
- first, merge the branches locally - git checkout foo then git merge origin/bar
- second, push the merge commit from local foo to remote foo - git push gerrit HEAD:refs/for/foo

Dont forget to put changeId into merge commit.

In general there is no need to review a commit twice. Isntead you need to review merge commits or rebase method. Consider using rebase if your branches not specific ones, like dev vs. release

Community
  • 1
  • 1
laplasz
  • 3,359
  • 1
  • 29
  • 40
  • I thought of this too, but it won't work. First of all, if `bar` can be fast forwarded to `foo`, merge won't even do anything, and if you try merging `bar` to `foo` with `--no-ff` option, the created commit will be empty. – Dunno Sep 01 '16 at 18:09
0

When doing a merge, git doesn't add a change-Id. You have to amend the merge commit to make git to add a new change-id.

This will allow you to push to gerrit the merge commit. The default behavior of gerrit hook is to not add a change-id to a git merge.

Another solution that I would recommand is to do a rebase instead of a merge. You could rebase bar onto foo with git rebase foo from branch bar

Flows
  • 3,675
  • 3
  • 28
  • 52