See Fix merge conflicts.
My pull request has not been accepted and they want me to update the commit without making another one (amend the commit)
Amend the commit and force a push.
To keep the work you've done:
git reset --soft origin
To keep the work you've done, but unstaging the files:
git reset origin
To destroy the work you've done:
git reset --hard origin
In all these cases, you can specify the branch: instead of origin
use origin/<branch>
.
Revert a commit by making a new one which goes back to previous code or force a push.
I have made changes via GitHub though (not via Git!); and so the folder on my PC is behind a few commits!
If you want to retrieve the last commits but the very last one, remember that pull
is basically fetch
and then merge
, so let's do the two separately.
If a fork:
git fetch upstream
or, if an original repository:
git remote -v update
Now, git status
should say that you're behind a few commits.
git log origin/master
for the details and the commit names (the hashes).
Now you can merge (fast-forward, in this case) up to the specific commit that you want:
git merge [copy-paste hash here]
Finally, force a push.
git push --force-with-lease
--force-with-lease stops the command if there are other other commits ahead of you. If that happens, you have no other option than to make a new commit which reverts back to previous code.
The --force option instead is the aggressive one, which overwrites any eventual work on the remote branch. Don't use this in a public repository: "rewriting history" is very bad practice; if you do, people who have already cloned your repository would have to be informed of this forced push and they'll have to manually fix their local history e.g. with git pull --rebase
; instead make a new commit which reverts back to previous code.
Where you can use --force?
-
In a private testing repository, e.g. to simplify the history (logs).
-
On a small public branch of a fork you made, e.g. for preparing a small bugfix for a pull request.
Possible situation: you did your changes on the master branch
You are not working on a new branch but on the master branch of your fork. In this case you need to get the data back from the upstream:
git reset --soft upstream/master
git push --force-with-lease
See Fix merge conflicts.
Revert the last commit:
git revert HEAD
In the text editor, change the message if you want and save the file.
Then do a regular push:
git push
Prepare a new commit reverting the last 3 commits:
git revert -n HEAD~3..HEAD
git commit -m "Revert last 3 commits, sorry"
Regular push:
git push
git commit --amend
Then, in the text editor, change the message and save the commit.
Make sure you don't have any unwanted changes staged before doing this or they will get committed too.
Change what you need to. E.g. if you forgot to include my_file.cpp or you have to make some changes to it, you have to stage it again:
git add my_file.cpp
Amend:
git commit --amend --no-edit
--no-edit is to leave the commit message unchanged.
Make another commit or force a push.
Get back the original code:
git restore '*.cpp'
Un-stage files that you staged with git add
:
git reset '*.cpp'
Revert everything:
git restore :/
I changed the code and staged changes with git add
, but I now want to reset everything back to how it was before
git reset --hard origin
git reset --hard master
if original repository (not a fork)
You can specify the branch too:
git reset --hard origin/<branch>
I changed the code and staged changes with git add
, but I then realized that I'm on the wrong branch
It could be a problem about permissions. Do:
git diff
If the output is something like:
diff --git a/src/main.cpp b/src/main.cpp
old mode 100644
new mode 100755
this means that the file in your hard disk has a different permission (mode) than what's in the repository.
This may happen for example when moving a Git repository across different hard drives / partitions, or when moving it across Windows and Linux.
First of all, notice that Git only tracks whether a file is executable or not, not the full set of *nix permissions. So for Git to recognize a change, you can only do +x
or -x
.
Anyway:
You can make Git ignore the executable bit by doing:
git config core.filemode false
That will solve the problem; however, if you do want some files to have executable permissions and you want to save this information on the online repository, you don't want to do that; in this case what you need to do to solve the issue is to change the permissions of the files in your hard drive to match the online repository again:
Remove the executable bit from all files:
sudo chmod -R -x .
This will also revoke your ability to list the directories, so fix it:
sudo chmod -R +X .
Now, if you do have any files you want to keep executable, such as .sh scripts, you'll need to revert those. For each of those files do:
chmod +x ./compile.sh
Do not mount the shared folder automatically, because it will mount it with different and unchangeable permissions. In the machine options, give a name to the folder (in this example shared_folder_name
), uncheck Automatic mount, and do not specify a mount point. Then, edit your /etc/fstab:
shared_folder_name /mnt/existing_folder vboxsf rw,uid=1000,gid=1000,nosuid,nodev,nofail 0 0
-
Option 1: commit the changes.
-
Option 2: stash them in the stack (where you push and pop them from):
git stash
To pull the stash:
git stash pop
-
Option 3: discard the changes:
git reset --hard
or
git checkout --track --force origin/branch
git branch --set-upstream-to=origin/remote_branch local_branch
It doesn't matter, Git doesn't work with the metadata of files. For example, try cloning a new repository, and you'll notice that the modification date of each file is the current date, because you created those files right now in your local filesystem.
Keep in mind that those all caps names like HEAD
are meant to be there, see Named refs.
Clean outdated branches:
git fetch --prune
Maybe it's a tag:
git tag --delete <tag_name>