• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1#!/usr/bin/env python3
2# coding=utf-8
3#
4# Copyright (c) 2022-2024 Huawei Device Co., Ltd.
5# Licensed under the Apache License, Version 2.0 (the "License");
6# you may not use this file except in compliance with the License.
7# You may obtain a copy of the License at
8#
9# http://www.apache.org/licenses/LICENSE-2.0
10#
11# Unless required by applicable law or agreed to in writing, software
12# distributed under the License is distributed on an "AS IS" BASIS,
13# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14# See the License for the specific language governing permissions and
15# limitations under the License.
16
17import git
18import os
19import re
20import sys
21
22LINTER_PATH = 'ets2panda/linter'
23
24merge_re = re.compile(r'Merge pull request !')
25revert_re = re.compile(r'This reverts commit (.+)\.')
26cherry_pick_re = re.compile(r'\(cherry picked from commit (.+)\)')
27
28
29def get_branch_map(repo, branch_name, path):
30    result = {}
31
32    commits = list(repo.iter_commits(branch_name, path))
33    commits.reverse()
34    for commit in commits:
35        msg = commit.message
36        if merge_re.search(msg) is not None:
37            continue
38
39        revert_match = revert_re.search(msg)
40        if revert_match is not None:
41            sha = revert_match.group(1)
42            if sha in result:
43                del result[sha]
44                continue
45
46        cherry_pick_match = cherry_pick_re.search(msg)
47        sha = commit.hexsha if cherry_pick_match is None else cherry_pick_match.group(1)
48        if sha not in result:
49            result[sha] = commit
50        else:
51            raise Exception(f'Duplicate commit {sha}')
52
53    return result
54
55
56def print_complement(of, to):
57    print('-' * 40)
58    for sha in to:
59        if sha not in of:
60            commit = to[sha]
61            print('{}\n\n{}'.format(commit.hexsha, commit.message.strip('\n')))
62            print('-' * 40)
63
64
65def main():
66    if len(sys.argv) != 3:
67        print('Usage:\n{} first_branch_name second_branch_name'.format(sys.argv[0]))
68        return -1
69
70    first_branch_name = sys.argv[1]
71    second_branch_name = sys.argv[2]
72
73    repo = git.Repo(os.getcwd() + '/../..')
74    first_branch_map = get_branch_map(repo, first_branch_name, LINTER_PATH)
75    second_branch_map = get_branch_map(repo, second_branch_name, LINTER_PATH)
76
77    print('Commits in `{}`, but not in `{}`:\n'.format(first_branch_name, second_branch_name))
78    print_complement(second_branch_map, first_branch_map)
79
80    print('\n')
81    print('=' * 80)
82    print('\n')
83
84    print('Commits in `{}`, but not in `{}`:\n'.format(second_branch_name, first_branch_name))
85    print_complement(first_branch_map, second_branch_map)
86
87    return 0
88
89if __name__ == '__main__':
90    sys.exit(main())
91