##// END OF EJS Templates
tests: update test-commandserver to pass our import checker
Augie Fackler -
r33923:1a6707b4 default
parent child Browse files
Show More
@@ -1,997 +1,1000 b''
1 #if windows
1 #if windows
2 $ PYTHONPATH="$TESTDIR/../contrib;$PYTHONPATH"
2 $ PYTHONPATH="$TESTDIR/../contrib;$PYTHONPATH"
3 #else
3 #else
4 $ PYTHONPATH="$TESTDIR/../contrib:$PYTHONPATH"
4 $ PYTHONPATH="$TESTDIR/../contrib:$PYTHONPATH"
5 #endif
5 #endif
6 $ export PYTHONPATH
6 $ export PYTHONPATH
7
7
8 typical client does not want echo-back messages, so test without it:
8 typical client does not want echo-back messages, so test without it:
9
9
10 $ grep -v '^promptecho ' < $HGRCPATH >> $HGRCPATH.new
10 $ grep -v '^promptecho ' < $HGRCPATH >> $HGRCPATH.new
11 $ mv $HGRCPATH.new $HGRCPATH
11 $ mv $HGRCPATH.new $HGRCPATH
12
12
13 $ hg init repo
13 $ hg init repo
14 $ cd repo
14 $ cd repo
15
15
16 >>> from __future__ import print_function
16 >>> from __future__ import absolute_import, print_function
17 >>> from hgclient import readchannel, runcommand, check
17 >>> import os
18 >>> import sys
19 >>> from hgclient import check, readchannel, runcommand
18 >>> @check
20 >>> @check
19 ... def hellomessage(server):
21 ... def hellomessage(server):
20 ... ch, data = readchannel(server)
22 ... ch, data = readchannel(server)
21 ... print('%c, %r' % (ch, data))
23 ... print('%c, %r' % (ch, data))
22 ... # run an arbitrary command to make sure the next thing the server
24 ... # run an arbitrary command to make sure the next thing the server
23 ... # sends isn't part of the hello message
25 ... # sends isn't part of the hello message
24 ... runcommand(server, ['id'])
26 ... runcommand(server, ['id'])
25 o, 'capabilities: getencoding runcommand\nencoding: *\npid: *' (glob)
27 o, 'capabilities: getencoding runcommand\nencoding: *\npid: *' (glob)
26 *** runcommand id
28 *** runcommand id
27 000000000000 tip
29 000000000000 tip
28
30
29 >>> from hgclient import check
31 >>> from hgclient import check
30 >>> @check
32 >>> @check
31 ... def unknowncommand(server):
33 ... def unknowncommand(server):
32 ... server.stdin.write('unknowncommand\n')
34 ... server.stdin.write('unknowncommand\n')
33 abort: unknown command unknowncommand
35 abort: unknown command unknowncommand
34
36
35 >>> from hgclient import readchannel, runcommand, check
37 >>> from hgclient import check, readchannel, runcommand
36 >>> @check
38 >>> @check
37 ... def checkruncommand(server):
39 ... def checkruncommand(server):
38 ... # hello block
40 ... # hello block
39 ... readchannel(server)
41 ... readchannel(server)
40 ...
42 ...
41 ... # no args
43 ... # no args
42 ... runcommand(server, [])
44 ... runcommand(server, [])
43 ...
45 ...
44 ... # global options
46 ... # global options
45 ... runcommand(server, ['id', '--quiet'])
47 ... runcommand(server, ['id', '--quiet'])
46 ...
48 ...
47 ... # make sure global options don't stick through requests
49 ... # make sure global options don't stick through requests
48 ... runcommand(server, ['id'])
50 ... runcommand(server, ['id'])
49 ...
51 ...
50 ... # --config
52 ... # --config
51 ... runcommand(server, ['id', '--config', 'ui.quiet=True'])
53 ... runcommand(server, ['id', '--config', 'ui.quiet=True'])
52 ...
54 ...
53 ... # make sure --config doesn't stick
55 ... # make sure --config doesn't stick
54 ... runcommand(server, ['id'])
56 ... runcommand(server, ['id'])
55 ...
57 ...
56 ... # negative return code should be masked
58 ... # negative return code should be masked
57 ... runcommand(server, ['id', '-runknown'])
59 ... runcommand(server, ['id', '-runknown'])
58 *** runcommand
60 *** runcommand
59 Mercurial Distributed SCM
61 Mercurial Distributed SCM
60
62
61 basic commands:
63 basic commands:
62
64
63 add add the specified files on the next commit
65 add add the specified files on the next commit
64 annotate show changeset information by line for each file
66 annotate show changeset information by line for each file
65 clone make a copy of an existing repository
67 clone make a copy of an existing repository
66 commit commit the specified files or all outstanding changes
68 commit commit the specified files or all outstanding changes
67 diff diff repository (or selected files)
69 diff diff repository (or selected files)
68 export dump the header and diffs for one or more changesets
70 export dump the header and diffs for one or more changesets
69 forget forget the specified files on the next commit
71 forget forget the specified files on the next commit
70 init create a new repository in the given directory
72 init create a new repository in the given directory
71 log show revision history of entire repository or files
73 log show revision history of entire repository or files
72 merge merge another revision into working directory
74 merge merge another revision into working directory
73 pull pull changes from the specified source
75 pull pull changes from the specified source
74 push push changes to the specified destination
76 push push changes to the specified destination
75 remove remove the specified files on the next commit
77 remove remove the specified files on the next commit
76 serve start stand-alone webserver
78 serve start stand-alone webserver
77 status show changed files in the working directory
79 status show changed files in the working directory
78 summary summarize working directory state
80 summary summarize working directory state
79 update update working directory (or switch revisions)
81 update update working directory (or switch revisions)
80
82
81 (use 'hg help' for the full list of commands or 'hg -v' for details)
83 (use 'hg help' for the full list of commands or 'hg -v' for details)
82 *** runcommand id --quiet
84 *** runcommand id --quiet
83 000000000000
85 000000000000
84 *** runcommand id
86 *** runcommand id
85 000000000000 tip
87 000000000000 tip
86 *** runcommand id --config ui.quiet=True
88 *** runcommand id --config ui.quiet=True
87 000000000000
89 000000000000
88 *** runcommand id
90 *** runcommand id
89 000000000000 tip
91 000000000000 tip
90 *** runcommand id -runknown
92 *** runcommand id -runknown
91 abort: unknown revision 'unknown'!
93 abort: unknown revision 'unknown'!
92 [255]
94 [255]
93
95
94 >>> from hgclient import readchannel, check
96 >>> from hgclient import check, readchannel
95 >>> @check
97 >>> @check
96 ... def inputeof(server):
98 ... def inputeof(server):
97 ... readchannel(server)
99 ... readchannel(server)
98 ... server.stdin.write('runcommand\n')
100 ... server.stdin.write('runcommand\n')
99 ... # close stdin while server is waiting for input
101 ... # close stdin while server is waiting for input
100 ... server.stdin.close()
102 ... server.stdin.close()
101 ...
103 ...
102 ... # server exits with 1 if the pipe closed while reading the command
104 ... # server exits with 1 if the pipe closed while reading the command
103 ... print('server exit code =', server.wait())
105 ... print('server exit code =', server.wait())
104 server exit code = 1
106 server exit code = 1
105
107
106 >>> from hgclient import readchannel, runcommand, check, stringio
108 >>> from hgclient import check, readchannel, runcommand, stringio
107 >>> @check
109 >>> @check
108 ... def serverinput(server):
110 ... def serverinput(server):
109 ... readchannel(server)
111 ... readchannel(server)
110 ...
112 ...
111 ... patch = """
113 ... patch = """
112 ... # HG changeset patch
114 ... # HG changeset patch
113 ... # User test
115 ... # User test
114 ... # Date 0 0
116 ... # Date 0 0
115 ... # Node ID c103a3dec114d882c98382d684d8af798d09d857
117 ... # Node ID c103a3dec114d882c98382d684d8af798d09d857
116 ... # Parent 0000000000000000000000000000000000000000
118 ... # Parent 0000000000000000000000000000000000000000
117 ... 1
119 ... 1
118 ...
120 ...
119 ... diff -r 000000000000 -r c103a3dec114 a
121 ... diff -r 000000000000 -r c103a3dec114 a
120 ... --- /dev/null Thu Jan 01 00:00:00 1970 +0000
122 ... --- /dev/null Thu Jan 01 00:00:00 1970 +0000
121 ... +++ b/a Thu Jan 01 00:00:00 1970 +0000
123 ... +++ b/a Thu Jan 01 00:00:00 1970 +0000
122 ... @@ -0,0 +1,1 @@
124 ... @@ -0,0 +1,1 @@
123 ... +1
125 ... +1
124 ... """
126 ... """
125 ...
127 ...
126 ... runcommand(server, ['import', '-'], input=stringio(patch))
128 ... runcommand(server, ['import', '-'], input=stringio(patch))
127 ... runcommand(server, ['log'])
129 ... runcommand(server, ['log'])
128 *** runcommand import -
130 *** runcommand import -
129 applying patch from stdin
131 applying patch from stdin
130 *** runcommand log
132 *** runcommand log
131 changeset: 0:eff892de26ec
133 changeset: 0:eff892de26ec
132 tag: tip
134 tag: tip
133 user: test
135 user: test
134 date: Thu Jan 01 00:00:00 1970 +0000
136 date: Thu Jan 01 00:00:00 1970 +0000
135 summary: 1
137 summary: 1
136
138
137
139
138 check that "histedit --commands=-" can read rules from the input channel:
140 check that "histedit --commands=-" can read rules from the input channel:
139
141
140 >>> import cStringIO
142 >>> import cStringIO
141 >>> from hgclient import readchannel, runcommand, check
143 >>> from hgclient import check, readchannel, runcommand
142 >>> @check
144 >>> @check
143 ... def serverinput(server):
145 ... def serverinput(server):
144 ... readchannel(server)
146 ... readchannel(server)
145 ... rules = 'pick eff892de26ec\n'
147 ... rules = 'pick eff892de26ec\n'
146 ... runcommand(server, ['histedit', '0', '--commands=-',
148 ... runcommand(server, ['histedit', '0', '--commands=-',
147 ... '--config', 'extensions.histedit='],
149 ... '--config', 'extensions.histedit='],
148 ... input=cStringIO.StringIO(rules))
150 ... input=cStringIO.StringIO(rules))
149 *** runcommand histedit 0 --commands=- --config extensions.histedit=
151 *** runcommand histedit 0 --commands=- --config extensions.histedit=
150
152
151 check that --cwd doesn't persist between requests:
153 check that --cwd doesn't persist between requests:
152
154
153 $ mkdir foo
155 $ mkdir foo
154 $ touch foo/bar
156 $ touch foo/bar
155 >>> from hgclient import readchannel, runcommand, check
157 >>> from hgclient import check, readchannel, runcommand
156 >>> @check
158 >>> @check
157 ... def cwd(server):
159 ... def cwd(server):
158 ... readchannel(server)
160 ... readchannel(server)
159 ... runcommand(server, ['--cwd', 'foo', 'st', 'bar'])
161 ... runcommand(server, ['--cwd', 'foo', 'st', 'bar'])
160 ... runcommand(server, ['st', 'foo/bar'])
162 ... runcommand(server, ['st', 'foo/bar'])
161 *** runcommand --cwd foo st bar
163 *** runcommand --cwd foo st bar
162 ? bar
164 ? bar
163 *** runcommand st foo/bar
165 *** runcommand st foo/bar
164 ? foo/bar
166 ? foo/bar
165
167
166 $ rm foo/bar
168 $ rm foo/bar
167
169
168
170
169 check that local configs for the cached repo aren't inherited when -R is used:
171 check that local configs for the cached repo aren't inherited when -R is used:
170
172
171 $ cat <<EOF >> .hg/hgrc
173 $ cat <<EOF >> .hg/hgrc
172 > [ui]
174 > [ui]
173 > foo = bar
175 > foo = bar
174 > EOF
176 > EOF
175
177
176 >>> from hgclient import readchannel, sep, runcommand, check
178 >>> from hgclient import check, readchannel, runcommand, sep
177 >>> @check
179 >>> @check
178 ... def localhgrc(server):
180 ... def localhgrc(server):
179 ... readchannel(server)
181 ... readchannel(server)
180 ...
182 ...
181 ... # the cached repo local hgrc contains ui.foo=bar, so showconfig should
183 ... # the cached repo local hgrc contains ui.foo=bar, so showconfig should
182 ... # show it
184 ... # show it
183 ... runcommand(server, ['showconfig'], outfilter=sep)
185 ... runcommand(server, ['showconfig'], outfilter=sep)
184 ...
186 ...
185 ... # but not for this repo
187 ... # but not for this repo
186 ... runcommand(server, ['init', 'foo'])
188 ... runcommand(server, ['init', 'foo'])
187 ... runcommand(server, ['-R', 'foo', 'showconfig', 'ui', 'defaults'])
189 ... runcommand(server, ['-R', 'foo', 'showconfig', 'ui', 'defaults'])
188 *** runcommand showconfig
190 *** runcommand showconfig
189 bundle.mainreporoot=$TESTTMP/repo
191 bundle.mainreporoot=$TESTTMP/repo
190 devel.all-warnings=true
192 devel.all-warnings=true
191 devel.default-date=0 0
193 devel.default-date=0 0
192 extensions.fsmonitor= (fsmonitor !)
194 extensions.fsmonitor= (fsmonitor !)
193 largefiles.usercache=$TESTTMP/.cache/largefiles
195 largefiles.usercache=$TESTTMP/.cache/largefiles
194 ui.slash=True
196 ui.slash=True
195 ui.interactive=False
197 ui.interactive=False
196 ui.mergemarkers=detailed
198 ui.mergemarkers=detailed
197 ui.usehttp2=true (?)
199 ui.usehttp2=true (?)
198 ui.foo=bar
200 ui.foo=bar
199 ui.nontty=true
201 ui.nontty=true
200 web.address=localhost
202 web.address=localhost
201 web\.ipv6=(?:True|False) (re)
203 web\.ipv6=(?:True|False) (re)
202 *** runcommand init foo
204 *** runcommand init foo
203 *** runcommand -R foo showconfig ui defaults
205 *** runcommand -R foo showconfig ui defaults
204 ui.slash=True
206 ui.slash=True
205 ui.interactive=False
207 ui.interactive=False
206 ui.mergemarkers=detailed
208 ui.mergemarkers=detailed
207 ui.usehttp2=true (?)
209 ui.usehttp2=true (?)
208 ui.nontty=true
210 ui.nontty=true
209
211
210 $ rm -R foo
212 $ rm -R foo
211
213
212 #if windows
214 #if windows
213 $ PYTHONPATH="$TESTTMP/repo;$PYTHONPATH"
215 $ PYTHONPATH="$TESTTMP/repo;$PYTHONPATH"
214 #else
216 #else
215 $ PYTHONPATH="$TESTTMP/repo:$PYTHONPATH"
217 $ PYTHONPATH="$TESTTMP/repo:$PYTHONPATH"
216 #endif
218 #endif
217
219
218 $ cat <<EOF > hook.py
220 $ cat <<EOF > hook.py
219 > from __future__ import print_function
221 > from __future__ import print_function
220 > import sys
222 > import sys
221 > def hook(**args):
223 > def hook(**args):
222 > print('hook talking')
224 > print('hook talking')
223 > print('now try to read something: %r' % sys.stdin.read())
225 > print('now try to read something: %r' % sys.stdin.read())
224 > EOF
226 > EOF
225
227
226 >>> from hgclient import readchannel, runcommand, check, stringio
228 >>> from hgclient import check, readchannel, runcommand, stringio
227 >>> @check
229 >>> @check
228 ... def hookoutput(server):
230 ... def hookoutput(server):
229 ... readchannel(server)
231 ... readchannel(server)
230 ... runcommand(server, ['--config',
232 ... runcommand(server, ['--config',
231 ... 'hooks.pre-identify=python:hook.hook',
233 ... 'hooks.pre-identify=python:hook.hook',
232 ... 'id'],
234 ... 'id'],
233 ... input=stringio('some input'))
235 ... input=stringio('some input'))
234 *** runcommand --config hooks.pre-identify=python:hook.hook id
236 *** runcommand --config hooks.pre-identify=python:hook.hook id
235 eff892de26ec tip
237 eff892de26ec tip
236
238
237 Clean hook cached version
239 Clean hook cached version
238 $ rm hook.py*
240 $ rm hook.py*
239 $ rm -Rf __pycache__
241 $ rm -Rf __pycache__
240
242
241 $ echo a >> a
243 $ echo a >> a
242 >>> import os
244 >>> import os
243 >>> from hgclient import readchannel, runcommand, check
245 >>> from hgclient import check, readchannel, runcommand
244 >>> @check
246 >>> @check
245 ... def outsidechanges(server):
247 ... def outsidechanges(server):
246 ... readchannel(server)
248 ... readchannel(server)
247 ... runcommand(server, ['status'])
249 ... runcommand(server, ['status'])
248 ... os.system('hg ci -Am2')
250 ... os.system('hg ci -Am2')
249 ... runcommand(server, ['tip'])
251 ... runcommand(server, ['tip'])
250 ... runcommand(server, ['status'])
252 ... runcommand(server, ['status'])
251 *** runcommand status
253 *** runcommand status
252 M a
254 M a
253 *** runcommand tip
255 *** runcommand tip
254 changeset: 1:d3a0a68be6de
256 changeset: 1:d3a0a68be6de
255 tag: tip
257 tag: tip
256 user: test
258 user: test
257 date: Thu Jan 01 00:00:00 1970 +0000
259 date: Thu Jan 01 00:00:00 1970 +0000
258 summary: 2
260 summary: 2
259
261
260 *** runcommand status
262 *** runcommand status
261
263
262 >>> import os
264 >>> import os
263 >>> from hgclient import readchannel, runcommand, check
265 >>> from hgclient import check, readchannel, runcommand
264 >>> @check
266 >>> @check
265 ... def bookmarks(server):
267 ... def bookmarks(server):
266 ... readchannel(server)
268 ... readchannel(server)
267 ... runcommand(server, ['bookmarks'])
269 ... runcommand(server, ['bookmarks'])
268 ...
270 ...
269 ... # changes .hg/bookmarks
271 ... # changes .hg/bookmarks
270 ... os.system('hg bookmark -i bm1')
272 ... os.system('hg bookmark -i bm1')
271 ... os.system('hg bookmark -i bm2')
273 ... os.system('hg bookmark -i bm2')
272 ... runcommand(server, ['bookmarks'])
274 ... runcommand(server, ['bookmarks'])
273 ...
275 ...
274 ... # changes .hg/bookmarks.current
276 ... # changes .hg/bookmarks.current
275 ... os.system('hg upd bm1 -q')
277 ... os.system('hg upd bm1 -q')
276 ... runcommand(server, ['bookmarks'])
278 ... runcommand(server, ['bookmarks'])
277 ...
279 ...
278 ... runcommand(server, ['bookmarks', 'bm3'])
280 ... runcommand(server, ['bookmarks', 'bm3'])
279 ... f = open('a', 'ab')
281 ... f = open('a', 'ab')
280 ... f.write('a\n')
282 ... f.write('a\n')
281 ... f.close()
283 ... f.close()
282 ... runcommand(server, ['commit', '-Amm'])
284 ... runcommand(server, ['commit', '-Amm'])
283 ... runcommand(server, ['bookmarks'])
285 ... runcommand(server, ['bookmarks'])
284 ... print('')
286 ... print('')
285 *** runcommand bookmarks
287 *** runcommand bookmarks
286 no bookmarks set
288 no bookmarks set
287 *** runcommand bookmarks
289 *** runcommand bookmarks
288 bm1 1:d3a0a68be6de
290 bm1 1:d3a0a68be6de
289 bm2 1:d3a0a68be6de
291 bm2 1:d3a0a68be6de
290 *** runcommand bookmarks
292 *** runcommand bookmarks
291 * bm1 1:d3a0a68be6de
293 * bm1 1:d3a0a68be6de
292 bm2 1:d3a0a68be6de
294 bm2 1:d3a0a68be6de
293 *** runcommand bookmarks bm3
295 *** runcommand bookmarks bm3
294 *** runcommand commit -Amm
296 *** runcommand commit -Amm
295 *** runcommand bookmarks
297 *** runcommand bookmarks
296 bm1 1:d3a0a68be6de
298 bm1 1:d3a0a68be6de
297 bm2 1:d3a0a68be6de
299 bm2 1:d3a0a68be6de
298 * bm3 2:aef17e88f5f0
300 * bm3 2:aef17e88f5f0
299
301
300
302
301 >>> import os
303 >>> import os
302 >>> from hgclient import readchannel, runcommand, check
304 >>> from hgclient import check, readchannel, runcommand
303 >>> @check
305 >>> @check
304 ... def tagscache(server):
306 ... def tagscache(server):
305 ... readchannel(server)
307 ... readchannel(server)
306 ... runcommand(server, ['id', '-t', '-r', '0'])
308 ... runcommand(server, ['id', '-t', '-r', '0'])
307 ... os.system('hg tag -r 0 foo')
309 ... os.system('hg tag -r 0 foo')
308 ... runcommand(server, ['id', '-t', '-r', '0'])
310 ... runcommand(server, ['id', '-t', '-r', '0'])
309 *** runcommand id -t -r 0
311 *** runcommand id -t -r 0
310
312
311 *** runcommand id -t -r 0
313 *** runcommand id -t -r 0
312 foo
314 foo
313
315
314 >>> import os
316 >>> import os
315 >>> from hgclient import readchannel, runcommand, check
317 >>> from hgclient import check, readchannel, runcommand
316 >>> @check
318 >>> @check
317 ... def setphase(server):
319 ... def setphase(server):
318 ... readchannel(server)
320 ... readchannel(server)
319 ... runcommand(server, ['phase', '-r', '.'])
321 ... runcommand(server, ['phase', '-r', '.'])
320 ... os.system('hg phase -r . -p')
322 ... os.system('hg phase -r . -p')
321 ... runcommand(server, ['phase', '-r', '.'])
323 ... runcommand(server, ['phase', '-r', '.'])
322 *** runcommand phase -r .
324 *** runcommand phase -r .
323 3: draft
325 3: draft
324 *** runcommand phase -r .
326 *** runcommand phase -r .
325 3: public
327 3: public
326
328
327 $ echo a >> a
329 $ echo a >> a
328 >>> from hgclient import readchannel, runcommand, check
330 >>> from hgclient import check, readchannel, runcommand
329 >>> @check
331 >>> @check
330 ... def rollback(server):
332 ... def rollback(server):
331 ... readchannel(server)
333 ... readchannel(server)
332 ... runcommand(server, ['phase', '-r', '.', '-p'])
334 ... runcommand(server, ['phase', '-r', '.', '-p'])
333 ... runcommand(server, ['commit', '-Am.'])
335 ... runcommand(server, ['commit', '-Am.'])
334 ... runcommand(server, ['rollback'])
336 ... runcommand(server, ['rollback'])
335 ... runcommand(server, ['phase', '-r', '.'])
337 ... runcommand(server, ['phase', '-r', '.'])
336 ... print('')
338 ... print('')
337 *** runcommand phase -r . -p
339 *** runcommand phase -r . -p
338 no phases changed
340 no phases changed
339 *** runcommand commit -Am.
341 *** runcommand commit -Am.
340 *** runcommand rollback
342 *** runcommand rollback
341 repository tip rolled back to revision 3 (undo commit)
343 repository tip rolled back to revision 3 (undo commit)
342 working directory now based on revision 3
344 working directory now based on revision 3
343 *** runcommand phase -r .
345 *** runcommand phase -r .
344 3: public
346 3: public
345
347
346
348
347 >>> import os
349 >>> import os
348 >>> from hgclient import readchannel, runcommand, check
350 >>> from hgclient import check, readchannel, runcommand
349 >>> @check
351 >>> @check
350 ... def branch(server):
352 ... def branch(server):
351 ... readchannel(server)
353 ... readchannel(server)
352 ... runcommand(server, ['branch'])
354 ... runcommand(server, ['branch'])
353 ... os.system('hg branch foo')
355 ... os.system('hg branch foo')
354 ... runcommand(server, ['branch'])
356 ... runcommand(server, ['branch'])
355 ... os.system('hg branch default')
357 ... os.system('hg branch default')
356 *** runcommand branch
358 *** runcommand branch
357 default
359 default
358 marked working directory as branch foo
360 marked working directory as branch foo
359 (branches are permanent and global, did you want a bookmark?)
361 (branches are permanent and global, did you want a bookmark?)
360 *** runcommand branch
362 *** runcommand branch
361 foo
363 foo
362 marked working directory as branch default
364 marked working directory as branch default
363 (branches are permanent and global, did you want a bookmark?)
365 (branches are permanent and global, did you want a bookmark?)
364
366
365 $ touch .hgignore
367 $ touch .hgignore
366 >>> import os
368 >>> import os
367 >>> from hgclient import readchannel, runcommand, check
369 >>> from hgclient import check, readchannel, runcommand
368 >>> @check
370 >>> @check
369 ... def hgignore(server):
371 ... def hgignore(server):
370 ... readchannel(server)
372 ... readchannel(server)
371 ... runcommand(server, ['commit', '-Am.'])
373 ... runcommand(server, ['commit', '-Am.'])
372 ... f = open('ignored-file', 'ab')
374 ... f = open('ignored-file', 'ab')
373 ... f.write('')
375 ... f.write('')
374 ... f.close()
376 ... f.close()
375 ... f = open('.hgignore', 'ab')
377 ... f = open('.hgignore', 'ab')
376 ... f.write('ignored-file')
378 ... f.write('ignored-file')
377 ... f.close()
379 ... f.close()
378 ... runcommand(server, ['status', '-i', '-u'])
380 ... runcommand(server, ['status', '-i', '-u'])
379 ... print('')
381 ... print('')
380 *** runcommand commit -Am.
382 *** runcommand commit -Am.
381 adding .hgignore
383 adding .hgignore
382 *** runcommand status -i -u
384 *** runcommand status -i -u
383 I ignored-file
385 I ignored-file
384
386
385
387
386 cache of non-public revisions should be invalidated on repository change
388 cache of non-public revisions should be invalidated on repository change
387 (issue4855):
389 (issue4855):
388
390
389 >>> import os
391 >>> import os
390 >>> from hgclient import readchannel, runcommand, check
392 >>> from hgclient import check, readchannel, runcommand
391 >>> @check
393 >>> @check
392 ... def phasesetscacheaftercommit(server):
394 ... def phasesetscacheaftercommit(server):
393 ... readchannel(server)
395 ... readchannel(server)
394 ... # load _phasecache._phaserevs and _phasesets
396 ... # load _phasecache._phaserevs and _phasesets
395 ... runcommand(server, ['log', '-qr', 'draft()'])
397 ... runcommand(server, ['log', '-qr', 'draft()'])
396 ... # create draft commits by another process
398 ... # create draft commits by another process
397 ... for i in xrange(5, 7):
399 ... for i in xrange(5, 7):
398 ... f = open('a', 'ab')
400 ... f = open('a', 'ab')
399 ... f.seek(0, os.SEEK_END)
401 ... f.seek(0, os.SEEK_END)
400 ... f.write('a\n')
402 ... f.write('a\n')
401 ... f.close()
403 ... f.close()
402 ... os.system('hg commit -Aqm%d' % i)
404 ... os.system('hg commit -Aqm%d' % i)
403 ... # new commits should be listed as draft revisions
405 ... # new commits should be listed as draft revisions
404 ... runcommand(server, ['log', '-qr', 'draft()'])
406 ... runcommand(server, ['log', '-qr', 'draft()'])
405 ... print('')
407 ... print('')
406 *** runcommand log -qr draft()
408 *** runcommand log -qr draft()
407 4:7966c8e3734d
409 4:7966c8e3734d
408 *** runcommand log -qr draft()
410 *** runcommand log -qr draft()
409 4:7966c8e3734d
411 4:7966c8e3734d
410 5:41f6602d1c4f
412 5:41f6602d1c4f
411 6:10501e202c35
413 6:10501e202c35
412
414
413
415
414 >>> import os
416 >>> import os
415 >>> from hgclient import readchannel, runcommand, check
417 >>> from hgclient import check, readchannel, runcommand
416 >>> @check
418 >>> @check
417 ... def phasesetscacheafterstrip(server):
419 ... def phasesetscacheafterstrip(server):
418 ... readchannel(server)
420 ... readchannel(server)
419 ... # load _phasecache._phaserevs and _phasesets
421 ... # load _phasecache._phaserevs and _phasesets
420 ... runcommand(server, ['log', '-qr', 'draft()'])
422 ... runcommand(server, ['log', '-qr', 'draft()'])
421 ... # strip cached revisions by another process
423 ... # strip cached revisions by another process
422 ... os.system('hg --config extensions.strip= strip -q 5')
424 ... os.system('hg --config extensions.strip= strip -q 5')
423 ... # shouldn't abort by "unknown revision '6'"
425 ... # shouldn't abort by "unknown revision '6'"
424 ... runcommand(server, ['log', '-qr', 'draft()'])
426 ... runcommand(server, ['log', '-qr', 'draft()'])
425 ... print('')
427 ... print('')
426 *** runcommand log -qr draft()
428 *** runcommand log -qr draft()
427 4:7966c8e3734d
429 4:7966c8e3734d
428 5:41f6602d1c4f
430 5:41f6602d1c4f
429 6:10501e202c35
431 6:10501e202c35
430 *** runcommand log -qr draft()
432 *** runcommand log -qr draft()
431 4:7966c8e3734d
433 4:7966c8e3734d
432
434
433
435
434 cache of phase roots should be invalidated on strip (issue3827):
436 cache of phase roots should be invalidated on strip (issue3827):
435
437
436 >>> import os
438 >>> import os
437 >>> from hgclient import readchannel, sep, runcommand, check
439 >>> from hgclient import check, readchannel, runcommand, sep
438 >>> @check
440 >>> @check
439 ... def phasecacheafterstrip(server):
441 ... def phasecacheafterstrip(server):
440 ... readchannel(server)
442 ... readchannel(server)
441 ...
443 ...
442 ... # create new head, 5:731265503d86
444 ... # create new head, 5:731265503d86
443 ... runcommand(server, ['update', '-C', '0'])
445 ... runcommand(server, ['update', '-C', '0'])
444 ... f = open('a', 'ab')
446 ... f = open('a', 'ab')
445 ... f.write('a\n')
447 ... f.write('a\n')
446 ... f.close()
448 ... f.close()
447 ... runcommand(server, ['commit', '-Am.', 'a'])
449 ... runcommand(server, ['commit', '-Am.', 'a'])
448 ... runcommand(server, ['log', '-Gq'])
450 ... runcommand(server, ['log', '-Gq'])
449 ...
451 ...
450 ... # make it public; draft marker moves to 4:7966c8e3734d
452 ... # make it public; draft marker moves to 4:7966c8e3734d
451 ... runcommand(server, ['phase', '-p', '.'])
453 ... runcommand(server, ['phase', '-p', '.'])
452 ... # load _phasecache.phaseroots
454 ... # load _phasecache.phaseroots
453 ... runcommand(server, ['phase', '.'], outfilter=sep)
455 ... runcommand(server, ['phase', '.'], outfilter=sep)
454 ...
456 ...
455 ... # strip 1::4 outside server
457 ... # strip 1::4 outside server
456 ... os.system('hg -q --config extensions.mq= strip 1')
458 ... os.system('hg -q --config extensions.mq= strip 1')
457 ...
459 ...
458 ... # shouldn't raise "7966c8e3734d: no node!"
460 ... # shouldn't raise "7966c8e3734d: no node!"
459 ... runcommand(server, ['branches'])
461 ... runcommand(server, ['branches'])
460 *** runcommand update -C 0
462 *** runcommand update -C 0
461 1 files updated, 0 files merged, 2 files removed, 0 files unresolved
463 1 files updated, 0 files merged, 2 files removed, 0 files unresolved
462 (leaving bookmark bm3)
464 (leaving bookmark bm3)
463 *** runcommand commit -Am. a
465 *** runcommand commit -Am. a
464 created new head
466 created new head
465 *** runcommand log -Gq
467 *** runcommand log -Gq
466 @ 5:731265503d86
468 @ 5:731265503d86
467 |
469 |
468 | o 4:7966c8e3734d
470 | o 4:7966c8e3734d
469 | |
471 | |
470 | o 3:b9b85890c400
472 | o 3:b9b85890c400
471 | |
473 | |
472 | o 2:aef17e88f5f0
474 | o 2:aef17e88f5f0
473 | |
475 | |
474 | o 1:d3a0a68be6de
476 | o 1:d3a0a68be6de
475 |/
477 |/
476 o 0:eff892de26ec
478 o 0:eff892de26ec
477
479
478 *** runcommand phase -p .
480 *** runcommand phase -p .
479 *** runcommand phase .
481 *** runcommand phase .
480 5: public
482 5: public
481 *** runcommand branches
483 *** runcommand branches
482 default 1:731265503d86
484 default 1:731265503d86
483
485
484 in-memory cache must be reloaded if transaction is aborted. otherwise
486 in-memory cache must be reloaded if transaction is aborted. otherwise
485 changelog and manifest would have invalid node:
487 changelog and manifest would have invalid node:
486
488
487 $ echo a >> a
489 $ echo a >> a
488 >>> from hgclient import readchannel, runcommand, check
490 >>> from hgclient import check, readchannel, runcommand
489 >>> @check
491 >>> @check
490 ... def txabort(server):
492 ... def txabort(server):
491 ... readchannel(server)
493 ... readchannel(server)
492 ... runcommand(server, ['commit', '--config', 'hooks.pretxncommit=false',
494 ... runcommand(server, ['commit', '--config', 'hooks.pretxncommit=false',
493 ... '-mfoo'])
495 ... '-mfoo'])
494 ... runcommand(server, ['verify'])
496 ... runcommand(server, ['verify'])
495 *** runcommand commit --config hooks.pretxncommit=false -mfoo
497 *** runcommand commit --config hooks.pretxncommit=false -mfoo
496 transaction abort!
498 transaction abort!
497 rollback completed
499 rollback completed
498 abort: pretxncommit hook exited with status 1
500 abort: pretxncommit hook exited with status 1
499 [255]
501 [255]
500 *** runcommand verify
502 *** runcommand verify
501 checking changesets
503 checking changesets
502 checking manifests
504 checking manifests
503 crosschecking files in changesets and manifests
505 crosschecking files in changesets and manifests
504 checking files
506 checking files
505 1 files, 2 changesets, 2 total revisions
507 1 files, 2 changesets, 2 total revisions
506 $ hg revert --no-backup -aq
508 $ hg revert --no-backup -aq
507
509
508 $ cat >> .hg/hgrc << EOF
510 $ cat >> .hg/hgrc << EOF
509 > [experimental]
511 > [experimental]
510 > stabilization=createmarkers
512 > stabilization=createmarkers
511 > EOF
513 > EOF
512
514
513 >>> import os
515 >>> import os
514 >>> from hgclient import readchannel, runcommand, check
516 >>> from hgclient import check, readchannel, runcommand
515 >>> @check
517 >>> @check
516 ... def obsolete(server):
518 ... def obsolete(server):
517 ... readchannel(server)
519 ... readchannel(server)
518 ...
520 ...
519 ... runcommand(server, ['up', 'null'])
521 ... runcommand(server, ['up', 'null'])
520 ... runcommand(server, ['phase', '-df', 'tip'])
522 ... runcommand(server, ['phase', '-df', 'tip'])
521 ... cmd = 'hg debugobsolete `hg log -r tip --template {node}`'
523 ... cmd = 'hg debugobsolete `hg log -r tip --template {node}`'
522 ... if os.name == 'nt':
524 ... if os.name == 'nt':
523 ... cmd = 'sh -c "%s"' % cmd # run in sh, not cmd.exe
525 ... cmd = 'sh -c "%s"' % cmd # run in sh, not cmd.exe
524 ... os.system(cmd)
526 ... os.system(cmd)
525 ... runcommand(server, ['log', '--hidden'])
527 ... runcommand(server, ['log', '--hidden'])
526 ... runcommand(server, ['log'])
528 ... runcommand(server, ['log'])
527 *** runcommand up null
529 *** runcommand up null
528 0 files updated, 0 files merged, 1 files removed, 0 files unresolved
530 0 files updated, 0 files merged, 1 files removed, 0 files unresolved
529 *** runcommand phase -df tip
531 *** runcommand phase -df tip
530 obsoleted 1 changesets
532 obsoleted 1 changesets
531 *** runcommand log --hidden
533 *** runcommand log --hidden
532 changeset: 1:731265503d86
534 changeset: 1:731265503d86
533 tag: tip
535 tag: tip
534 user: test
536 user: test
535 date: Thu Jan 01 00:00:00 1970 +0000
537 date: Thu Jan 01 00:00:00 1970 +0000
536 summary: .
538 summary: .
537
539
538 changeset: 0:eff892de26ec
540 changeset: 0:eff892de26ec
539 bookmark: bm1
541 bookmark: bm1
540 bookmark: bm2
542 bookmark: bm2
541 bookmark: bm3
543 bookmark: bm3
542 user: test
544 user: test
543 date: Thu Jan 01 00:00:00 1970 +0000
545 date: Thu Jan 01 00:00:00 1970 +0000
544 summary: 1
546 summary: 1
545
547
546 *** runcommand log
548 *** runcommand log
547 changeset: 0:eff892de26ec
549 changeset: 0:eff892de26ec
548 bookmark: bm1
550 bookmark: bm1
549 bookmark: bm2
551 bookmark: bm2
550 bookmark: bm3
552 bookmark: bm3
551 tag: tip
553 tag: tip
552 user: test
554 user: test
553 date: Thu Jan 01 00:00:00 1970 +0000
555 date: Thu Jan 01 00:00:00 1970 +0000
554 summary: 1
556 summary: 1
555
557
556
558
557 $ cat <<EOF >> .hg/hgrc
559 $ cat <<EOF >> .hg/hgrc
558 > [extensions]
560 > [extensions]
559 > mq =
561 > mq =
560 > EOF
562 > EOF
561
563
562 >>> import os
564 >>> import os
563 >>> from hgclient import readchannel, runcommand, check
565 >>> from hgclient import check, readchannel, runcommand
564 >>> @check
566 >>> @check
565 ... def mqoutsidechanges(server):
567 ... def mqoutsidechanges(server):
566 ... readchannel(server)
568 ... readchannel(server)
567 ...
569 ...
568 ... # load repo.mq
570 ... # load repo.mq
569 ... runcommand(server, ['qapplied'])
571 ... runcommand(server, ['qapplied'])
570 ... os.system('hg qnew 0.diff')
572 ... os.system('hg qnew 0.diff')
571 ... # repo.mq should be invalidated
573 ... # repo.mq should be invalidated
572 ... runcommand(server, ['qapplied'])
574 ... runcommand(server, ['qapplied'])
573 ...
575 ...
574 ... runcommand(server, ['qpop', '--all'])
576 ... runcommand(server, ['qpop', '--all'])
575 ... os.system('hg qqueue --create foo')
577 ... os.system('hg qqueue --create foo')
576 ... # repo.mq should be recreated to point to new queue
578 ... # repo.mq should be recreated to point to new queue
577 ... runcommand(server, ['qqueue', '--active'])
579 ... runcommand(server, ['qqueue', '--active'])
578 *** runcommand qapplied
580 *** runcommand qapplied
579 *** runcommand qapplied
581 *** runcommand qapplied
580 0.diff
582 0.diff
581 *** runcommand qpop --all
583 *** runcommand qpop --all
582 popping 0.diff
584 popping 0.diff
583 patch queue now empty
585 patch queue now empty
584 *** runcommand qqueue --active
586 *** runcommand qqueue --active
585 foo
587 foo
586
588
587 $ cat <<EOF > dbgui.py
589 $ cat <<EOF > dbgui.py
588 > import os, sys
590 > import os
591 > import sys
589 > from mercurial import commands, registrar
592 > from mercurial import commands, registrar
590 > cmdtable = {}
593 > cmdtable = {}
591 > command = registrar.command(cmdtable)
594 > command = registrar.command(cmdtable)
592 > @command(b"debuggetpass", norepo=True)
595 > @command(b"debuggetpass", norepo=True)
593 > def debuggetpass(ui):
596 > def debuggetpass(ui):
594 > ui.write("%s\\n" % ui.getpass())
597 > ui.write("%s\\n" % ui.getpass())
595 > @command(b"debugprompt", norepo=True)
598 > @command(b"debugprompt", norepo=True)
596 > def debugprompt(ui):
599 > def debugprompt(ui):
597 > ui.write("%s\\n" % ui.prompt("prompt:"))
600 > ui.write("%s\\n" % ui.prompt("prompt:"))
598 > @command(b"debugreadstdin", norepo=True)
601 > @command(b"debugreadstdin", norepo=True)
599 > def debugreadstdin(ui):
602 > def debugreadstdin(ui):
600 > ui.write("read: %r\n" % sys.stdin.read(1))
603 > ui.write("read: %r\n" % sys.stdin.read(1))
601 > @command(b"debugwritestdout", norepo=True)
604 > @command(b"debugwritestdout", norepo=True)
602 > def debugwritestdout(ui):
605 > def debugwritestdout(ui):
603 > os.write(1, "low-level stdout fd and\n")
606 > os.write(1, "low-level stdout fd and\n")
604 > sys.stdout.write("stdout should be redirected to /dev/null\n")
607 > sys.stdout.write("stdout should be redirected to /dev/null\n")
605 > sys.stdout.flush()
608 > sys.stdout.flush()
606 > EOF
609 > EOF
607 $ cat <<EOF >> .hg/hgrc
610 $ cat <<EOF >> .hg/hgrc
608 > [extensions]
611 > [extensions]
609 > dbgui = dbgui.py
612 > dbgui = dbgui.py
610 > EOF
613 > EOF
611
614
612 >>> from hgclient import readchannel, runcommand, check, stringio
615 >>> from hgclient import check, readchannel, runcommand, stringio
613 >>> @check
616 >>> @check
614 ... def getpass(server):
617 ... def getpass(server):
615 ... readchannel(server)
618 ... readchannel(server)
616 ... runcommand(server, ['debuggetpass', '--config',
619 ... runcommand(server, ['debuggetpass', '--config',
617 ... 'ui.interactive=True'],
620 ... 'ui.interactive=True'],
618 ... input=stringio('1234\n'))
621 ... input=stringio('1234\n'))
619 ... runcommand(server, ['debuggetpass', '--config',
622 ... runcommand(server, ['debuggetpass', '--config',
620 ... 'ui.interactive=True'],
623 ... 'ui.interactive=True'],
621 ... input=stringio('\n'))
624 ... input=stringio('\n'))
622 ... runcommand(server, ['debuggetpass', '--config',
625 ... runcommand(server, ['debuggetpass', '--config',
623 ... 'ui.interactive=True'],
626 ... 'ui.interactive=True'],
624 ... input=stringio(''))
627 ... input=stringio(''))
625 ... runcommand(server, ['debugprompt', '--config',
628 ... runcommand(server, ['debugprompt', '--config',
626 ... 'ui.interactive=True'],
629 ... 'ui.interactive=True'],
627 ... input=stringio('5678\n'))
630 ... input=stringio('5678\n'))
628 ... runcommand(server, ['debugreadstdin'])
631 ... runcommand(server, ['debugreadstdin'])
629 ... runcommand(server, ['debugwritestdout'])
632 ... runcommand(server, ['debugwritestdout'])
630 *** runcommand debuggetpass --config ui.interactive=True
633 *** runcommand debuggetpass --config ui.interactive=True
631 password: 1234
634 password: 1234
632 *** runcommand debuggetpass --config ui.interactive=True
635 *** runcommand debuggetpass --config ui.interactive=True
633 password:
636 password:
634 *** runcommand debuggetpass --config ui.interactive=True
637 *** runcommand debuggetpass --config ui.interactive=True
635 password: abort: response expected
638 password: abort: response expected
636 [255]
639 [255]
637 *** runcommand debugprompt --config ui.interactive=True
640 *** runcommand debugprompt --config ui.interactive=True
638 prompt: 5678
641 prompt: 5678
639 *** runcommand debugreadstdin
642 *** runcommand debugreadstdin
640 read: ''
643 read: ''
641 *** runcommand debugwritestdout
644 *** runcommand debugwritestdout
642
645
643
646
644 run commandserver in commandserver, which is silly but should work:
647 run commandserver in commandserver, which is silly but should work:
645
648
646 >>> from __future__ import print_function
649 >>> from __future__ import print_function
647 >>> from hgclient import readchannel, runcommand, check, stringio
650 >>> from hgclient import check, readchannel, runcommand, stringio
648 >>> @check
651 >>> @check
649 ... def nested(server):
652 ... def nested(server):
650 ... print('%c, %r' % readchannel(server))
653 ... print('%c, %r' % readchannel(server))
651 ... class nestedserver(object):
654 ... class nestedserver(object):
652 ... stdin = stringio('getencoding\n')
655 ... stdin = stringio('getencoding\n')
653 ... stdout = stringio()
656 ... stdout = stringio()
654 ... runcommand(server, ['serve', '--cmdserver', 'pipe'],
657 ... runcommand(server, ['serve', '--cmdserver', 'pipe'],
655 ... output=nestedserver.stdout, input=nestedserver.stdin)
658 ... output=nestedserver.stdout, input=nestedserver.stdin)
656 ... nestedserver.stdout.seek(0)
659 ... nestedserver.stdout.seek(0)
657 ... print('%c, %r' % readchannel(nestedserver)) # hello
660 ... print('%c, %r' % readchannel(nestedserver)) # hello
658 ... print('%c, %r' % readchannel(nestedserver)) # getencoding
661 ... print('%c, %r' % readchannel(nestedserver)) # getencoding
659 o, 'capabilities: getencoding runcommand\nencoding: *\npid: *' (glob)
662 o, 'capabilities: getencoding runcommand\nencoding: *\npid: *' (glob)
660 *** runcommand serve --cmdserver pipe
663 *** runcommand serve --cmdserver pipe
661 o, 'capabilities: getencoding runcommand\nencoding: *\npid: *' (glob)
664 o, 'capabilities: getencoding runcommand\nencoding: *\npid: *' (glob)
662 r, '*' (glob)
665 r, '*' (glob)
663
666
664
667
665 start without repository:
668 start without repository:
666
669
667 $ cd ..
670 $ cd ..
668
671
669 >>> from __future__ import print_function
672 >>> from __future__ import print_function
670 >>> from hgclient import readchannel, runcommand, check
673 >>> from hgclient import check, readchannel, runcommand
671 >>> @check
674 >>> @check
672 ... def hellomessage(server):
675 ... def hellomessage(server):
673 ... ch, data = readchannel(server)
676 ... ch, data = readchannel(server)
674 ... print('%c, %r' % (ch, data))
677 ... print('%c, %r' % (ch, data))
675 ... # run an arbitrary command to make sure the next thing the server
678 ... # run an arbitrary command to make sure the next thing the server
676 ... # sends isn't part of the hello message
679 ... # sends isn't part of the hello message
677 ... runcommand(server, ['id'])
680 ... runcommand(server, ['id'])
678 o, 'capabilities: getencoding runcommand\nencoding: *\npid: *' (glob)
681 o, 'capabilities: getencoding runcommand\nencoding: *\npid: *' (glob)
679 *** runcommand id
682 *** runcommand id
680 abort: there is no Mercurial repository here (.hg not found)
683 abort: there is no Mercurial repository here (.hg not found)
681 [255]
684 [255]
682
685
683 >>> from hgclient import readchannel, runcommand, check
686 >>> from hgclient import check, readchannel, runcommand
684 >>> @check
687 >>> @check
685 ... def startwithoutrepo(server):
688 ... def startwithoutrepo(server):
686 ... readchannel(server)
689 ... readchannel(server)
687 ... runcommand(server, ['init', 'repo2'])
690 ... runcommand(server, ['init', 'repo2'])
688 ... runcommand(server, ['id', '-R', 'repo2'])
691 ... runcommand(server, ['id', '-R', 'repo2'])
689 *** runcommand init repo2
692 *** runcommand init repo2
690 *** runcommand id -R repo2
693 *** runcommand id -R repo2
691 000000000000 tip
694 000000000000 tip
692
695
693
696
694 don't fall back to cwd if invalid -R path is specified (issue4805):
697 don't fall back to cwd if invalid -R path is specified (issue4805):
695
698
696 $ cd repo
699 $ cd repo
697 $ hg serve --cmdserver pipe -R ../nonexistent
700 $ hg serve --cmdserver pipe -R ../nonexistent
698 abort: repository ../nonexistent not found!
701 abort: repository ../nonexistent not found!
699 [255]
702 [255]
700 $ cd ..
703 $ cd ..
701
704
702
705
703 unix domain socket:
706 unix domain socket:
704
707
705 $ cd repo
708 $ cd repo
706 $ hg update -q
709 $ hg update -q
707
710
708 #if unix-socket unix-permissions
711 #if unix-socket unix-permissions
709
712
710 >>> from __future__ import print_function
713 >>> from __future__ import print_function
711 >>> from hgclient import unixserver, readchannel, runcommand, check, stringio
714 >>> from hgclient import check, readchannel, runcommand, stringio, unixserver
712 >>> server = unixserver('.hg/server.sock', '.hg/server.log')
715 >>> server = unixserver('.hg/server.sock', '.hg/server.log')
713 >>> def hellomessage(conn):
716 >>> def hellomessage(conn):
714 ... ch, data = readchannel(conn)
717 ... ch, data = readchannel(conn)
715 ... print('%c, %r' % (ch, data))
718 ... print('%c, %r' % (ch, data))
716 ... runcommand(conn, ['id'])
719 ... runcommand(conn, ['id'])
717 >>> check(hellomessage, server.connect)
720 >>> check(hellomessage, server.connect)
718 o, 'capabilities: getencoding runcommand\nencoding: *\npid: *' (glob)
721 o, 'capabilities: getencoding runcommand\nencoding: *\npid: *' (glob)
719 *** runcommand id
722 *** runcommand id
720 eff892de26ec tip bm1/bm2/bm3
723 eff892de26ec tip bm1/bm2/bm3
721 >>> def unknowncommand(conn):
724 >>> def unknowncommand(conn):
722 ... readchannel(conn)
725 ... readchannel(conn)
723 ... conn.stdin.write('unknowncommand\n')
726 ... conn.stdin.write('unknowncommand\n')
724 >>> check(unknowncommand, server.connect) # error sent to server.log
727 >>> check(unknowncommand, server.connect) # error sent to server.log
725 >>> def serverinput(conn):
728 >>> def serverinput(conn):
726 ... readchannel(conn)
729 ... readchannel(conn)
727 ... patch = """
730 ... patch = """
728 ... # HG changeset patch
731 ... # HG changeset patch
729 ... # User test
732 ... # User test
730 ... # Date 0 0
733 ... # Date 0 0
731 ... 2
734 ... 2
732 ...
735 ...
733 ... diff -r eff892de26ec -r 1ed24be7e7a0 a
736 ... diff -r eff892de26ec -r 1ed24be7e7a0 a
734 ... --- a/a
737 ... --- a/a
735 ... +++ b/a
738 ... +++ b/a
736 ... @@ -1,1 +1,2 @@
739 ... @@ -1,1 +1,2 @@
737 ... 1
740 ... 1
738 ... +2
741 ... +2
739 ... """
742 ... """
740 ... runcommand(conn, ['import', '-'], input=stringio(patch))
743 ... runcommand(conn, ['import', '-'], input=stringio(patch))
741 ... runcommand(conn, ['log', '-rtip', '-q'])
744 ... runcommand(conn, ['log', '-rtip', '-q'])
742 >>> check(serverinput, server.connect)
745 >>> check(serverinput, server.connect)
743 *** runcommand import -
746 *** runcommand import -
744 applying patch from stdin
747 applying patch from stdin
745 *** runcommand log -rtip -q
748 *** runcommand log -rtip -q
746 2:1ed24be7e7a0
749 2:1ed24be7e7a0
747 >>> server.shutdown()
750 >>> server.shutdown()
748
751
749 $ cat .hg/server.log
752 $ cat .hg/server.log
750 listening at .hg/server.sock
753 listening at .hg/server.sock
751 abort: unknown command unknowncommand
754 abort: unknown command unknowncommand
752 killed!
755 killed!
753 $ rm .hg/server.log
756 $ rm .hg/server.log
754
757
755 if server crashed before hello, traceback will be sent to 'e' channel as
758 if server crashed before hello, traceback will be sent to 'e' channel as
756 last ditch:
759 last ditch:
757
760
758 $ cat <<EOF >> .hg/hgrc
761 $ cat <<EOF >> .hg/hgrc
759 > [cmdserver]
762 > [cmdserver]
760 > log = inexistent/path.log
763 > log = inexistent/path.log
761 > EOF
764 > EOF
762 >>> from __future__ import print_function
765 >>> from __future__ import print_function
763 >>> from hgclient import unixserver, readchannel, check
766 >>> from hgclient import check, readchannel, unixserver
764 >>> server = unixserver('.hg/server.sock', '.hg/server.log')
767 >>> server = unixserver('.hg/server.sock', '.hg/server.log')
765 >>> def earlycrash(conn):
768 >>> def earlycrash(conn):
766 ... while True:
769 ... while True:
767 ... try:
770 ... try:
768 ... ch, data = readchannel(conn)
771 ... ch, data = readchannel(conn)
769 ... if not data.startswith(' '):
772 ... if not data.startswith(' '):
770 ... print('%c, %r' % (ch, data))
773 ... print('%c, %r' % (ch, data))
771 ... except EOFError:
774 ... except EOFError:
772 ... break
775 ... break
773 >>> check(earlycrash, server.connect)
776 >>> check(earlycrash, server.connect)
774 e, 'Traceback (most recent call last):\n'
777 e, 'Traceback (most recent call last):\n'
775 e, "IOError: *" (glob)
778 e, "IOError: *" (glob)
776 >>> server.shutdown()
779 >>> server.shutdown()
777
780
778 $ cat .hg/server.log | grep -v '^ '
781 $ cat .hg/server.log | grep -v '^ '
779 listening at .hg/server.sock
782 listening at .hg/server.sock
780 Traceback (most recent call last):
783 Traceback (most recent call last):
781 IOError: * (glob)
784 IOError: * (glob)
782 killed!
785 killed!
783 #endif
786 #endif
784 #if no-unix-socket
787 #if no-unix-socket
785
788
786 $ hg serve --cmdserver unix -a .hg/server.sock
789 $ hg serve --cmdserver unix -a .hg/server.sock
787 abort: unsupported platform
790 abort: unsupported platform
788 [255]
791 [255]
789
792
790 #endif
793 #endif
791
794
792 $ cd ..
795 $ cd ..
793
796
794 Test that accessing to invalid changelog cache is avoided at
797 Test that accessing to invalid changelog cache is avoided at
795 subsequent operations even if repo object is reused even after failure
798 subsequent operations even if repo object is reused even after failure
796 of transaction (see 0a7610758c42 also)
799 of transaction (see 0a7610758c42 also)
797
800
798 "hg log" after failure of transaction is needed to detect invalid
801 "hg log" after failure of transaction is needed to detect invalid
799 cache in repoview: this can't detect by "hg verify" only.
802 cache in repoview: this can't detect by "hg verify" only.
800
803
801 Combination of "finalization" and "empty-ness of changelog" (2 x 2 =
804 Combination of "finalization" and "empty-ness of changelog" (2 x 2 =
802 4) are tested, because '00changelog.i' are differently changed in each
805 4) are tested, because '00changelog.i' are differently changed in each
803 cases.
806 cases.
804
807
805 $ cat > $TESTTMP/failafterfinalize.py <<EOF
808 $ cat > $TESTTMP/failafterfinalize.py <<EOF
806 > # extension to abort transaction after finalization forcibly
809 > # extension to abort transaction after finalization forcibly
807 > from mercurial import commands, error, extensions, lock as lockmod
810 > from mercurial import commands, error, extensions, lock as lockmod
808 > def fail(tr):
811 > def fail(tr):
809 > raise error.Abort('fail after finalization')
812 > raise error.Abort('fail after finalization')
810 > def reposetup(ui, repo):
813 > def reposetup(ui, repo):
811 > class failrepo(repo.__class__):
814 > class failrepo(repo.__class__):
812 > def commitctx(self, ctx, error=False):
815 > def commitctx(self, ctx, error=False):
813 > if self.ui.configbool('failafterfinalize', 'fail'):
816 > if self.ui.configbool('failafterfinalize', 'fail'):
814 > # 'sorted()' by ASCII code on category names causes
817 > # 'sorted()' by ASCII code on category names causes
815 > # invoking 'fail' after finalization of changelog
818 > # invoking 'fail' after finalization of changelog
816 > # using "'cl-%i' % id(self)" as category name
819 > # using "'cl-%i' % id(self)" as category name
817 > self.currenttransaction().addfinalize('zzzzzzzz', fail)
820 > self.currenttransaction().addfinalize('zzzzzzzz', fail)
818 > return super(failrepo, self).commitctx(ctx, error)
821 > return super(failrepo, self).commitctx(ctx, error)
819 > repo.__class__ = failrepo
822 > repo.__class__ = failrepo
820 > EOF
823 > EOF
821
824
822 $ hg init repo3
825 $ hg init repo3
823 $ cd repo3
826 $ cd repo3
824
827
825 $ cat <<EOF >> $HGRCPATH
828 $ cat <<EOF >> $HGRCPATH
826 > [ui]
829 > [ui]
827 > logtemplate = {rev} {desc|firstline} ({files})\n
830 > logtemplate = {rev} {desc|firstline} ({files})\n
828 >
831 >
829 > [extensions]
832 > [extensions]
830 > failafterfinalize = $TESTTMP/failafterfinalize.py
833 > failafterfinalize = $TESTTMP/failafterfinalize.py
831 > EOF
834 > EOF
832
835
833 - test failure with "empty changelog"
836 - test failure with "empty changelog"
834
837
835 $ echo foo > foo
838 $ echo foo > foo
836 $ hg add foo
839 $ hg add foo
837
840
838 (failure before finalization)
841 (failure before finalization)
839
842
840 >>> from hgclient import readchannel, runcommand, check
843 >>> from hgclient import check, readchannel, runcommand
841 >>> @check
844 >>> @check
842 ... def abort(server):
845 ... def abort(server):
843 ... readchannel(server)
846 ... readchannel(server)
844 ... runcommand(server, ['commit',
847 ... runcommand(server, ['commit',
845 ... '--config', 'hooks.pretxncommit=false',
848 ... '--config', 'hooks.pretxncommit=false',
846 ... '-mfoo'])
849 ... '-mfoo'])
847 ... runcommand(server, ['log'])
850 ... runcommand(server, ['log'])
848 ... runcommand(server, ['verify', '-q'])
851 ... runcommand(server, ['verify', '-q'])
849 *** runcommand commit --config hooks.pretxncommit=false -mfoo
852 *** runcommand commit --config hooks.pretxncommit=false -mfoo
850 transaction abort!
853 transaction abort!
851 rollback completed
854 rollback completed
852 abort: pretxncommit hook exited with status 1
855 abort: pretxncommit hook exited with status 1
853 [255]
856 [255]
854 *** runcommand log
857 *** runcommand log
855 *** runcommand verify -q
858 *** runcommand verify -q
856
859
857 (failure after finalization)
860 (failure after finalization)
858
861
859 >>> from hgclient import readchannel, runcommand, check
862 >>> from hgclient import check, readchannel, runcommand
860 >>> @check
863 >>> @check
861 ... def abort(server):
864 ... def abort(server):
862 ... readchannel(server)
865 ... readchannel(server)
863 ... runcommand(server, ['commit',
866 ... runcommand(server, ['commit',
864 ... '--config', 'failafterfinalize.fail=true',
867 ... '--config', 'failafterfinalize.fail=true',
865 ... '-mfoo'])
868 ... '-mfoo'])
866 ... runcommand(server, ['log'])
869 ... runcommand(server, ['log'])
867 ... runcommand(server, ['verify', '-q'])
870 ... runcommand(server, ['verify', '-q'])
868 *** runcommand commit --config failafterfinalize.fail=true -mfoo
871 *** runcommand commit --config failafterfinalize.fail=true -mfoo
869 transaction abort!
872 transaction abort!
870 rollback completed
873 rollback completed
871 abort: fail after finalization
874 abort: fail after finalization
872 [255]
875 [255]
873 *** runcommand log
876 *** runcommand log
874 *** runcommand verify -q
877 *** runcommand verify -q
875
878
876 - test failure with "not-empty changelog"
879 - test failure with "not-empty changelog"
877
880
878 $ echo bar > bar
881 $ echo bar > bar
879 $ hg add bar
882 $ hg add bar
880 $ hg commit -mbar bar
883 $ hg commit -mbar bar
881
884
882 (failure before finalization)
885 (failure before finalization)
883
886
884 >>> from hgclient import readchannel, runcommand, check
887 >>> from hgclient import check, readchannel, runcommand
885 >>> @check
888 >>> @check
886 ... def abort(server):
889 ... def abort(server):
887 ... readchannel(server)
890 ... readchannel(server)
888 ... runcommand(server, ['commit',
891 ... runcommand(server, ['commit',
889 ... '--config', 'hooks.pretxncommit=false',
892 ... '--config', 'hooks.pretxncommit=false',
890 ... '-mfoo', 'foo'])
893 ... '-mfoo', 'foo'])
891 ... runcommand(server, ['log'])
894 ... runcommand(server, ['log'])
892 ... runcommand(server, ['verify', '-q'])
895 ... runcommand(server, ['verify', '-q'])
893 *** runcommand commit --config hooks.pretxncommit=false -mfoo foo
896 *** runcommand commit --config hooks.pretxncommit=false -mfoo foo
894 transaction abort!
897 transaction abort!
895 rollback completed
898 rollback completed
896 abort: pretxncommit hook exited with status 1
899 abort: pretxncommit hook exited with status 1
897 [255]
900 [255]
898 *** runcommand log
901 *** runcommand log
899 0 bar (bar)
902 0 bar (bar)
900 *** runcommand verify -q
903 *** runcommand verify -q
901
904
902 (failure after finalization)
905 (failure after finalization)
903
906
904 >>> from hgclient import readchannel, runcommand, check
907 >>> from hgclient import check, readchannel, runcommand
905 >>> @check
908 >>> @check
906 ... def abort(server):
909 ... def abort(server):
907 ... readchannel(server)
910 ... readchannel(server)
908 ... runcommand(server, ['commit',
911 ... runcommand(server, ['commit',
909 ... '--config', 'failafterfinalize.fail=true',
912 ... '--config', 'failafterfinalize.fail=true',
910 ... '-mfoo', 'foo'])
913 ... '-mfoo', 'foo'])
911 ... runcommand(server, ['log'])
914 ... runcommand(server, ['log'])
912 ... runcommand(server, ['verify', '-q'])
915 ... runcommand(server, ['verify', '-q'])
913 *** runcommand commit --config failafterfinalize.fail=true -mfoo foo
916 *** runcommand commit --config failafterfinalize.fail=true -mfoo foo
914 transaction abort!
917 transaction abort!
915 rollback completed
918 rollback completed
916 abort: fail after finalization
919 abort: fail after finalization
917 [255]
920 [255]
918 *** runcommand log
921 *** runcommand log
919 0 bar (bar)
922 0 bar (bar)
920 *** runcommand verify -q
923 *** runcommand verify -q
921
924
922 $ cd ..
925 $ cd ..
923
926
924 Test symlink traversal over cached audited paths:
927 Test symlink traversal over cached audited paths:
925 -------------------------------------------------
928 -------------------------------------------------
926
929
927 #if symlink
930 #if symlink
928
931
929 set up symlink hell
932 set up symlink hell
930
933
931 $ mkdir merge-symlink-out
934 $ mkdir merge-symlink-out
932 $ hg init merge-symlink
935 $ hg init merge-symlink
933 $ cd merge-symlink
936 $ cd merge-symlink
934 $ touch base
937 $ touch base
935 $ hg commit -qAm base
938 $ hg commit -qAm base
936 $ ln -s ../merge-symlink-out a
939 $ ln -s ../merge-symlink-out a
937 $ hg commit -qAm 'symlink a -> ../merge-symlink-out'
940 $ hg commit -qAm 'symlink a -> ../merge-symlink-out'
938 $ hg up -q 0
941 $ hg up -q 0
939 $ mkdir a
942 $ mkdir a
940 $ touch a/poisoned
943 $ touch a/poisoned
941 $ hg commit -qAm 'file a/poisoned'
944 $ hg commit -qAm 'file a/poisoned'
942 $ hg log -G -T '{rev}: {desc}\n'
945 $ hg log -G -T '{rev}: {desc}\n'
943 @ 2: file a/poisoned
946 @ 2: file a/poisoned
944 |
947 |
945 | o 1: symlink a -> ../merge-symlink-out
948 | o 1: symlink a -> ../merge-symlink-out
946 |/
949 |/
947 o 0: base
950 o 0: base
948
951
949
952
950 try trivial merge after update: cache of audited paths should be discarded,
953 try trivial merge after update: cache of audited paths should be discarded,
951 and the merge should fail (issue5628)
954 and the merge should fail (issue5628)
952
955
953 $ hg up -q null
956 $ hg up -q null
954 >>> from hgclient import readchannel, runcommand, check
957 >>> from hgclient import check, readchannel, runcommand
955 >>> @check
958 >>> @check
956 ... def merge(server):
959 ... def merge(server):
957 ... readchannel(server)
960 ... readchannel(server)
958 ... # audit a/poisoned as a good path
961 ... # audit a/poisoned as a good path
959 ... runcommand(server, ['up', '-qC', '2'])
962 ... runcommand(server, ['up', '-qC', '2'])
960 ... runcommand(server, ['up', '-qC', '1'])
963 ... runcommand(server, ['up', '-qC', '1'])
961 ... # here a is a symlink, so a/poisoned is bad
964 ... # here a is a symlink, so a/poisoned is bad
962 ... runcommand(server, ['merge', '2'])
965 ... runcommand(server, ['merge', '2'])
963 *** runcommand up -qC 2
966 *** runcommand up -qC 2
964 *** runcommand up -qC 1
967 *** runcommand up -qC 1
965 *** runcommand merge 2
968 *** runcommand merge 2
966 abort: path 'a/poisoned' traverses symbolic link 'a'
969 abort: path 'a/poisoned' traverses symbolic link 'a'
967 [255]
970 [255]
968 $ ls ../merge-symlink-out
971 $ ls ../merge-symlink-out
969
972
970 cache of repo.auditor should be discarded, so matcher would never traverse
973 cache of repo.auditor should be discarded, so matcher would never traverse
971 symlinks:
974 symlinks:
972
975
973 $ hg up -qC 0
976 $ hg up -qC 0
974 $ touch ../merge-symlink-out/poisoned
977 $ touch ../merge-symlink-out/poisoned
975 >>> from hgclient import readchannel, runcommand, check
978 >>> from hgclient import check, readchannel, runcommand
976 >>> @check
979 >>> @check
977 ... def files(server):
980 ... def files(server):
978 ... readchannel(server)
981 ... readchannel(server)
979 ... runcommand(server, ['up', '-qC', '2'])
982 ... runcommand(server, ['up', '-qC', '2'])
980 ... # audit a/poisoned as a good path
983 ... # audit a/poisoned as a good path
981 ... runcommand(server, ['files', 'a/poisoned'])
984 ... runcommand(server, ['files', 'a/poisoned'])
982 ... runcommand(server, ['up', '-qC', '0'])
985 ... runcommand(server, ['up', '-qC', '0'])
983 ... runcommand(server, ['up', '-qC', '1'])
986 ... runcommand(server, ['up', '-qC', '1'])
984 ... # here 'a' is a symlink, so a/poisoned should be warned
987 ... # here 'a' is a symlink, so a/poisoned should be warned
985 ... runcommand(server, ['files', 'a/poisoned'])
988 ... runcommand(server, ['files', 'a/poisoned'])
986 *** runcommand up -qC 2
989 *** runcommand up -qC 2
987 *** runcommand files a/poisoned
990 *** runcommand files a/poisoned
988 a/poisoned
991 a/poisoned
989 *** runcommand up -qC 0
992 *** runcommand up -qC 0
990 *** runcommand up -qC 1
993 *** runcommand up -qC 1
991 *** runcommand files a/poisoned
994 *** runcommand files a/poisoned
992 abort: path 'a/poisoned' traverses symbolic link 'a'
995 abort: path 'a/poisoned' traverses symbolic link 'a'
993 [255]
996 [255]
994
997
995 $ cd ..
998 $ cd ..
996
999
997 #endif
1000 #endif
General Comments 0
You need to be logged in to leave comments. Login now