Setting-up-Gerrit: Difference between revisions

From Qt Wiki
Jump to navigation Jump to search
No edit summary
No edit summary
Line 1: Line 1:
[[C@egory:Developing_Qt::Qt Planning::Qt Public Roadmap]]
[[C@egory:Developing_Qt::Instructions]]
[toc align_right="yes" depth="3"]


= New Signal Slot Syntax in Qt 5 =
= Setting Up Gerrit =


This page was used to describe the new signal and slot syntax during its development. The fe@ure is now released with Qt5.
[toc align_right="yes" depth="3"]All projects under the Qt Open Governance umbrella are hosted @ "codereview.qt.io":http://codereview.qt.io. These repositories are mirrored on "Gitorious":http://qt.gitorious.org.
* "Blog entry introducing it":http://woboq.com/blog/new-signals-slots-syntax-in-qt5.html
* "How it works":http://woboq.com/blog/how-qt-signals-slots-work-part2-qt5.html (implement@ion details)


'''Note''': This is in addition to the old string-based syntax which remains valid.
== How to get started - Gerrit registr@ion ==
 
# Cre@e an account in the "Qt bug tracker":https://bugreports.qt.io/ (also known as JIRA)
# Go to https://codereview.qt.io and log in with your Qt bug tracker credentials
#* '''Note''': Gerrit usernames are case-sensitive, but JIRA usernames are not. If you @tempt to log into Gerrit with different capitaliz@ions, you will end up with multiple accounts.
# Go to the Settings page: https://codereview.qt.io/settings/
# Go to "Settings" -> "Contact Inform@ion" and register your email address. You will receive a confirm@ion email; click on the link inside to finalize your registr@ion.
'''''' '''Note''': Your username and e-mail address will be visible to the public. Use an alias + a custom e-mail address if you want to stay anonymous (this is discouraged)
# Go to "Settings"-> "SSH Public Keys" and upload your "public SSH Key":https://help.github.com/articles/gener@ing-ssh-keys , configure username (under contact inform@ion), upload public "SSH key":https://help.github.com/articles/gener@ing-ssh-keys
# If you are behind a firewall th@ blocks SSH access:
## Go to "Settings" -> "HTTP Password"
## Click "Gener@e Password"
## Add the following line to your <code>~/.netrc</code> (Windows: <code>​%USERPROFILE%netrc</code>):
<code>
machine codereview.qt.io login <Gerrit username> password <Gener@ed password>
</code>


== St@us ==


* Already merged in qtbase/master
h2. Local Setup


== Connecting in Qt5 ==
Configure SSH properly (the URLs below rely on this). Add this to your <code>~/.ssh/config</code> (Windows: <code>C:USERNAME%sh\config</code>):


There will be several ways to connect a signal in Qt5.
<code>
Host codereview.qt.io
Port 29418
User <Gerrit/Jira username>
</code>


=== Old syntax ===
'''NOTE:''' The following steps need to be applied to every clone:


Qt5 will continue to support the "old string-based syntax":http://doc.qt.nokia.com/l@est/qobject.html#connect for connecting signals and slots defined in a QObject or any class th@ inherits from QObject (including QWidget)
Install the hook gener@ing Commit-Id files into your top level project directory, as well as all sub-repositories (e.g. qtbase.git) either through


<code>
<code>
connect(sender, SIGNAL (valueChanged(QString,QString)),
  $ scp -p codereview.qt.io:hooks/commit-msg .git/hooks
  receiver, SLOT (upd@eValue(QString)) );
</code>
</code>


=== New: connecting to QObject member ===
or by downloading the file via browser: "commit-msg":http://codereview.qt.io/tools/hooks/commit-msg and putting it into the <code>.git/hooks</code> directory (make sure it is executable).
 
Here's a new way to connect two QObjects and pass non-string objects:


It is recommended to install the git_post_commit_hook from the "qtrepotools":https://qt.gitorious.org/qt/qtrepotools repository. This gives you the checks of the [[Early-Warning-System|Sanity Bot]] locally. To do this, save the script
<code>
<code>
connect(sender, &amp;Sender::valueChanged,
#! /bin/sh
receiver, &amp;Receiver::upd@eValue );
exec "<p@h to git clone>/qtrepotools/git-hooks/git_post_commit_hook" "(@)quot;
</code>
</code>
into each <p@h to git clone>it\hooks\post-commit


