• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1#!/usr/bin/env python
2# Copyright 2015 the V8 project authors. All rights reserved.
3# Use of this source code is governed by a BSD-style license that can be
4# found in the LICENSE file.
5
6import mergeinfo
7import shutil
8import unittest
9
10from collections import namedtuple
11from os import path
12from subprocess import Popen, PIPE, check_call
13
14TEST_CONFIG = {
15  "GIT_REPO": "/tmp/test-v8-search-related-commits",
16}
17
18class TestMergeInfo(unittest.TestCase):
19
20  base_dir = TEST_CONFIG["GIT_REPO"]
21
22  def _execute_git(self, git_args):
23
24    fullCommand = ["git", "-C", self.base_dir] + git_args
25    p = Popen(args=fullCommand, stdin=PIPE,
26        stdout=PIPE, stderr=PIPE)
27    output, err = p.communicate()
28    rc = p.returncode
29    if rc != 0:
30      raise Exception(err)
31    return output
32
33  def _update_origin(self):
34    # Fetch from origin to get/update the origin/main branch
35    self._execute_git(['fetch', 'origin'])
36
37  def setUp(self):
38    if path.exists(self.base_dir):
39      shutil.rmtree(self.base_dir)
40
41    check_call(["git", "init", self.base_dir])
42
43    # Add fake remote with name 'origin'
44    self._execute_git(['remote', 'add', 'origin', self.base_dir])
45
46    # Initial commit
47    message = '''Initial commit'''
48
49    self._make_empty_commit(message)
50
51  def tearDown(self):
52    if path.exists(self.base_dir):
53      shutil.rmtree(self.base_dir)
54
55  def _assert_correct_standard_result(
56      self, result, all_commits, hash_of_first_commit):
57    self.assertEqual(len(result), 1, "Main commit not found")
58    self.assertTrue(
59        result.get(hash_of_first_commit),
60        "Main commit is wrong")
61
62    self.assertEqual(
63        len(result[hash_of_first_commit]),
64        1,
65        "Child commit not found")
66    self.assertEqual(
67        all_commits[2],
68        result[hash_of_first_commit][0],
69        "Child commit wrong")
70
71  def _get_commits(self):
72    commits = self._execute_git(
73        ["log", "--format=%H", "--reverse"]).splitlines()
74    return commits
75
76  def _get_branches(self, hash):
77    return mergeinfo.get_branches_for_commit(self.base_dir, hash)
78
79  def _make_empty_commit(self, message):
80    self._execute_git(["commit", "--allow-empty", "-m", message])
81    self._update_origin()
82    return self._get_commits()[-1]
83
84  def testCanDescribeCommit(self):
85    commits = self._get_commits()
86    hash_of_first_commit = commits[0]
87
88    result = mergeinfo.describe_commit(
89        self.base_dir,
90        hash_of_first_commit).splitlines()
91
92    self.assertEqual(
93        result[0],
94        'commit ' + hash_of_first_commit)
95
96  def testCanDescribeCommitSingleLine(self):
97    commits = self._get_commits()
98    hash_of_first_commit = commits[0]
99
100    result = mergeinfo.describe_commit(
101        self.base_dir,
102        hash_of_first_commit, True).splitlines()
103
104    self.assertEqual(
105        str(result[0]),
106        str(hash_of_first_commit[0:7]) + ' Initial commit')
107
108  def testSearchFollowUpCommits(self):
109    commits = self._get_commits()
110    hash_of_first_commit = commits[0]
111
112    message = 'Follow-up commit of '  + hash_of_first_commit
113    self._make_empty_commit(message)
114    self._make_empty_commit(message)
115    self._make_empty_commit(message)
116    commits = self._get_commits()
117    message = 'Not related commit'
118    self._make_empty_commit(message)
119
120    followups = mergeinfo.get_followup_commits(
121        self.base_dir,
122        hash_of_first_commit)
123    self.assertEqual(set(followups), set(commits[1:]))
124
125  def testSearchMerges(self):
126    self._execute_git(['branch', 'test'])
127    self._execute_git(['checkout', 'main'])
128    message = 'real initial commit'
129    self._make_empty_commit(message)
130    commits = self._get_commits()
131    hash_of_first_commit = commits[0]
132
133    self._execute_git(['checkout', 'test'])
134    message = 'Not related commit'
135    self._make_empty_commit(message)
136
137    # This should be found
138    message = 'Merge '  + hash_of_first_commit
139    hash_of_hit = self._make_empty_commit(message)
140
141    # This should be ignored
142    message = 'Cr-Branched-From: '  + hash_of_first_commit
143    hash_of_ignored = self._make_empty_commit(message)
144
145    self._execute_git(['checkout', 'main'])
146
147    followups = mergeinfo.get_followup_commits(
148        self.base_dir,
149        hash_of_first_commit)
150
151    # Check if follow ups and merges are not overlapping
152    self.assertEqual(len(followups), 0)
153
154    message = 'Follow-up commit of '  + hash_of_first_commit
155    hash_of_followup = self._make_empty_commit(message)
156
157    merges = mergeinfo.get_merge_commits(self.base_dir, hash_of_first_commit)
158    # Check if follow up is ignored
159    self.assertTrue(hash_of_followup not in merges)
160
161    # Check for proper return of merges
162    self.assertTrue(hash_of_hit in merges)
163    self.assertTrue(hash_of_ignored not in merges)
164
165  def testIsLkgr(self):
166    commits = self._get_commits()
167    hash_of_first_commit = commits[0]
168    self._make_empty_commit('This one is the lkgr head')
169    self._execute_git(['branch', 'remotes/origin/lkgr'])
170    hash_of_not_lkgr = self._make_empty_commit('This one is not yet lkgr')
171
172    branches = self._get_branches(hash_of_first_commit);
173    self.assertTrue(mergeinfo.is_lkgr(branches))
174    branches = self._get_branches(hash_of_not_lkgr);
175    self.assertFalse(mergeinfo.is_lkgr(branches))
176
177  def testShowFirstCanary(self):
178    commits = self._get_commits()
179    hash_of_first_commit = commits[0]
180
181    branches = self._get_branches(hash_of_first_commit);
182    self.assertEqual(mergeinfo.get_first_canary(branches), 'No Canary coverage')
183
184    self._execute_git(['branch', 'remotes/origin/chromium/2345'])
185    self._execute_git(['branch', 'remotes/origin/chromium/2346'])
186
187    branches = self._get_branches(hash_of_first_commit);
188    self.assertEqual(mergeinfo.get_first_canary(branches), '2345')
189
190  def testFirstV8Version(self):
191    commits = self._get_commits()
192    hash_of_first_commit = commits[0]
193
194    self._execute_git(['branch', 'remotes/origin/chromium/2345'])
195    self._execute_git(['branch', 'remotes/origin/chromium/2346'])
196    branches = self._get_branches(hash_of_first_commit);
197    self.assertEqual(mergeinfo.get_first_v8_version(branches), '--')
198
199    self._execute_git(['branch', 'remotes/origin/5.7.1'])
200    self._execute_git(['branch', 'remotes/origin/5.8.1'])
201    branches = self._get_branches(hash_of_first_commit);
202    self.assertEqual(mergeinfo.get_first_v8_version(branches), '5.7.1')
203
204    self._execute_git(['branch', 'remotes/origin/5.6.1'])
205    branches = self._get_branches(hash_of_first_commit);
206    self.assertEqual(mergeinfo.get_first_v8_version(branches), '5.6.1')
207
208if __name__ == "__main__":
209   unittest.main()
210