Gerrit Introduction

From Qt Wiki
Revision as of 21:24, 2 March 2015 by Ossi (talk | contribs) (more WIP)
Jump to navigation Jump to search


Attention: this page is currently being reworked by User:Ossi.

Introduction to Gerrit

Note, if you are a first time Gerrit user, please take a look at the Setting-up-Gerrit page.

Overview

Main Features

Gerrit is a web-based tool that is used for code review. Its main features are the side-by-side difference viewing and inline commenting, which makes code reviews a quick and simple task. It is used together with the Git version control system. Gerrit allows authorized contributors to merge Changes to the Git repository, after reviews are done. Contributors can get their code reviewed with little effort, and get their Changes quickly through the system.

Basic Workflow

Gerrit usage has two stages: First, the contributor uploads Changes to Gerrit with Git, and second, peers use the web browser to make reviews. The review process includes the following steps:

  • Review Changes
  • Publish comments
  • Approve or abandon Changes

Repository Structure

Gerrit can manage multiple repositories (projects). Branches are fully supported by Gerrit, each repository can have any number of branches.

Gerrit Intro Structure.png

Gerrit stores Changes, which are normal commits, as references in the refs/changes/ namespace. When contributors push Changes, they prepend refs/for/ to the target branch. For example, when contributor uploads a commit to the stable branch, the target ref will be refs/for/stable.

Terminology

Common terms used in Gerrit:

Term Description
Change The unit of review. Results in a single commit when merged to the Git repository.

Change numbers are unique and never change.

Patch Set A revision of a Change. Each time a Change is modified, it will receive a new Patch Set.

Patch Set numbering starts from 1. Technically, a Patch Set is a unique Git commit.

Approval Category Name for a scope that is checked during review process. Qt is using the categories Code Review and Sanity Review.
Score A value in an Approval Category. Indicates if a Change is approved and can be submitted to the Git repository.
Submit An action that allows Gerrit to merge a Change to the Git repository.
Abandon Action that archives a Change. An abandoned Change can be restored later.
Project A Git repository.

Creating and Uploading Contributions

Preparation

Before any contribution can be created, a Git clone of the target repository must be obtained and properly configured. The necessary steps are explained in Setting up Gerrit.

Creating a New Contribution

All contributions are uploaded with a regular Git push. Gerrit handles reviews at the commit level. A single contribution can easily result in several reviewable Changes in Gerrit. The contributor prepares a contribution by following these steps:

  1. Creating or updating the local repository
  2. Optionally creating a topic branch
  3. Doing changes
  4. Committing the changes
  5. Uploading the commit(s) to Gerrit
  6. Soliciting feedback

Creating a topic branch

Keep code organized in "topic branches.":http://git-scm.com/book/en/Git-Branching-Branching-Workflows This is what Git excels in. "next-big-thing" is used as an example topic branch below:

$ git checkout -b next-big-thing
Switched to a new branch 'next-big-thing'
$

Making Changes

Use your favorite editor to complete a coding task.

$ edit src/foo.cc
$

Committing Changes

Call git add on all files that should be included in the commit that is created, and finally call git commit to create a new commit as follows:

$ git add src/foo.cc
$ git commit

Note: It is recommended that you use a graphical tool like git gui instead of the command line.

At this point you will enter your commit message into the editor. If you correctly set up the clone, you will be presented with a template for the commit message.

The guidelines for creating good commit messages - and creating good commits in general, for that matter - are outlined in the Commit Policy.

Write a message, save it, and quit the editor. Git will produce output similar to this:

[next-big-thing c82710a] My Feature
 1 files changed, 1 insertions(+), 0 deletions(-)
 create mode 100644 src/foo.cc
$

On initial creation of a commit, if the commit-msg hook is set up properly, an additional line in the form of "Change-Id: …" should be been added.

You can/should verify the commit with git show, or git log -p if the contribution consists of multiple commits.

To revise the latest commit use git commit --amend. If the contribution consists of multiple commits, you will need to use git rebase --interactive to revise earlier commits.

Uploading Commits

Changes are pushed to Gerrit with git push. Note that a special target ref is used. Gerrit reports how many Changes were created and provides links to these Changes.

