Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(519)

Side by Side Diff: git_tools.py

Issue 281183003: Eliminate redundant work and control parallelism. (Closed) Base URL: http://src.chromium.org/svn/trunk/tools/deps2git
Patch Set: Created 6 years, 7 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
« no previous file with comments | « deps2git.py ('k') | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 #!/usr/bin/python 1 #!/usr/bin/python
2 # Copyright (c) 2012 The Chromium Authors. All rights reserved. 2 # Copyright (c) 2012 The Chromium Authors. All rights reserved.
3 # Use of this source code is governed by a BSD-style license that can be 3 # Use of this source code is governed by a BSD-style license that can be
4 # found in the LICENSE file. 4 # found in the LICENSE file.
5 5
6
7 import cStringIO 6 import cStringIO
8 import os 7 import os
9 import re 8 import re
10 import subprocess 9 import subprocess
11 import sys 10 import sys
12 import threading 11 import threading
13 12
13 try:
14 import git_cache
15 except ImportError:
16 for p in os.environ['PATH'].split(os.pathsep):
17 if (os.path.basename(p) == 'depot_tools' and
18 os.path.exists(os.path.join(p, 'git_cache.py'))):
19 sys.path.append(p)
20 import git_cache
21
14 22
15 # Show more information about the commands being executed. 23 # Show more information about the commands being executed.
16 VERBOSE = False 24 VERBOSE = False
17 25
18 # The longest any single subprocess will be allowed to run. 26 # The longest any single subprocess will be allowed to run.
19 TIMEOUT = 40 * 60 27 TIMEOUT = 40 * 60
20 28
21 class AbnormalExit(Exception): 29 class AbnormalExit(Exception):
22 pass 30 pass
23 31
(...skipping 23 matching lines...) Expand all
47 def close(self): 55 def close(self):
48 # Empty out the line buffer. 56 # Empty out the line buffer.
49 self.write('\n') 57 self.write('\n')
50 self.out_q.put(None) 58 self.out_q.put(None)
51 self.closed = True 59 self.closed = True
52 60
53 61
54 def GetStatusOutput(cmd, cwd=None, out_buffer=None): 62 def GetStatusOutput(cmd, cwd=None, out_buffer=None):
55 """Return (status, output) of executing cmd in a shell.""" 63 """Return (status, output) of executing cmd in a shell."""
56 if VERBOSE: 64 if VERBOSE:
57 print '' 65 print >> sys.stderr, ''
58 print '[DEBUG] Running "%s"' % cmd 66 print >> sys.stderr, '[DEBUG] Running "%s"' % cmd
59 67
60 def _thread_main(): 68 def _thread_main():
61 thr = threading.current_thread() 69 thr = threading.current_thread()
62 thr.status = -1 70 thr.status = -1
63 thr.stdout = '' 71 thr.stdout = ''
64 thr.stderr = '<timeout>' 72 thr.stderr = '<timeout>'
65 try: 73 try:
66 if out_buffer: 74 if out_buffer:
67 proc = subprocess.Popen(cmd, shell=True, 75 proc = subprocess.Popen(cmd, shell=True,
68 cwd=cwd, stdout=subprocess.PIPE, 76 cwd=cwd, stdout=subprocess.PIPE,
(...skipping 24 matching lines...) Expand all
93 101
94 thr = threading.Thread(target=_thread_main) 102 thr = threading.Thread(target=_thread_main)
95 thr.daemon = True 103 thr.daemon = True
96 thr.start() 104 thr.start()
97 thr.join(TIMEOUT) 105 thr.join(TIMEOUT)
98 106
99 # pylint: disable=E1101 107 # pylint: disable=E1101
100 if VERBOSE: 108 if VERBOSE:
101 short_output = ' '.join(thr.stdout.splitlines()) 109 short_output = ' '.join(thr.stdout.splitlines())
102 short_output = short_output.strip(' \t\n\r') 110 short_output = short_output.strip(' \t\n\r')
103 print '[DEBUG] Output: %d, %-60s' % (thr.status, short_output) 111 print >> sys.stderr, (
112 '[DEBUG] Output: %d, %-60s' % (thr.status, short_output))
104 113
105 return (thr.status, thr.stdout) 114 return (thr.status, thr.stdout)
106 115
107 116
108 def Git(git_repo, command, is_mirror=False, out_buffer=None): 117 def Git(git_repo, command, is_mirror=False, out_buffer=None):
109 """Execute a git command within a local git repo.""" 118 """Execute a git command within a local git repo."""
110 if is_mirror: 119 if is_mirror:
111 if git_repo: 120 if git_repo:
112 cmd = 'git --git-dir=%s %s' % (git_repo, command) 121 cmd = 'git --git-dir=%s %s' % (git_repo, command)
113 else: 122 else:
114 cmd = 'git %s' % command 123 cmd = 'git %s' % command
115 cwd = None 124 cwd = None
116 else: 125 else:
117 cmd = 'git %s' % command 126 cmd = 'git %s' % command
118 cwd = git_repo 127 cwd = git_repo
119 (status, output) = GetStatusOutput(cmd, cwd, out_buffer) 128 (status, output) = GetStatusOutput(cmd, cwd, out_buffer)
120 # For Abnormal Exit, Windows returns -1, Posix returns 128. 129 # For Abnormal Exit, Windows returns -1, Posix returns 128.
121 if status in [-1, 128]: 130 if status in [-1, 128]:
122 raise AbnormalExit('Failed to run %s. Exited Abnormally. output %s' % 131 raise AbnormalExit('Failed to run %s. Exited Abnormally. output %s' %
123 (cmd, output)) 132 (cmd, output))
124 elif status != 0: 133 elif status != 0:
125 raise Exception('Failed to run %s. error %d. output %s' % (cmd, status, 134 raise Exception('Failed to run %s. error %d. output %s' % (cmd, status,
126 output)) 135 output))
127 return (status, output) 136 return (status, output)
128 137
129 138
130 def GetCacheRepoDir(git_url, cache_dir): 139 def Clone(git_url, git_repo, is_mirror, out_buffer=None):
131 """Assuming we used git_cache to populate a cache, get the repo directory."""
132 _, out = Git(None, 'cache exists --cache-dir=%s %s' % (cache_dir, git_url),
133 is_mirror=True)
134 return out.strip()
135
136
137 def Clone(git_url, git_repo, is_mirror, out_queue=None, cache_dir=None,
138 shallow=False):
139 """Clone a repository.""" 140 """Clone a repository."""
140 repo_name = git_url.split('/')[-1]
141 if out_queue:
142 buf = StdioBuffer(repo_name, out_queue)
143 else:
144 buf = None
145
146 if is_mirror == 'bare':
147 if shallow:
148 if 'adobe' in git_url:
149 # --shallow by default checks out 10000 revision, but for really large
150 # repos like adobe ones, we want significantly less than 10000.
151 shallow_arg = '--depth 10 '
152 else:
153 shallow_arg = '--shallow '
154 else:
155 shallow_arg = ''
156 cmd = 'cache populate -v --cache-dir %s %s%s' % (cache_dir, shallow_arg,
157 git_url)
158 return Git(None, cmd, is_mirror=True, out_buffer=buf)
159
160 cmd = 'clone' 141 cmd = 'clone'
161 if is_mirror: 142 if is_mirror:
162 cmd += ' --mirror' 143 cmd += ' --mirror'
163 cmd += ' %s %s' % (git_url, git_repo) 144 cmd += ' %s %s' % (git_url, git_repo)
164 145
165 if not is_mirror and not os.path.exists(git_repo): 146 if not is_mirror and not os.path.exists(git_repo):
166 os.makedirs(git_repo) 147 os.makedirs(git_repo)
167 148
168 return Git(None, cmd, is_mirror, buf) 149 return Git(None, cmd, is_mirror=is_mirror, out_buffer=out_buffer)
150
151
152 def PopulateCache(git_url, shallow=False):
153 # --shallow by default checks out 10000 revision, but for really large
154 # repos like adobe ones, we want significantly less than 10000.
155 depth = None
156 if shallow and 'adobe' in git_url:
157 depth = 10
158 mirror = git_cache.Mirror(git_url, print_func=lambda *args: None)
159 mirror.populate(depth=depth, shallow=shallow)
160 return mirror.mirror_path
169 161
170 162
171 def Fetch(git_repo, git_url, is_mirror): 163 def Fetch(git_repo, git_url, is_mirror):
172 """Fetch the latest objects for a given git repository.""" 164 """Fetch the latest objects for a given git repository."""
173 # Always update the upstream url 165 # Always update the upstream url
174 Git(git_repo, 'config remote.origin.url %s' % git_url) 166 Git(git_repo, 'config remote.origin.url %s' % git_url)
175 Git(git_repo, 'fetch origin', is_mirror) 167 Git(git_repo, 'fetch origin', is_mirror)
176 168
177 169
178 def Ping(git_repo, verbose=False): 170 def Ping(git_repo, verbose=False):
(...skipping 89 matching lines...) Expand 10 before | Expand all | Expand 10 after
268 260
269 # Check if svn_rev is newer than the current refspec revision. 261 # Check if svn_rev is newer than the current refspec revision.
270 try: 262 try:
271 found_rev = _FindRevForCommitish(git_repo, refspec, is_mirror) 263 found_rev = _FindRevForCommitish(git_repo, refspec, is_mirror)
272 # Sometimes this fails because it's looking in a branch that hasn't been 264 # Sometimes this fails because it's looking in a branch that hasn't been
273 # fetched from upstream yet. Let it fetch and try again. 265 # fetched from upstream yet. Let it fetch and try again.
274 except AbnormalExit: 266 except AbnormalExit:
275 found_rev = None 267 found_rev = None
276 if (not found_rev or found_rev < int(svn_rev)) and fetch_url: 268 if (not found_rev or found_rev < int(svn_rev)) and fetch_url:
277 if VERBOSE: 269 if VERBOSE:
278 print 'Fetching %s %s [%s < %s]' % (git_repo, refspec, found_rev, svn_rev) 270 print >> sys.stderr, (
271 'Fetching %s %s [%s < %s]' % (git_repo, refspec, found_rev, svn_rev))
279 Fetch(git_repo, fetch_url, is_mirror) 272 Fetch(git_repo, fetch_url, is_mirror)
280 found_rev = _FindRevForCommitish(git_repo, refspec, is_mirror) 273 found_rev = _FindRevForCommitish(git_repo, refspec, is_mirror)
281 274
282 # Find the first commit matching the given git-svn-id regex. 275 # Find the first commit matching the given git-svn-id regex.
283 _, output = Git( 276 _, output = Git(
284 git_repo, 277 git_repo,
285 ('log -E --grep="^git-svn-id: [^@]*@%s [A-Za-z0-9-]*$" ' 278 ('log -E --grep="^git-svn-id: [^@]*@%s [A-Za-z0-9-]*$" '
286 '-1 --format="%%H" %s') % (regex, refspec), 279 '-1 --format="%%H" %s') % (regex, refspec),
287 is_mirror) 280 is_mirror)
288 output = output.strip() 281 output = output.strip()
289 if not re.match('^[0-9a-fA-F]{40}$', output): 282 if not re.match('^[0-9a-fA-F]{40}$', output):
290 raise SearchError('Cannot find revision %s in %s:%s' % (svn_rev, git_repo, 283 raise SearchError('Cannot find revision %s in %s:%s' % (svn_rev, git_repo,
291 refspec)) 284 refspec))
292 285
293 # Check if it actually matched the svn_rev that was requested. 286 # Check if it actually matched the svn_rev that was requested.
294 found_rev = _FindRevForCommitish(git_repo, output, is_mirror) 287 found_rev = _FindRevForCommitish(git_repo, output, is_mirror)
295 found_msg = svn_rev 288 found_msg = svn_rev
296 if found_rev != int(svn_rev): 289 if found_rev != int(svn_rev):
297 found_msg = '%s [actual: %s]' % (svn_rev, found_rev) 290 found_msg = '%s [actual: %s]' % (svn_rev, found_rev)
298 print '%s: %s <-> %s' % (git_repo, output, found_msg) 291 print >> sys.stderr, '%s: %s <-> %s' % (git_repo, output, found_msg)
299 return output 292 return output
300 293
301 294
302 def SearchExact(git_repo, svn_rev, is_mirror, refspec='FETCH_HEAD', 295 def SearchExact(git_repo, svn_rev, is_mirror, refspec='FETCH_HEAD',
303 fetch_url=None): 296 fetch_url=None):
304 """Return the Git commit id exactly matching the given SVN revision. 297 """Return the Git commit id exactly matching the given SVN revision.
305 298
306 If fetch_url is not None, will update repo if revision is newer.""" 299 If fetch_url is not None, will update repo if revision is newer."""
307 regex = str(svn_rev) 300 regex = str(svn_rev)
308 return _SearchImpl(git_repo, svn_rev, is_mirror, refspec, fetch_url, regex) 301 return _SearchImpl(git_repo, svn_rev, is_mirror, refspec, fetch_url, regex)
309 302
310 303
311 def Search(git_repo, svn_rev, is_mirror, refspec='FETCH_HEAD', fetch_url=None): 304 def Search(git_repo, svn_rev, is_mirror, refspec='FETCH_HEAD', fetch_url=None):
312 """Return the Git commit id fuzzy matching the given SVN revision. 305 """Return the Git commit id fuzzy matching the given SVN revision.
313 306
314 If fetch_url is not None, will update repo if revision is newer.""" 307 If fetch_url is not None, will update repo if revision is newer."""
315 regex = CreateLessThanOrEqualRegex(svn_rev) 308 regex = CreateLessThanOrEqualRegex(svn_rev)
316 return _SearchImpl(git_repo, svn_rev, is_mirror, refspec, fetch_url, regex) 309 return _SearchImpl(git_repo, svn_rev, is_mirror, refspec, fetch_url, regex)
OLDNEW
« no previous file with comments | « deps2git.py ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698