How to retrieve branch whose tree has been removed and deleted? - bazaar

I have a bazaar repository holding several branches. I recently removed one of the trees with bzr remove-tree path/to/branch followed by rm -r path/to/branch. Now if I understand correctly, the repository should still hold the branch history, since I never did bzr remove-branch. However, I can't figure out how to retrieve the branch to continue working on it. Can someone help?

You can use bzr heads --dead to see the heads (= most recent revisions) of deleted branches, including their global revision ids.
You can then do:
bzr branch -r REVISION_ID REPO_DIR BRANCH_DIR
Here, REVISION_ID is the id of the head that you want to restore, REPO_DIR is the directory that holds the repository, and BRANCH_DIR is the directory where you want the branch to be stored.
Edit: If the above doesn't work for some reason, you can also do:
bzr init BRANCH_DIR
cd BRANCH_DIR
bzr pull -r REVISION_ID .
BRANCH_DIR must be underneath the repository directory, of course.

Related

how to get all branchs from repository?

I'm a new user with git, and I use gitBash.
When I execute $git clone http:..../name.git, the master branch of name is downloading. But when I execute $git branch -a I just see the master branch, no others.
But I have some others branchs... Why I can't see all branches ? How do that ?
thx.
git branch -a only displays local branches you have already checked out.
You want to use git branch -r (where -r stands for remote). This should list all the remote branches available (I can't test this right now, but I'm fairly certain it works).

Recreating a bazaar repository while only retaining a few of the branches

