11

注意:与此类似的问题,但有一些重要的变化。

给定提交 ID,我有以下函数来重写提交日期:

rewrite-commit-date () {
    local commit="$1"
    local newdate="$2"
    newdate="$(date -R --date "$newdate")"
    echo ">>>> Rewriting commit $commit date: $newdate"
    git filter-branch --env-filter \
        "if test \$GIT_COMMIT = '$commit'
         then
             export GIT_AUTHOR_DATE
             export GIT_COMMITTER_DATE
             GIT_AUTHOR_DATE='$newdate'
             GIT_COMMITTER_DATE='$newdate'
         fi" &&
    rm -fr "$(git rev-parse --git-dir)/refs/original/"
}

我正在尝试实现类似的功能rewrite-commit-message来更改提交消息。我想要的是:

  1. 该函数rewrite-commit-message接受两个参数:commit_idnew_commit_message
  2. 无需知道旧的提交信息:拥有commit_id就足以知道要更改哪个提交
  3. git commit --amend,因为这与旧提交有关(不一定与最近的提交有关)
  4. 不用担心重写历史和主仓库:我在一个特性分支工作,我可以这样做git push -f
  5. 我想用filter-branch这个,但我不知道如何:
    • 将更改应用到特定的提交:函数中使用test的是 in ,但我不打算在这里做,因为我不想更改与提交环境相关的任何内容,而是更改提交消息。rewrite-commit-dateenv-filterenv-filter
    • 如何强制提交消息?需要原始--msg-filter提交消息。我不关心原始提交消息。有没有--force-msg-filter类似的?

我正在寻找的内容与类似,但有一些警告:

  1. 不要将更改应用于一系列提交,而是应用于特定提交
  2. 我不关心原始提交消息,因为我想完全覆盖它
4

1 回答 1

8

考虑到以下警告,这个小脚本可以工作:

  1. 这会将您的历史从提交改写到分支的尖端。因为您在问题中说这不是问题,所以这符合条件。

  2. 您的提交包含在master分支中。您可以通过将分支名称作为另一个参数传递来轻松更改此设置,但提交最好在分支中。您可能应该为此建立一些验证,也许使用git rev-parse --abbrev-ref HEAD或也许git branch --all --contains <commit>

无需再费周折:

#!/bin/bash

change-commit-msg(){

  commit="$1"
  newmsg="$2"
  branch="master"

  git checkout $commit
  git commit --amend -m "$newmsg"
  git cherry-pick $commit..$branch
  git branch -f $branch
  git checkout $branch

}

演示

git init
echo init > a && git add . && git commit -m "init"
echo another > a && git commit -am "another"
echo lastly > a && git commit -am "lastly"
git log --graph --oneline --all --decorate
* bca608c (HEAD -> master) lastly
* 4577ab5 another
* b3d018c init
change-commit-msg 4577ab5 "something else"
* c7d03bb (HEAD -> master) lastly
* 3ec2c3e something else
* b3d018c init
于 2016-08-16T21:48:43.723 回答