Gerrit Introduction: Difference between revisions
(remove tag) |
m (→Creating Commits: More proper en-dashes.) |
||
(43 intermediate revisions by 16 users not shown) | |||
Line 1: | Line 1: | ||
[[Category: | [[Category:Developing Qt::Process]] | ||
[[Category:Tools::Gerrit]] | |||
'''Note, if you are a first time Gerrit user, please take a look at the [[Setting up Gerrit]] page.''' | '''Note, if you are a first time Gerrit user, please take a look at the [[Setting up Gerrit]] page.''' | ||
== Overview == | ==Overview== | ||
NB., the screenshots were taken from a very old version of Gerrit, and consequently should be viewed as ideographic. | |||
Gerrit | Also, the current version of Gerrit comes with [https://codereview.qt-project.org/Documentation/intro-gerrit-walkthrough.html its own introduction]. | ||
People familiar with GitHub/GitLab may appreciate this [https://codereview.qt-project.org/Documentation/intro-gerrit-walkthrough-github.html rundown of workflow differences]. | |||
===Main Features=== | |||
Gerrit is a web-based tool that is used for code review. Its main features are side-by-side difference viewing and inline commenting. These make 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. | |||
=== Repository Structure === | ===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 can manage multiple repositories (projects). Branches are fully supported by Gerrit, each repository can have any number of branches. | ||
Line 23: | Line 30: | ||
[[File:Gerrit_Intro_Structure.png]] | [[File:Gerrit_Intro_Structure.png]] | ||
Gerrit stores Changes, which are normal commits, as references in the refs/changes/ namespace. When contributors push Changes, they prepend <tt>refs/for/</tt> to the target branch. For example, when contributor uploads a commit to the <tt> | Gerrit stores Changes, which are normal commits, as references in the refs/changes/ namespace. When contributors push Changes, they prepend <tt>refs/for/</tt> to the target branch. For example, when contributor uploads a commit to the <tt>dev</tt> branch, the target ref will be <tt>refs/for/dev</tt>. | ||
=== Terminology === | ===Terminology=== | ||
Common terms used in Gerrit: | Common terms used in Gerrit: | ||
Line 35: | Line 42: | ||
|'''Change''' | |'''Change''' | ||
|The unit of review. Results in a single commit when merged to the Git repository. | |The unit of review. Results in a single commit when merged to the Git repository. | ||
Change numbers are unique and never change. | Change numbers (identifiers) are unique and never change. | ||
|- | |- | ||
|'''Patch Set''' | |'''Patch Set''' | ||
Line 58: | Line 65: | ||
|} | |} | ||
== Creating and Uploading Contributions == | ==Creating and Uploading Contributions== | ||
=== Preparation === | ===Preparation=== | ||
Before any contribution can be created, a Git clone of the target repository must be obtained and properly configured. | 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]]. | The necessary steps are explained in [[Setting up Gerrit]]. | ||
=== Creating a New Contribution === | ===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: | 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: | ||
# Creating or updating the local repository | #Creating or updating the local repository | ||
# Optionally creating a topic branch | #Optionally creating a topic branch | ||
# | #Creating commits | ||
#Uploading the commit(s) to Gerrit | |||
# Uploading the commit(s) to Gerrit | #Soliciting feedback | ||
# Soliciting feedback | |||
==== Creating a topic branch ==== | ====Creating a topic branch==== | ||
Keep code organized in | Keep code organized in [http://git-scm.com/book/en/Git-Branching-Branching-Workflows topic branches.] This is what Git excels in. "next-big-thing" is used as an example topic branch below: | ||
<pre> | <pre> | ||
$ git | $ git switch -c next-big-thing | ||
Switched to a new branch 'next-big-thing' | Switched to a new branch 'next-big-thing' | ||
$ | $ | ||
</pre> | </pre> | ||
==== | ====Creating Commits==== | ||
See the [[Git Introduction]] to get started. | |||
Here are a few notes specific to Qt/Gerrit: | |||
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 | *If you correctly set up the clone, the commit message editor will present you with a template for the message. | ||
*The guidelines for creating good commit messages – and creating good commits in general, for that matter – are outlined in the [[Commit Policy]]. | |||
*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 have been added. | |||
====Uploading Commits==== | |||
Changes are pushed to Gerrit with <tt>git push or git gpush(see below)</tt>. Note that a special target ref is used. | |||
Changes are pushed to Gerrit with <tt>git push</tt>. Note that a special target ref is used. | |||
Gerrit reports how many Changes were created and provides links to these Changes. | Gerrit reports how many Changes were created and provides links to these Changes. | ||
Line 144: | Line 120: | ||
remote: https://codereview.qt-project.org/12345 | remote: https://codereview.qt-project.org/12345 | ||
remote: | remote: | ||
To ssh://qtcontributor@codereview.qt. | To ssh://qtcontributor@codereview.qt-project.org:29418/qt/qtbase | ||
* [new branch] HEAD -> refs/for/dev | * [new branch] HEAD -> refs/for/dev | ||
$ | $ | ||
</pre> | </pre> | ||
When pushing to Gerrit, a typical | When pushing to Gerrit, a typical [http://git-scm.com/book/en/Git-Internals-The-Refspec refspec] uses HEAD as the source ref and a special Gerrit ref for the target branch. The target ref has the format <tt>refs/for/<branch name></tt>. Pushes to this target ref causes Gerrit to create new Changes for all commits pushed this way. To group your Changes, push to a [[Gerrit Introduction#Topics in Gerrit|topic]] by using the format <tt>refs/for/<branch name>%topic=<topic name></tt>. | ||
Note that it is possible to use any other ref as source ref instead of HEAD when necessary. | 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. | See [[Branch Guidelines]] to decide about the target branch. | ||
It is recommended that you use the git-gpush command from our | It is recommended that you use the git-gpush command from our [http://code.qt.io/cgit/qt/qtrepotools.git/ qtrepotools repository] For more information on using Git Scripts see [[Git-gpush-scripts|our page on Git Scripts.]] | ||
<pre> | <pre> | ||
Line 162: | Line 138: | ||
Once a Change has been created, it can be viewed in the web browser: | Once a Change has been created, it can be viewed in the web browser: | ||
[[File: | [[File:QtGerritChangeLightmode.png|1000x1000px]] | ||
==== Soliciting Feedback ==== | ====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 " | 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 pen icon next to the names of the "Reviewers" to add any other registered user(s) to the review. | ||
Alternatively, reviewers can be added already when uploading a contribution. Use the git-gpush tool for that purpose: | Alternatively, reviewers can be added already when uploading a contribution. Use the git-gpush tool for that purpose: | ||
Line 175: | Line 151: | ||
</pre> | </pre> | ||
== Review Workflow == | ==Review Workflow== | ||
It is easy to get an overview of pending contributions in the " | It is easy to get an overview of pending contributions in the "Your" page, also known as the "Dashboard": | ||
[[File:Gerrit_Intro_Dashboard.png]] | [[File:Gerrit_Intro_Dashboard.png|1200x1200px]] | ||
It is possible to find Changes by issuing [https://codereview.qt-project.org/Documentation/user-search.html search queries]. Links for the Change owner, project name and branch name in the search result listings can be used to quickly search for related Changes. | It is possible to find Changes by issuing [https://codereview.qt-project.org/Documentation/user-search.html search queries]. Links for the Change owner, project name and branch name in the search result listings can be used to quickly search for related Changes. | ||
The navigation bar at the top of the Gerrit web view provides quick access to common search queries under the " | The navigation bar at the top of the Gerrit web view provides quick access to common search queries under the "Your" and "Changes" items. | ||
=== Reviewing Contributions === | ===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 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. | ||
Line 191: | Line 167: | ||
The following steps are needed to complete a code review: | The following steps are needed to complete a code review: | ||
# Opening the Change page (entered from the Dashboard or following a link in a notification mail) | #Opening the Change page (entered from the Dashboard or following a link in a notification mail) | ||
# Reviewing changed files | #Reviewing changed files | ||
# Publishing comments and reviewing results | #Publishing comments and reviewing results | ||
==== Viewing the Change Overview ==== | ====Viewing the Change Overview==== | ||
Changes can have several Patch Sets. When Changes get updated after review, the Patch Set number increases. | Changes can have several Patch Sets. When Changes get updated after review, the Patch Set number increases. | ||
[[File: | [[File:Gerrit Intro PatchSets.png]] | ||
==== Reviewing Changed Files ==== | ====Reviewing Changed Files==== | ||
Changes are compared side-by-side or in the unified diff view. | 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"). | 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 | Comments are posted by double clicking on a line. Comments are saved as drafts until they are published. | ||
Note that comments are formatted as flowed text, discarding individual line breaks. A simple [https://wiki.hpdd.intel.com/display/PUB/2012/02/16/Comment+formatting+on+Gerrit Wiki-like syntax] is supported. | |||
[[File:Gerrit_Intro_Commenting.png]] | [[File:Gerrit_Intro_Commenting.png|1200x1200px]] | ||
[[File: | [[File:Gerrit Intro CommentDrafts.png|1200x1200px]] | ||
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. | 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 ===== | =====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: | 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: | ||
[[File:Gerrit_Intro_CheckingOut.png]] | [[File:Gerrit_Intro_CheckingOut.png|1200x1200px]] | ||
[[File:DownloadPatch2.png|1200x1200px]] | |||
<pre> | <pre> | ||
$ git fetch ssh://qtcontributor@codereview.qt. | $ git fetch ssh://qtcontributor@codereview.qt-project.org:29418/qt/qtbase refs/changes/19/419/1 && git checkout FETCH_HEAD | ||
From ssh://codereview.qt. | From ssh://codereview.qt-project.org:29418/qt/qtbase | ||
* branch refs/changes/19/419/1 -> FETCH_HEAD | * branch refs/changes/19/419/1 -> FETCH_HEAD | ||
Note: checking out 'FETCH_HEAD'. | Note: checking out 'FETCH_HEAD'. | ||
Line 243: | Line 222: | ||
This makes it possible to use the usual git commands to view changes, to build the code, and to run tests. | This makes it possible to use the usual git commands to view changes, to build the code, and to run tests. | ||
==== Publishing Comments ==== | ====Publishing Comments==== | ||
When all files are reviewed, the reviewer continues to the Publish Comments screen with the Review button. | 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 review is completed by writing an optional cover message and giving a score. The cover message uses the same [https://wiki.hpdd.intel.com/display/PUB/2012/02/16/Comment+formatting+on+Gerrit Wiki-like syntax] as inline comments. | ||
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). | 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). | ||
A Sanity Review score should '''not''' be given unless the [[ | A Sanity Review score should '''not''' be given unless the [[Early Warning System|Sanity Bot]] made a mistake and needs to be overridden. | ||
[[File:Gerrit_Intro_Publishing.png]] | [[File:Gerrit_Intro_Publishing.png|1000x1000px]] | ||
[[File:Gerrit_Intro_Published.png]] | [[File:Gerrit_Intro_Published.png|1200x1200px]] | ||
===== Publishing Review Results From The Command Line ===== | =====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. | 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 === | ===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 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. | ||
Line 267: | Line 246: | ||
The contributor processes the feedback by following these steps: | The contributor processes the feedback by following these steps: | ||
# Opening the Change page (entered from the Dashboard or following a link in a notification mail) | #Opening the Change page (entered from the Dashboard or following a link in a notification mail) | ||
# Locating comments in the Change page | #Locating comments in the Change page | ||
# Reading and writing in-line comments | #Reading and writing in-line comments | ||
# Publishing a reply and/or uploading a new Patch Set | #Publishing a reply and/or uploading a new Patch Set | ||
==== Locating Comments in The Change ==== | ====Locating Comments in The Change==== | ||
Comments are located | Comments are located in their own tab next to the files tab. | ||
[[File:Gerrit_Intro_Comments.png]] | [[File:Gerrit_Intro_Comments.png|1200x1200px]] | ||
==== Reading in-line Comments ==== | ====Reading in-line Comments==== | ||
Replies can be posted by clicking the | Replies can be posted by clicking the 'Reply' button as shown in the image below: | ||
[[File:Gerrit_Intro_Replying.png]] | [[File:Gerrit_Intro_Replying.png|1200x1200px]] | ||
Note that the comments are '''not''' actually posted until you publish them. | Note that the comments are '''not''' actually posted until you publish them. | ||
Line 288: | Line 267: | ||
'''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. | '''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 === | ===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. | 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. | ||
Line 294: | Line 273: | ||
Updating a Change is done by following these steps: | Updating a Change is done by following these steps: | ||
# Accessing the Changes | #Accessing the Changes | ||
# Modifying the Change(s) | #Modifying the Change(s) | ||
# Pushing updated Changes | #Pushing updated Changes | ||
==== Accessing The Changes ==== | |||
====Note for github/bitbucket/... users==== | |||
''Note'', that in contrast to ''github'', ''bitbucket'', ''gitlab'' etc., in Gerrit the change under review is a single commit. | |||
(In github etc. the review is about whether to merge the feature branch into master, in Gerrit the review is about whether the commit should be accepted into master.) | |||
So in order to change the content of a review, there must be a single new commit that contains everything you would like to review. | |||
This is not "rewriting public history" because the commits under review are not (yet) part of the "public history" – only after they are accepted, they become part of the projects history. | |||
The following sections explain how to create a new commit that is suitable to replace the old commit for the review. | |||
====Accessing The Changes==== | |||
If the original commit(s) are still available, it is possible to amend them right away. Otherwise, download the Change(s) the same way as for local review. | If the original commit(s) are still available, it is possible to amend them right away. Otherwise, download the Change(s) the same way as for local review. | ||
Line 312: | Line 300: | ||
''Note:'' Please do '''not''' rebase unnecessarily, as this makes inter-diffs much less useful. | ''Note:'' Please do '''not''' rebase unnecessarily, as this makes inter-diffs much less useful. | ||
==== Modifying Commits ==== | ====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 <tt>git rebase --interactive</tt> to revise earlier commits. | Modifications in the working tree are committed with the --amend option. If the contribution consists of multiple commits, you will need to use <tt>git rebase --interactive</tt> to revise earlier commits. | ||
Line 330: | Line 318: | ||
Pay even more attention to copying the Change-Id when you redo commits from scratch. | Pay even more attention to copying the Change-Id when you redo commits from scratch. | ||
==== Pushing Updated Changes ==== | ====Pushing Updated Changes==== | ||
The commit(s) are uploaded back to Gerrit with the same target ref as before. After the push, new Patch Sets will have been created for the target Change(s): | The commit(s) are uploaded back to Gerrit with the same target ref as before. After the push, new Patch Sets will have been created for the target Change(s): | ||
<pre> | <pre> | ||
$ git push | $ git push gerrit HEAD:refs/for/dev | ||
Counting objects: 6, done. | Counting objects: 6, done. | ||
Delta compression using up to 2 threads. | Delta compression using up to 2 threads. | ||
Line 343: | Line 331: | ||
remote: Resolving deltas: 100% (2/2) | remote: Resolving deltas: 100% (2/2) | ||
remote: Processing changes: updated: 1, refs: 1, done | remote: Processing changes: updated: 1, refs: 1, done | ||
To ssh://qtcontributor@codereview.qt. | To ssh://qtcontributor@codereview.qt-project.org:29418/qt/qtbase.git | ||
* [new branch] HEAD -> refs/for/dev | * [new branch] HEAD -> refs/for/dev | ||
$ | $ | ||
</pre> | </pre> | ||
[[ | If anything goes wrong at this stage, please see the [[Gerrit Caveats and Hints| troubleshooting chart]]. Otherwise, when you reload the gerrit page in your browser, you should see the change, like this: | ||
[[File:Gerrit_Intro_Updating.png|1200x1200px]] | |||
==Integrating Changes== | |||
To submit a Change to the CI system press the "Stage". button on the top right | |||
It is usually best when the contributor submits their own Changes. | It is usually best when the contributor submits their own Changes. | ||
Even if there are multiple reviewers, only one +2 approval is required. However, if other reviewers have shown a specific interest in a contribution, such as by repeated comments, it is polite to give them some time to add a +1 or +2 before submitting. | Even if there are multiple reviewers, only one +2 approval is required. However, if other reviewers have shown a specific interest in a contribution, such as by repeated comments, it is polite to give them some time to add a +1 or +2 before submitting. See the [[Review_Policy]] for more details. | ||
[[File:Gerrit_Intro_Submitting.png]] | [[File:Gerrit_Intro_Submitting.png|1200x1200px]] | ||
=== Continuous Integration === | ===Continuous Integration=== | ||
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. | 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. | ||
Line 371: | Line 358: | ||
As part of the customization, Changes gained 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 at regular intervals and move them to the Integrating state. From the Integrating state Changes are either submitted or moved back to the New state. If builds succeed and tests pass, the Changes are submitted or merged into their destination branch. Otherwise they are moved back to the New state for further analysis. The contributor of the affected Change(s) is expected to analyze the failure and upload fixes as necessary. | As part of the customization, Changes gained 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 at regular intervals and move them to the Integrating state. From the Integrating state Changes are either submitted or moved back to the New state. If builds succeed and tests pass, the Changes are submitted or merged into their destination branch. Otherwise they are moved back to the New state for further analysis. The contributor of the affected Change(s) is expected to analyze the failure and upload fixes as necessary. | ||
== Abandoning and Deferring Contributions == | ==Abandoning and Deferring Contributions== | ||
Changes which are inherently flawed or became inapplicable should be abandoned. | Changes which are inherently flawed or became inapplicable should be abandoned. | ||
Line 382: | Line 369: | ||
Abandoning is a normal operation that is used to maintain Gerrit and hide Changes that will not make their way to the Git repository, for any reason. | Abandoning is a normal operation that is used to maintain Gerrit and hide Changes that will not make their way to the Git repository, for any reason. | ||
To abandon a Change, its owner or an Administrator can click the "Abandon | To abandon a Change, its owner or an Administrator can click the "Abandon" button: | ||
[[File:Gerrit_Intro_Abandon.png]] | [[File:Gerrit_Intro_Abandon.png|1200x1200px]] | ||
[[File:Gerrit_Intro_Abandoned.png]] | [[File:Gerrit_Intro_Abandoned.png|1200x1200px]] | ||
== Feature Branches == | ==Feature Branches== | ||
The Qt Project's handling of branches is documented by the [[Branch Guidelines]]. | The Qt Project's handling of branches is documented by the [[Branch Guidelines]]. | ||
=== Topics vs. Branches === | ===Topics vs. Branches=== | ||
Gerrit topics can be used as "feature branches". A topic is created when a target ref like <tt>refs/for/<branch name> | Gerrit topics can be used as "feature branches". A topic is created when a target ref like <tt>refs/for/<branch name>%topic=<topic name></tt> is used. 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 === | ===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. | 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 === | ===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. | 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. | ||
== | ==Moving Changes to Different Branches== | ||
It sometimes happens that you push a change for the wrong branch. To correct this mistake, do '''''not''''' create a new change, but instead ask Gerrit to move the existing change to a new branch. You'll find the action in the menu opened by the "three vertical dots" button near the top right of each change. | |||
Take care to make subsequent pushes of the change to the new branch, as otherwise a duplicate will be created. | |||
If the action cannot be executed (typically, you are not the Change's owner, or a conflicting Change exists), ask a [https://codereview.qt-project.org/#/admin/groups/1,members Gerrit Administrator] to deal with the issue. | |||
==Closing Remarks== | |||
See [[Gerrit Caveats and Hints]] to avoid common traps. | |||
There is a process for [[Requesting New Repositories|requesting new repositories]]. | |||
Report bugs in our Gerrit to | Report bugs in our Gerrit to [https://bugreports.qt.io/issues/?jql=project%20%3D%20QTQAINFRA%20AND%20component%20%3D%20Gerrit the bugtracker]. Ideally, provide a link to an [http://code.google.com/p/gerrit/issues/list upstream issue] (note that the issue may be already closed, as we are typically lagging by several versions). |
Latest revision as of 09:57, 11 September 2024
Note, if you are a first time Gerrit user, please take a look at the Setting up Gerrit page.
Overview
NB., the screenshots were taken from a very old version of Gerrit, and consequently should be viewed as ideographic.
Also, the current version of Gerrit comes with its own introduction.
People familiar with GitHub/GitLab may appreciate this rundown of workflow differences.
Main Features
Gerrit is a web-based tool that is used for code review. Its main features are side-by-side difference viewing and inline commenting. These make 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 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 dev branch, the target ref will be refs/for/dev.
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 (identifiers) 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:
- Creating or updating the local repository
- Optionally creating a topic branch
- Creating commits
- Uploading the commit(s) to Gerrit
- Soliciting feedback
Creating a topic branch
Keep code organized in topic branches. This is what Git excels in. "next-big-thing" is used as an example topic branch below:
$ git switch -c next-big-thing Switched to a new branch 'next-big-thing' $
Creating Commits
See the Git Introduction to get started.
Here are a few notes specific to Qt/Gerrit:
- If you correctly set up the clone, the commit message editor will present you with a template for the message.
- The guidelines for creating good commit messages – and creating good commits in general, for that matter – are outlined in the Commit Policy.
- 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 have been added.
Uploading Commits
Changes are pushed to Gerrit with git push or git gpush(see below). 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: 100% (2/2) remote: Processing changes: new: 1, refs: 1, done remote: remote: New Changes: remote: https://codereview.qt-project.org/12345 remote: To ssh://qtcontributor@codereview.qt-project.org:29418/qt/qtbase * [new branch] HEAD -> refs/for/dev $
When pushing to Gerrit, a typical 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=<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 For more information on using Git Scripts see our page on Git Scripts.
$ git gpush [same output as above]
Once a Change has been created, it can be viewed in the web browser:
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 pen icon next to the names of the "Reviewers" to add any other registered user(s) to the review.
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 "Your" page, also known as the "Dashboard":
It is possible to find Changes by issuing search queries. Links for the Change owner, project name and branch name in the search result listings can be used to quickly search for related Changes.
The navigation bar at the top of the Gerrit web view provides quick access to common search queries under the "Your" and "Changes" items.
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:
- Opening the Change page (entered from the Dashboard or following a link in a notification mail)
- Reviewing changed files
- 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.
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.
Note that comments are formatted as flowed text, discarding individual line breaks. A simple Wiki-like syntax is supported.
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:
$ git fetch ssh://qtcontributor@codereview.qt-project.org:29418/qt/qtbase refs/changes/19/419/1 && git checkout FETCH_HEAD From ssh://codereview.qt-project.org: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' $
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 cover message uses the same Wiki-like syntax as inline comments.
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).
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:
- Opening the Change page (entered from the Dashboard or following a link in a notification mail)
- Locating comments in the Change page
- Reading and writing in-line comments
- Publishing a reply and/or uploading a new Patch Set
Locating Comments in The Change
Comments are located in their own tab next to the files tab.
Reading in-line Comments
Replies can be posted by clicking the 'Reply' button as shown in the image below:
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:
- Accessing the Changes
- Modifying the Change(s)
- Pushing updated Changes
Note for github/bitbucket/... users
Note, that in contrast to github, bitbucket, gitlab etc., in Gerrit the change under review is a single commit. (In github etc. the review is about whether to merge the feature branch into master, in Gerrit the review is about whether the commit should be accepted into master.) So in order to change the content of a review, there must be a single new commit that contains everything you would like to review. This is not "rewriting public history" because the commits under review are not (yet) part of the "public history" – only after they are accepted, they become part of the projects history. The following sections explain how to create a new commit that is suitable to replace the old commit for the review.
Accessing The Changes
If the original commit(s) are still available, it is possible to amend them right away. Otherwise, download the Change(s) the same way as for local review.
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 $
Pay even more attention to copying the Change-Id when you redo commits from scratch.
Pushing Updated Changes
The commit(s) are uploaded back to Gerrit with the same target ref as before. After the push, new Patch Sets will have been created for the target Change(s):
$ 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), 419 bytes, done. Total 4 (delta 2), reused 0 (delta 0) remote: Resolving deltas: 100% (2/2) remote: Processing changes: updated: 1, refs: 1, done To ssh://qtcontributor@codereview.qt-project.org:29418/qt/qtbase.git * [new branch] HEAD -> refs/for/dev $
If anything goes wrong at this stage, please see the troubleshooting chart. Otherwise, when you reload the gerrit page in your browser, you should see the change, like this:
Integrating Changes
To submit a Change to the CI system press the "Stage". button on the top right
It is usually best when the contributor submits their own Changes.
Even if there are multiple reviewers, only one +2 approval is required. However, if other reviewers have shown a specific interest in a contribution, such as by repeated comments, it is polite to give them some time to add a +1 or +2 before submitting. See the Review_Policy for more details.
Continuous Integration
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.
As part of the customization, Changes gained 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 at regular intervals and move them to the Integrating state. From the Integrating state Changes are either submitted or moved back to the New state. If builds succeed and tests pass, the Changes are submitted or merged into their destination branch. Otherwise they are moved back to the New state for further analysis. The contributor of the affected Change(s) is expected to analyze the failure and upload fixes as necessary.
Abandoning and Deferring Contributions
Changes which are inherently flawed or became inapplicable should 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.
Changes which have potential but will not be worked on in the near future should be deferred. Deferred Changes are basically abandoned, but are more easily accessible via the "My Deferred Changes" menu item.
Abandoning is a normal operation that is used to maintain Gerrit and hide Changes that will not make their way to the Git repository, for any reason.
To abandon a Change, its owner or an Administrator can click the "Abandon" button:
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 target ref like refs/for/<branch name>%topic=<topic name> is used. 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.
Moving Changes to Different Branches
It sometimes happens that you push a change for the wrong branch. To correct this mistake, do not create a new change, but instead ask Gerrit to move the existing change to a new branch. You'll find the action in the menu opened by the "three vertical dots" button near the top right of each change.
Take care to make subsequent pushes of the change to the new branch, as otherwise a duplicate will be created.
If the action cannot be executed (typically, you are not the Change's owner, or a conflicting Change exists), ask a Gerrit Administrator to deal with the issue.
Closing Remarks
See Gerrit Caveats and Hints to avoid common traps.
There is a process for requesting new repositories.
Report bugs in our Gerrit to the bugtracker. Ideally, provide a link to an upstream issue (note that the issue may be already closed, as we are typically lagging by several versions).