(EDIT: Removed my question, leaving a link to the question that confused me, because there's some useful stuff in some of the comments here)
The question here confused me, but was actually answered fully. That question asked how to build a new repository with only a few of the branches of the original repository.
I'm not entirely sure from your post what you're looking for. I'm taking a stab at giving an answer; let me know if that's not what you need.
The following is a simple script to copy all branches from a source to a target repo. Note that it won't work if the branch directory names contain any whitespace. You will have to setup the target repository with bzr init-repo first.
#!/bin/sh
SOURCEREPO=$1
TARGETREPO=$2
if [ ! -d "$TARGETREPO/.bzr" ]; then
echo "$TARGETREPO is not a Bazaar repository; create one with bzr init-repo"
exit 1
fi
BRANCHES=`cd "$SOURCEREPO"; find * -name .bzr -exec dirname '{}' ';'`
for branch in $BRANCHES; do
mkdir -p "$TARGETREPO/$branch"
if [ ! -d "$TARGETREPO/$branch/.bzr" ]; then
echo "Cloning $branch"
bzr branch --use-existing-dir "$SOURCEREPO/$branch" "$TARGETREPO/$branch" \
&& bzr config -d "$TARGETREPO/$branch" --remove parent_location
else
echo "Existing branch in $TARGETREPO/$branch"
fi
done
Basically, it does a bzr branch sourcerepo/branchdir targetrepo/branchdir for all branches and then uses bzr config to get rid of the parent location setting for each copy of a branch (because that location will presumably soon disappear).
I'm not quite sure what you really want here. Adding a remote branch to your local repository and recreating a repository from another are completely different things. The linked question is about the second, and the answers are spot-on, so I will address what you originally intended to do.
First of all, it's confusing when you say "main trunk repository", because "trunk" typically means a "main branch", and branches and repositories are different concepts, so "trunk repository" doesn't really make sense.
It seems to me that you have a shared repository: a container directory for multiple branches. For the sake of clarity: you create a shared repository with the command bzr init-repo, and you create branches in it with bzr init (new empty branch), or with bzr branch (copy of another branch, local or not).
Let's say you have a shared repository organized like this:
└── /tmp/shared/repo
   ├── bugfix123
   ├── feature1
   └── feature2
If you want to add remote branches of your teammates, you can do it with:
bzr branch url_of_remote_branch /tmp/shared/repo/somename
For example if your teammate has a branch at the url lp:~jack/proj/bugfix312 you could get it into your local repository with:
bzr branch lp:~jack/proj/bugfix312 /tmp/shared/repo/bugfix312
If later you decide you don't want to merge this branch, you can get rid of it with the commands:
bzr remove-branch /tmp/shared/repo/bugfix312
rm -fr /tmp/shared/repo/bugfix312
The first command only removes Bazaar's branch data, it keeps the directory intact. The second removes the working directory itself.
Let me know if you are looking for something else.

Can I take a bazaar branch and make it my main shared repository?

I have a bazaar repository on a shared server. I'd like to clean up the repo and set it up from scratch but maintain my history. I don't know how the repository was created initially (is there a way to find out?).
Can I take a branch and make that into my main shared repo?
Is this a viable process:
bzr init-repo --no-trees /home/bzr/myrepository
cd /home/bzr/myrepository
bzr init stable
cp /home/oldbzr/branch_taken_from_current_repo/* ./stable/
cp /home/oldbzr/branch_taken_from_current_repo/.bzr ./stable/
Thanks
A "branch" and a "repo" in Bazaar are totally separate concepts. You don't convert a branch into a repo. What you usually think of as a repo (in SVN or Git, for example) is actually a branch in Bazaar. What you want to do is create a new repo, then copy the old branch into the new repo.
You almost have it right, but you don't want to use "cp", you want to use "bzr branch". Note: You can usually use "cp" to copy branches except when you want Bazaar to move a branch into, out of, or across a repository -- then you need "bzr branch" to intelligently repack the history. So here is what you want to do:
bzr init-repo --no-trees /home/bzr/myrepository
cd /home/bzr/myrepository
bzr branch /home/oldbzr/branch_taken_from_current_repo stable
Note that I am not doing "bzr init" -- I don't want to create a new branch, just copy the old one. And I am not manually copying the old branch or its .bzr directory. If you copy the old branch's .bzr, it will not end up using the new repository. By doing a "bzr branch" it will go "oh hey, I am moving into a repository. Therefore, I will put all of my commit data into the shared repository, and just put a lightweight branch in 'stable'."
You can use just plain branch into your shared repo as mgiuca suggested, but you also can convert your standalone branch to use shared repository. For that your steps should be extended with bzr reconfigure call:
bzr init-repo --no-trees /home/bzr/myrepository
cd /home/bzr/myrepository
bzr init stable
cp /home/oldbzr/branch_taken_from_current_repo/* ./stable/
cp /home/oldbzr/branch_taken_from_current_repo/.bzr ./stable/
cd stable
bzr reconfigure --use-shared
So, if we omit cp then you can create a shared repository "around" your branch:
cd /path/to/my/branch
bzr info # you should see you branch is standalone,
# i.e. not using shared repo
bzr init-repo ../ # create shared repo in parent directory
bzr reconfigure --use-shared # convert standalone branch to repository branch
bzr info # now you should see your branch is using shared repo

git rebase --onto causes conflict — why?

I'm trying a
git rebase --onto master myremote/master~21 myremote/master
to add the latest 21 commits from a remote repository on mine.
What git tells me is that there's a conflict — but how's that possible?
In my understanding it's just taking that 21 commits and applying them on top of my master. How can there be conflicts?
Thanks for help!
I'm doing that btw because somehow I messed up my git-svn repository (the remote), and there's 21 commits which I don't manage to commit to subversion. So I'm trying with a fresh git-svn clone, in which I'm adding those 21 commits.
There is conflict if:
master has commit that are not in myremote/master.
those commits include common files/changes with one the last 21 myremote/master commits.
If somehow the fresh git-svn clone has different SHA1 than the previous git-svn repo, then there is no close common ancestors, and the chances of conflicts are that much higher.
See "How to identify conflicting commits by hash during git rebase?" for illustrations of conflicts during a rebase.
One way to reset your local master to myremote/master would be to:
git checkout -b tmp myremote/master # local tmp branch from myremote/master HEAD.
git merge -s ours master # ignore completely master content
git checkout master
git merge tmp # fast-forward to tmp HEAD
If you hadn't made any changes in your local master before fetching myremote/master, this should work.

Why does git-svn dcommit leave duplicate commits in my git repo? Can I stop it doing that?

My typical git-svn workflow is:
git checkout -b story-xyz
git commit -a -m "work"
git commit -a -m "more work"
git checkout master
git svn fetch
git merge remotes/trunk
git checkout story-xyz
git rebase master (sometimes with -i)
git checkout master
git merge story-xyz
At this point I have my master and story-xyz branches pointing to the same commit, one or more commits ahead of remotes/trunk. Everything since remotes/trunk is in one linear history.
last svn commit [remotes/trunk] <--- work <--- more work [master, story-xyz]
I then run
git svn dcommit
I expected to see the commits between remotes/trunk and master become Subversion revisions, and end up with a single linear history with remotes/trunk, master and story-xyz all pointing to the latest revision, like so:
last svn commit <--- work <--- more work [master, story-xyz, remotes/trunk]
My Subversion revisions go in fine, but I end up with a two-branched structure. The common root of the branch is the Subversion HEAD before I committed. Both branches contain the same series of commits, in the sense that they contain the same diffs. The branch story-xyz is at the head of one branch, remotes/trunk and master at the other:
last svn commit <--- work <--- more work [master, remotes/trunk]
|
\- work <--- more work [story-xyz]
The git commits that I had before running git svn dcommit are on the lower branch (story-xyz), with my git commit messages, git user name and email, and git commit timestamps. The commits on the upper branch are new git commits. They use my Subversion username, the timestamp when I ran the dcommit, and the commit messages have the git-svn-id field appended to them.
This is all OK, and I can carry on working. The problem is that I look in gitk and see what looks like an unmerged branch story-xyz. It's pretty hard to tell the difference between a story branch that I have merged back into master, and one that I haven't. The most obvious way to spot it is the duplicate commit messages. I could delete the story-xyz branch, but that feels like I'm not using git properly and I've lost some of my history.
Am I missing something that would stop git-svn from doing this? Or is this just one of the ways that interacting with Subversion dilutes the power and freedom of git?
I don't think you're really missing anything. You might be doing some unnecessary work, though. In this case, you have two pointers to the "more work" commit, and you are asking git-svn to move one of them. The other one still stays where it is.
You don't really need the master branch. Git-svn doesn't care about what branch you are dcommiting. IIRC, it uses the first svn-remote it can find among the ancestors of the current commit.
I'll offer another version of the workflow:
git checkout -b story-xyz remotes/trunk
git commit -a -m "work"
git commit -a -m "more work"
git svn fetch
git rebase remotes/trunk (with -i, perhaps)
git svn dcommit
This should give you a tree without the extra branch. You need to be careful with fast-forward merges, though.