##// END OF EJS Templates
cleanup: polyfill assertRaisesRegex so we can avoid assertRaisesRegexp...
Augie Fackler -
r37733:1859b9a7 default
parent child Browse files
Show More
@@ -1,84 +1,90 b''
1 from __future__ import absolute_import
1 from __future__ import absolute_import
2
2
3 import unittest
3 import unittest
4 import silenttestrunner
4 import silenttestrunner
5
5
6 from mercurial import (
6 from mercurial import (
7 error,
7 error,
8 scmutil,
8 scmutil,
9 )
9 )
10
10
11 class mockfile(object):
11 class mockfile(object):
12 def __init__(self, name, fs):
12 def __init__(self, name, fs):
13 self.name = name
13 self.name = name
14 self.fs = fs
14 self.fs = fs
15
15
16 def __enter__(self):
16 def __enter__(self):
17 return self
17 return self
18
18
19 def __exit__(self, *args, **kwargs):
19 def __exit__(self, *args, **kwargs):
20 pass
20 pass
21
21
22 def write(self, text):
22 def write(self, text):
23 self.fs.contents[self.name] = text
23 self.fs.contents[self.name] = text
24
24
25 def read(self):
25 def read(self):
26 return self.fs.contents[self.name]
26 return self.fs.contents[self.name]
27
27
28 class mockvfs(object):
28 class mockvfs(object):
29 def __init__(self):
29 def __init__(self):
30 self.contents = {}
30 self.contents = {}
31
31
32 def read(self, path):
32 def read(self, path):
33 return mockfile(path, self).read()
33 return mockfile(path, self).read()
34
34
35 def readlines(self, path):
35 def readlines(self, path):
36 # lines need to contain the trailing '\n' to mock the real readlines
36 # lines need to contain the trailing '\n' to mock the real readlines
37 return [l for l in mockfile(path, self).read().splitlines(True)]
37 return [l for l in mockfile(path, self).read().splitlines(True)]
38
38
39 def __call__(self, path, mode, atomictemp):
39 def __call__(self, path, mode, atomictemp):
40 return mockfile(path, self)
40 return mockfile(path, self)
41
41
42 class testsimplekeyvaluefile(unittest.TestCase):
42 class testsimplekeyvaluefile(unittest.TestCase):
43 def setUp(self):
43 def setUp(self):
44 self.vfs = mockvfs()
44 self.vfs = mockvfs()
45
45
46 def testbasicwritingiandreading(self):
46 def testbasicwritingiandreading(self):
47 dw = {'key1': 'value1', 'Key2': 'value2'}
47 dw = {'key1': 'value1', 'Key2': 'value2'}
48 scmutil.simplekeyvaluefile(self.vfs, 'kvfile').write(dw)
48 scmutil.simplekeyvaluefile(self.vfs, 'kvfile').write(dw)
49 self.assertEqual(sorted(self.vfs.read('kvfile').split('\n')),
49 self.assertEqual(sorted(self.vfs.read('kvfile').split('\n')),
50 ['', 'Key2=value2', 'key1=value1'])
50 ['', 'Key2=value2', 'key1=value1'])
51 dr = scmutil.simplekeyvaluefile(self.vfs, 'kvfile').read()
51 dr = scmutil.simplekeyvaluefile(self.vfs, 'kvfile').read()
52 self.assertEqual(dr, dw)
52 self.assertEqual(dr, dw)
53
53
54 if not getattr(unittest.TestCase, 'assertRaisesRegex', False):
55 # Python 3.7 deprecates the regex*p* version, but 2.7 lacks
56 # the regex version.
57 assertRaisesRegex = (# camelcase-required
58 unittest.TestCase.assertRaisesRegexp)
59
54 def testinvalidkeys(self):
60 def testinvalidkeys(self):
55 d = {'0key1': 'value1', 'Key2': 'value2'}
61 d = {'0key1': 'value1', 'Key2': 'value2'}
56 with self.assertRaisesRegexp(error.ProgrammingError,
62 with self.assertRaisesRegex(error.ProgrammingError,
57 'keys must start with a letter.*'):
63 'keys must start with a letter.*'):
58 scmutil.simplekeyvaluefile(self.vfs, 'kvfile').write(d)
64 scmutil.simplekeyvaluefile(self.vfs, 'kvfile').write(d)
59
65
60 d = {'key1@': 'value1', 'Key2': 'value2'}
66 d = {'key1@': 'value1', 'Key2': 'value2'}
61 with self.assertRaisesRegexp(error.ProgrammingError, 'invalid key.*'):
67 with self.assertRaisesRegex(error.ProgrammingError, 'invalid key.*'):
62 scmutil.simplekeyvaluefile(self.vfs, 'kvfile').write(d)
68 scmutil.simplekeyvaluefile(self.vfs, 'kvfile').write(d)
63
69
64 def testinvalidvalues(self):
70 def testinvalidvalues(self):
65 d = {'key1': 'value1', 'Key2': 'value2\n'}
71 d = {'key1': 'value1', 'Key2': 'value2\n'}
66 with self.assertRaisesRegexp(error.ProgrammingError, 'invalid val.*'):
72 with self.assertRaisesRegex(error.ProgrammingError, 'invalid val.*'):
67 scmutil.simplekeyvaluefile(self.vfs, 'kvfile').write(d)
73 scmutil.simplekeyvaluefile(self.vfs, 'kvfile').write(d)
68
74
69 def testcorruptedfile(self):
75 def testcorruptedfile(self):
70 self.vfs.contents['badfile'] = 'ababagalamaga\n'
76 self.vfs.contents['badfile'] = 'ababagalamaga\n'
71 with self.assertRaisesRegexp(error.CorruptedState,
77 with self.assertRaisesRegex(error.CorruptedState,
72 'dictionary.*element.*'):
78 'dictionary.*element.*'):
73 scmutil.simplekeyvaluefile(self.vfs, 'badfile').read()
79 scmutil.simplekeyvaluefile(self.vfs, 'badfile').read()
74
80
75 def testfirstline(self):
81 def testfirstline(self):
76 dw = {'key1': 'value1'}
82 dw = {'key1': 'value1'}
77 scmutil.simplekeyvaluefile(self.vfs, 'fl').write(dw, firstline='1.0')
83 scmutil.simplekeyvaluefile(self.vfs, 'fl').write(dw, firstline='1.0')
78 self.assertEqual(self.vfs.read('fl'), '1.0\nkey1=value1\n')
84 self.assertEqual(self.vfs.read('fl'), '1.0\nkey1=value1\n')
79 dr = scmutil.simplekeyvaluefile(self.vfs, 'fl')\
85 dr = scmutil.simplekeyvaluefile(self.vfs, 'fl')\
80 .read(firstlinenonkeyval=True)
86 .read(firstlinenonkeyval=True)
81 self.assertEqual(dr, {'__firstline': '1.0', 'key1': 'value1'})
87 self.assertEqual(dr, {'__firstline': '1.0', 'key1': 'value1'})
82
88
83 if __name__ == "__main__":
89 if __name__ == "__main__":
84 silenttestrunner.main(__name__)
90 silenttestrunner.main(__name__)
@@ -1,130 +1,143 b''
1 from __future__ import absolute_import
1 from __future__ import absolute_import
2
2
3 import unittest
3 import unittest
4
4
5 from mercurial import (
5 from mercurial import (
6 error,
6 error,
7 wireprotoframing as framing,
7 wireprotoframing as framing,
8 )
8 )
9
9
10 ffs = framing.makeframefromhumanstring
10 ffs = framing.makeframefromhumanstring
11
11
12 def sendframe(reactor, frame):
12 def sendframe(reactor, frame):
13 """Send a frame bytearray to a reactor."""
13 """Send a frame bytearray to a reactor."""
14 header = framing.parseheader(frame)
14 header = framing.parseheader(frame)
15 payload = frame[framing.FRAME_HEADER_SIZE:]
15 payload = frame[framing.FRAME_HEADER_SIZE:]
16 assert len(payload) == header.length
16 assert len(payload) == header.length
17
17
18 return reactor.onframerecv(framing.frame(header.requestid,
18 return reactor.onframerecv(framing.frame(header.requestid,
19 header.streamid,
19 header.streamid,
20 header.streamflags,
20 header.streamflags,
21 header.typeid,
21 header.typeid,
22 header.flags,
22 header.flags,
23 payload))
23 payload))
24
24
25 class SingleSendTests(unittest.TestCase):
25 class SingleSendTests(unittest.TestCase):
26 """A reactor that can only send once rejects subsequent sends."""
26 """A reactor that can only send once rejects subsequent sends."""
27
28 if not getattr(unittest.TestCase, 'assertRaisesRegex', False):
29 # Python 3.7 deprecates the regex*p* version, but 2.7 lacks
30 # the regex version.
31 assertRaisesRegex = (# camelcase-required
32 unittest.TestCase.assertRaisesRegexp)
33
27 def testbasic(self):
34 def testbasic(self):
28 reactor = framing.clientreactor(hasmultiplesend=False, buffersends=True)
35 reactor = framing.clientreactor(hasmultiplesend=False, buffersends=True)
29
36
30 request, action, meta = reactor.callcommand(b'foo', {})
37 request, action, meta = reactor.callcommand(b'foo', {})
31 self.assertEqual(request.state, b'pending')
38 self.assertEqual(request.state, b'pending')
32 self.assertEqual(action, b'noop')
39 self.assertEqual(action, b'noop')
33
40
34 action, meta = reactor.flushcommands()
41 action, meta = reactor.flushcommands()
35 self.assertEqual(action, b'sendframes')
42 self.assertEqual(action, b'sendframes')
36
43
37 for frame in meta[b'framegen']:
44 for frame in meta[b'framegen']:
38 self.assertEqual(request.state, b'sending')
45 self.assertEqual(request.state, b'sending')
39
46
40 self.assertEqual(request.state, b'sent')
47 self.assertEqual(request.state, b'sent')
41
48
42 with self.assertRaisesRegexp(error.ProgrammingError,
49 with self.assertRaisesRegex(error.ProgrammingError,
43 'cannot issue new commands'):
50 'cannot issue new commands'):
44 reactor.callcommand(b'foo', {})
51 reactor.callcommand(b'foo', {})
45
52
46 with self.assertRaisesRegexp(error.ProgrammingError,
53 with self.assertRaisesRegex(error.ProgrammingError,
47 'cannot issue new commands'):
54 'cannot issue new commands'):
48 reactor.callcommand(b'foo', {})
55 reactor.callcommand(b'foo', {})
49
56
50 class NoBufferTests(unittest.TestCase):
57 class NoBufferTests(unittest.TestCase):
51 """A reactor without send buffering sends requests immediately."""
58 """A reactor without send buffering sends requests immediately."""
52 def testbasic(self):
59 def testbasic(self):
53 reactor = framing.clientreactor(hasmultiplesend=True, buffersends=False)
60 reactor = framing.clientreactor(hasmultiplesend=True, buffersends=False)
54
61
55 request, action, meta = reactor.callcommand(b'command1', {})
62 request, action, meta = reactor.callcommand(b'command1', {})
56 self.assertEqual(request.requestid, 1)
63 self.assertEqual(request.requestid, 1)
57 self.assertEqual(action, b'sendframes')
64 self.assertEqual(action, b'sendframes')
58
65
59 self.assertEqual(request.state, b'pending')
66 self.assertEqual(request.state, b'pending')
60
67
61 for frame in meta[b'framegen']:
68 for frame in meta[b'framegen']:
62 self.assertEqual(request.state, b'sending')
69 self.assertEqual(request.state, b'sending')
63
70
64 self.assertEqual(request.state, b'sent')
71 self.assertEqual(request.state, b'sent')
65
72
66 action, meta = reactor.flushcommands()
73 action, meta = reactor.flushcommands()
67 self.assertEqual(action, b'noop')
74 self.assertEqual(action, b'noop')
68
75
69 # And we can send another command.
76 # And we can send another command.
70 request, action, meta = reactor.callcommand(b'command2', {})
77 request, action, meta = reactor.callcommand(b'command2', {})
71 self.assertEqual(request.requestid, 3)
78 self.assertEqual(request.requestid, 3)
72 self.assertEqual(action, b'sendframes')
79 self.assertEqual(action, b'sendframes')
73
80
74 for frame in meta[b'framegen']:
81 for frame in meta[b'framegen']:
75 self.assertEqual(request.state, b'sending')
82 self.assertEqual(request.state, b'sending')
76
83
77 self.assertEqual(request.state, b'sent')
84 self.assertEqual(request.state, b'sent')
78
85
79 class BadFrameRecvTests(unittest.TestCase):
86 class BadFrameRecvTests(unittest.TestCase):
87 if not getattr(unittest.TestCase, 'assertRaisesRegex', False):
88 # Python 3.7 deprecates the regex*p* version, but 2.7 lacks
89 # the regex version.
90 assertRaisesRegex = (# camelcase-required
91 unittest.TestCase.assertRaisesRegexp)
92
80 def testoddstream(self):
93 def testoddstream(self):
81 reactor = framing.clientreactor()
94 reactor = framing.clientreactor()
82
95
83 action, meta = sendframe(reactor, ffs(b'1 1 0 1 0 foo'))
96 action, meta = sendframe(reactor, ffs(b'1 1 0 1 0 foo'))
84 self.assertEqual(action, b'error')
97 self.assertEqual(action, b'error')
85 self.assertEqual(meta[b'message'],
98 self.assertEqual(meta[b'message'],
86 b'received frame with odd numbered stream ID: 1')
99 b'received frame with odd numbered stream ID: 1')
87
100
88 def testunknownstream(self):
101 def testunknownstream(self):
89 reactor = framing.clientreactor()
102 reactor = framing.clientreactor()
90
103
91 action, meta = sendframe(reactor, ffs(b'1 0 0 1 0 foo'))
104 action, meta = sendframe(reactor, ffs(b'1 0 0 1 0 foo'))
92 self.assertEqual(action, b'error')
105 self.assertEqual(action, b'error')
93 self.assertEqual(meta[b'message'],
106 self.assertEqual(meta[b'message'],
94 b'received frame on unknown stream without beginning '
107 b'received frame on unknown stream without beginning '
95 b'of stream flag set')
108 b'of stream flag set')
96
109
97 def testunhandledframetype(self):
110 def testunhandledframetype(self):
98 reactor = framing.clientreactor(buffersends=False)
111 reactor = framing.clientreactor(buffersends=False)
99
112
100 request, action, meta = reactor.callcommand(b'foo', {})
113 request, action, meta = reactor.callcommand(b'foo', {})
101 for frame in meta[b'framegen']:
114 for frame in meta[b'framegen']:
102 pass
115 pass
103
116
104 with self.assertRaisesRegexp(error.ProgrammingError,
117 with self.assertRaisesRegex(error.ProgrammingError,
105 'unhandled frame type'):
118 'unhandled frame type'):
106 sendframe(reactor, ffs(b'1 0 stream-begin text-output 0 foo'))
119 sendframe(reactor, ffs(b'1 0 stream-begin text-output 0 foo'))
107
120
108 class StreamTests(unittest.TestCase):
121 class StreamTests(unittest.TestCase):
109 def testmultipleresponseframes(self):
122 def testmultipleresponseframes(self):
110 reactor = framing.clientreactor(buffersends=False)
123 reactor = framing.clientreactor(buffersends=False)
111
124
112 request, action, meta = reactor.callcommand(b'foo', {})
125 request, action, meta = reactor.callcommand(b'foo', {})
113
126
114 self.assertEqual(action, b'sendframes')
127 self.assertEqual(action, b'sendframes')
115 for f in meta[b'framegen']:
128 for f in meta[b'framegen']:
116 pass
129 pass
117
130
118 action, meta = sendframe(
131 action, meta = sendframe(
119 reactor,
132 reactor,
120 ffs(b'%d 0 stream-begin 4 0 foo' % request.requestid))
133 ffs(b'%d 0 stream-begin 4 0 foo' % request.requestid))
121 self.assertEqual(action, b'responsedata')
134 self.assertEqual(action, b'responsedata')
122
135
123 action, meta = sendframe(
136 action, meta = sendframe(
124 reactor,
137 reactor,
125 ffs(b'%d 0 0 4 eos bar' % request.requestid))
138 ffs(b'%d 0 0 4 eos bar' % request.requestid))
126 self.assertEqual(action, b'responsedata')
139 self.assertEqual(action, b'responsedata')
127
140
128 if __name__ == '__main__':
141 if __name__ == '__main__':
129 import silenttestrunner
142 import silenttestrunner
130 silenttestrunner.main(__name__)
143 silenttestrunner.main(__name__)
@@ -1,191 +1,197 b''
1 from __future__ import absolute_import, print_function
1 from __future__ import absolute_import, print_function
2
2
3 import unittest
3 import unittest
4
4
5 from mercurial import (
5 from mercurial import (
6 util,
6 util,
7 wireprotoframing as framing,
7 wireprotoframing as framing,
8 )
8 )
9
9
10 ffs = framing.makeframefromhumanstring
10 ffs = framing.makeframefromhumanstring
11
11
12 class FrameHumanStringTests(unittest.TestCase):
12 class FrameHumanStringTests(unittest.TestCase):
13 def testbasic(self):
13 def testbasic(self):
14 self.assertEqual(ffs(b'1 1 0 1 0 '),
14 self.assertEqual(ffs(b'1 1 0 1 0 '),
15 b'\x00\x00\x00\x01\x00\x01\x00\x10')
15 b'\x00\x00\x00\x01\x00\x01\x00\x10')
16
16
17 self.assertEqual(ffs(b'2 4 0 1 0 '),
17 self.assertEqual(ffs(b'2 4 0 1 0 '),
18 b'\x00\x00\x00\x02\x00\x04\x00\x10')
18 b'\x00\x00\x00\x02\x00\x04\x00\x10')
19
19
20 self.assertEqual(ffs(b'2 4 0 1 0 foo'),
20 self.assertEqual(ffs(b'2 4 0 1 0 foo'),
21 b'\x03\x00\x00\x02\x00\x04\x00\x10foo')
21 b'\x03\x00\x00\x02\x00\x04\x00\x10foo')
22
22
23 def testcborint(self):
23 def testcborint(self):
24 self.assertEqual(ffs(b'1 1 0 1 0 cbor:15'),
24 self.assertEqual(ffs(b'1 1 0 1 0 cbor:15'),
25 b'\x01\x00\x00\x01\x00\x01\x00\x10\x0f')
25 b'\x01\x00\x00\x01\x00\x01\x00\x10\x0f')
26
26
27 self.assertEqual(ffs(b'1 1 0 1 0 cbor:42'),
27 self.assertEqual(ffs(b'1 1 0 1 0 cbor:42'),
28 b'\x02\x00\x00\x01\x00\x01\x00\x10\x18*')
28 b'\x02\x00\x00\x01\x00\x01\x00\x10\x18*')
29
29
30 self.assertEqual(ffs(b'1 1 0 1 0 cbor:1048576'),
30 self.assertEqual(ffs(b'1 1 0 1 0 cbor:1048576'),
31 b'\x05\x00\x00\x01\x00\x01\x00\x10\x1a'
31 b'\x05\x00\x00\x01\x00\x01\x00\x10\x1a'
32 b'\x00\x10\x00\x00')
32 b'\x00\x10\x00\x00')
33
33
34 self.assertEqual(ffs(b'1 1 0 1 0 cbor:0'),
34 self.assertEqual(ffs(b'1 1 0 1 0 cbor:0'),
35 b'\x01\x00\x00\x01\x00\x01\x00\x10\x00')
35 b'\x01\x00\x00\x01\x00\x01\x00\x10\x00')
36
36
37 self.assertEqual(ffs(b'1 1 0 1 0 cbor:-1'),
37 self.assertEqual(ffs(b'1 1 0 1 0 cbor:-1'),
38 b'\x01\x00\x00\x01\x00\x01\x00\x10 ')
38 b'\x01\x00\x00\x01\x00\x01\x00\x10 ')
39
39
40 self.assertEqual(ffs(b'1 1 0 1 0 cbor:-342542'),
40 self.assertEqual(ffs(b'1 1 0 1 0 cbor:-342542'),
41 b'\x05\x00\x00\x01\x00\x01\x00\x10:\x00\x05:\r')
41 b'\x05\x00\x00\x01\x00\x01\x00\x10:\x00\x05:\r')
42
42
43 def testcborstrings(self):
43 def testcborstrings(self):
44 self.assertEqual(ffs(b"1 1 0 1 0 cbor:b'foo'"),
44 self.assertEqual(ffs(b"1 1 0 1 0 cbor:b'foo'"),
45 b'\x04\x00\x00\x01\x00\x01\x00\x10Cfoo')
45 b'\x04\x00\x00\x01\x00\x01\x00\x10Cfoo')
46
46
47 self.assertEqual(ffs(b"1 1 0 1 0 cbor:u'foo'"),
47 self.assertEqual(ffs(b"1 1 0 1 0 cbor:u'foo'"),
48 b'\x04\x00\x00\x01\x00\x01\x00\x10cfoo')
48 b'\x04\x00\x00\x01\x00\x01\x00\x10cfoo')
49
49
50 def testcborlists(self):
50 def testcborlists(self):
51 self.assertEqual(ffs(b"1 1 0 1 0 cbor:[None, True, False, 42, b'foo']"),
51 self.assertEqual(ffs(b"1 1 0 1 0 cbor:[None, True, False, 42, b'foo']"),
52 b'\n\x00\x00\x01\x00\x01\x00\x10\x85\xf6\xf5\xf4'
52 b'\n\x00\x00\x01\x00\x01\x00\x10\x85\xf6\xf5\xf4'
53 b'\x18*Cfoo')
53 b'\x18*Cfoo')
54
54
55 def testcbordicts(self):
55 def testcbordicts(self):
56 self.assertEqual(ffs(b"1 1 0 1 0 "
56 self.assertEqual(ffs(b"1 1 0 1 0 "
57 b"cbor:{b'foo': b'val1', b'bar': b'val2'}"),
57 b"cbor:{b'foo': b'val1', b'bar': b'val2'}"),
58 b'\x13\x00\x00\x01\x00\x01\x00\x10\xa2'
58 b'\x13\x00\x00\x01\x00\x01\x00\x10\xa2'
59 b'CbarDval2CfooDval1')
59 b'CbarDval2CfooDval1')
60
60
61 class FrameTests(unittest.TestCase):
61 class FrameTests(unittest.TestCase):
62 def testdataexactframesize(self):
62 def testdataexactframesize(self):
63 data = util.bytesio(b'x' * framing.DEFAULT_MAX_FRAME_SIZE)
63 data = util.bytesio(b'x' * framing.DEFAULT_MAX_FRAME_SIZE)
64
64
65 stream = framing.stream(1)
65 stream = framing.stream(1)
66 frames = list(framing.createcommandframes(stream, 1, b'command',
66 frames = list(framing.createcommandframes(stream, 1, b'command',
67 {}, data))
67 {}, data))
68 self.assertEqual(frames, [
68 self.assertEqual(frames, [
69 ffs(b'1 1 stream-begin command-request new|have-data '
69 ffs(b'1 1 stream-begin command-request new|have-data '
70 b"cbor:{b'name': b'command'}"),
70 b"cbor:{b'name': b'command'}"),
71 ffs(b'1 1 0 command-data continuation %s' % data.getvalue()),
71 ffs(b'1 1 0 command-data continuation %s' % data.getvalue()),
72 ffs(b'1 1 0 command-data eos ')
72 ffs(b'1 1 0 command-data eos ')
73 ])
73 ])
74
74
75 def testdatamultipleframes(self):
75 def testdatamultipleframes(self):
76 data = util.bytesio(b'x' * (framing.DEFAULT_MAX_FRAME_SIZE + 1))
76 data = util.bytesio(b'x' * (framing.DEFAULT_MAX_FRAME_SIZE + 1))
77
77
78 stream = framing.stream(1)
78 stream = framing.stream(1)
79 frames = list(framing.createcommandframes(stream, 1, b'command', {},
79 frames = list(framing.createcommandframes(stream, 1, b'command', {},
80 data))
80 data))
81 self.assertEqual(frames, [
81 self.assertEqual(frames, [
82 ffs(b'1 1 stream-begin command-request new|have-data '
82 ffs(b'1 1 stream-begin command-request new|have-data '
83 b"cbor:{b'name': b'command'}"),
83 b"cbor:{b'name': b'command'}"),
84 ffs(b'1 1 0 command-data continuation %s' % (
84 ffs(b'1 1 0 command-data continuation %s' % (
85 b'x' * framing.DEFAULT_MAX_FRAME_SIZE)),
85 b'x' * framing.DEFAULT_MAX_FRAME_SIZE)),
86 ffs(b'1 1 0 command-data eos x'),
86 ffs(b'1 1 0 command-data eos x'),
87 ])
87 ])
88
88
89 def testargsanddata(self):
89 def testargsanddata(self):
90 data = util.bytesio(b'x' * 100)
90 data = util.bytesio(b'x' * 100)
91
91
92 stream = framing.stream(1)
92 stream = framing.stream(1)
93 frames = list(framing.createcommandframes(stream, 1, b'command', {
93 frames = list(framing.createcommandframes(stream, 1, b'command', {
94 b'key1': b'key1value',
94 b'key1': b'key1value',
95 b'key2': b'key2value',
95 b'key2': b'key2value',
96 b'key3': b'key3value',
96 b'key3': b'key3value',
97 }, data))
97 }, data))
98
98
99 self.assertEqual(frames, [
99 self.assertEqual(frames, [
100 ffs(b'1 1 stream-begin command-request new|have-data '
100 ffs(b'1 1 stream-begin command-request new|have-data '
101 b"cbor:{b'name': b'command', b'args': {b'key1': b'key1value', "
101 b"cbor:{b'name': b'command', b'args': {b'key1': b'key1value', "
102 b"b'key2': b'key2value', b'key3': b'key3value'}}"),
102 b"b'key2': b'key2value', b'key3': b'key3value'}}"),
103 ffs(b'1 1 0 command-data eos %s' % data.getvalue()),
103 ffs(b'1 1 0 command-data eos %s' % data.getvalue()),
104 ])
104 ])
105
105
106 if not getattr(unittest.TestCase, 'assertRaisesRegex', False):
107 # Python 3.7 deprecates the regex*p* version, but 2.7 lacks
108 # the regex version.
109 assertRaisesRegex = (# camelcase-required
110 unittest.TestCase.assertRaisesRegexp)
111
106 def testtextoutputformattingstringtype(self):
112 def testtextoutputformattingstringtype(self):
107 """Formatting string must be bytes."""
113 """Formatting string must be bytes."""
108 with self.assertRaisesRegexp(ValueError, 'must use bytes formatting '):
114 with self.assertRaisesRegex(ValueError, 'must use bytes formatting '):
109 list(framing.createtextoutputframe(None, 1, [
115 list(framing.createtextoutputframe(None, 1, [
110 (b'foo'.decode('ascii'), [], [])]))
116 (b'foo'.decode('ascii'), [], [])]))
111
117
112 def testtextoutputargumentbytes(self):
118 def testtextoutputargumentbytes(self):
113 with self.assertRaisesRegexp(ValueError, 'must use bytes for argument'):
119 with self.assertRaisesRegex(ValueError, 'must use bytes for argument'):
114 list(framing.createtextoutputframe(None, 1, [
120 list(framing.createtextoutputframe(None, 1, [
115 (b'foo', [b'foo'.decode('ascii')], [])]))
121 (b'foo', [b'foo'.decode('ascii')], [])]))
116
122
117 def testtextoutputlabelbytes(self):
123 def testtextoutputlabelbytes(self):
118 with self.assertRaisesRegexp(ValueError, 'must use bytes for labels'):
124 with self.assertRaisesRegex(ValueError, 'must use bytes for labels'):
119 list(framing.createtextoutputframe(None, 1, [
125 list(framing.createtextoutputframe(None, 1, [
120 (b'foo', [], [b'foo'.decode('ascii')])]))
126 (b'foo', [], [b'foo'.decode('ascii')])]))
121
127
122 def testtextoutput1simpleatom(self):
128 def testtextoutput1simpleatom(self):
123 stream = framing.stream(1)
129 stream = framing.stream(1)
124 val = list(framing.createtextoutputframe(stream, 1, [
130 val = list(framing.createtextoutputframe(stream, 1, [
125 (b'foo', [], [])]))
131 (b'foo', [], [])]))
126
132
127 self.assertEqual(val, [
133 self.assertEqual(val, [
128 ffs(b'1 1 stream-begin text-output 0 '
134 ffs(b'1 1 stream-begin text-output 0 '
129 b"cbor:[{b'msg': b'foo'}]"),
135 b"cbor:[{b'msg': b'foo'}]"),
130 ])
136 ])
131
137
132 def testtextoutput2simpleatoms(self):
138 def testtextoutput2simpleatoms(self):
133 stream = framing.stream(1)
139 stream = framing.stream(1)
134 val = list(framing.createtextoutputframe(stream, 1, [
140 val = list(framing.createtextoutputframe(stream, 1, [
135 (b'foo', [], []),
141 (b'foo', [], []),
136 (b'bar', [], []),
142 (b'bar', [], []),
137 ]))
143 ]))
138
144
139 self.assertEqual(val, [
145 self.assertEqual(val, [
140 ffs(b'1 1 stream-begin text-output 0 '
146 ffs(b'1 1 stream-begin text-output 0 '
141 b"cbor:[{b'msg': b'foo'}, {b'msg': b'bar'}]")
147 b"cbor:[{b'msg': b'foo'}, {b'msg': b'bar'}]")
142 ])
148 ])
143
149
144 def testtextoutput1arg(self):
150 def testtextoutput1arg(self):
145 stream = framing.stream(1)
151 stream = framing.stream(1)
146 val = list(framing.createtextoutputframe(stream, 1, [
152 val = list(framing.createtextoutputframe(stream, 1, [
147 (b'foo %s', [b'val1'], []),
153 (b'foo %s', [b'val1'], []),
148 ]))
154 ]))
149
155
150 self.assertEqual(val, [
156 self.assertEqual(val, [
151 ffs(b'1 1 stream-begin text-output 0 '
157 ffs(b'1 1 stream-begin text-output 0 '
152 b"cbor:[{b'msg': b'foo %s', b'args': [b'val1']}]")
158 b"cbor:[{b'msg': b'foo %s', b'args': [b'val1']}]")
153 ])
159 ])
154
160
155 def testtextoutput2arg(self):
161 def testtextoutput2arg(self):
156 stream = framing.stream(1)
162 stream = framing.stream(1)
157 val = list(framing.createtextoutputframe(stream, 1, [
163 val = list(framing.createtextoutputframe(stream, 1, [
158 (b'foo %s %s', [b'val', b'value'], []),
164 (b'foo %s %s', [b'val', b'value'], []),
159 ]))
165 ]))
160
166
161 self.assertEqual(val, [
167 self.assertEqual(val, [
162 ffs(b'1 1 stream-begin text-output 0 '
168 ffs(b'1 1 stream-begin text-output 0 '
163 b"cbor:[{b'msg': b'foo %s %s', b'args': [b'val', b'value']}]")
169 b"cbor:[{b'msg': b'foo %s %s', b'args': [b'val', b'value']}]")
164 ])
170 ])
165
171
166 def testtextoutput1label(self):
172 def testtextoutput1label(self):
167 stream = framing.stream(1)
173 stream = framing.stream(1)
168 val = list(framing.createtextoutputframe(stream, 1, [
174 val = list(framing.createtextoutputframe(stream, 1, [
169 (b'foo', [], [b'label']),
175 (b'foo', [], [b'label']),
170 ]))
176 ]))
171
177
172 self.assertEqual(val, [
178 self.assertEqual(val, [
173 ffs(b'1 1 stream-begin text-output 0 '
179 ffs(b'1 1 stream-begin text-output 0 '
174 b"cbor:[{b'msg': b'foo', b'labels': [b'label']}]")
180 b"cbor:[{b'msg': b'foo', b'labels': [b'label']}]")
175 ])
181 ])
176
182
177 def testargandlabel(self):
183 def testargandlabel(self):
178 stream = framing.stream(1)
184 stream = framing.stream(1)
179 val = list(framing.createtextoutputframe(stream, 1, [
185 val = list(framing.createtextoutputframe(stream, 1, [
180 (b'foo %s', [b'arg'], [b'label']),
186 (b'foo %s', [b'arg'], [b'label']),
181 ]))
187 ]))
182
188
183 self.assertEqual(val, [
189 self.assertEqual(val, [
184 ffs(b'1 1 stream-begin text-output 0 '
190 ffs(b'1 1 stream-begin text-output 0 '
185 b"cbor:[{b'msg': b'foo %s', b'args': [b'arg'], "
191 b"cbor:[{b'msg': b'foo %s', b'args': [b'arg'], "
186 b"b'labels': [b'label']}]")
192 b"b'labels': [b'label']}]")
187 ])
193 ])
188
194
189 if __name__ == '__main__':
195 if __name__ == '__main__':
190 import silenttestrunner
196 import silenttestrunner
191 silenttestrunner.main(__name__)
197 silenttestrunner.main(__name__)
@@ -1,416 +1,422 b''
1 from __future__ import absolute_import, print_function
1 from __future__ import absolute_import, print_function
2
2
3 import unittest
3 import unittest
4
4
5 from mercurial.hgweb import (
5 from mercurial.hgweb import (
6 request as requestmod,
6 request as requestmod,
7 )
7 )
8 from mercurial import (
8 from mercurial import (
9 error,
9 error,
10 )
10 )
11
11
12 DEFAULT_ENV = {
12 DEFAULT_ENV = {
13 r'REQUEST_METHOD': r'GET',
13 r'REQUEST_METHOD': r'GET',
14 r'SERVER_NAME': r'testserver',
14 r'SERVER_NAME': r'testserver',
15 r'SERVER_PORT': r'80',
15 r'SERVER_PORT': r'80',
16 r'SERVER_PROTOCOL': r'http',
16 r'SERVER_PROTOCOL': r'http',
17 r'wsgi.version': (1, 0),
17 r'wsgi.version': (1, 0),
18 r'wsgi.url_scheme': r'http',
18 r'wsgi.url_scheme': r'http',
19 r'wsgi.input': None,
19 r'wsgi.input': None,
20 r'wsgi.errors': None,
20 r'wsgi.errors': None,
21 r'wsgi.multithread': False,
21 r'wsgi.multithread': False,
22 r'wsgi.multiprocess': True,
22 r'wsgi.multiprocess': True,
23 r'wsgi.run_once': False,
23 r'wsgi.run_once': False,
24 }
24 }
25
25
26 def parse(env, reponame=None, altbaseurl=None, extra=None):
26 def parse(env, reponame=None, altbaseurl=None, extra=None):
27 env = dict(env)
27 env = dict(env)
28 env.update(extra or {})
28 env.update(extra or {})
29
29
30 return requestmod.parserequestfromenv(env, reponame=reponame,
30 return requestmod.parserequestfromenv(env, reponame=reponame,
31 altbaseurl=altbaseurl)
31 altbaseurl=altbaseurl)
32
32
33 class ParseRequestTests(unittest.TestCase):
33 class ParseRequestTests(unittest.TestCase):
34 def testdefault(self):
34 def testdefault(self):
35 r = parse(DEFAULT_ENV)
35 r = parse(DEFAULT_ENV)
36 self.assertEqual(r.url, b'http://testserver')
36 self.assertEqual(r.url, b'http://testserver')
37 self.assertEqual(r.baseurl, b'http://testserver')
37 self.assertEqual(r.baseurl, b'http://testserver')
38 self.assertEqual(r.advertisedurl, b'http://testserver')
38 self.assertEqual(r.advertisedurl, b'http://testserver')
39 self.assertEqual(r.advertisedbaseurl, b'http://testserver')
39 self.assertEqual(r.advertisedbaseurl, b'http://testserver')
40 self.assertEqual(r.urlscheme, b'http')
40 self.assertEqual(r.urlscheme, b'http')
41 self.assertEqual(r.method, b'GET')
41 self.assertEqual(r.method, b'GET')
42 self.assertIsNone(r.remoteuser)
42 self.assertIsNone(r.remoteuser)
43 self.assertIsNone(r.remotehost)
43 self.assertIsNone(r.remotehost)
44 self.assertEqual(r.apppath, b'')
44 self.assertEqual(r.apppath, b'')
45 self.assertEqual(r.dispatchparts, [])
45 self.assertEqual(r.dispatchparts, [])
46 self.assertIsNone(r.dispatchpath)
46 self.assertIsNone(r.dispatchpath)
47 self.assertIsNone(r.reponame)
47 self.assertIsNone(r.reponame)
48 self.assertEqual(r.querystring, b'')
48 self.assertEqual(r.querystring, b'')
49 self.assertEqual(len(r.qsparams), 0)
49 self.assertEqual(len(r.qsparams), 0)
50 self.assertEqual(len(r.headers), 0)
50 self.assertEqual(len(r.headers), 0)
51
51
52 def testcustomport(self):
52 def testcustomport(self):
53 r = parse(DEFAULT_ENV, extra={
53 r = parse(DEFAULT_ENV, extra={
54 r'SERVER_PORT': r'8000',
54 r'SERVER_PORT': r'8000',
55 })
55 })
56
56
57 self.assertEqual(r.url, b'http://testserver:8000')
57 self.assertEqual(r.url, b'http://testserver:8000')
58 self.assertEqual(r.baseurl, b'http://testserver:8000')
58 self.assertEqual(r.baseurl, b'http://testserver:8000')
59 self.assertEqual(r.advertisedurl, b'http://testserver:8000')
59 self.assertEqual(r.advertisedurl, b'http://testserver:8000')
60 self.assertEqual(r.advertisedbaseurl, b'http://testserver:8000')
60 self.assertEqual(r.advertisedbaseurl, b'http://testserver:8000')
61
61
62 r = parse(DEFAULT_ENV, extra={
62 r = parse(DEFAULT_ENV, extra={
63 r'SERVER_PORT': r'4000',
63 r'SERVER_PORT': r'4000',
64 r'wsgi.url_scheme': r'https',
64 r'wsgi.url_scheme': r'https',
65 })
65 })
66
66
67 self.assertEqual(r.url, b'https://testserver:4000')
67 self.assertEqual(r.url, b'https://testserver:4000')
68 self.assertEqual(r.baseurl, b'https://testserver:4000')
68 self.assertEqual(r.baseurl, b'https://testserver:4000')
69 self.assertEqual(r.advertisedurl, b'https://testserver:4000')
69 self.assertEqual(r.advertisedurl, b'https://testserver:4000')
70 self.assertEqual(r.advertisedbaseurl, b'https://testserver:4000')
70 self.assertEqual(r.advertisedbaseurl, b'https://testserver:4000')
71
71
72 def testhttphost(self):
72 def testhttphost(self):
73 r = parse(DEFAULT_ENV, extra={
73 r = parse(DEFAULT_ENV, extra={
74 r'HTTP_HOST': r'altserver',
74 r'HTTP_HOST': r'altserver',
75 })
75 })
76
76
77 self.assertEqual(r.url, b'http://altserver')
77 self.assertEqual(r.url, b'http://altserver')
78 self.assertEqual(r.baseurl, b'http://altserver')
78 self.assertEqual(r.baseurl, b'http://altserver')
79 self.assertEqual(r.advertisedurl, b'http://testserver')
79 self.assertEqual(r.advertisedurl, b'http://testserver')
80 self.assertEqual(r.advertisedbaseurl, b'http://testserver')
80 self.assertEqual(r.advertisedbaseurl, b'http://testserver')
81
81
82 def testscriptname(self):
82 def testscriptname(self):
83 r = parse(DEFAULT_ENV, extra={
83 r = parse(DEFAULT_ENV, extra={
84 r'SCRIPT_NAME': r'',
84 r'SCRIPT_NAME': r'',
85 })
85 })
86
86
87 self.assertEqual(r.url, b'http://testserver')
87 self.assertEqual(r.url, b'http://testserver')
88 self.assertEqual(r.baseurl, b'http://testserver')
88 self.assertEqual(r.baseurl, b'http://testserver')
89 self.assertEqual(r.advertisedurl, b'http://testserver')
89 self.assertEqual(r.advertisedurl, b'http://testserver')
90 self.assertEqual(r.advertisedbaseurl, b'http://testserver')
90 self.assertEqual(r.advertisedbaseurl, b'http://testserver')
91 self.assertEqual(r.apppath, b'')
91 self.assertEqual(r.apppath, b'')
92 self.assertEqual(r.dispatchparts, [])
92 self.assertEqual(r.dispatchparts, [])
93 self.assertIsNone(r.dispatchpath)
93 self.assertIsNone(r.dispatchpath)
94
94
95 r = parse(DEFAULT_ENV, extra={
95 r = parse(DEFAULT_ENV, extra={
96 r'SCRIPT_NAME': r'/script',
96 r'SCRIPT_NAME': r'/script',
97 })
97 })
98
98
99 self.assertEqual(r.url, b'http://testserver/script')
99 self.assertEqual(r.url, b'http://testserver/script')
100 self.assertEqual(r.baseurl, b'http://testserver')
100 self.assertEqual(r.baseurl, b'http://testserver')
101 self.assertEqual(r.advertisedurl, b'http://testserver/script')
101 self.assertEqual(r.advertisedurl, b'http://testserver/script')
102 self.assertEqual(r.advertisedbaseurl, b'http://testserver')
102 self.assertEqual(r.advertisedbaseurl, b'http://testserver')
103 self.assertEqual(r.apppath, b'/script')
103 self.assertEqual(r.apppath, b'/script')
104 self.assertEqual(r.dispatchparts, [])
104 self.assertEqual(r.dispatchparts, [])
105 self.assertIsNone(r.dispatchpath)
105 self.assertIsNone(r.dispatchpath)
106
106
107 r = parse(DEFAULT_ENV, extra={
107 r = parse(DEFAULT_ENV, extra={
108 r'SCRIPT_NAME': r'/multiple words',
108 r'SCRIPT_NAME': r'/multiple words',
109 })
109 })
110
110
111 self.assertEqual(r.url, b'http://testserver/multiple%20words')
111 self.assertEqual(r.url, b'http://testserver/multiple%20words')
112 self.assertEqual(r.baseurl, b'http://testserver')
112 self.assertEqual(r.baseurl, b'http://testserver')
113 self.assertEqual(r.advertisedurl, b'http://testserver/multiple%20words')
113 self.assertEqual(r.advertisedurl, b'http://testserver/multiple%20words')
114 self.assertEqual(r.advertisedbaseurl, b'http://testserver')
114 self.assertEqual(r.advertisedbaseurl, b'http://testserver')
115 self.assertEqual(r.apppath, b'/multiple words')
115 self.assertEqual(r.apppath, b'/multiple words')
116 self.assertEqual(r.dispatchparts, [])
116 self.assertEqual(r.dispatchparts, [])
117 self.assertIsNone(r.dispatchpath)
117 self.assertIsNone(r.dispatchpath)
118
118
119 def testpathinfo(self):
119 def testpathinfo(self):
120 r = parse(DEFAULT_ENV, extra={
120 r = parse(DEFAULT_ENV, extra={
121 r'PATH_INFO': r'',
121 r'PATH_INFO': r'',
122 })
122 })
123
123
124 self.assertEqual(r.url, b'http://testserver')
124 self.assertEqual(r.url, b'http://testserver')
125 self.assertEqual(r.baseurl, b'http://testserver')
125 self.assertEqual(r.baseurl, b'http://testserver')
126 self.assertEqual(r.advertisedurl, b'http://testserver')
126 self.assertEqual(r.advertisedurl, b'http://testserver')
127 self.assertEqual(r.advertisedbaseurl, b'http://testserver')
127 self.assertEqual(r.advertisedbaseurl, b'http://testserver')
128 self.assertEqual(r.apppath, b'')
128 self.assertEqual(r.apppath, b'')
129 self.assertEqual(r.dispatchparts, [])
129 self.assertEqual(r.dispatchparts, [])
130 self.assertEqual(r.dispatchpath, b'')
130 self.assertEqual(r.dispatchpath, b'')
131
131
132 r = parse(DEFAULT_ENV, extra={
132 r = parse(DEFAULT_ENV, extra={
133 r'PATH_INFO': r'/pathinfo',
133 r'PATH_INFO': r'/pathinfo',
134 })
134 })
135
135
136 self.assertEqual(r.url, b'http://testserver/pathinfo')
136 self.assertEqual(r.url, b'http://testserver/pathinfo')
137 self.assertEqual(r.baseurl, b'http://testserver')
137 self.assertEqual(r.baseurl, b'http://testserver')
138 self.assertEqual(r.advertisedurl, b'http://testserver/pathinfo')
138 self.assertEqual(r.advertisedurl, b'http://testserver/pathinfo')
139 self.assertEqual(r.advertisedbaseurl, b'http://testserver')
139 self.assertEqual(r.advertisedbaseurl, b'http://testserver')
140 self.assertEqual(r.apppath, b'')
140 self.assertEqual(r.apppath, b'')
141 self.assertEqual(r.dispatchparts, [b'pathinfo'])
141 self.assertEqual(r.dispatchparts, [b'pathinfo'])
142 self.assertEqual(r.dispatchpath, b'pathinfo')
142 self.assertEqual(r.dispatchpath, b'pathinfo')
143
143
144 r = parse(DEFAULT_ENV, extra={
144 r = parse(DEFAULT_ENV, extra={
145 r'PATH_INFO': r'/one/two/',
145 r'PATH_INFO': r'/one/two/',
146 })
146 })
147
147
148 self.assertEqual(r.url, b'http://testserver/one/two/')
148 self.assertEqual(r.url, b'http://testserver/one/two/')
149 self.assertEqual(r.baseurl, b'http://testserver')
149 self.assertEqual(r.baseurl, b'http://testserver')
150 self.assertEqual(r.advertisedurl, b'http://testserver/one/two/')
150 self.assertEqual(r.advertisedurl, b'http://testserver/one/two/')
151 self.assertEqual(r.advertisedbaseurl, b'http://testserver')
151 self.assertEqual(r.advertisedbaseurl, b'http://testserver')
152 self.assertEqual(r.apppath, b'')
152 self.assertEqual(r.apppath, b'')
153 self.assertEqual(r.dispatchparts, [b'one', b'two'])
153 self.assertEqual(r.dispatchparts, [b'one', b'two'])
154 self.assertEqual(r.dispatchpath, b'one/two')
154 self.assertEqual(r.dispatchpath, b'one/two')
155
155
156 def testscriptandpathinfo(self):
156 def testscriptandpathinfo(self):
157 r = parse(DEFAULT_ENV, extra={
157 r = parse(DEFAULT_ENV, extra={
158 r'SCRIPT_NAME': r'/script',
158 r'SCRIPT_NAME': r'/script',
159 r'PATH_INFO': r'/pathinfo',
159 r'PATH_INFO': r'/pathinfo',
160 })
160 })
161
161
162 self.assertEqual(r.url, b'http://testserver/script/pathinfo')
162 self.assertEqual(r.url, b'http://testserver/script/pathinfo')
163 self.assertEqual(r.baseurl, b'http://testserver')
163 self.assertEqual(r.baseurl, b'http://testserver')
164 self.assertEqual(r.advertisedurl, b'http://testserver/script/pathinfo')
164 self.assertEqual(r.advertisedurl, b'http://testserver/script/pathinfo')
165 self.assertEqual(r.advertisedbaseurl, b'http://testserver')
165 self.assertEqual(r.advertisedbaseurl, b'http://testserver')
166 self.assertEqual(r.apppath, b'/script')
166 self.assertEqual(r.apppath, b'/script')
167 self.assertEqual(r.dispatchparts, [b'pathinfo'])
167 self.assertEqual(r.dispatchparts, [b'pathinfo'])
168 self.assertEqual(r.dispatchpath, b'pathinfo')
168 self.assertEqual(r.dispatchpath, b'pathinfo')
169
169
170 r = parse(DEFAULT_ENV, extra={
170 r = parse(DEFAULT_ENV, extra={
171 r'SCRIPT_NAME': r'/script1/script2',
171 r'SCRIPT_NAME': r'/script1/script2',
172 r'PATH_INFO': r'/path1/path2',
172 r'PATH_INFO': r'/path1/path2',
173 })
173 })
174
174
175 self.assertEqual(r.url,
175 self.assertEqual(r.url,
176 b'http://testserver/script1/script2/path1/path2')
176 b'http://testserver/script1/script2/path1/path2')
177 self.assertEqual(r.baseurl, b'http://testserver')
177 self.assertEqual(r.baseurl, b'http://testserver')
178 self.assertEqual(r.advertisedurl,
178 self.assertEqual(r.advertisedurl,
179 b'http://testserver/script1/script2/path1/path2')
179 b'http://testserver/script1/script2/path1/path2')
180 self.assertEqual(r.advertisedbaseurl, b'http://testserver')
180 self.assertEqual(r.advertisedbaseurl, b'http://testserver')
181 self.assertEqual(r.apppath, b'/script1/script2')
181 self.assertEqual(r.apppath, b'/script1/script2')
182 self.assertEqual(r.dispatchparts, [b'path1', b'path2'])
182 self.assertEqual(r.dispatchparts, [b'path1', b'path2'])
183 self.assertEqual(r.dispatchpath, b'path1/path2')
183 self.assertEqual(r.dispatchpath, b'path1/path2')
184
184
185 r = parse(DEFAULT_ENV, extra={
185 r = parse(DEFAULT_ENV, extra={
186 r'HTTP_HOST': r'hostserver',
186 r'HTTP_HOST': r'hostserver',
187 r'SCRIPT_NAME': r'/script',
187 r'SCRIPT_NAME': r'/script',
188 r'PATH_INFO': r'/pathinfo',
188 r'PATH_INFO': r'/pathinfo',
189 })
189 })
190
190
191 self.assertEqual(r.url, b'http://hostserver/script/pathinfo')
191 self.assertEqual(r.url, b'http://hostserver/script/pathinfo')
192 self.assertEqual(r.baseurl, b'http://hostserver')
192 self.assertEqual(r.baseurl, b'http://hostserver')
193 self.assertEqual(r.advertisedurl, b'http://testserver/script/pathinfo')
193 self.assertEqual(r.advertisedurl, b'http://testserver/script/pathinfo')
194 self.assertEqual(r.advertisedbaseurl, b'http://testserver')
194 self.assertEqual(r.advertisedbaseurl, b'http://testserver')
195 self.assertEqual(r.apppath, b'/script')
195 self.assertEqual(r.apppath, b'/script')
196 self.assertEqual(r.dispatchparts, [b'pathinfo'])
196 self.assertEqual(r.dispatchparts, [b'pathinfo'])
197 self.assertEqual(r.dispatchpath, b'pathinfo')
197 self.assertEqual(r.dispatchpath, b'pathinfo')
198
198
199 if not getattr(unittest.TestCase, 'assertRaisesRegex', False):
200 # Python 3.7 deprecates the regex*p* version, but 2.7 lacks
201 # the regex version.
202 assertRaisesRegex = (# camelcase-required
203 unittest.TestCase.assertRaisesRegexp)
204
199 def testreponame(self):
205 def testreponame(self):
200 """repository path components get stripped from URL."""
206 """repository path components get stripped from URL."""
201
207
202 with self.assertRaisesRegexp(error.ProgrammingError,
208 with self.assertRaisesRegex(error.ProgrammingError,
203 b'reponame requires PATH_INFO'):
209 b'reponame requires PATH_INFO'):
204 parse(DEFAULT_ENV, reponame=b'repo')
210 parse(DEFAULT_ENV, reponame=b'repo')
205
211
206 with self.assertRaisesRegexp(error.ProgrammingError,
212 with self.assertRaisesRegex(error.ProgrammingError,
207 b'PATH_INFO does not begin with repo '
213 b'PATH_INFO does not begin with repo '
208 b'name'):
214 b'name'):
209 parse(DEFAULT_ENV, reponame=b'repo', extra={
215 parse(DEFAULT_ENV, reponame=b'repo', extra={
210 r'PATH_INFO': r'/pathinfo',
216 r'PATH_INFO': r'/pathinfo',
211 })
217 })
212
218
213 with self.assertRaisesRegexp(error.ProgrammingError,
219 with self.assertRaisesRegex(error.ProgrammingError,
214 b'reponame prefix of PATH_INFO'):
220 b'reponame prefix of PATH_INFO'):
215 parse(DEFAULT_ENV, reponame=b'repo', extra={
221 parse(DEFAULT_ENV, reponame=b'repo', extra={
216 r'PATH_INFO': r'/repoextra/path',
222 r'PATH_INFO': r'/repoextra/path',
217 })
223 })
218
224
219 r = parse(DEFAULT_ENV, reponame=b'repo', extra={
225 r = parse(DEFAULT_ENV, reponame=b'repo', extra={
220 r'PATH_INFO': r'/repo/path1/path2',
226 r'PATH_INFO': r'/repo/path1/path2',
221 })
227 })
222
228
223 self.assertEqual(r.url, b'http://testserver/repo/path1/path2')
229 self.assertEqual(r.url, b'http://testserver/repo/path1/path2')
224 self.assertEqual(r.baseurl, b'http://testserver')
230 self.assertEqual(r.baseurl, b'http://testserver')
225 self.assertEqual(r.advertisedurl, b'http://testserver/repo/path1/path2')
231 self.assertEqual(r.advertisedurl, b'http://testserver/repo/path1/path2')
226 self.assertEqual(r.advertisedbaseurl, b'http://testserver')
232 self.assertEqual(r.advertisedbaseurl, b'http://testserver')
227 self.assertEqual(r.apppath, b'/repo')
233 self.assertEqual(r.apppath, b'/repo')
228 self.assertEqual(r.dispatchparts, [b'path1', b'path2'])
234 self.assertEqual(r.dispatchparts, [b'path1', b'path2'])
229 self.assertEqual(r.dispatchpath, b'path1/path2')
235 self.assertEqual(r.dispatchpath, b'path1/path2')
230 self.assertEqual(r.reponame, b'repo')
236 self.assertEqual(r.reponame, b'repo')
231
237
232 r = parse(DEFAULT_ENV, reponame=b'prefix/repo', extra={
238 r = parse(DEFAULT_ENV, reponame=b'prefix/repo', extra={
233 r'PATH_INFO': r'/prefix/repo/path1/path2',
239 r'PATH_INFO': r'/prefix/repo/path1/path2',
234 })
240 })
235
241
236 self.assertEqual(r.url, b'http://testserver/prefix/repo/path1/path2')
242 self.assertEqual(r.url, b'http://testserver/prefix/repo/path1/path2')
237 self.assertEqual(r.baseurl, b'http://testserver')
243 self.assertEqual(r.baseurl, b'http://testserver')
238 self.assertEqual(r.advertisedurl,
244 self.assertEqual(r.advertisedurl,
239 b'http://testserver/prefix/repo/path1/path2')
245 b'http://testserver/prefix/repo/path1/path2')
240 self.assertEqual(r.advertisedbaseurl, b'http://testserver')
246 self.assertEqual(r.advertisedbaseurl, b'http://testserver')
241 self.assertEqual(r.apppath, b'/prefix/repo')
247 self.assertEqual(r.apppath, b'/prefix/repo')
242 self.assertEqual(r.dispatchparts, [b'path1', b'path2'])
248 self.assertEqual(r.dispatchparts, [b'path1', b'path2'])
243 self.assertEqual(r.dispatchpath, b'path1/path2')
249 self.assertEqual(r.dispatchpath, b'path1/path2')
244 self.assertEqual(r.reponame, b'prefix/repo')
250 self.assertEqual(r.reponame, b'prefix/repo')
245
251
246 def testaltbaseurl(self):
252 def testaltbaseurl(self):
247 # Simple hostname remap.
253 # Simple hostname remap.
248 r = parse(DEFAULT_ENV, altbaseurl='http://altserver')
254 r = parse(DEFAULT_ENV, altbaseurl='http://altserver')
249
255
250 self.assertEqual(r.url, b'http://testserver')
256 self.assertEqual(r.url, b'http://testserver')
251 self.assertEqual(r.baseurl, b'http://testserver')
257 self.assertEqual(r.baseurl, b'http://testserver')
252 self.assertEqual(r.advertisedurl, b'http://altserver')
258 self.assertEqual(r.advertisedurl, b'http://altserver')
253 self.assertEqual(r.advertisedbaseurl, b'http://altserver')
259 self.assertEqual(r.advertisedbaseurl, b'http://altserver')
254 self.assertEqual(r.urlscheme, b'http')
260 self.assertEqual(r.urlscheme, b'http')
255 self.assertEqual(r.apppath, b'')
261 self.assertEqual(r.apppath, b'')
256 self.assertEqual(r.dispatchparts, [])
262 self.assertEqual(r.dispatchparts, [])
257 self.assertIsNone(r.dispatchpath)
263 self.assertIsNone(r.dispatchpath)
258 self.assertIsNone(r.reponame)
264 self.assertIsNone(r.reponame)
259
265
260 # With a custom port.
266 # With a custom port.
261 r = parse(DEFAULT_ENV, altbaseurl='http://altserver:8000')
267 r = parse(DEFAULT_ENV, altbaseurl='http://altserver:8000')
262 self.assertEqual(r.url, b'http://testserver')
268 self.assertEqual(r.url, b'http://testserver')
263 self.assertEqual(r.baseurl, b'http://testserver')
269 self.assertEqual(r.baseurl, b'http://testserver')
264 self.assertEqual(r.advertisedurl, b'http://altserver:8000')
270 self.assertEqual(r.advertisedurl, b'http://altserver:8000')
265 self.assertEqual(r.advertisedbaseurl, b'http://altserver:8000')
271 self.assertEqual(r.advertisedbaseurl, b'http://altserver:8000')
266 self.assertEqual(r.urlscheme, b'http')
272 self.assertEqual(r.urlscheme, b'http')
267 self.assertEqual(r.apppath, b'')
273 self.assertEqual(r.apppath, b'')
268 self.assertEqual(r.dispatchparts, [])
274 self.assertEqual(r.dispatchparts, [])
269 self.assertIsNone(r.dispatchpath)
275 self.assertIsNone(r.dispatchpath)
270 self.assertIsNone(r.reponame)
276 self.assertIsNone(r.reponame)
271
277
272 # With a changed protocol.
278 # With a changed protocol.
273 r = parse(DEFAULT_ENV, altbaseurl='https://altserver')
279 r = parse(DEFAULT_ENV, altbaseurl='https://altserver')
274 self.assertEqual(r.url, b'http://testserver')
280 self.assertEqual(r.url, b'http://testserver')
275 self.assertEqual(r.baseurl, b'http://testserver')
281 self.assertEqual(r.baseurl, b'http://testserver')
276 self.assertEqual(r.advertisedurl, b'https://altserver')
282 self.assertEqual(r.advertisedurl, b'https://altserver')
277 self.assertEqual(r.advertisedbaseurl, b'https://altserver')
283 self.assertEqual(r.advertisedbaseurl, b'https://altserver')
278 # URL scheme is defined as the actual scheme, not advertised.
284 # URL scheme is defined as the actual scheme, not advertised.
279 self.assertEqual(r.urlscheme, b'http')
285 self.assertEqual(r.urlscheme, b'http')
280 self.assertEqual(r.apppath, b'')
286 self.assertEqual(r.apppath, b'')
281 self.assertEqual(r.dispatchparts, [])
287 self.assertEqual(r.dispatchparts, [])
282 self.assertIsNone(r.dispatchpath)
288 self.assertIsNone(r.dispatchpath)
283 self.assertIsNone(r.reponame)
289 self.assertIsNone(r.reponame)
284
290
285 # Need to specify explicit port number for proper https:// alt URLs.
291 # Need to specify explicit port number for proper https:// alt URLs.
286 r = parse(DEFAULT_ENV, altbaseurl='https://altserver:443')
292 r = parse(DEFAULT_ENV, altbaseurl='https://altserver:443')
287 self.assertEqual(r.url, b'http://testserver')
293 self.assertEqual(r.url, b'http://testserver')
288 self.assertEqual(r.baseurl, b'http://testserver')
294 self.assertEqual(r.baseurl, b'http://testserver')
289 self.assertEqual(r.advertisedurl, b'https://altserver')
295 self.assertEqual(r.advertisedurl, b'https://altserver')
290 self.assertEqual(r.advertisedbaseurl, b'https://altserver')
296 self.assertEqual(r.advertisedbaseurl, b'https://altserver')
291 self.assertEqual(r.urlscheme, b'http')
297 self.assertEqual(r.urlscheme, b'http')
292 self.assertEqual(r.apppath, b'')
298 self.assertEqual(r.apppath, b'')
293 self.assertEqual(r.dispatchparts, [])
299 self.assertEqual(r.dispatchparts, [])
294 self.assertIsNone(r.dispatchpath)
300 self.assertIsNone(r.dispatchpath)
295 self.assertIsNone(r.reponame)
301 self.assertIsNone(r.reponame)
296
302
297 # With only PATH_INFO defined.
303 # With only PATH_INFO defined.
298 r = parse(DEFAULT_ENV, altbaseurl='http://altserver', extra={
304 r = parse(DEFAULT_ENV, altbaseurl='http://altserver', extra={
299 r'PATH_INFO': r'/path1/path2',
305 r'PATH_INFO': r'/path1/path2',
300 })
306 })
301 self.assertEqual(r.url, b'http://testserver/path1/path2')
307 self.assertEqual(r.url, b'http://testserver/path1/path2')
302 self.assertEqual(r.baseurl, b'http://testserver')
308 self.assertEqual(r.baseurl, b'http://testserver')
303 self.assertEqual(r.advertisedurl, b'http://altserver/path1/path2')
309 self.assertEqual(r.advertisedurl, b'http://altserver/path1/path2')
304 self.assertEqual(r.advertisedbaseurl, b'http://altserver')
310 self.assertEqual(r.advertisedbaseurl, b'http://altserver')
305 self.assertEqual(r.urlscheme, b'http')
311 self.assertEqual(r.urlscheme, b'http')
306 self.assertEqual(r.apppath, b'')
312 self.assertEqual(r.apppath, b'')
307 self.assertEqual(r.dispatchparts, [b'path1', b'path2'])
313 self.assertEqual(r.dispatchparts, [b'path1', b'path2'])
308 self.assertEqual(r.dispatchpath, b'path1/path2')
314 self.assertEqual(r.dispatchpath, b'path1/path2')
309 self.assertIsNone(r.reponame)
315 self.assertIsNone(r.reponame)
310
316
311 # Path on alt URL.
317 # Path on alt URL.
312 r = parse(DEFAULT_ENV, altbaseurl='http://altserver/altpath')
318 r = parse(DEFAULT_ENV, altbaseurl='http://altserver/altpath')
313 self.assertEqual(r.url, b'http://testserver')
319 self.assertEqual(r.url, b'http://testserver')
314 self.assertEqual(r.baseurl, b'http://testserver')
320 self.assertEqual(r.baseurl, b'http://testserver')
315 self.assertEqual(r.advertisedurl, b'http://altserver/altpath')
321 self.assertEqual(r.advertisedurl, b'http://altserver/altpath')
316 self.assertEqual(r.advertisedbaseurl, b'http://altserver')
322 self.assertEqual(r.advertisedbaseurl, b'http://altserver')
317 self.assertEqual(r.urlscheme, b'http')
323 self.assertEqual(r.urlscheme, b'http')
318 self.assertEqual(r.apppath, b'/altpath')
324 self.assertEqual(r.apppath, b'/altpath')
319 self.assertEqual(r.dispatchparts, [])
325 self.assertEqual(r.dispatchparts, [])
320 self.assertIsNone(r.dispatchpath)
326 self.assertIsNone(r.dispatchpath)
321 self.assertIsNone(r.reponame)
327 self.assertIsNone(r.reponame)
322
328
323 # With a trailing slash.
329 # With a trailing slash.
324 r = parse(DEFAULT_ENV, altbaseurl='http://altserver/altpath/')
330 r = parse(DEFAULT_ENV, altbaseurl='http://altserver/altpath/')
325 self.assertEqual(r.url, b'http://testserver')
331 self.assertEqual(r.url, b'http://testserver')
326 self.assertEqual(r.baseurl, b'http://testserver')
332 self.assertEqual(r.baseurl, b'http://testserver')
327 self.assertEqual(r.advertisedurl, b'http://altserver/altpath/')
333 self.assertEqual(r.advertisedurl, b'http://altserver/altpath/')
328 self.assertEqual(r.advertisedbaseurl, b'http://altserver')
334 self.assertEqual(r.advertisedbaseurl, b'http://altserver')
329 self.assertEqual(r.urlscheme, b'http')
335 self.assertEqual(r.urlscheme, b'http')
330 self.assertEqual(r.apppath, b'/altpath/')
336 self.assertEqual(r.apppath, b'/altpath/')
331 self.assertEqual(r.dispatchparts, [])
337 self.assertEqual(r.dispatchparts, [])
332 self.assertIsNone(r.dispatchpath)
338 self.assertIsNone(r.dispatchpath)
333 self.assertIsNone(r.reponame)
339 self.assertIsNone(r.reponame)
334
340
335 # PATH_INFO + path on alt URL.
341 # PATH_INFO + path on alt URL.
336 r = parse(DEFAULT_ENV, altbaseurl='http://altserver/altpath', extra={
342 r = parse(DEFAULT_ENV, altbaseurl='http://altserver/altpath', extra={
337 r'PATH_INFO': r'/path1/path2',
343 r'PATH_INFO': r'/path1/path2',
338 })
344 })
339 self.assertEqual(r.url, b'http://testserver/path1/path2')
345 self.assertEqual(r.url, b'http://testserver/path1/path2')
340 self.assertEqual(r.baseurl, b'http://testserver')
346 self.assertEqual(r.baseurl, b'http://testserver')
341 self.assertEqual(r.advertisedurl,
347 self.assertEqual(r.advertisedurl,
342 b'http://altserver/altpath/path1/path2')
348 b'http://altserver/altpath/path1/path2')
343 self.assertEqual(r.advertisedbaseurl, b'http://altserver')
349 self.assertEqual(r.advertisedbaseurl, b'http://altserver')
344 self.assertEqual(r.urlscheme, b'http')
350 self.assertEqual(r.urlscheme, b'http')
345 self.assertEqual(r.apppath, b'/altpath')
351 self.assertEqual(r.apppath, b'/altpath')
346 self.assertEqual(r.dispatchparts, [b'path1', b'path2'])
352 self.assertEqual(r.dispatchparts, [b'path1', b'path2'])
347 self.assertEqual(r.dispatchpath, b'path1/path2')
353 self.assertEqual(r.dispatchpath, b'path1/path2')
348 self.assertIsNone(r.reponame)
354 self.assertIsNone(r.reponame)
349
355
350 # PATH_INFO + path on alt URL with trailing slash.
356 # PATH_INFO + path on alt URL with trailing slash.
351 r = parse(DEFAULT_ENV, altbaseurl='http://altserver/altpath/', extra={
357 r = parse(DEFAULT_ENV, altbaseurl='http://altserver/altpath/', extra={
352 r'PATH_INFO': r'/path1/path2',
358 r'PATH_INFO': r'/path1/path2',
353 })
359 })
354 self.assertEqual(r.url, b'http://testserver/path1/path2')
360 self.assertEqual(r.url, b'http://testserver/path1/path2')
355 self.assertEqual(r.baseurl, b'http://testserver')
361 self.assertEqual(r.baseurl, b'http://testserver')
356 self.assertEqual(r.advertisedurl,
362 self.assertEqual(r.advertisedurl,
357 b'http://altserver/altpath//path1/path2')
363 b'http://altserver/altpath//path1/path2')
358 self.assertEqual(r.advertisedbaseurl, b'http://altserver')
364 self.assertEqual(r.advertisedbaseurl, b'http://altserver')
359 self.assertEqual(r.urlscheme, b'http')
365 self.assertEqual(r.urlscheme, b'http')
360 self.assertEqual(r.apppath, b'/altpath/')
366 self.assertEqual(r.apppath, b'/altpath/')
361 self.assertEqual(r.dispatchparts, [b'path1', b'path2'])
367 self.assertEqual(r.dispatchparts, [b'path1', b'path2'])
362 self.assertEqual(r.dispatchpath, b'path1/path2')
368 self.assertEqual(r.dispatchpath, b'path1/path2')
363 self.assertIsNone(r.reponame)
369 self.assertIsNone(r.reponame)
364
370
365 # Local SCRIPT_NAME is ignored.
371 # Local SCRIPT_NAME is ignored.
366 r = parse(DEFAULT_ENV, altbaseurl='http://altserver', extra={
372 r = parse(DEFAULT_ENV, altbaseurl='http://altserver', extra={
367 r'SCRIPT_NAME': r'/script',
373 r'SCRIPT_NAME': r'/script',
368 r'PATH_INFO': r'/path1/path2',
374 r'PATH_INFO': r'/path1/path2',
369 })
375 })
370 self.assertEqual(r.url, b'http://testserver/script/path1/path2')
376 self.assertEqual(r.url, b'http://testserver/script/path1/path2')
371 self.assertEqual(r.baseurl, b'http://testserver')
377 self.assertEqual(r.baseurl, b'http://testserver')
372 self.assertEqual(r.advertisedurl, b'http://altserver/path1/path2')
378 self.assertEqual(r.advertisedurl, b'http://altserver/path1/path2')
373 self.assertEqual(r.advertisedbaseurl, b'http://altserver')
379 self.assertEqual(r.advertisedbaseurl, b'http://altserver')
374 self.assertEqual(r.urlscheme, b'http')
380 self.assertEqual(r.urlscheme, b'http')
375 self.assertEqual(r.apppath, b'')
381 self.assertEqual(r.apppath, b'')
376 self.assertEqual(r.dispatchparts, [b'path1', b'path2'])
382 self.assertEqual(r.dispatchparts, [b'path1', b'path2'])
377 self.assertEqual(r.dispatchpath, b'path1/path2')
383 self.assertEqual(r.dispatchpath, b'path1/path2')
378 self.assertIsNone(r.reponame)
384 self.assertIsNone(r.reponame)
379
385
380 # Use remote's path for script name, app path
386 # Use remote's path for script name, app path
381 r = parse(DEFAULT_ENV, altbaseurl='http://altserver/altroot', extra={
387 r = parse(DEFAULT_ENV, altbaseurl='http://altserver/altroot', extra={
382 r'SCRIPT_NAME': r'/script',
388 r'SCRIPT_NAME': r'/script',
383 r'PATH_INFO': r'/path1/path2',
389 r'PATH_INFO': r'/path1/path2',
384 })
390 })
385 self.assertEqual(r.url, b'http://testserver/script/path1/path2')
391 self.assertEqual(r.url, b'http://testserver/script/path1/path2')
386 self.assertEqual(r.baseurl, b'http://testserver')
392 self.assertEqual(r.baseurl, b'http://testserver')
387 self.assertEqual(r.advertisedurl,
393 self.assertEqual(r.advertisedurl,
388 b'http://altserver/altroot/path1/path2')
394 b'http://altserver/altroot/path1/path2')
389 self.assertEqual(r.advertisedbaseurl, b'http://altserver')
395 self.assertEqual(r.advertisedbaseurl, b'http://altserver')
390 self.assertEqual(r.urlscheme, b'http')
396 self.assertEqual(r.urlscheme, b'http')
391 self.assertEqual(r.apppath, b'/altroot')
397 self.assertEqual(r.apppath, b'/altroot')
392 self.assertEqual(r.dispatchparts, [b'path1', b'path2'])
398 self.assertEqual(r.dispatchparts, [b'path1', b'path2'])
393 self.assertEqual(r.dispatchpath, b'path1/path2')
399 self.assertEqual(r.dispatchpath, b'path1/path2')
394 self.assertIsNone(r.reponame)
400 self.assertIsNone(r.reponame)
395
401
396 # reponame is factored in properly.
402 # reponame is factored in properly.
397 r = parse(DEFAULT_ENV, reponame=b'repo',
403 r = parse(DEFAULT_ENV, reponame=b'repo',
398 altbaseurl='http://altserver/altroot',
404 altbaseurl='http://altserver/altroot',
399 extra={
405 extra={
400 r'SCRIPT_NAME': r'/script',
406 r'SCRIPT_NAME': r'/script',
401 r'PATH_INFO': r'/repo/path1/path2',
407 r'PATH_INFO': r'/repo/path1/path2',
402 })
408 })
403
409
404 self.assertEqual(r.url, b'http://testserver/script/repo/path1/path2')
410 self.assertEqual(r.url, b'http://testserver/script/repo/path1/path2')
405 self.assertEqual(r.baseurl, b'http://testserver')
411 self.assertEqual(r.baseurl, b'http://testserver')
406 self.assertEqual(r.advertisedurl,
412 self.assertEqual(r.advertisedurl,
407 b'http://altserver/altroot/repo/path1/path2')
413 b'http://altserver/altroot/repo/path1/path2')
408 self.assertEqual(r.advertisedbaseurl, b'http://altserver')
414 self.assertEqual(r.advertisedbaseurl, b'http://altserver')
409 self.assertEqual(r.apppath, b'/altroot/repo')
415 self.assertEqual(r.apppath, b'/altroot/repo')
410 self.assertEqual(r.dispatchparts, [b'path1', b'path2'])
416 self.assertEqual(r.dispatchparts, [b'path1', b'path2'])
411 self.assertEqual(r.dispatchpath, b'path1/path2')
417 self.assertEqual(r.dispatchpath, b'path1/path2')
412 self.assertEqual(r.reponame, b'repo')
418 self.assertEqual(r.reponame, b'repo')
413
419
414 if __name__ == '__main__':
420 if __name__ == '__main__':
415 import silenttestrunner
421 import silenttestrunner
416 silenttestrunner.main(__name__)
422 silenttestrunner.main(__name__)
General Comments 0
You need to be logged in to leave comments. Login now