Mercurial > hgbook
comparison contrib/sillybench.py @ 721:2180358c32c4
Move some files to contrib
author | Dongsheng Song <dongsheng.song@gmail.com> |
---|---|
date | Thu, 12 Mar 2009 15:40:40 +0800 |
parents | sillybench/sillybench.py@b2b593eb56e7 |
children |
comparison
equal
deleted
inserted
replaced
720:1ef7708b3b7f | 721:2180358c32c4 |
---|---|
1 #!/usr/bin/python | |
2 # | |
3 # Silly benchmarking program, to give a vague idea of how fast a few | |
4 # tools are on a handful of common operations. | |
5 # | |
6 # Use a fairly big and real source tarball to test with: Firefox | |
7 # 2.0.0.3 (37622 files, 5374 directories, 343MB unpacked onto | |
8 # 4KB-blocksize ext3). | |
9 | |
10 import csv | |
11 import os | |
12 import shutil | |
13 import sys | |
14 import tempfile | |
15 import time | |
16 import urllib2 | |
17 | |
18 url = 'ftp://ftp.mozilla.org/pub/mozilla.org/firefox/releases/2.0.0.3/source/firefox-2.0.0.3-source.tar.bz2' | |
19 | |
20 class CommandFailure(Exception): | |
21 pass | |
22 | |
23 class rcs(object): | |
24 def __init__(self): | |
25 self.logfp = open(self.__class__.__name__ + '.csv', 'w') | |
26 self.csv = csv.writer(self.logfp) | |
27 | |
28 def download(self): | |
29 name = url[url.rfind('/')+1:] | |
30 path = os.path.join(os.environ['HOME'], name) | |
31 if not os.path.isfile(path): | |
32 ofp = open(path + '.part', 'wb') | |
33 try: | |
34 ifp = urllib2.urlopen(url) | |
35 nbytes = ifp.info()['content-length'] | |
36 sys.stdout.write('%s: %s bytes ' % (name, nbytes)) | |
37 sys.stdout.flush() | |
38 while True: | |
39 data = ifp.read(131072) | |
40 if not data: break | |
41 sys.stdout.write('.') | |
42 sys.stdout.flush() | |
43 ofp.write(data) | |
44 del ofp | |
45 os.rename(path + '.part', path) | |
46 except: | |
47 if os.path.exists(path + '.part'): | |
48 os.unlink(path + '.part') | |
49 if os.path.exists(path): | |
50 os.unlink(path) | |
51 raise | |
52 return path | |
53 | |
54 def run(self, args, mustsucceed=True): | |
55 ret = os.spawnvp(os.P_WAIT, args[0], args) | |
56 if ret < 0: | |
57 msg = 'killed by signal %d' % (-ret) | |
58 if ret > 0: | |
59 msg = 'exited with status %d' % (ret) | |
60 if ret: | |
61 if mustsucceed: | |
62 raise CommandFailure('%s: %s' % (msg, ' '.join(args))) | |
63 print >> sys.stderr, 'WARNING: %s: %s' % (msg, ' '.join(args)) | |
64 | |
65 def time(self, *args, **kwargs): | |
66 start = time.time() | |
67 self.run(*args, **kwargs) | |
68 end = time.time() | |
69 return end - start | |
70 | |
71 def logtime(self, name, elapsed, rest=[]): | |
72 self.log('time:' + name, '%.3f' % elapsed, rest) | |
73 | |
74 def log(self, name, value, rest=[]): | |
75 item = (name, value, repr(rest)) | |
76 print ' '.join(item) | |
77 self.csv.writerow(item) | |
78 self.logfp.flush() | |
79 | |
80 def unpack(self): | |
81 tarball = self.download() | |
82 t = self.time(['tar', '-C', self.wdir, '-jxf', tarball]) | |
83 self.logtime('internal:untar', t) | |
84 for name in os.listdir(os.path.join(self.wdir, 'mozilla')): | |
85 os.rename(os.path.join(self.wdir, 'mozilla', name), | |
86 os.path.join(self.wdir, name)) | |
87 | |
88 def cleanup(self): | |
89 pass | |
90 | |
91 def add(self, paths): | |
92 pass | |
93 | |
94 def commit(self, msg, paths): | |
95 pass | |
96 | |
97 def status(self, path): | |
98 pass | |
99 | |
100 def remove(self, path): | |
101 pass | |
102 | |
103 | |
104 class subversion(rcs): | |
105 def __init__(self, root): | |
106 rcs.__init__(self) | |
107 self.repo = os.path.join(root, 'repo') | |
108 self.wdir = os.path.join(root, 'wc') | |
109 create = self.time(['svnadmin', 'create', '--fs-type=fsfs', self.repo]) | |
110 self.logtime('svn:create', create) | |
111 co = self.time(['svn', 'co', 'file://' + self.repo, self.wdir]) | |
112 self.logtime('svn:co', co) | |
113 self.logtime('init', create + co) | |
114 os.chdir(self.wdir) | |
115 | |
116 def dropmeta(self, names): | |
117 return [n for n in names if os.path.basename(n) != '.svn'] | |
118 | |
119 def add(self, paths): | |
120 t = self.time(['svn', 'add', '-q'] + paths) | |
121 self.logtime('add %r' % paths, t) | |
122 | |
123 def commit(self, msg, paths=[]): | |
124 if paths: | |
125 t = self.time(['svn', 'ci', '-q', '-m', msg] + paths) | |
126 else: | |
127 t = self.time(['svn', 'ci', '-q', '-m', msg]) | |
128 self.logtime('commit %r' % paths, t) | |
129 | |
130 | |
131 class mercurial(rcs): | |
132 def __init__(self, root): | |
133 rcs.__init__(self) | |
134 self.repo = os.path.join(root, 'repo') | |
135 self.wdir = self.repo | |
136 init = self.time(['hg', 'init', self.repo]) | |
137 self.logtime('init', init) | |
138 os.chdir(self.wdir) | |
139 | |
140 def dropmeta(self, names): | |
141 return [n for n in names if os.path.basename(n) != '.hg'] | |
142 | |
143 def add(self, paths): | |
144 t = self.time(['hg', 'add', '-q'] + paths) | |
145 self.logtime('add %r' % paths, t) | |
146 | |
147 def commit(self, msg, paths=[]): | |
148 if paths: | |
149 t = self.time(['hg', 'ci', '-q', '-m', msg] + paths) | |
150 else: | |
151 t = self.time(['hg', 'ci', '-q', '-m', msg]) | |
152 self.logtime('commit %r' % paths, t) | |
153 | |
154 def benchmark(cls): | |
155 oldcwd = os.getcwd() | |
156 root = tempfile.mkdtemp(prefix='sillybench.') | |
157 try: | |
158 print 'root', root | |
159 inst = cls(root) | |
160 inst.unpack() | |
161 names = inst.dropmeta(os.listdir('.')) | |
162 dirs = [n for n in names if os.path.isdir(n)] | |
163 nondirs = [n for n in names if not os.path.isdir(n)] | |
164 dirs.sort(key=hash) | |
165 names.sort(key=hash) | |
166 for d in dirs[:len(dirs)/2]: | |
167 inst.add([d]) | |
168 inst.commit('Add %r' % d, [d]) | |
169 inst.add(dirs[len(dirs)/2:] + names) | |
170 inst.commit('Add remaining dirs and files') | |
171 finally: | |
172 print >> sys.stderr, '[cleaning up...]' | |
173 shutil.rmtree(root) | |
174 os.chdir(oldcwd) | |
175 | |
176 benchmark(mercurial) | |
177 #benchmark(subversion) |