如何更改一系列提交的作者?


当前回答

我发现所提供的版本非常激进,特别是如果你从其他开发人员那里提交补丁,这将从本质上窃取他们的代码。

下面的版本确实适用于所有分支机构,并分别更改作者和发件人以防止这种情况发生。

感谢leif81的所有选择。

#!/bin/bash

git filter-branch --env-filter '
if [ "$GIT_AUTHOR_NAME" = "<old author>" ];
then
    GIT_AUTHOR_NAME="<new author>";
    GIT_AUTHOR_EMAIL="<youmail@somehost.ext>";
fi
if [ "$GIT_COMMITTER_NAME" = "<old committer>" ];
then
    GIT_COMMITTER_NAME="<new commiter>";
    GIT_COMMITTER_EMAIL="<youmail@somehost.ext>";
fi
' -- --all

其他回答

我也想添加我的示例。我想用给定的参数创建一个bash_function。

这在mint-linux 17.3中有效

# $1 => email to change, $2 => new_name, $3 => new E-Mail

function git_change_user_config_for_commit {

 # defaults
 WRONG_EMAIL=${1:-"you_wrong_mail@hello.world"}
 NEW_NAME=${2:-"your name"}
 NEW_EMAIL=${3:-"new_mail@hello.world"}

 git filter-branch -f --env-filter "
  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
 " --tag-name-filter cat -- --branches --tags;
}

注意:这个答案会改变SHA1,所以在已经推送的分支上使用它时要小心。如果你只想修复一个名字的拼写或更新一封旧邮件,Git可以让你不用使用.mailmap重写历史。

使用回扣

首先,如果您还没有这样做,您可能需要在git-config中修复您的名称:

git config --global user.name "New Author Name"
git config --global user.email "<email@address.example>"

这是可选的,但它也将确保重置提交者名称,假设这是您所需要的。

要使用rebase重写一系列提交的元数据,请执行

git rebase -r <some commit before all of your bad commits> \
    --exec 'git commit --amend --no-edit --reset-author'

--exec将在每次提交被重写后运行gitcommit步骤(就像您运行gitcommit&&gitrebase一样——重复继续)。

如果您还想更改第一次提交(也称为“root”提交),则必须在rebase调用中添加--root。

这将把提交人和作者都更改为user.name/user.email配置。如果不想更改该配置,可以使用--author“New author Name”<email@address.example>“而不是--reset-author。请注意,这样做不会更新提交者,只更新作者。

单次提交

如果您只想更改最近的提交,则无需重新设置基准。只需修改承诺:

 git commit --amend --no-edit --reset-author

整个项目历史

git rebase -r --root --exec "git commit --amend --no-edit --reset-author"

对于较旧的Git客户端(2020年7月之前)

-r、 --您可能不存在重基合并。作为替换,可以使用-p。请注意,-p存在严重问题,现已弃用。

运行git-rebase-i<sha1或起点的ref>使用edit(或e)标记要更改的所有提交循环执行以下两个命令,直到处理完所有提交:gitcommit--modify--reuse message=HEAD--author=“新作者<new@author.email>";git rebase—继续

这将保留所有其他提交信息(包括日期)。--reuse message=HEAD选项阻止消息编辑器启动。

我发现所提供的版本非常激进,特别是如果你从其他开发人员那里提交补丁,这将从本质上窃取他们的代码。

下面的版本确实适用于所有分支机构,并分别更改作者和发件人以防止这种情况发生。

感谢leif81的所有选择。

#!/bin/bash

git filter-branch --env-filter '
if [ "$GIT_AUTHOR_NAME" = "<old author>" ];
then
    GIT_AUTHOR_NAME="<new author>";
    GIT_AUTHOR_EMAIL="<youmail@somehost.ext>";
fi
if [ "$GIT_COMMITTER_NAME" = "<old committer>" ];
then
    GIT_COMMITTER_NAME="<new commiter>";
    GIT_COMMITTER_EMAIL="<youmail@somehost.ext>";
fi
' -- --all

正如docgnome所提到的,重写历史是危险的,会破坏其他人的知识库。

但是,如果您真的想这样做,并且您处于bash环境中(在Linux和Windows中没有问题,您可以使用git bash,这是安装git时提供的),请使用gitfilter分支:

git filter-branch --env-filter '
  if [ $GIT_AUTHOR_EMAIL = bad@email ];
    then GIT_AUTHOR_EMAIL=correct@email;
  fi;
export GIT_AUTHOR_EMAIL'

要加快速度,可以指定要重写的修订范围:

git filter-branch --env-filter '
  if [ $GIT_AUTHOR_EMAIL = bad@email ];
    then GIT_AUTHOR_EMAIL=correct@email;
  fi;
export GIT_AUTHOR_EMAIL' HEAD~20..HEAD