nntrn / save

https://nntrn.github.io/save/
2 stars 0 forks source link

Git Commands #7

Open nntrn opened 1 year ago

nntrn commented 1 year ago

ls-tree

List files in another branch

git -p ls-tree -r --name-only mybranch:mydir

git config

# Cache credentials for each local directory where you clone a repository
git config --global credential.useHttpPath true

# Use SSH instead of HTTPS when connecting 
git config --global url.ssh://git@github.com/.insteadOf https://github.com/

Speed up Git in Windows

# does filesystem operations in parallel to hide latency
git config --global core.preloadindex true

# fixes UAC issues
git config --global core.fscache true

# minimizes the number of files in .git
git config --global gc.auto 256
# get latest commit id
git rev-parse upstream/master
nntrn commented 1 year ago

git filter-branch

Remove files in commits

git filter-branch --index-filter 'git rm --cached --ignore-unmatch public/*' HEAD

Remove empty commits

git filter-branch --commit-filter 'git_commit_non_empty_tree "$@"' -f HEAD

Update name and email in commits

git filter-branch --env-filter '
WRONG_EMAIL="nntrn@wrong.com"
NEW_NAME="nntrn"
NEW_EMAIL="17685332+nntrn@users.noreply.github.com"

if [ "$GIT_COMMITTER_EMAIL" = "$WRONG_EMAIL" ]
then
    export GIT_COMMITTER_NAME="$NEW_NAME"
    export GIT_COMMITTER_EMAIL="$NEW_EMAIL"
fi
if [ "$GIT_AUTHOR_EMAIL" = "$WRONG_EMAIL" ]
then
    export GIT_AUTHOR_NAME="$NEW_NAME"
    export GIT_AUTHOR_EMAIL="$NEW_EMAIL"
fi
' -f HEAD

Remove commits by author

git filter-branch --commit-filter '
if [ "$GIT_AUTHOR_NAME" != "nntrn" ];
then
  skip_commit "$@"
else
  git commit-tree "$@"
fi' -f HEAD
nntrn commented 1 year ago

git filter

Hide secrets in commits

# ~/.gitconfig or .git/config
[filter "cleanPass"]
  clean = sed -e 's/secretpassword/hiddenpassword/g'
  smudge = sed -e 's/hiddenpassword/secretpassword/g'
# .gitattributes or .git/info/attributes
.env text eol=lf filter=cleanPass
$ echo "PASSWORD=secretpassword" >.env
$ git add .env
$ git commit -m "Add .env"

$ git show HEAD:.env
PASSWORD=hiddenpassword

$ cat .env
PASSWORD=secretpassword

Source: https://developers.redhat.com/articles/2022/02/02/protect-secrets-git-cleansmudge-filter

nntrn commented 1 year ago

Preserve changes

This method creates a new branch from your current one to preserve your changes. The commits on the new branch are undone, and then only the files you want to preserve are recommitted.

# This preserves your old files.
git checkout -b new_branch_name
# See the list of your commits. # Find the hash of the last commit before your changes.
git log
# Where abcdef is the hash found in the step above.
git reset --soft abcdef
# Commit the found files into the new_branch_name.
git commit <files_to_preserve> -m "preserved files"

[Source]

nntrn commented 1 year ago

Global changes

To make global changes across the source tree, it‘s often easiest to use sed with git-ls-files, using -i for in-place changing (this is generally safe, as we don’t use symlinks much, but there are few places that do). Remember that you don't need to use xargs, since sed can take multiple input files. E.g., to strip trailing whitespace from C++ and header files:

sed -i -E 's/\s+$//' $(git ls-files '*.cpp' '*.h')

You may also find git-grep useful for limiting the scope of your changes, using -l for listing files.

sed -i -E '...' $(git grep -lw Foo '*.cpp' '*.h')

Remember that you can restrict sed actions to matching (or non-matching) lines. For example, to skip lines with a line comment, use the following:

'\,//, ! s/foo/bar/g'

[Source]

nntrn commented 1 year ago
previous command new command
git checkout <branch> git switch <branch>
git checkout N/A (use git status)
git checkout -b <new_branch> [<start_point>] git switch -c <new-branch> [<start-point>]
git checkout -B <new_branch> [<start_point>] git switch -C <new-branch> [<start-point>]
git checkout --orphan <new_branch> git switch --orphan <new-branch>
git checkout --orphan <new_branch> <start_point> N/A (use git switch <start-point> then git switch --orphan <new-branch>)
git checkout [--detach] <commit> git switch --detach <commit>
git checkout --detach [<branch>] git switch --detach [<branch>]
git checkout [--] <pathspec>… git restore [--] <pathspec>…
git checkout --pathspec-from-file=<file> git restore --pathspec-from-file=<file>
git checkout <tree-ish> [--] <pathspec>… git restore -s <tree> [--] <pathspec>…
git checkout <tree-ish> --pathspec-from-file=<file> git restore -s <tree> --pathspec-from-file=<file>
git checkout -p [<tree-ish>] [--] [<pathspec>…] git restore -p [-s <tree>] [--] [<pathspec>…]

Source: Answer to What's the difference between git switch and git checkout <branch>

nntrn commented 1 year ago

label git diff

MOD_PATTERN='^.+(\[-|\{\+).*$' \
ADD_PATTERN='^\{\+.*\+\}$' \
REM_PATTERN='^\[-.*-\]$' \
git diff --word-diff --unified=0 | sed -nr \
    -e "s/$MOD_PATTERN/modified/p" \
    -e "s/$ADD_PATTERN/added/p" \
    -e "s/$REM_PATTERN/removed/p" \
    | sort | uniq -c

https://stackoverflow.com/a/9933440