Git稳定分支:查找未被cherry-pick的提交

22

我有以下的git历史记录:

A --- B --- C --- D' --- E' [master]
 \
  \ --- D --- E --- F [stable]
我们有一个政策,从稳定分支(cherry-pick)挑选所有更改,并将它们应用到主分支上;D'和E'是从稳定分支(cherry-pick)挑选出来的提交,F没有被(cherry-pick)挑选(被遗忘了)。 如何获取一个差异(diff),以显示未被(cherry-pick)挑选到master分支中的F?
我们不想使用合并(merge),因为:
- 没有合并提交的更清晰的历史记录 - 稳定分支的提交很少 - 我们有许多不同的稳定分支
2个回答

18

这正是 git cherry 命令的用途。

它不应该错过未选中的更改,但如果选择操作涉及冲突解决,则偶尔可能列出您认为已选择的更改。


我希望git log有一个--no-merges选项。 - angularsen
1
@anjdreas,似乎在Git 2.13.2中cherry不列出合并提交。 - Fish Monitor

-2

Git 命令无法解决此问题。 我已经编写了这个脚本,它可以帮助。

脚本首先计算分支 branch1 和 branch2 的合并基础。然后从合并基础到 branch1 和 branch2 的头部分别创建两个列表。接着,它创建一个哈希表,其中包含 branch2 上的提交和提交消息的 md5sum。然后,它遍历 branch1 的提交列表,并检查它是否存在于 branch2 的哈希表中。

在上述情况下,branch1 是稳定版,而 branch2 是主版本。

#!/bin/bash

## Usage: ./missing_cherrypicks.sh branch1 branch2
## This script will find commits in branch1 missing in branch2
## Final list of missing commit will be in file missing_commits_branch1_branch2.csv

branch1=$1
branch2=$2

# Calculate mergebase of branch1 and branch2
mb=`git merge-base origin/$1 origin/$2`
rm -rf missing_commits_${branch1}_${branch2}.csv
echo "COMMIT,AUTHOR,MESSAGE,FILESLIST" >> missing_commits_${branch1}_${branch2}.csv

# Get commit list on both branches from merge-base
declare -a commitlist1=`git rev-list $mb..origin/$1`
declare -a commitlist2=`git rev-list $mb..origin/$2`

## Make HashKey for branch2
declare -A CommitHash
for com2 in ${commitlist2[@]}
do
  message2=`git log --pretty=oneline $com2 | head -1| sed "s/${com2} //" | sed 's/ *$//' | cut -c1-35`
  hashkey=`echo $message2 |md5sum |xargs | awk '{print $1}'`
  CommitHash[${hashkey}]=$com2
done

# Find commits of commitlist1 and check if they are in commitlist2
for com1 in ${commitlist1[@]}
do
   message1=`git log --pretty=oneline $com1 | head -1| sed "s/${com1} //"| sed 's/ *$//'| cut -c1-35`
   hashkey1=`echo $message1 |md5sum |xargs | awk '{print $1}'`
   if [[ -z ${CommitHash[${hashkey1}]} ]]
   then
      echo "------$com1-----------"
      author=$(git show $com1 |grep ^Author:|awk -F":" '{print $2}')
      fileslist=`git diff-tree --no-commit-id --name-only -r $com1`
      fl=""
      for file in ${fileslist[@]}
      do
          fl=${fl}":"$file
      done

      echo "------$author-------"
      echo "$com1,$author,$message1,$fl" >> missing_commits_${branch1}_${branch2}.csv
   fi
done

1
你能否详细说明一下如何以及为什么这样解决了OP的问题?仅仅粘贴一些代码并不是一个好的答案,尽管它可能在技术上回答了这个问题。 - Paul Kertscher
脚本首先计算分支branch1和branch2的合并基础。然后它从合并基础到branch1和branch2的末尾分别创建两个列表。接着,它创建了一个基于branch2提交信息md5sum的哈希表。然后,它遍历branch1的提交列表,并检查它是否存在于branch2哈希表中。 - Gaurav Negi
在上面的例子中,branch1 是稳定的分支,而 branch2 是主分支。 - Gaurav Negi
请相应地编辑您的答案,不要在评论中添加细节。 - Paul Kertscher
添加了脚本的详细信息。 - Gaurav Negi

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接