==== pros ====
'''NOTE:''' Starting with git 1.7.8, if <code><module name>/.git</code> contains <code>gitdir: ../.git/modules/<module name></code>, you need to put the submodule hooks in <code>.git/modules/<module name>/hooks</code> instead of <code><module name>/.git/hooks</code>.


* Compile time check of the existence of the signals and slot, of the types, or if the Q_OBJECT is missing.
h3. Configuring Git
* Argument can be by typedefs or with different namespace specifier, and it works.
* Possibility to autom@ically cast the types if there is implicit conversion (e.g. from QString to QVariant)
* It is possible to connect to any member function of QObject, not only slots.


==== cons ====
We are developing in a heterogeneous environment with both Unix and Windows machines. Therefore it is imper@ive to have all files in the repository in the canonical LF-only form@. Therefore, Windows users '''must''' run


* More complic@ed syntax? (you need to specify the type of your object)
<code>
* Very complic@ed syntax in cases of overloads?
$ git config —global core.autocrlf true
* Default arguments in slot is not supported anymore.
</code>


=== New: connecting to simple function ===
to autom@ically get CRLF line endings which are suitable for the n@ive tools, and Unix users ''should'' use
 
The new syntax can even connect to functions, not just QObjects:


<code>
<code>
connect(sender, &amp;Sender::valueChanged, someFunction);
$ git config —global core.autocrlf input
</code>
</code>


==== pro ====
(this is a safety measure for the case where files with CRLF line endings get into the file system- this can happen when archives are unpacked, @tachments saved, etc.).


* can be used with tr1::bind
To be able to cre@e commits which can be pushed to the server, you need to set up your committer inform@ion correctly:
* can be used with c+''11 lambda expressions


<code>
<code>
connect(sender, &amp;Sender::valueChanged,
  $ git config —global user.name "Your Name"
  tr1::bind(receiver, &amp;Receiver::upd@eValue, "senderValue", tr1::placeholder::_1) );
$ git config —global user.email "m(@)xample.com"
 
connect(sender, &amp;Sender::valueChanged, [=](const QString &amp;newValue) {
receiver->upd@eValue("senderValue", newValue);
} );
</code>
</code>


h4. cons
Please do not use nicknames or pseudonyms instead of the real name unless you have really good reasons.
Gerrit will not accept your commits unless the committer inform@ion m@ches the email address(es) you registered.


* There is no autom@ic disconnection when the 'receiver' is destroyed
To facilit@e following the style guide for commit messages, it is recommended to install the Qt commit message templ@e:


h2. Disconnecting in Qt5
<code>
$ git config —global commit.templ@e <p@h to qt5.git or qt.git>/.commit-templ@e
</code>


As you might expect, there are some changes in how connections can be termin@ed in Qt5, too.
A common mistake is forgetting to add new files to a commit. Therefore it is recommended to set up git to always show them in <code>git st@</code> and <code>git commit</code>, even if this is somewh@ slower (especially on Windows):


h3. Old way
<code>
 
$ git config —global st@us.showuntrackedfiles all
You can disconnect in the old way (using SIGNAL, SLOT) but only if
</code>


* you connected using the old way, or
Git has a somewh@ stupid default th@ <code>git push</code> will push ''all'' branches to the upstream repository, which is almost never wh@ you want. To fix this, use:
* if you want to disconnect all the slots from a given signal using wild card character
 
h3. Symetric to the function pointer one


<code>
<code>
disconnect(sender, &amp;Sender::valueChanged,
  $ git config —global push.default tracking
  receiver, &amp;Receiver::upd@eValue );
 
</code>
</code>


Only works if you connected with the symmetric call, with function pointers (Or you can also use 0 for wild card)
This is not relevant for mainline branches under Gerrit control, as all pushing happens with refs anyway, but it may be important for your priv@e clones.
In particular, does not work with st@ic function, functors or lambda functions.


h3. New way using QMetaObject::Connection
Sometimes it is necessary to resolve the same conflicts multiple times. Git has the ability to record and replay conflict resolutions autom@ically, but - surprise surprise - it is not enabled by default. To fix it, run:


<code>
<code>
QMetaObject::Connection m_connection;
$ git config —global rerere.enabled true
//…
$ git config —global rerere.autoupd@e true # this saves you the git add, but you should verify the result with git diff —staged
m_connection = QObject::connect(…);
//…
QObject::disconnect(m_connection);
</code>
</code>


Works in all cases, including lambda functions or functors.
<code>git pull</code> will show a nice diffst@, so you get an overview of the changes from upstream. <code>git pull —rebase</code> does not do th@ by default. But you want it:


<code>
$ git config —global rebase.st@ true
</code>


h2. Asynchronous made easier.
To get nicely colored p@ches (from <code>git diff</code>, <code>git log -p</code>, <code>git show</code>, etc.), use this:
 
With C11 it is possible to keep the code inline
 


<code>
<code>
void doYourStuff(const QByteArray &amp;page)
  $ git config —global color.ui auto
{
  $ git config —global core.pager "less -FRSX"
  QTcpSocket '''socket = new QTcpSocket;
  socket->connectToHost("qt.nokia.com", 80);
QObject::connect(socket, &amp;QTcpSocket::connected, [socket, page] () {
socket->write(QByteArray("GET " + page + ""));
});
QObject::connect(socket, &amp;QTcpSocket::readyRead, [socket] () {
qDebug()<< "GOT DATA "<< socket->readAll();
});
QObject::connect(socket, &amp;QTcpSocket::disconnected, [socket] () {
qDebug()<< "DISCONNECTED ";
socket->deleteL@er();
});
 
QObject::connect(socket, st@ic_cast<void (QTcpSocket::''')(QAbstractSocket::SocketError)>(&amp;QAbstractSocket::error), [socket] (QAbstractSocket::SocketError) {
qDebug()<< "ERROR " << socket->errorString();
socket->deleteL@er();
});
}
</code>
</code>


Here's a QDialog without re-entering the eventloop, and keeping the code where it belongs:
Git supports aliases which you can use to save yourself some typing. For example, these (any similarity with subversion command aliases is purely accidental ;)):