$ git push gerrit HEAD:refs/for/dev
Counting objects: 6, done.
Delta compression using up to 2 threads.
Compressing objects: 100% (3/3), done.
Writing objects: 100% (4/4), 407 bytes, done.
Total 4 (delta 2), reused 0 (delta 0)
remote: Resolving deltas: 0% (0/2)
To ssh://<username>@codereview.qt.io:29418/qt/qtbase
 * [new branch] HEAD -> refs/for/dev

FIXME: the interesting part is missing here

$

When pushing to Gerrit, "a typical refspec":http://git-scm.com/book/en/Git-Internals-The-Refspec uses HEAD as the source ref and a special Gerrit ref for the target branch. The target ref has the format refs/for/<branch name>. Pushes to this target ref causes Gerrit to create new Changes for all commits pushed this way. To group your Changes, push to a topic by using the format refs/for/<branch name>/<topic name>. Note that it is possible to use any other ref as source ref instead of HEAD when necessary. See Branch Guidelines to decide about the target branch.

It is recommended that you use the git-gpush command from our "qtrepotools repository":https://code.qt.io/qt/qtrepotools (make sure to add the bin directory to your PATH for maximal convenience):

$ git gpush
[same output as above]

Soliciting Feedback

The contributor requests feedback by adding reviewers to the Change. This is typically done via the web browser. Access the Change with the web browser and use the "Add Reviewer" button to add any other registered user to the review like in the picture below:

Gerrit Intro ChangeScreen.png

Alternatively, reviewers can be added already when uploading a contribution. Use the git-gpush tool for that purpose:

$ git gpush +approver@example.com
[same output as above]

Review Workflow

It is easy to get an overview of pending contributions in the "My Changes" page, also known as the "Dashboard":

Gerrit Intro Dashboard.png

Reviewing Contributions

The review process starts with choosing a Change to review. After choosing a Change, changed files can be viewed side-by-side and comments can be posted in-line to each file. Contributions are typically reviewed by Approvers, but anyone can make a review.

The following steps are needed to complete a code review:

  1. Opening the Change page (entered from the Dashboard or following a link in a notification mail)
  2. Reviewing changed files
  3. Publishing comments and reviewing results

Viewing the Change Overview

Changes can have several Patch Sets. When Changes get updated after review, the Patch Set number increases.

http://developer.qt.nokia.com/uploads/gerrit/3_3_2_viewing_change_overview.png

Reviewing Changed Files

Changes are compared side-by-side or in the unified diff view. The reviewer can also compare differences between specific Patch Sets (also called "inter-diffs").

Comments are posted by double clicking on a line. Comments are saved as drafts until they are published as in the pictures:

http://developer.qt.nokia.com/uploads/gerrit/3_3_3_reviewing_changed_files_1.png

http://developer.qt.nokia.com/uploads/gerrit/3_3_3_reviewing_changed_files_2.png

Gerrit keeps track which files have been reviewed and which files have comments ready to be published. If an ongoing review is interrupted, the reviewer can return later and resume where they left off. Draft comments can be edited and deleted before they are published.

Downloading Changes

It is also possible to download Changes for local review. The easiest way to do that is to copy the Download link from Gerrit to the command line:

http://developer.qt.nokia.com/uploads/gerrit/3_3_1_1_command_line_review_downloading_change.png

This makes it possible to use the usual git commands to view changes, to build the code, and to run tests.

Publishing Comments

When all files are reviewed, the reviewer continues to the Publish Comments screen with the Review button.

The review is completed by writing an optional cover message and giving a score.

The Code Review category has 5 levels. A Change can only be submitted after it receives a +2 score, and cannot be be submitted if it receives a -2 score. Giving these scores is limited to Approvers; regular contributors can give only advisory scores (-1 to +1).

http://developer.qt.nokia.com/uploads/gerrit/3_3_4_publishing_comments_1.png

http://developer.qt.nokia.com/uploads/gerrit/3_3_4_publishing_comments_2.png

A Sanity Review score should not be given unless the Sanity Bot made a mistake and needs to be overridden.

Publishing Review Results From The Command Line

