Difference between revisions of "Bazaar"
m |
|||
Line 13: | Line 13: | ||
To fetch development branches or the trunk using Bazaar, you need [http://bazaar-vcs.org/ Bazaar]. You should make yourself familiar with the basic documentation. | To fetch development branches or the trunk using Bazaar, you need [http://bazaar-vcs.org/ Bazaar]. You should make yourself familiar with the basic documentation. | ||
− | To contribute back, we | + | To contribute back, we recommend you "rebase" your work before we integrate it, if possible; this makes all integration conflicts happen to you, and not the poor merging operator. You'll need the [http://bazaar-vcs.org/Rebase bzr-rebase] plugin for that. |
To take over the merging operator duty and manage the two way syncing of the Bazaar branches and SVN, you'll need the [http://bazaar-vcs.org/BzrForeignBranches/Subversion bzr-svn] plugin and its somewhat difficult dependencies. Difficult unless you run Ubuntu, then you get everything you need apart from the plugin itself. Lucky bastard. | To take over the merging operator duty and manage the two way syncing of the Bazaar branches and SVN, you'll need the [http://bazaar-vcs.org/BzrForeignBranches/Subversion bzr-svn] plugin and its somewhat difficult dependencies. Difficult unless you run Ubuntu, then you get everything you need apart from the plugin itself. Lucky bastard. | ||
Line 29: | Line 29: | ||
In the following, we assume your username at launchpad is john.doe, and you want to work at our [https://code.launchpad.net/~armagetronad-dev/armagetronad/trunk-armagetronad-work trunk branch]; the URL to the writable branch then is bzr+ssh://john.doe@bazaar.launchpad.net/~armagetronad-dev/armagetronad/trunk-armagetronad-work. If you're just interested in read only access, you can use the read only URL http://bazaar.launchpad.net/~armagetronad-dev/armagetronad/trunk-armagetronad-work instead. If you want to access a branch maintained by a single developer named jane.doe, replace ~armagetronad-dev with ~jane.doe; just check the branch details on launchpad. We'll abbreviate the URL you're going to use as <URL>, because we're lazy typers. | In the following, we assume your username at launchpad is john.doe, and you want to work at our [https://code.launchpad.net/~armagetronad-dev/armagetronad/trunk-armagetronad-work trunk branch]; the URL to the writable branch then is bzr+ssh://john.doe@bazaar.launchpad.net/~armagetronad-dev/armagetronad/trunk-armagetronad-work. If you're just interested in read only access, you can use the read only URL http://bazaar.launchpad.net/~armagetronad-dev/armagetronad/trunk-armagetronad-work instead. If you want to access a branch maintained by a single developer named jane.doe, replace ~armagetronad-dev with ~jane.doe; just check the branch details on launchpad. We'll abbreviate the URL you're going to use as <URL>, because we're lazy typers. | ||
− | == | + | == Distributed, shmistributed. I just want to work on the mainline or someone else's development branch. Is there no simple way? == |
− | + | There is. You can use bzr in a mode where it behaves like SVN; in this mode, you store no local history, and all operations like commits and log queries go to the remote server. Fetching a local copy of a branch in this way is called a "checkout". Just do | |
+ | bzr checkout <URL> --lightweight | ||
+ | and then use the checkout like an SVN checkout, just replacing 'svn' with 'bzr'. The only noteworthy difference is that in bzr, moves are primitive operations, usable with "bzr mv a b", while in svn, copies are primitive. | ||
− | + | Without the --lightweight, you will fetch the complete history, and read operations on it will no longer go to the remote server. Commits will still go directly to the remote branch. There is a quirk with the launchpad bzr branches, however: directly checking out a branch via its writable URL fails, you have to do the following. Fetch the read-only URL and the writeable URL and do | |
+ | bzr checkout <read only URL> | ||
+ | cd <checkout> | ||
+ | bzr switch <writable URL> | ||
− | + | Anyway, with checkouts, you don't have to worry about managing the branch. If bzr refuses a commit, just do | |
− | + | bzr update | |
− | + | resolve any conflicts, and try again, just like you did with SVN. | |
+ | [https://help.launchpad.net/FeatureHighlights/TeamBranches Read the official Launchpad docs here]. | ||
− | + | == Alternative: Work Branches == | |
− | + | The other way to work with bzr is to use its distributed nature. You fetch a complete copy of a branch for local work: | |
− | |||
− | The | ||
bzr branch <URL> | bzr branch <URL> | ||
cd <branch> | cd <branch> | ||
Line 53: | Line 57: | ||
for that the first time; the next time, you'll only need to use | for that the first time; the next time, you'll only need to use | ||
bzr push | bzr push | ||
− | If bzr tells you that the branches have diverged, | + | If bzr tells you that the branches have diverged, you have two choices: |
+ | |||
+ | === Merge vs. Rebase === | ||
+ | |||
+ | The one way is to merge the changes from the remote branch into yours. This puts all changes that happened in the remote branch into your local branch as an additional change. Do | ||
+ | bzr merge | ||
+ | (resolve conflicts) | ||
+ | bzr commit | ||
+ | bzr push | ||
+ | |||
+ | The other way is to reorder the changes in your local branch to match the order in the remote branch, with your changes coming last. Do | ||
bzr rebase | bzr rebase | ||
bzr pull | bzr pull | ||
bzr push | bzr push | ||
− | + | You'll need the "rebase" plugin mentioned earlier for this. | |
− | |||
− | |||
− | + | The end result is effectively the same; both the changes in the remote branch that happened since your last pull and your changes will be in both branches. However, with "bzr merge", your changes will be first in the history, while with "bzr rebase", the remote changes will be first. Obviously, the result of "bzr rebase" is more correct, and should be picked whenever possible. In the following cases, you should use "bzr merge" instead: | |
− | + | * the remote branch is NOT a mainline branch (trunk, 0.2.8), but a development or hack branch. | |
− | + | * your local branch is not just your private work branch, but a branch you publish and others merge from. | |
+ | In both cases, repeated "bzr rebase" causes repeated conflict possibilities and duplication of changes. We don't want that. | ||
− | + | So, what happens if you use "bzr merge" and push the result back to a mainline branch to integrate it into SVN? Nothing terrible, the sync scripts will notice the change of order in the history and correct it with a merge themselves. The following is a log example where a bzr user merged the change "first change to A from SVN" into his branch after committing the "added B in bzr" change to it: | |
− | + | ------------------------------------------------------------------------ | |
− | + | r7 | manuel | 2008-02-10 16:29:13 +0100 (Sun, 10 Feb 2008) | 17 lines | |
− | + | Automatic merging of commits that would change history order: | |
+ | ------------------------------------------------------------ | ||
+ | revno: 2.1.2 | ||
+ | committer: Manuel Moos <z-man@users.sf.net> | ||
+ | branch nick: A-trunk-work | ||
+ | timestamp: Sun 2008-02-10 14:45:13 +0100 | ||
+ | message: | ||
+ | merging in bzr: | ||
+ | manuel 2008-02-10 first change to A from SVN | ||
+ | ------------------------------------------------------------ | ||
+ | revno: 2.1.1 | ||
+ | committer: Manuel Moos <z-man@users.sf.net> | ||
+ | branch nick: A-trunk-work | ||
+ | timestamp: Sun 2008-02-10 14:43:48 +0100 | ||
+ | message: | ||
+ | added B in bzr | ||
+ | ------------------------------------------------------------------------ | ||
+ | r5 | manuel | 2008-02-10 14:42:15 +0100 (Sun, 10 Feb 2008) | 2 lines | ||
+ | second change to A on svn | ||
+ | ------------------------------------------------------------------------ | ||
+ | r4 | manuel | 2008-02-10 14:41:44 +0100 (Sun, 10 Feb 2008) | 2 lines | ||
+ | first change to A from SVN | ||
− | + | If the bzr user had done multiple commits, they'd all be collapsed into one commit to SVN. | |
== Development or hack branches == | == Development or hack branches == | ||
Line 99: | Line 133: | ||
It is a good idea to make a backup (a simple copy, or publishing it) of your branch before you do this. | It is a good idea to make a backup (a simple copy, or publishing it) of your branch before you do this. | ||
− | To keep your branch up to date with changes on the mainline, you | + | To keep your branch up to date with changes on the mainline, you can do |
− | bzr | + | bzr merge |
− | bzr | + | (resolve conflicts) |
− | in regular intervals | + | bzr commit |
− | + | in regular intervals. During this process, you may encounter conflicts. Resolve them, then mark them as resolved using "bzr resolved <filename>". | |
− | |||
=== Merging back to the mainline === | === Merging back to the mainline === | ||
If it has been decided that a development branch is ready to be integrated into the mainline, get it up to date one last time: | If it has been decided that a development branch is ready to be integrated into the mainline, get it up to date one last time: | ||
− | bzr | + | bzr merge |
− | bzr | + | bzr commit |
and then push the changes back: | and then push the changes back: | ||
bzr push <mainline URL> | bzr push <mainline URL> | ||
− | All the changes | + | All the changes from your branch will appear as one huge merge in SVN. |
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
=== Integrating changes === | === Integrating changes === | ||
Line 137: | Line 156: | ||
bzr pull ../B | bzr pull ../B | ||
− | and hopefully, if the maintainer of B did his rebasings as he should, that's it, and you can republish your branch A. If not, you'll have to | + | and hopefully, if the maintainer of B did his rebasings/merging as he should, that's it, and you can republish your branch A. If not, you'll have to merge: |
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
cd A | cd A | ||
bzr merge ../B | bzr merge ../B | ||
− | + | (resolve conflicts) | |
bzr commit | bzr commit | ||
− | |||
− | |||
=== Switching the base branch === | === Switching the base branch === | ||
Line 156: | Line 167: | ||
If a development branch was based on a stabilization branch, say 0.3.1, but has been rejected for integration there (say, it was too late), you can just move it to the trunk with | If a development branch was based on a stabilization branch, say 0.3.1, but has been rejected for integration there (say, it was too late), you can just move it to the trunk with | ||
− | bzr | + | bzr merge <URL_OF_TRUNK> |
bzr pull --remember <URL_OF_TRUNK> | bzr pull --remember <URL_OF_TRUNK> | ||
Revision as of 11:59, 10 February 2008
Sections: Installing the Game | Playing the Game | Competition Hub | Server Administration | Extending Armagetron Advanced | Development Docs
Bazaar (bzr) and how we use it
This is work in progress and has not yet been approved by management. Hold your horses.
What we're doing with it
Our main source repository for long term history and releases still is managed with SVN at SourceForge, but our current development trunk and feature development branches that originate from it (and will be eventually merged back) are managed with Bazaar.
Tools you need
To fetch development branches or the trunk using Bazaar, you need Bazaar. You should make yourself familiar with the basic documentation.
To contribute back, we recommend you "rebase" your work before we integrate it, if possible; this makes all integration conflicts happen to you, and not the poor merging operator. You'll need the bzr-rebase plugin for that.
To take over the merging operator duty and manage the two way syncing of the Bazaar branches and SVN, you'll need the bzr-svn plugin and its somewhat difficult dependencies. Difficult unless you run Ubuntu, then you get everything you need apart from the plugin itself. Lucky bastard.
Branch storage
Currently, we're using Launchpad as the primary high performance host for the bzr branches. We have a project and a team registered, and you can browse our main branches. Each branch detail page has instructions what you need to point your bzr at to fetch it and to commit to it.
Mirrors (well, the originals, actually) of the branches that are synced with SVN are available here; the -work branches are the ones mirrored to launchpad, the -sync branches are the hopefully identical copyes that get synced with SVN.
You are encouraged to create your own mirrors of these branches and publish them for others to fetch and to note the location here.
Workflow
In the following, we assume your username at launchpad is john.doe, and you want to work at our trunk branch; the URL to the writable branch then is bzr+ssh://john.doe@bazaar.launchpad.net/~armagetronad-dev/armagetronad/trunk-armagetronad-work. If you're just interested in read only access, you can use the read only URL http://bazaar.launchpad.net/~armagetronad-dev/armagetronad/trunk-armagetronad-work instead. If you want to access a branch maintained by a single developer named jane.doe, replace ~armagetronad-dev with ~jane.doe; just check the branch details on launchpad. We'll abbreviate the URL you're going to use as <URL>, because we're lazy typers.
Distributed, shmistributed. I just want to work on the mainline or someone else's development branch. Is there no simple way?
There is. You can use bzr in a mode where it behaves like SVN; in this mode, you store no local history, and all operations like commits and log queries go to the remote server. Fetching a local copy of a branch in this way is called a "checkout". Just do
bzr checkout <URL> --lightweight
and then use the checkout like an SVN checkout, just replacing 'svn' with 'bzr'. The only noteworthy difference is that in bzr, moves are primitive operations, usable with "bzr mv a b", while in svn, copies are primitive.
Without the --lightweight, you will fetch the complete history, and read operations on it will no longer go to the remote server. Commits will still go directly to the remote branch. There is a quirk with the launchpad bzr branches, however: directly checking out a branch via its writable URL fails, you have to do the following. Fetch the read-only URL and the writeable URL and do
bzr checkout <read only URL> cd <checkout> bzr switch <writable URL>
Anyway, with checkouts, you don't have to worry about managing the branch. If bzr refuses a commit, just do
bzr update
resolve any conflicts, and try again, just like you did with SVN.
Read the official Launchpad docs here.
Alternative: Work Branches
The other way to work with bzr is to use its distributed nature. You fetch a complete copy of a branch for local work:
bzr branch <URL> cd <branch>
There, you do your work; bzr's commands are virtually identical to those of svn, you can add, remove and move files and directories. Use "bzr ignore" to tell bzr to ignore certain files. Use "bzr commit" to record changes.
The big difference to SVN is that all these operations only modify your local copy of the branch. To publish your work, you'll need to get it back to the remote branch. Use
bzr push <URL>
for that the first time; the next time, you'll only need to use
bzr push
If bzr tells you that the branches have diverged, you have two choices:
Merge vs. Rebase
The one way is to merge the changes from the remote branch into yours. This puts all changes that happened in the remote branch into your local branch as an additional change. Do
bzr merge (resolve conflicts) bzr commit bzr push
The other way is to reorder the changes in your local branch to match the order in the remote branch, with your changes coming last. Do
bzr rebase bzr pull bzr push
You'll need the "rebase" plugin mentioned earlier for this.
The end result is effectively the same; both the changes in the remote branch that happened since your last pull and your changes will be in both branches. However, with "bzr merge", your changes will be first in the history, while with "bzr rebase", the remote changes will be first. Obviously, the result of "bzr rebase" is more correct, and should be picked whenever possible. In the following cases, you should use "bzr merge" instead:
- the remote branch is NOT a mainline branch (trunk, 0.2.8), but a development or hack branch.
- your local branch is not just your private work branch, but a branch you publish and others merge from.
In both cases, repeated "bzr rebase" causes repeated conflict possibilities and duplication of changes. We don't want that.
So, what happens if you use "bzr merge" and push the result back to a mainline branch to integrate it into SVN? Nothing terrible, the sync scripts will notice the change of order in the history and correct it with a merge themselves. The following is a log example where a bzr user merged the change "first change to A from SVN" into his branch after committing the "added B in bzr" change to it:
------------------------------------------------------------------------ r7 | manuel | 2008-02-10 16:29:13 +0100 (Sun, 10 Feb 2008) | 17 lines Automatic merging of commits that would change history order: ------------------------------------------------------------ revno: 2.1.2 committer: Manuel Moos <z-man@users.sf.net> branch nick: A-trunk-work timestamp: Sun 2008-02-10 14:45:13 +0100 message: merging in bzr: manuel 2008-02-10 first change to A from SVN ------------------------------------------------------------ revno: 2.1.1 committer: Manuel Moos <z-man@users.sf.net> branch nick: A-trunk-work timestamp: Sun 2008-02-10 14:43:48 +0100 message: added B in bzr ------------------------------------------------------------------------ r5 | manuel | 2008-02-10 14:42:15 +0100 (Sun, 10 Feb 2008) | 2 lines second change to A on svn ------------------------------------------------------------------------ r4 | manuel | 2008-02-10 14:41:44 +0100 (Sun, 10 Feb 2008) | 2 lines first change to A from SVN
If the bzr user had done multiple commits, they'd all be collapsed into one commit to SVN.
Development or hack branches
Whenever you want to do some work you won't be able to finish in one go, you should consider branching a development branch off the current mainline or the current stabilization branch. The same holds if you are not a team member, but want to work on your own code modification of arma and want to keep it up to date with current development, make it easy for others to fetch your changes without getting tons of conflicts, and maybe submit it for integration later.
Creation
To create a development branch of <URL>, pick a local name <name> for it and do
bzr branch <URL> <name> cd <name>
then, you can still work as if you had an SVN checkout, but this time, changes will stay local on your hard disk and will not get committed immediately.
Publishing
To publish your branch on launchpad, select a nice name for it. A good naming convention would be to remove the -work suffix all of the mainline branches have, and replace it with the name of your feature. So, for example, if you want to add flying cylces to the trunk (name trunk-armagetronad-work, URL bzr+ssh://john.doe@bazaar.launchpad.net/~armagetronad-dev/armagetronad/trunk-armagetronad-work), you would name your branch trunk-armagetronad-flyingcycles, and your URL would be bzr+ssh://john.doe@bazaar.launchpad.net/~armagetronad-dev/armagetronad/trunk-armagetronad-flyingcycles. Let's call this URL <URL2>.
To publish your branch, you simply do
bzr push <URL2>
from within your branch.
To publish updates to your branch, you'll only have to do
bzr push
from then on.
Keeping up to date
It is a good idea to make a backup (a simple copy, or publishing it) of your branch before you do this.
To keep your branch up to date with changes on the mainline, you can do
bzr merge (resolve conflicts) bzr commit
in regular intervals. During this process, you may encounter conflicts. Resolve them, then mark them as resolved using "bzr resolved <filename>".
Merging back to the mainline
If it has been decided that a development branch is ready to be integrated into the mainline, get it up to date one last time:
bzr merge bzr commit
and then push the changes back:
bzr push <mainline URL>
All the changes from your branch will appear as one huge merge in SVN.
Integrating changes
To integrate changes done by someone into a branch maintained by you, you should make one local copy of each of these branches, let's call them A and B. A is your branch, B is the branch containing changes to be integrated. Of course, A and B should not be your only copies of the branches.
You then do
cd A bzr pull ../B
and hopefully, if the maintainer of B did his rebasings/merging as he should, that's it, and you can republish your branch A. If not, you'll have to merge:
cd A bzr merge ../B (resolve conflicts) bzr commit
Switching the base branch
NOTE: This does not yet work for 0.2.8 to the trunk. The 0.2.8 branch was started in CVS and merged back incrementally using SVN, this procedure here can't work.
If a development branch was based on a stabilization branch, say 0.3.1, but has been rejected for integration there (say, it was too late), you can just move it to the trunk with
bzr merge <URL_OF_TRUNK> bzr pull --remember <URL_OF_TRUNK>
From then on, you'll receive all the changes from the trunk.
Merging bugfixes
NOTE: This does not yet work for 0.2.8 to the trunk. The 0.2.8 branch was started in CVS and merged back incrementally using SVN, this procedure here can't work.
Say TRUNK is a local copy of a trunk branch, and BRANCH is a stabilization branch (say 0.3.1) branching from it, changes from BRANCH can be merged into TRUNK with bzr using
cd TRUNK bzr merge ../BRANCH (resolve conflicts) bzr commit bzr push <URL of TRUNK>
When editing the commit message, please copy the merge metainformation that you see there into the commit message. SVN does not store the metainfo, so the only way to keep it for us to read is to put it into the commit message.
Sections: Installing the Game | Playing the Game | Competition Hub | Server Administration | Extending Armagetron Advanced | Development Docs