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