An alternative to browser-based review is to use the Gerrit ssh command line interface. Please do not do this, as scripting a step which is meant to be visual and interactive removes the additional safety net.

Processing Review Feedback

The contributor can view feedback on their contributions by accessing the Change page and reading comments file-by-file. It is possible to reply to comments and have a discussion about the code review in-line.

The contributor processes the feedback by following these steps:

  1. Opening the Change page (entered from the Dashboard or following a link in a notification mail)
  2. Locating comments in the Change page
  3. Reading and writing in-line comments
  4. Publishing a reply and/or uploading a new Patch Set

Locating Comments in The Change

Comments are below the list of Patch Sets. In the picture below the comments for Patch Set 2 are examined:

Gerrit Intro Comments.png

Reading in-line Comments

Replies can be posted by clicking the comment like in the picture below:

Gerrit Intro Replying.png

Note that the comments are not actually posted until you publish them.

Note: do not reply to the notification mails you get from Gerrit. The mails you send this way will not be publicly visible and archived.

Updating a Contribution With New Code

Most Changes require multiple iterations of the review process. The contributor needs to update the Change if it received some comments that require action or it did not merge with the branch tip. Each time a Change is updated, it gains a new Patch Set.

Updating a change is done by following these steps:

  1. Accessing the Changes
  2. Modifying the Change(s)
  3. Pushing updated Changes

Accessing The Changes

If the original commit is still available, it is possible to continue editing it. Otherwise, download the Change by using the download link provided by Gerrit:

http://developer.qt.nokia.com/uploads/gerrit/3_4_1_accessing_change_code.png

 $ git fetch ssh://qtcontributor@codereview.qt.io:29418/qt/qtbase
  refs/changes/19/419/1 && git checkout FETCH_HEAD
 From ssh://codereview.qt.io:29418/qt/qtbase
  * branch refs/changes/19/419/1-> FETCH_HEAD
 Note: checking out 'FETCH_HEAD'.
 
 You are in 'detached HEAD' state. You can look around, make experimental
 changes and commit them, and you can discard any commits you make in this
 state without impacting any branches by performing another checkout.  

 If you want to create a new branch to retain commits you create, you may
 do so (now or later) by using -b with the checkout command again. Example:

 git checkout -b new_branch_name

 HEAD is now at 9a006a3… My Feature
 $ git checkout -b changes/419
 Switched to a new branch 'changes/419'
 $

If Gerrit reported a merge conflict, now would be the time to rebase the Changes:

$ git rebase --onto origin/dev

If you are not using a separate branch, you can just use git pull --rebase.

Note: Please do not rebase unnecessarily, as this makes inter-diffs much less useful.

Modifying Commits

Modifications in the working tree are committed with the --amend option. If the contribution consists of multiple commits, you will need to use git rebase --interactive to revise earlier commits.

When you amend commit messages, make sure to preserve the Change-Id footer, as this is how Gerrit identifies new Patch Sets for existing Changes.

 $ vim src/foo.cc
 $ git add src/foo.cc
 $ git commit --amend
 [changes/419 2ea7773] My Feature
  1 files changed, 1 insertions(+), 0 deletions(-)
  create mode 100644 src/foo.cc
 $

Pushing Updated Changes

The commit(s) are uploaded back to Gerrit with the same target ref as before. After the push, new Patch Set will have been created for the target Change(s):

 $ git push origin HEAD:refs/for/dev
 Counting objects: 6, done.
 Delta compression using up to 2 threads.
 Compressing objects: 100% (3/3), done.
 Writing objects: 100% (4/4), 419 bytes, done.
 Total 4 (delta 2), reused 0 (delta 0)
 remote: Resolving deltas: 0% (0/2)
 To ssh://qtcontributor@codereview.qt.io:29418/qt/qtbase.git
  * [new branch] HEAD -> refs/for/dev
 $

http://developer.qt.nokia.com/uploads/gerrit/3_4_3_pushing_updated_change.png

Approving And Abandoning

Approving And Submitting a Contribution

