I got a huge code base, with many changes, I want to branch it, and push it to a remote new branch, but to push only change sets from the last month, make the first change of the month look like i开发者_如何转开发t's the creation of the repository, meaning I don't care about previous changes. I'm sure it's possible, just don't know what's it called and how to do it.
First, let's suppose that you've found the commit from about a month ago that you want to be the new first commit, perhaps with git show HEAD@{1.month.ago}
or by just looking through git log
. Let's say that that commit is f414f31
. Let's also suppose that the name of the branch you're working on is called dev
.
You say that you want it to appear that a later commit was the first one in the repository, so there's no real point in keeping this branch in the same repository - there will be no history in common at all. So, let's create a new empty repository in order to start from a clean slate:
mkdir squashed-repository
cd squashed-repository
git init
Now let's add a remote that refers to your old repository, and fetch all the branches from there as remote-tracking branches in your new repository.
git remote add previous /home/whoever/original-repository/
git fetch previous
Now update your working tree and index from the commit at the start of the month:
git checkout f414f31 .
(Note the .
at the end of that line.)
Now create a commit from the state of the index:
git commit -m 'A new start.'
Now you use git rebase
to replay all of the commits from after f414f31
up to and including previous/dev
on top of your new master
, which currently only has one commit.
git rebase --onto master b1cbc10e84bb2e2 previous/master
You may have to fix some conflicts during that rebase. By default, git rebase
will linearize the history when it reapplies the changes introduced by those commits - you can tell it to try to preserve them with -p
, but that may not work.
Now the master
branch in this new repository should be as you want it, so you can remove the remote we created:
git remote rm previous
I should say that I'd generally try to avoid this type of rewriting of history, especially if you've shared the original repository with anyone. In any case, the earlier history can be really useful - is it really so bad to keep that in your repository?
There is the git checkout --orphan
method that can create an independent branch that can be used in a similar manner, that may save some key strokes.
Obviously (?), as implied by other, things will be simpler if you have selected a simple linear portion of history as your baseline.
Edit: the clone step is detailed at how-to-clone-a-single-branch-in-git
If I get your request correctly, you want to create a new repository starting at a specific point from your current repository. Why? Because you want to keep it clean and eliminate every history behind that certain specific point. Now, that's more likely a good idea, and here is a link to better answer.
The key term here is either squash or filter-branch. You just need to have a backup first.
Above of all, you're requesting a very specific thing to do in GitExtensions. It does not do that. It does not do many things, in all truth... That's why it even gives you a button to command line.
You'll need it. You'll need command line tweaking. If you're not confortable on doing that, then you're out of luck. I know no git gui tools that will do this job for you.
Below, is just part of my previous (now legacy) answer, before op's new comment on his true intents.
If that was not the case, let's assume there's a good reason for "taking a code, branching it, and pushing partially". Then, all you have to do is follow Mark's directions, right there in the other answer.
Or, let's assume it is for backup. Then, that's a bad way to do it. Instead, get a backup tool, and use it. Simple as that. GIT isn't meant for backup and shouldn't be used for such, despite many attempts. I highly advice using CrashPlan or even Dropbox (my referral link).
One potential solution would be using a filter-branch query in order to isolate the relevant commits (one month old or less) in its own repo.
But that means pushing to a new repo, not pushing a new branch in an existing repo.
Unless you create a disjoint branch (a new root commit), with no common history. See "Adding older versions of code to git repo".
In that case, you would indeed push a new branch based on the result of filter-branch
(which serves to split the repo history and isolate the changes that you want).
精彩评论