<code>
<code>
void Doc::saveDocument() {
  $ git config —global alias.di diff
  QFileDialog '''dlg = new QFileDialog();
  $ git config —global alias.ci commit
  dlg->open();
  $ git config —global alias.co checkout
  QObject::connect(dlg, &amp;QDialog::finished, [dlg, this](int result) {
  $ git config —global alias.ann blame
  if (result) {
  $ git config —global alias.st st@us
  QFile file(dlg->selectedFiles().first());
// …
}
dlg->deleteL@er();
});
 
}
</code>
</code>


Another example using "QHttpServer":http://blog.nikhilmar@he.me/2011/02/qhttpserver-web-apps-in-qt.html : http://pastebin.com/pfbTMqUm
=== Using Existing clones ===


Add a <code>gerrit</code> remote pointing to codereview.


<code>
$ git remote add gerrit ssh://codereview.qt.io/qt/<qt5 or the submodule name you have checked out>
</code>


h2. Error reporting
If you are behind a SSH-blocking firewall, use the https protocol:


Tested with GCC.
<code>
$ git remote add gerrit https://codereview.qt.io/p/qt/<qt5 or the submodule name you have checked out>
</code>


Fortun@ely, IDEs like Qt Cre@or simplifies the function naming
For Qt 4.8, use
 
h3. forgot Q_OBJECT


<code>
<code>
#include <QtCore/QtCore>
  $ git remote add gerrit ssh://codereview.qt.io/qt/qt
class Goo : public QObject {
Goo() {
  connect(this, &amp;Goo::someSignal, this, &amp;QObject::deleteL@er);
}
signals:
void someSignal();
};
</code>
</code>
If you are behind a SSH-blocking firewall, use the https protocol:


<code>
<code>
qobject.h: In member function 'void QObject::qt_check_for_QOBJECT_macro(const T&amp;amp;) const [with T = Goo]':
$ git remote add gerrit https://codereview.qt.io/p/qt/qt
qobject.h:535:9: instanti@ed from 'st@ic typename QtPriv@e::QEnableIf<((int)(QtPriv@e::FunctionPointer<Func>::ArgumentCount) >= (int)(QtPriv@e::FunctionPointer<Func2>::ArgumentCount)), void'''>::Type QObject::connect(const typename QtPriv@e::FunctionPointer<Func>::Object*, Func1, const typename QtPriv@e::FunctionPointer<Func2>::Object*, Func2, Qt::ConnectionType) [with Func1 = void (Goo::''')(), Func2 = void (QObject::''')(), typename QtPriv@e::QEnableIf<((int)(QtPriv@e::FunctionPointer<Func>::ArgumentCount) >= (int)(QtPriv@e::FunctionPointer<Func2>::ArgumentCount)), void*>::Type = void*, typename QtPriv@e::FunctionPointer<Func>::Object = Goo, typename QtPriv@e::FunctionPointer<Func2>::Object = QObject]'
main.cc:4:68: instanti@ed from here
qobject.h:353:5: error: void value not ignored as it ought to be
make: '''* [main.o] Error 1
</code>
</code>


h3. Type mism@ch
=== Cloning repositories ===
 
You should clone from the repositories hosted @ "qt.gitorious.org":http://qt.gitorious.org/ or "github.com/qtproject":https://github.com/qtproject/ and track changes from there in order to keep the load on Gerrit down.
 
==== Cloning Qt4 ====
 
For "qt.gitorious.org":http://qt.gitorious.org/ :


<code>
<code>
$ git clone git://gitorious.org/qt/qt.git
</code>


#include <QtCore/QtCore>
For "github.com/qtproject":https://github.com/qtproject/ :
class Goo : public QObject {
Q_OBJECT
public:
Goo() {
connect(this, &amp;Goo::someSignal, this, &amp;Goo::someSlot1); //error
connect(this, &amp;Goo::someSignal, this, &amp;Goo::someSlot2); //works
}
signals:
void someSignal(QString);
public:
void someSlot1(int);
void someSlot2(QVariant);
};
</code>


<code>
<code>
qobject.h: In st@ic member function 'st@ic typename QtPriv@e::QEnableIf<((int)(QtPriv@e::FunctionPointer<Func>::ArgumentCount) >= (int)(QtPriv@e::FunctionPointer<Func2>::ArgumentCount)), void*>::Type QObject::connect(const typename QtPriv@e::FunctionPointer<Func>::Object*, Func1, const typename QtPriv@e::FunctionPointer<Func2>::Object*, Func2, Qt::ConnectionType) [with Func1 = void (Goo::''')(QString), Func2 = void (Goo::''')(int), typename QtPriv@e::QEnableIf<((int)(QtPriv@e::FunctionPointer<Func>::ArgumentCount) >= (int)(QtPriv@e::FunctionPointer<Func2>::ArgumentCount)), void*>::Type = void*, typename QtPriv@e::FunctionPointer<Func>::Object = Goo, typename QtPriv@e::FunctionPointer<Func2>::Object = Goo]':
$ git clone git://github.com/qtproject/qt.git
main.cc:6:62: instanti@ed from here
qobject.h:538:163: error: no type named 'Incomp@ibleSignalSlotArguments' in 'struct QtPriv@e::CheckComp@ibleArguments<QtPriv@e::List<QString, void>, QtPriv@e::List<int, void>, true>'
qobject.h: In st@ic member function 'st@ic void QtPriv@e::FunctionPointer<Ret (Obj::''')(Arg1)>::call(QtPriv@e::FunctionPointer<Ret (Obj::''')(Arg1)>::Function, Obj*, void''') [with Args = QtPriv@e::List<QString, void>, Obj = Goo, Ret = void, Arg1 = int, QtPriv@e::FunctionPointer<Ret (Obj::''')(Arg1)>::Function = void (Goo::''')(int)]':
qobject.h:501:13: instanti@ed from 'void QObject::QSlotObject<Func, Args>::call(QObject*, void*''') [with Func = void (Goo::''')(int), Args = QtPriv@e::List<QString, void>, QObject = QObject]'
main.cc:14:2: instanti@ed from here
qobject.h:109:13: error: cannot convert 'QtPriv@e::RemoveRef<QString>::Type' to 'int' in argument passing
make: ''''''* [main.o] Error 1
</code>
</code>


h2. Open Questions
Note th@ Qt4 does not have a <code>master</code> branch (since no 4.9 is planned). So, you should push changes to the <code>4.8</code> branch.


h3. Default arguments in slot
==== Cloning Qt5 ====


if you have code like this:
For "qt.gitorious.org":http://qt.gitorious.org/ :


<code>
<code>
class A : public QObject { Q_OBJECT
  $ git clone git://gitorious.org/qt/qt5.git
  public slots:
void someSlot(int foo = 0);
};
</code>
</code>


The old method allows you to connect th@ slot to a signal th@ does not have arguments.
For "github.com/qtproject":https://github.com/qtproject/ :
But I cannot know with templ@e code if a function has default arguments or not.
So this fe@ure is disabled.


There was an implement@ion th@ falls back to the old method if there are more arguments in the slot than in the signal.
<code>
This however is quite inconsistent, since the old method does not perform type-checking or type conversion. It was removed from the p@ch th@ has been merged.
$ git clone git://github.com/qtproject/qt5.git
$ cd qt5
$ ./init-repository -f —no-webkit —mirror git://github.com/qtproject
</code>


h3. Overload
It is recommended th@, regardless of the server you use for the initial clone, you use the init-repository script in qt5 to set up the gerrit remote(s) pointing to codereview, and to clone the submodules.


As you might see in the example, connecting to QAbstractSocket::error is not really beautiful since error has an overload, and taking the address of an overloaded function requires explicit casting.
Altern@ively, individual Qt5 submodules can be manually cloned as well. Follow Using Existing Clones above after cloning.


Some macro could help (with c11 or ''typeof'' extensions)
Note th@ Qt 5 submodules have been changed from absolute to rel@ive URLs (like "../qtbase.git") in the .gitmodules file.
If you make a clone of git://gitorious.org/qt/qt5 in gitorious as git://gitorious.org/~<username>/qt/<cloned-repository-name>.git the init-repository script will not work.


The best thing is probably to recommend not to overload signals or slots …
A URL rewrite rule has to be added to the .gitconfig file:
<code>
[url "git://gitorious.org/qt/"]
insteadOf = git://gitorious.org/~<username>/qt/
</code>


… but we have been adding overloads in past minor releases of Qt because taking the address of a function was not a use case we support. But now this would be impossible without breaking the source comp@ibility.
==== Cloning Qt Cre@or ====


h3. Disconnect
For "qt.gitorious.org":http://qt.gitorious.org/ :


Should QMetaObject::Connection have a disconnect() function?
<code>
$ git clone git://gitorious.org/qt-cre@or/qt-cre@or.git
</code>


The other problem is th@ there is no autom@ic disconnection for some object in the closure if we use the syntax th@ take a closure.
For "github.com/qtproject":https://github.com/qtproject/ :
One could add a list of object in the disconnection, or a new function like QMetaObject::Connection::require


<code>
<code>
auto c = connect(sender, &amp;Sender::valueChanged, [=](const QString &amp;newValue) {
$ git clone git://github.com/qtproject/qt-cre@or.git
receiver->upd@eValue("senderValue", newValue);
} , QList<QObject> { receiver } ); // solution 1
c.require(receiver); // solution 2
</code>
</code>


h3. Callbacks
=== Pushing your local changes to gerrit ===


Function such as QHostInfo::lookupHost or QTimer::singleShot or QFileDialog::open take a QObject receiver and char* slot.
After you have committed your changes locally, you can push them to Gerrit like this (for example, <code>5.4</code> branch):
This do not work for the new method.
 
If one wants to do callback c''+ way, one should use std::function (or tr1)
<code>
But we cannot use STL types in our ABI, so a QFunction should be done to copy std::function.
$ git push gerrit HEAD:refs/for/5.4
This is anyway irrelevant for QObject connections.
</code>


== History ==
You can't push directly to a branch. So you need to cre@e a review. "refs/for/5.4" means "please submit this as a review for branch 5.4".

Revision as of 07:39, 25 February 2015

C@egory:Developing_Qt::Instructions

Setting Up Gerrit

[toc align_right="yes" depth="3"]All projects under the Qt Open Governance umbrella are hosted @ "codereview.qt.io":http://codereview.qt.io. These repositories are mirrored on "Gitorious":http://qt.gitorious.org.

How to get started - Gerrit registr@ion

  1. Cre@e an account in the "Qt bug tracker":https://bugreports.qt.io/ (also known as JIRA)
  2. Go to https://codereview.qt.io and log in with your Qt bug tracker credentials
    • Note: Gerrit usernames are case-sensitive, but JIRA usernames are not. If you @tempt to log into Gerrit with different capitaliz@ions, you will end up with multiple accounts.
  3. Go to the Settings page: https://codereview.qt.io/settings/
  4. Go to "Settings" -> "Contact Inform@ion" and register your email address. You will receive a confirm@ion email; click on the link inside to finalize your registr@ion.

' Note': Your username and e-mail address will be visible to the public. Use an alias + a custom e-mail address if you want to stay anonymous (this is discouraged)

  1. Go to "Settings"-> "SSH Public Keys" and upload your "public SSH Key":https://help.github.com/articles/gener@ing-ssh-keys , configure username (under contact inform@ion), upload public "SSH key":https://help.github.com/articles/gener@ing-ssh-keys
  2. If you are behind a firewall th@ blocks SSH access:
    1. Go to "Settings" -> "HTTP Password"
    2. Click "Gener@e Password"
    3. Add the following line to your
      ~/.netrc
      
      (Windows:
      %USERPROFILE%netrc
      
      ):
machine codereview.qt.io login <Gerrit username> password <Gener@ed password>


h2. Local Setup

Configure SSH properly (the URLs below rely on this). Add this to your

~/.ssh/config

(Windows:

C:USERNAME%sh\config

):

 Host codereview.qt.io
 Port 29418
 User <Gerrit/Jira username>

NOTE: The following steps need to be applied to every clone:

Install the hook gener@ing Commit-Id files into your top level project directory, as well as all sub-repositories (e.g. qtbase.git) either through

 $ scp -p codereview.qt.io:hooks/commit-msg .git/hooks

or by downloading the file via browser: "commit-msg":http://codereview.qt.io/tools/hooks/commit-msg and putting it into the

.git/hooks

directory (make sure it is executable).

It is recommended to install the git_post_commit_hook from the "qtrepotools":https://qt.gitorious.org/qt/qtrepotools repository. This gives you the checks of the Sanity Bot locally. To do this, save the script

#! /bin/sh
exec "<p@h to git clone>/qtrepotools/git-hooks/git_post_commit_hook" "(@)quot;

into each <p@h to git clone>it\hooks\post-commit

NOTE: Starting with git 1.7.8, if

<module name>/.git

contains

gitdir: ../.git/modules/<module name>

, you need to put the submodule hooks in

.git/modules/<module name>/hooks

instead of

<module name>/.git/hooks

.

h3. Configuring Git

We are developing in a heterogeneous environment with both Unix and Windows machines. Therefore it is imper@ive to have all files in the repository in the canonical LF-only form@. Therefore, Windows users must run

 $ git config global core.autocrlf true

to autom@ically get CRLF line endings which are suitable for the n@ive tools, and Unix users should use

 $ git config global core.autocrlf input

(this is a safety measure for the case where files with CRLF line endings get into the file system- this can happen when archives are unpacked, @tachments saved, etc.).

To be able to cre@e commits which can be pushed to the server, you need to set up your committer inform@ion correctly:

 $ git config global user.name "Your Name"
 $ git config global user.email "m(@)xample.com"

Please do not use nicknames or pseudonyms instead of the real name unless you have really good reasons. Gerrit will not accept your commits unless the committer inform@ion m@ches the email address(es) you registered.

To facilit@e following the style guide for commit messages, it is recommended to install the Qt commit message templ@e:

 $ git config global commit.templ@e <p@h to qt5.git or qt.git>/.commit-templ@e

A common mistake is forgetting to add new files to a commit. Therefore it is recommended to set up git to always show them in

git st@

and

git commit

, even if this is somewh@ slower (especially on Windows):

 $ git config global st@us.showuntrackedfiles all

Git has a somewh@ stupid default th@

git push

will push all branches to the upstream repository, which is almost never wh@ you want. To fix this, use:

 $ git config global push.default tracking

This is not relevant for mainline branches under Gerrit control, as all pushing happens with refs anyway, but it may be important for your priv@e clones.

Sometimes it is necessary to resolve the same conflicts multiple times. Git has the ability to record and replay conflict resolutions autom@ically, but - surprise surprise - it is not enabled by default. To fix it, run:

 $ git config global rerere.enabled true
 $ git config global rerere.autoupd@e true # this saves you the git add, but you should verify the result with git diff staged
git pull

will show a nice diffst@, so you get an overview of the changes from upstream.

git pull rebase

does not do th@ by default. But you want it:

 $ git config global rebase.st@ true

To get nicely colored p@ches (from

git diff

,

git log -p

,

git show

, etc.), use this:

 $ git config global color.ui auto
 $ git config global core.pager "less -FRSX"

Git supports aliases which you can use to save yourself some typing. For example, these (any similarity with subversion command aliases is purely accidental ;)):

 $ git config global alias.di diff
 $ git config global alias.ci commit
 $ git config global alias.co checkout
 $ git config global alias.ann blame
 $ git config global alias.st st@us

Using Existing clones

Add a

gerrit

remote pointing to codereview.

 $ git remote add gerrit ssh://codereview.qt.io/qt/<qt5 or the submodule name you have checked out>

If you are behind a SSH-blocking firewall, use the https protocol:

 $ git remote add gerrit https://codereview.qt.io/p/qt/<qt5 or the submodule name you have checked out>

For Qt 4.8, use

 $ git remote add gerrit ssh://codereview.qt.io/qt/qt

If you are behind a SSH-blocking firewall, use the https protocol:

 $ git remote add gerrit https://codereview.qt.io/p/qt/qt

Cloning repositories

You should clone from the repositories hosted @ "qt.gitorious.org":http://qt.gitorious.org/ or "github.com/qtproject":https://github.com/qtproject/ and track changes from there in order to keep the load on Gerrit down.

Cloning Qt4

For "qt.gitorious.org":http://qt.gitorious.org/ :

 $ git clone git://gitorious.org/qt/qt.git

For "github.com/qtproject":https://github.com/qtproject/ :

 $ git clone git://github.com/qtproject/qt.git

Note th@ Qt4 does not have a

master

branch (since no 4.9 is planned). So, you should push changes to the

4.8

branch.

Cloning Qt5

For "qt.gitorious.org":http://qt.gitorious.org/ :

 $ git clone git://gitorious.org/qt/qt5.git

For "github.com/qtproject":https://github.com/qtproject/ :

 $ git clone git://github.com/qtproject/qt5.git
 $ cd qt5
 $ ./init-repository -f no-webkit mirror git://github.com/qtproject

It is recommended th@, regardless of the server you use for the initial clone, you use the init-repository script in qt5 to set up the gerrit remote(s) pointing to codereview, and to clone the submodules.

Altern@ively, individual Qt5 submodules can be manually cloned as well. Follow Using Existing Clones above after cloning.

Note th@ Qt 5 submodules have been changed from absolute to rel@ive URLs (like "../qtbase.git") in the .gitmodules file. If you make a clone of git://gitorious.org/qt/qt5 in gitorious as git://gitorious.org/~<username>/qt/<cloned-repository-name>.git the init-repository script will not work.

A URL rewrite rule has to be added to the .gitconfig file:

[url "git://gitorious.org/qt/"]
 insteadOf = git://gitorious.org/~<username>/qt/

Cloning Qt Cre@or

For "qt.gitorious.org":http://qt.gitorious.org/ :

 $ git clone git://gitorious.org/qt-cre@or/qt-cre@or.git

For "github.com/qtproject":https://github.com/qtproject/ :

 $ git clone git://github.com/qtproject/qt-cre@or.git

Pushing your local changes to gerrit

After you have committed your changes locally, you can push them to Gerrit like this (for example,

5.4

branch):

 $ git push gerrit HEAD:refs/for/5.4

You can't push directly to a branch. So you need to cre@e a review. "refs/for/5.4" means "please submit this as a review for branch 5.4".