Depending on the project, an approved contribution will be submitted to the CI System (Qt 5) or a Git repository (Qt Creator). Changes are approved by reviewing and assigning them a score that is high enough for submission. By default, Changes require +2 for Code Review and +1 for Sanity Review categories to be approved. There are two ways to submit a Change. If the project is using a continuous integration system, Changes will be merged to staging. Otherwise, they will be submitted directly to their destination branche.

  • To submit a Change to CI system press "Merge Patch Set 1 to Staging".
  • To submit a Change to Git repository press "Submit Patch Set 1"

It is usually best when the contributor submits their own Changes.

http://developer.qt.nokia.com/uploads/gerrit/4_1_approving_and_submitting_a_contribution.png

If there are multiple relevant reviewers, you only need a +2 approval from one of them before staging. However if other reviewers have shown a specific interest in the patch, such as by repeated comments, it is polite to give them some time to add a +1 or +2 before staging.

Abandoning a Contribution


interrupt!!!


Those Changes that should not be submitted can be abandoned. An abandoned Change will disappear from open changes lists and is considered closed. Abandoned changes can be restored later if they become valid again or if they were abandoned by accident.

Abandoning changes is a normal operation that is used to maintain Gerrit and hide changes that will not make their way to Git repository, for any reason.

To abandon a change, owner, approver or maintainer can click "Abandon Change" button.

http://developer.qt.nokia.com/uploads/gerrit/4_2_abandoning_a_contribution_1.png

http://developer.qt.nokia.com/uploads/gerrit/4_2_abandoning_a_contribution_2.png

Finding new contributions by others

User can find changes by searching or by browsing projects and branches. Refer to Gerrit user's guide for detailed information how to use search queries. Links for change owner, project name and branch name in change tables can be used to access quick searches of the related changes.

Navigation bar at the top of the Gerrit web view can be used to quickly access

  • User's own changes
  • Changes the user is expected to review
  • All open, merged and abandoned changes

Continuous integration and staging

Workflow

Gerrit has been slightly customized for the Qt project. The continuous integration system that is running regular builds and tests has been incorporated to the workflow. Instead of directly submitting changes, changes can be merged to a staging branch. There is a staging branch for each normal branch. Staging branches are maintained by Gerrit and are not visible to the contributors.

http://developer.qt.nokia.com/uploads/gerrit/5_1_workflow.png

As part of customization, changes have new states. Changes in the New state are waiting for a review. After review, changes are merged to a staging branch and marked as staged. The continuous integration system will pick staged changes with regular intervals and move them to the Integrating stage. From the Integrating state changes are either submitted or moved back to the New state. If builds succeed and tests pass, submitted or merged their destination branch. Otherwise they are moved to the New state for further analysis. Contributor from whom the code originates from is expected to analyze why test and build phase failed and upload fixes.

Changes can still be submitted directly from new state, but only by users who have this specific access right in Gerrit.

Feature Branches

The Qt Project's handling of branches is documented by the Branch Guidelines.

Topics vs. Branches

Gerrit topics can be used as "feature branches". A topic is created when a special target ref is used. The syntax for the change set refspec is refs/for/<branch name>/<topic name>. It is often good enough to push a set of commits for review to a topic. However, if the contributor intends to work with others on a long-living branch, the Gerrit Administrators should be contacted for a new branch in Gerrit. Also, the QA team has to be contacted so they can include the new branch in the CI system builds. This way the code can be reviewed already when working on it in the branch.

Merging Feature Branches

Merges between feature branches and the mainline are like all other commits and are pushed, reviewed and staged the usual way. However, only 'Merge Masters' can push merge commits. User may recruit the merge master from outside project team if it they do not have person knowledgeable on Git available. Note: Do not create a merge from commits which have not been integrated yet.

Merging Branches Alien to Gerrit

This should not happen often. Nevertheless, only a merge commit should be pushed in this case. 'Push Master' can be asked to import the branch into Gerrit.

Providing feedback

Report bugs in our Gerrit to "the bugtracker":http://bugreports.qt.io/browse/QTQAINFRA/component/19470. Ideally, provide a link to an "upstream issue":http://code.google.com/p/gerrit/issues/list (note that the issue may be already closed, as we are typically lagging by several versions).