Tests: style.
This commit is contained in:
@@ -5,8 +5,8 @@ from subprocess import call
|
|||||||
import unittest
|
import unittest
|
||||||
import unit
|
import unit
|
||||||
|
|
||||||
class TestUnitAccessLog(unit.TestUnitApplicationPython):
|
|
||||||
|
|
||||||
|
class TestUnitAccessLog(unit.TestUnitApplicationPython):
|
||||||
def setUpClass():
|
def setUpClass():
|
||||||
unit.TestUnit().check_modules('python')
|
unit.TestUnit().check_modules('python')
|
||||||
|
|
||||||
@@ -22,34 +22,45 @@ class TestUnitAccessLog(unit.TestUnitApplicationPython):
|
|||||||
def test_access_log_keepalive(self):
|
def test_access_log_keepalive(self):
|
||||||
self.load('mirror')
|
self.load('mirror')
|
||||||
|
|
||||||
(resp, sock) = self.post(headers={
|
(resp, sock) = self.post(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Connection': 'keep-alive',
|
'Connection': 'keep-alive',
|
||||||
'Content-Type': 'text/html'
|
'Content-Type': 'text/html',
|
||||||
}, start=True, body='01234')
|
},
|
||||||
|
start=True,
|
||||||
|
body='01234',
|
||||||
|
)
|
||||||
|
|
||||||
time.sleep(0.2)
|
time.sleep(0.2)
|
||||||
|
|
||||||
self.assertIsNotNone(
|
self.assertIsNotNone(
|
||||||
self.search_in_log(r'"POST / HTTP/1.1" 200 5'), 'keepalive 1')
|
self.search_in_log(r'"POST / HTTP/1.1" 200 5'), 'keepalive 1'
|
||||||
|
)
|
||||||
|
|
||||||
resp = self.post(headers={
|
resp = self.post(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Connection': 'close',
|
'Connection': 'close',
|
||||||
'Content-Type': 'text/html'
|
'Content-Type': 'text/html',
|
||||||
}, sock=sock, body='0123456789')
|
},
|
||||||
|
sock=sock,
|
||||||
|
body='0123456789',
|
||||||
|
)
|
||||||
|
|
||||||
time.sleep(0.2)
|
time.sleep(0.2)
|
||||||
|
|
||||||
self.stop()
|
self.stop()
|
||||||
|
|
||||||
self.assertIsNotNone(
|
self.assertIsNotNone(
|
||||||
self.search_in_log(r'"POST / HTTP/1.1" 200 10'), 'keepalive 2')
|
self.search_in_log(r'"POST / HTTP/1.1" 200 10'), 'keepalive 2'
|
||||||
|
)
|
||||||
|
|
||||||
def test_access_log_pipeline(self):
|
def test_access_log_pipeline(self):
|
||||||
self.load('empty')
|
self.load('empty')
|
||||||
|
|
||||||
self.http(b"""GET / HTTP/1.1
|
self.http(
|
||||||
|
b"""GET / HTTP/1.1
|
||||||
Host: localhost
|
Host: localhost
|
||||||
Referer: Referer-1
|
Referer: Referer-1
|
||||||
|
|
||||||
@@ -62,7 +73,10 @@ Host: localhost
|
|||||||
Referer: Referer-3
|
Referer: Referer-3
|
||||||
Connection: close
|
Connection: close
|
||||||
|
|
||||||
""", raw_resp=True, raw=True)
|
""",
|
||||||
|
raw_resp=True,
|
||||||
|
raw=True,
|
||||||
|
)
|
||||||
|
|
||||||
time.sleep(0.2)
|
time.sleep(0.2)
|
||||||
|
|
||||||
@@ -70,22 +84,21 @@ Connection: close
|
|||||||
|
|
||||||
self.assertIsNotNone(
|
self.assertIsNotNone(
|
||||||
self.search_in_log(r'"GET / HTTP/1.1" 200 0 "Referer-1" "-"'),
|
self.search_in_log(r'"GET / HTTP/1.1" 200 0 "Referer-1" "-"'),
|
||||||
'pipeline 1')
|
'pipeline 1',
|
||||||
|
)
|
||||||
self.assertIsNotNone(
|
self.assertIsNotNone(
|
||||||
self.search_in_log(r'"GET / HTTP/1.1" 200 0 "Referer-2" "-"'),
|
self.search_in_log(r'"GET / HTTP/1.1" 200 0 "Referer-2" "-"'),
|
||||||
'pipeline 2')
|
'pipeline 2',
|
||||||
|
)
|
||||||
self.assertIsNotNone(
|
self.assertIsNotNone(
|
||||||
self.search_in_log(r'"GET / HTTP/1.1" 200 0 "Referer-3" "-"'),
|
self.search_in_log(r'"GET / HTTP/1.1" 200 0 "Referer-3" "-"'),
|
||||||
'pipeline 3')
|
'pipeline 3',
|
||||||
|
)
|
||||||
|
|
||||||
def test_access_log_ipv6(self):
|
def test_access_log_ipv6(self):
|
||||||
self.load('empty')
|
self.load('empty')
|
||||||
|
|
||||||
self.conf({
|
self.conf({"[::1]:7080": {"application": "empty"}}, 'listeners')
|
||||||
"[::1]:7080": {
|
|
||||||
"application": "empty"
|
|
||||||
}
|
|
||||||
}, 'listeners')
|
|
||||||
|
|
||||||
self.get(sock_type='ipv6')
|
self.get(sock_type='ipv6')
|
||||||
|
|
||||||
@@ -95,18 +108,17 @@ Connection: close
|
|||||||
|
|
||||||
self.assertIsNotNone(
|
self.assertIsNotNone(
|
||||||
self.search_in_log(
|
self.search_in_log(
|
||||||
r'::1 - - \[.+\] "GET / HTTP/1.1" 200 0 "-" "-"'), 'ipv6')
|
r'::1 - - \[.+\] "GET / HTTP/1.1" 200 0 "-" "-"'
|
||||||
|
),
|
||||||
|
'ipv6',
|
||||||
|
)
|
||||||
|
|
||||||
def test_access_log_unix(self):
|
def test_access_log_unix(self):
|
||||||
self.load('empty')
|
self.load('empty')
|
||||||
|
|
||||||
addr = self.testdir + '/sock'
|
addr = self.testdir + '/sock'
|
||||||
|
|
||||||
self.conf({
|
self.conf({"unix:" + addr: {"application": "empty"}}, 'listeners')
|
||||||
"unix:" + addr: {
|
|
||||||
"application": "empty"
|
|
||||||
}
|
|
||||||
}, 'listeners')
|
|
||||||
|
|
||||||
self.get(sock_type='unix', addr=addr)
|
self.get(sock_type='unix', addr=addr)
|
||||||
|
|
||||||
@@ -114,17 +126,23 @@ Connection: close
|
|||||||
|
|
||||||
self.stop()
|
self.stop()
|
||||||
|
|
||||||
self.assertIsNotNone(self.search_in_log(
|
self.assertIsNotNone(
|
||||||
r'unix: - - \[.+\] "GET / HTTP/1.1" 200 0 "-" "-"'), 'unix')
|
self.search_in_log(
|
||||||
|
r'unix: - - \[.+\] "GET / HTTP/1.1" 200 0 "-" "-"'
|
||||||
|
),
|
||||||
|
'unix',
|
||||||
|
)
|
||||||
|
|
||||||
def test_access_log_referer(self):
|
def test_access_log_referer(self):
|
||||||
self.load('empty')
|
self.load('empty')
|
||||||
|
|
||||||
self.get(headers={
|
self.get(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Referer': 'referer-value',
|
'Referer': 'referer-value',
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
})
|
}
|
||||||
|
)
|
||||||
|
|
||||||
time.sleep(0.2)
|
time.sleep(0.2)
|
||||||
|
|
||||||
@@ -132,16 +150,19 @@ Connection: close
|
|||||||
|
|
||||||
self.assertIsNotNone(
|
self.assertIsNotNone(
|
||||||
self.search_in_log(r'"GET / HTTP/1.1" 200 0 "referer-value" "-"'),
|
self.search_in_log(r'"GET / HTTP/1.1" 200 0 "referer-value" "-"'),
|
||||||
'referer')
|
'referer',
|
||||||
|
)
|
||||||
|
|
||||||
def test_access_log_user_agent(self):
|
def test_access_log_user_agent(self):
|
||||||
self.load('empty')
|
self.load('empty')
|
||||||
|
|
||||||
self.get(headers={
|
self.get(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'User-Agent': 'user-agent-value',
|
'User-Agent': 'user-agent-value',
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
})
|
}
|
||||||
|
)
|
||||||
|
|
||||||
time.sleep(0.2)
|
time.sleep(0.2)
|
||||||
|
|
||||||
@@ -149,7 +170,10 @@ Connection: close
|
|||||||
|
|
||||||
self.assertIsNotNone(
|
self.assertIsNotNone(
|
||||||
self.search_in_log(
|
self.search_in_log(
|
||||||
r'"GET / HTTP/1.1" 200 0 "-" "user-agent-value"'), 'user agent')
|
r'"GET / HTTP/1.1" 200 0 "-" "user-agent-value"'
|
||||||
|
),
|
||||||
|
'user agent',
|
||||||
|
)
|
||||||
|
|
||||||
def test_access_log_http10(self):
|
def test_access_log_http10(self):
|
||||||
self.load('empty')
|
self.load('empty')
|
||||||
@@ -161,8 +185,8 @@ Connection: close
|
|||||||
self.stop()
|
self.stop()
|
||||||
|
|
||||||
self.assertIsNotNone(
|
self.assertIsNotNone(
|
||||||
self.search_in_log(
|
self.search_in_log(r'"GET / HTTP/1.0" 200 0 "-" "-"'), 'http 1.0'
|
||||||
r'"GET / HTTP/1.0" 200 0 "-" "-"'), 'http 1.0')
|
)
|
||||||
|
|
||||||
def test_access_log_partial(self):
|
def test_access_log_partial(self):
|
||||||
self.load('empty')
|
self.load('empty')
|
||||||
@@ -174,7 +198,8 @@ Connection: close
|
|||||||
self.stop()
|
self.stop()
|
||||||
|
|
||||||
self.assertIsNotNone(
|
self.assertIsNotNone(
|
||||||
self.search_in_log(r'"GE" 400 0 "-" "-"'), 'partial')
|
self.search_in_log(r'"GE" 400 0 "-" "-"'), 'partial'
|
||||||
|
)
|
||||||
|
|
||||||
def test_access_log_partial_2(self):
|
def test_access_log_partial_2(self):
|
||||||
self.load('empty')
|
self.load('empty')
|
||||||
@@ -186,7 +211,8 @@ Connection: close
|
|||||||
self.stop()
|
self.stop()
|
||||||
|
|
||||||
self.assertIsNotNone(
|
self.assertIsNotNone(
|
||||||
self.search_in_log(r'"GET /" 400 \d+ "-" "-"'), 'partial 2')
|
self.search_in_log(r'"GET /" 400 \d+ "-" "-"'), 'partial 2'
|
||||||
|
)
|
||||||
|
|
||||||
def test_access_log_partial_3(self):
|
def test_access_log_partial_3(self):
|
||||||
self.load('empty')
|
self.load('empty')
|
||||||
@@ -198,7 +224,8 @@ Connection: close
|
|||||||
self.stop()
|
self.stop()
|
||||||
|
|
||||||
self.assertIsNotNone(
|
self.assertIsNotNone(
|
||||||
self.search_in_log(r'"GET /" 400 0 "-" "-"'), 'partial 3')
|
self.search_in_log(r'"GET /" 400 0 "-" "-"'), 'partial 3'
|
||||||
|
)
|
||||||
|
|
||||||
def test_access_log_partial_4(self):
|
def test_access_log_partial_4(self):
|
||||||
self.load('empty')
|
self.load('empty')
|
||||||
@@ -210,8 +237,8 @@ Connection: close
|
|||||||
self.stop()
|
self.stop()
|
||||||
|
|
||||||
self.assertIsNotNone(
|
self.assertIsNotNone(
|
||||||
self.search_in_log(r'"GET / HTTP/1.1" 400 0 "-" "-"'),
|
self.search_in_log(r'"GET / HTTP/1.1" 400 0 "-" "-"'), 'partial 4'
|
||||||
'partial 4')
|
)
|
||||||
|
|
||||||
def test_access_log_partial_5(self):
|
def test_access_log_partial_5(self):
|
||||||
self.load('empty')
|
self.load('empty')
|
||||||
@@ -221,7 +248,8 @@ Connection: close
|
|||||||
self.stop()
|
self.stop()
|
||||||
|
|
||||||
self.assertIsNotNone(
|
self.assertIsNotNone(
|
||||||
self.search_in_log(r'"GET / HTTP/1.1" 200 0 "-" "-"'), 'partial 5')
|
self.search_in_log(r'"GET / HTTP/1.1" 200 0 "-" "-"'), 'partial 5'
|
||||||
|
)
|
||||||
|
|
||||||
def test_access_log_get_parameters(self):
|
def test_access_log_get_parameters(self):
|
||||||
self.load('empty')
|
self.load('empty')
|
||||||
@@ -234,8 +262,10 @@ Connection: close
|
|||||||
|
|
||||||
self.assertIsNotNone(
|
self.assertIsNotNone(
|
||||||
self.search_in_log(
|
self.search_in_log(
|
||||||
r'"GET /\?blah&var=val HTTP/1.1" 200 0 "-" "-"'),
|
r'"GET /\?blah&var=val HTTP/1.1" 200 0 "-" "-"'
|
||||||
'get parameters')
|
),
|
||||||
|
'get parameters',
|
||||||
|
)
|
||||||
|
|
||||||
def test_access_log_delete(self):
|
def test_access_log_delete(self):
|
||||||
self.load('empty')
|
self.load('empty')
|
||||||
@@ -265,7 +295,8 @@ Connection: close
|
|||||||
|
|
||||||
self.assertIsNotNone(
|
self.assertIsNotNone(
|
||||||
self.search_in_log(r'"GET / HTTP/1.1" 200 0 "-" "-"', 'new.log'),
|
self.search_in_log(r'"GET / HTTP/1.1" 200 0 "-" "-"', 'new.log'),
|
||||||
'change')
|
'change',
|
||||||
|
)
|
||||||
|
|
||||||
def test_access_log_reopen(self):
|
def test_access_log_reopen(self):
|
||||||
self.load('empty')
|
self.load('empty')
|
||||||
@@ -284,7 +315,8 @@ Connection: close
|
|||||||
|
|
||||||
self.assertIsNotNone(
|
self.assertIsNotNone(
|
||||||
self.search_in_log(r'"GET / HTTP/1.1" 200 0 "-" "-"', 'new.log'),
|
self.search_in_log(r'"GET / HTTP/1.1" 200 0 "-" "-"', 'new.log'),
|
||||||
'rename new')
|
'rename new',
|
||||||
|
)
|
||||||
self.assertFalse(os.path.isfile(log_path), 'rename old')
|
self.assertFalse(os.path.isfile(log_path), 'rename old')
|
||||||
|
|
||||||
with open(self.testdir + '/unit.pid', 'r') as f:
|
with open(self.testdir + '/unit.pid', 'r') as f:
|
||||||
@@ -299,10 +331,13 @@ Connection: close
|
|||||||
time.sleep(0.2)
|
time.sleep(0.2)
|
||||||
|
|
||||||
self.assertIsNone(
|
self.assertIsNone(
|
||||||
self.search_in_log(r'/usr1', 'new.log'), 'rename new 2')
|
self.search_in_log(r'/usr1', 'new.log'), 'rename new 2'
|
||||||
|
)
|
||||||
self.assertIsNotNone(
|
self.assertIsNotNone(
|
||||||
self.search_in_log(r'"GET /usr1 HTTP/1.1" 200 0 "-" "-"'),
|
self.search_in_log(r'"GET /usr1 HTTP/1.1" 200 0 "-" "-"'),
|
||||||
'reopen 2')
|
'reopen 2',
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
if __name__ == '__main__':
|
if __name__ == '__main__':
|
||||||
TestUnitAccessLog.main()
|
TestUnitAccessLog.main()
|
||||||
|
|||||||
@@ -1,8 +1,8 @@
|
|||||||
import unittest
|
import unittest
|
||||||
import unit
|
import unit
|
||||||
|
|
||||||
class TestUnitConfiguration(unit.TestUnitControl):
|
|
||||||
|
|
||||||
|
class TestUnitConfiguration(unit.TestUnitControl):
|
||||||
def setUpClass():
|
def setUpClass():
|
||||||
unit.TestUnit().check_modules('python')
|
unit.TestUnit().check_modules('python')
|
||||||
|
|
||||||
@@ -13,7 +13,10 @@ class TestUnitConfiguration(unit.TestUnitControl):
|
|||||||
self.assertIn('error', self.conf('00'), 'leading zero')
|
self.assertIn('error', self.conf('00'), 'leading zero')
|
||||||
|
|
||||||
def test_json_unicode(self):
|
def test_json_unicode(self):
|
||||||
self.assertIn('success', self.conf(b"""
|
self.assertIn(
|
||||||
|
'success',
|
||||||
|
self.conf(
|
||||||
|
b"""
|
||||||
{
|
{
|
||||||
"ap\u0070": {
|
"ap\u0070": {
|
||||||
"type": "\u0070ython",
|
"type": "\u0070ython",
|
||||||
@@ -22,32 +25,51 @@ class TestUnitConfiguration(unit.TestUnitControl):
|
|||||||
"module": "wsgi"
|
"module": "wsgi"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
""", 'applications'), 'unicode')
|
""",
|
||||||
|
'applications',
|
||||||
|
),
|
||||||
|
'unicode',
|
||||||
|
)
|
||||||
|
|
||||||
self.assertDictEqual(self.conf_get('applications'), {
|
self.assertDictEqual(
|
||||||
|
self.conf_get('applications'),
|
||||||
|
{
|
||||||
"app": {
|
"app": {
|
||||||
"type": "python",
|
"type": "python",
|
||||||
"processes": { "spare": 0 },
|
"processes": {"spare": 0},
|
||||||
"path": "/app",
|
"path": "/app",
|
||||||
"module": "wsgi"
|
"module": "wsgi",
|
||||||
}
|
}
|
||||||
}, 'unicode get')
|
},
|
||||||
|
'unicode get',
|
||||||
|
)
|
||||||
|
|
||||||
def test_json_unicode_2(self):
|
def test_json_unicode_2(self):
|
||||||
self.assertIn('success', self.conf({
|
self.assertIn(
|
||||||
|
'success',
|
||||||
|
self.conf(
|
||||||
|
{
|
||||||
"приложение": {
|
"приложение": {
|
||||||
"type": "python",
|
"type": "python",
|
||||||
"processes": { "spare": 0 },
|
"processes": {"spare": 0},
|
||||||
"path": "/app",
|
"path": "/app",
|
||||||
"module": "wsgi"
|
"module": "wsgi",
|
||||||
}
|
}
|
||||||
}, 'applications'), 'unicode 2')
|
},
|
||||||
|
'applications',
|
||||||
|
),
|
||||||
|
'unicode 2',
|
||||||
|
)
|
||||||
|
|
||||||
self.assertIn('приложение', self.conf_get('applications'),
|
self.assertIn(
|
||||||
'unicode 2 get')
|
'приложение', self.conf_get('applications'), 'unicode 2 get'
|
||||||
|
)
|
||||||
|
|
||||||
def test_json_unicode_number(self):
|
def test_json_unicode_number(self):
|
||||||
self.assertIn('error', self.conf(b"""
|
self.assertIn(
|
||||||
|
'error',
|
||||||
|
self.conf(
|
||||||
|
b"""
|
||||||
{
|
{
|
||||||
"app": {
|
"app": {
|
||||||
"type": "python",
|
"type": "python",
|
||||||
@@ -56,7 +78,11 @@ class TestUnitConfiguration(unit.TestUnitControl):
|
|||||||
"module": "wsgi"
|
"module": "wsgi"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
""", 'applications'), 'unicode number')
|
""",
|
||||||
|
'applications',
|
||||||
|
),
|
||||||
|
'unicode number',
|
||||||
|
)
|
||||||
|
|
||||||
def test_applications_open_brace(self):
|
def test_applications_open_brace(self):
|
||||||
self.assertIn('error', self.conf('{', 'applications'), 'open brace')
|
self.assertIn('error', self.conf('{', 'applications'), 'open brace')
|
||||||
@@ -65,20 +91,25 @@ class TestUnitConfiguration(unit.TestUnitControl):
|
|||||||
self.assertIn('error', self.conf('"{}"', 'applications'), 'string')
|
self.assertIn('error', self.conf('"{}"', 'applications'), 'string')
|
||||||
|
|
||||||
def test_applications_type_only(self):
|
def test_applications_type_only(self):
|
||||||
self.skip_alerts.extend([
|
self.skip_alerts.extend(
|
||||||
|
[
|
||||||
r'python module is empty',
|
r'python module is empty',
|
||||||
r'failed to apply new conf',
|
r'failed to apply new conf',
|
||||||
r'process \d+ exited on signal'
|
r'process \d+ exited on signal',
|
||||||
])
|
]
|
||||||
|
)
|
||||||
|
|
||||||
self.assertIn('error', self.conf({
|
self.assertIn(
|
||||||
"app": {
|
'error',
|
||||||
"type": "python"
|
self.conf({"app": {"type": "python"}}, 'applications'),
|
||||||
}
|
'type only',
|
||||||
}, 'applications'), 'type only')
|
)
|
||||||
|
|
||||||
def test_applications_miss_quote(self):
|
def test_applications_miss_quote(self):
|
||||||
self.assertIn('error', self.conf("""
|
self.assertIn(
|
||||||
|
'error',
|
||||||
|
self.conf(
|
||||||
|
"""
|
||||||
{
|
{
|
||||||
app": {
|
app": {
|
||||||
"type": "python",
|
"type": "python",
|
||||||
@@ -87,10 +118,17 @@ class TestUnitConfiguration(unit.TestUnitControl):
|
|||||||
"module": "wsgi"
|
"module": "wsgi"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
""", 'applications'), 'miss quote')
|
""",
|
||||||
|
'applications',
|
||||||
|
),
|
||||||
|
'miss quote',
|
||||||
|
)
|
||||||
|
|
||||||
def test_applications_miss_colon(self):
|
def test_applications_miss_colon(self):
|
||||||
self.assertIn('error', self.conf("""
|
self.assertIn(
|
||||||
|
'error',
|
||||||
|
self.conf(
|
||||||
|
"""
|
||||||
{
|
{
|
||||||
"app" {
|
"app" {
|
||||||
"type": "python",
|
"type": "python",
|
||||||
@@ -99,10 +137,17 @@ class TestUnitConfiguration(unit.TestUnitControl):
|
|||||||
"module": "wsgi"
|
"module": "wsgi"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
""", 'applications'), 'miss colon')
|
""",
|
||||||
|
'applications',
|
||||||
|
),
|
||||||
|
'miss colon',
|
||||||
|
)
|
||||||
|
|
||||||
def test_applications_miss_comma(self):
|
def test_applications_miss_comma(self):
|
||||||
self.assertIn('error', self.conf("""
|
self.assertIn(
|
||||||
|
'error',
|
||||||
|
self.conf(
|
||||||
|
"""
|
||||||
{
|
{
|
||||||
"app": {
|
"app": {
|
||||||
"type": "python"
|
"type": "python"
|
||||||
@@ -111,181 +156,206 @@ class TestUnitConfiguration(unit.TestUnitControl):
|
|||||||
"module": "wsgi"
|
"module": "wsgi"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
""", 'applications'), 'miss comma')
|
""",
|
||||||
|
'applications',
|
||||||
|
),
|
||||||
|
'miss comma',
|
||||||
|
)
|
||||||
|
|
||||||
def test_applications_skip_spaces(self):
|
def test_applications_skip_spaces(self):
|
||||||
self.assertIn('success', self.conf(b'{ \n\r\t}', 'applications'),
|
self.assertIn(
|
||||||
'skip spaces')
|
'success', self.conf(b'{ \n\r\t}', 'applications'), 'skip spaces'
|
||||||
|
)
|
||||||
|
|
||||||
def test_applications_relative_path(self):
|
def test_applications_relative_path(self):
|
||||||
self.assertIn('success', self.conf({
|
self.assertIn(
|
||||||
|
'success',
|
||||||
|
self.conf(
|
||||||
|
{
|
||||||
"app": {
|
"app": {
|
||||||
"type": "python",
|
"type": "python",
|
||||||
"processes": { "spare": 0 },
|
"processes": {"spare": 0},
|
||||||
"path": "../app",
|
"path": "../app",
|
||||||
"module": "wsgi"
|
"module": "wsgi",
|
||||||
}
|
}
|
||||||
}, 'applications'), 'relative path')
|
},
|
||||||
|
'applications',
|
||||||
|
),
|
||||||
|
'relative path',
|
||||||
|
)
|
||||||
|
|
||||||
@unittest.expectedFailure
|
@unittest.expectedFailure
|
||||||
def test_listeners_empty(self):
|
def test_listeners_empty(self):
|
||||||
self.skip_sanitizer = True
|
self.skip_sanitizer = True
|
||||||
self.skip_alerts.extend([
|
self.skip_alerts.extend(
|
||||||
|
[
|
||||||
r'failed to apply previous configuration',
|
r'failed to apply previous configuration',
|
||||||
r'process \d+ exited on signal'
|
r'process \d+ exited on signal',
|
||||||
])
|
]
|
||||||
|
)
|
||||||
|
|
||||||
self.assertIn('error', self.conf({"*:7080":{}}, 'listeners'),
|
self.assertIn(
|
||||||
'listener empty')
|
'error', self.conf({"*:7080": {}}, 'listeners'), 'listener empty'
|
||||||
|
)
|
||||||
|
|
||||||
def test_listeners_no_app(self):
|
def test_listeners_no_app(self):
|
||||||
self.assertIn('error', self.conf({"*:7080":{"application":"app"}},
|
self.assertIn(
|
||||||
'listeners'), 'listeners no app')
|
'error',
|
||||||
|
self.conf({"*:7080": {"application": "app"}}, 'listeners'),
|
||||||
|
'listeners no app',
|
||||||
|
)
|
||||||
|
|
||||||
def test_listeners_wildcard(self):
|
def test_listeners_wildcard(self):
|
||||||
self.assertIn('success', self.conf({
|
self.assertIn(
|
||||||
"listeners": {
|
'success',
|
||||||
"*:7080": {
|
self.conf(
|
||||||
"application":"app"
|
{
|
||||||
}
|
"listeners": {"*:7080": {"application": "app"}},
|
||||||
},
|
|
||||||
"applications": {
|
"applications": {
|
||||||
"app": {
|
"app": {
|
||||||
"type": "python",
|
"type": "python",
|
||||||
"processes": { "spare": 0 },
|
"processes": {"spare": 0},
|
||||||
"path": "/app",
|
"path": "/app",
|
||||||
"module": "wsgi"
|
"module": "wsgi",
|
||||||
}
|
}
|
||||||
|
},
|
||||||
}
|
}
|
||||||
}), 'listeners wildcard')
|
),
|
||||||
|
'listeners wildcard',
|
||||||
|
)
|
||||||
|
|
||||||
def test_listeners_explicit(self):
|
def test_listeners_explicit(self):
|
||||||
self.assertIn('success', self.conf({
|
self.assertIn(
|
||||||
"listeners": {
|
'success',
|
||||||
"127.0.0.1:7080": {
|
self.conf(
|
||||||
"application":"app"
|
{
|
||||||
}
|
"listeners": {"127.0.0.1:7080": {"application": "app"}},
|
||||||
},
|
|
||||||
"applications": {
|
"applications": {
|
||||||
"app": {
|
"app": {
|
||||||
"type": "python",
|
"type": "python",
|
||||||
"processes": { "spare": 0 },
|
"processes": {"spare": 0},
|
||||||
"path": "/app",
|
"path": "/app",
|
||||||
"module": "wsgi"
|
"module": "wsgi",
|
||||||
}
|
}
|
||||||
|
},
|
||||||
}
|
}
|
||||||
}), 'explicit')
|
),
|
||||||
|
'explicit',
|
||||||
|
)
|
||||||
|
|
||||||
def test_listeners_explicit_ipv6(self):
|
def test_listeners_explicit_ipv6(self):
|
||||||
self.assertIn('success', self.conf({
|
self.assertIn(
|
||||||
"listeners": {
|
'success',
|
||||||
"[::1]:7080": {
|
self.conf(
|
||||||
"application":"app"
|
{
|
||||||
}
|
"listeners": {"[::1]:7080": {"application": "app"}},
|
||||||
},
|
|
||||||
"applications": {
|
"applications": {
|
||||||
"app": {
|
"app": {
|
||||||
"type": "python",
|
"type": "python",
|
||||||
"processes": { "spare": 0 },
|
"processes": {"spare": 0},
|
||||||
"path": "/app",
|
"path": "/app",
|
||||||
"module": "wsgi"
|
"module": "wsgi",
|
||||||
}
|
}
|
||||||
|
},
|
||||||
}
|
}
|
||||||
}), 'explicit ipv6')
|
),
|
||||||
|
'explicit ipv6',
|
||||||
|
)
|
||||||
|
|
||||||
def test_listeners_no_port(self):
|
def test_listeners_no_port(self):
|
||||||
self.skip_alerts.extend([
|
self.skip_alerts.extend(
|
||||||
|
[
|
||||||
r'invalid listener "127\.0\.0\.1"',
|
r'invalid listener "127\.0\.0\.1"',
|
||||||
r'failed to apply new conf',
|
r'failed to apply new conf',
|
||||||
r'process \d+ exited on signal'
|
r'process \d+ exited on signal',
|
||||||
])
|
]
|
||||||
|
)
|
||||||
|
|
||||||
self.assertIn('error', self.conf({
|
self.assertIn(
|
||||||
"listeners": {
|
'error',
|
||||||
"127.0.0.1": {
|
self.conf(
|
||||||
"application":"app"
|
{
|
||||||
}
|
"listeners": {"127.0.0.1": {"application": "app"}},
|
||||||
},
|
|
||||||
"applications": {
|
"applications": {
|
||||||
"app": {
|
"app": {
|
||||||
"type": "python",
|
"type": "python",
|
||||||
"processes": { "spare": 0 },
|
"processes": {"spare": 0},
|
||||||
"path": "/app",
|
"path": "/app",
|
||||||
"module": "wsgi"
|
"module": "wsgi",
|
||||||
}
|
}
|
||||||
|
},
|
||||||
}
|
}
|
||||||
}), 'no port')
|
),
|
||||||
|
'no port',
|
||||||
|
)
|
||||||
|
|
||||||
def test_json_application_name_large(self):
|
def test_json_application_name_large(self):
|
||||||
name = "X" * 1024 * 1024
|
name = "X" * 1024 * 1024
|
||||||
|
|
||||||
self.assertIn('success', self.conf({
|
self.assertIn(
|
||||||
"listeners": {
|
'success',
|
||||||
"*:7080": {
|
self.conf(
|
||||||
"application": name
|
{
|
||||||
}
|
"listeners": {"*:7080": {"application": name}},
|
||||||
},
|
|
||||||
"applications": {
|
"applications": {
|
||||||
name: {
|
name: {
|
||||||
"type": "python",
|
"type": "python",
|
||||||
"processes": { "spare": 0 },
|
"processes": {"spare": 0},
|
||||||
"path": "/app",
|
"path": "/app",
|
||||||
"module": "wsgi"
|
"module": "wsgi",
|
||||||
}
|
}
|
||||||
|
},
|
||||||
}
|
}
|
||||||
}))
|
),
|
||||||
|
)
|
||||||
|
|
||||||
@unittest.expectedFailure
|
@unittest.expectedFailure
|
||||||
def test_json_application_many(self):
|
def test_json_application_many(self):
|
||||||
self.skip_alerts.extend([
|
self.skip_alerts.extend(
|
||||||
r'eventfd.+failed',
|
[r'eventfd.+failed', r'epoll.+failed', r'failed to apply']
|
||||||
r'epoll.+failed',
|
)
|
||||||
r'failed to apply'
|
|
||||||
])
|
|
||||||
apps = 999
|
apps = 999
|
||||||
|
|
||||||
conf = {
|
conf = {
|
||||||
"applications":
|
"applications": {
|
||||||
{"app-" + str(a): {
|
"app-"
|
||||||
|
+ str(a): {
|
||||||
"type": "python",
|
"type": "python",
|
||||||
"processes": { "spare": 0 },
|
"processes": {"spare": 0},
|
||||||
"path": "/app",
|
"path": "/app",
|
||||||
"module": "wsgi"
|
"module": "wsgi",
|
||||||
} for a in range(apps)
|
}
|
||||||
|
for a in range(apps)
|
||||||
},
|
},
|
||||||
"listeners": {
|
"listeners": {
|
||||||
"*:" + str(7000 + a): {
|
"*:" + str(7000 + a): {"application": "app-" + str(a)}
|
||||||
"application": "app-" + str(a)
|
for a in range(apps)
|
||||||
} for a in range(apps)
|
},
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
self.assertIn('success', self.conf(conf))
|
self.assertIn('success', self.conf(conf))
|
||||||
|
|
||||||
def test_json_application_many2(self):
|
def test_json_application_many2(self):
|
||||||
self.skip_alerts.extend([
|
self.skip_alerts.extend(
|
||||||
r'eventfd.+failed',
|
[r'eventfd.+failed', r'epoll.+failed', r'failed to apply']
|
||||||
r'epoll.+failed',
|
)
|
||||||
r'failed to apply'
|
|
||||||
])
|
|
||||||
|
|
||||||
conf = {
|
conf = {
|
||||||
"applications":
|
"applications": {
|
||||||
{"app-" + str(a): {
|
"app-"
|
||||||
|
+ str(a): {
|
||||||
"type": "python",
|
"type": "python",
|
||||||
"processes": { "spare": 0 },
|
"processes": {"spare": 0},
|
||||||
"path": "/app",
|
"path": "/app",
|
||||||
"module": "wsgi"
|
"module": "wsgi",
|
||||||
} for a in range(999)
|
}
|
||||||
|
for a in range(999)
|
||||||
},
|
},
|
||||||
"listeners": {
|
"listeners": {"*:7001": {"application": "app-1"}},
|
||||||
"*:7001": {
|
|
||||||
"application": "app-1"
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
self.assertIn('success', self.conf(conf))
|
self.assertIn('success', self.conf(conf))
|
||||||
|
|
||||||
|
|
||||||
if __name__ == '__main__':
|
if __name__ == '__main__':
|
||||||
TestUnitConfiguration.main()
|
TestUnitConfiguration.main()
|
||||||
|
|||||||
@@ -1,8 +1,8 @@
|
|||||||
import unittest
|
import unittest
|
||||||
import unit
|
import unit
|
||||||
|
|
||||||
class TestUnitGoApplication(unit.TestUnitApplicationGo):
|
|
||||||
|
|
||||||
|
class TestUnitGoApplication(unit.TestUnitApplicationGo):
|
||||||
def setUpClass():
|
def setUpClass():
|
||||||
unit.TestUnit().check_modules('go')
|
unit.TestUnit().check_modules('go')
|
||||||
|
|
||||||
@@ -11,12 +11,15 @@ class TestUnitGoApplication(unit.TestUnitApplicationGo):
|
|||||||
|
|
||||||
body = 'Test body string.'
|
body = 'Test body string.'
|
||||||
|
|
||||||
resp = self.post(headers={
|
resp = self.post(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Content-Type': 'text/html',
|
'Content-Type': 'text/html',
|
||||||
'Custom-Header': 'blah',
|
'Custom-Header': 'blah',
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
}, body=body)
|
},
|
||||||
|
body=body,
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(resp['status'], 200, 'status')
|
self.assertEqual(resp['status'], 200, 'status')
|
||||||
headers = resp['headers']
|
headers = resp['headers']
|
||||||
@@ -25,10 +28,15 @@ class TestUnitGoApplication(unit.TestUnitApplicationGo):
|
|||||||
|
|
||||||
date = headers.pop('Date')
|
date = headers.pop('Date')
|
||||||
self.assertEqual(date[-4:], ' GMT', 'date header timezone')
|
self.assertEqual(date[-4:], ' GMT', 'date header timezone')
|
||||||
self.assertLess(abs(self.date_to_sec_epoch(date) - self.sec_epoch()), 5,
|
self.assertLess(
|
||||||
'date header')
|
abs(self.date_to_sec_epoch(date) - self.sec_epoch()),
|
||||||
|
5,
|
||||||
|
'date header',
|
||||||
|
)
|
||||||
|
|
||||||
self.assertDictEqual(headers, {
|
self.assertDictEqual(
|
||||||
|
headers,
|
||||||
|
{
|
||||||
'Content-Length': str(len(body)),
|
'Content-Length': str(len(body)),
|
||||||
'Content-Type': 'text/html',
|
'Content-Type': 'text/html',
|
||||||
'Request-Method': 'POST',
|
'Request-Method': 'POST',
|
||||||
@@ -38,8 +46,10 @@ class TestUnitGoApplication(unit.TestUnitApplicationGo):
|
|||||||
'Server-Protocol-Major': '1',
|
'Server-Protocol-Major': '1',
|
||||||
'Server-Protocol-Minor': '1',
|
'Server-Protocol-Minor': '1',
|
||||||
'Custom-Header': 'blah',
|
'Custom-Header': 'blah',
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
}, 'headers')
|
},
|
||||||
|
'headers',
|
||||||
|
)
|
||||||
self.assertEqual(resp['body'], body, 'body')
|
self.assertEqual(resp['body'], body, 'body')
|
||||||
|
|
||||||
def test_go_application_get_variables(self):
|
def test_go_application_get_variables(self):
|
||||||
@@ -53,11 +63,14 @@ class TestUnitGoApplication(unit.TestUnitApplicationGo):
|
|||||||
def test_go_application_post_variables(self):
|
def test_go_application_post_variables(self):
|
||||||
self.load('post_variables')
|
self.load('post_variables')
|
||||||
|
|
||||||
resp = self.post(headers={
|
resp = self.post(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Content-Type': 'application/x-www-form-urlencoded',
|
'Content-Type': 'application/x-www-form-urlencoded',
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
}, body='var1=val1&var2=&var3')
|
},
|
||||||
|
body='var1=val1&var2=&var3',
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(resp['headers']['X-Var-1'], 'val1', 'POST variables')
|
self.assertEqual(resp['headers']['X-Var-1'], 'val1', 'POST variables')
|
||||||
self.assertEqual(resp['headers']['X-Var-2'], '', 'POST variables 2')
|
self.assertEqual(resp['headers']['X-Var-2'], '', 'POST variables 2')
|
||||||
@@ -69,36 +82,47 @@ class TestUnitGoApplication(unit.TestUnitApplicationGo):
|
|||||||
resp = self.get()
|
resp = self.get()
|
||||||
|
|
||||||
self.assertEqual(resp['status'], 404, '404 status')
|
self.assertEqual(resp['status'], 404, '404 status')
|
||||||
self.assertRegex(resp['body'], r'<title>404 Not Found</title>',
|
self.assertRegex(
|
||||||
'404 body')
|
resp['body'], r'<title>404 Not Found</title>', '404 body'
|
||||||
|
)
|
||||||
|
|
||||||
def test_go_keepalive_body(self):
|
def test_go_keepalive_body(self):
|
||||||
self.load('mirror')
|
self.load('mirror')
|
||||||
|
|
||||||
(resp, sock) = self.post(headers={
|
(resp, sock) = self.post(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Connection': 'keep-alive',
|
'Connection': 'keep-alive',
|
||||||
'Content-Type': 'text/html'
|
'Content-Type': 'text/html',
|
||||||
}, start=True, body='0123456789' * 500)
|
},
|
||||||
|
start=True,
|
||||||
|
body='0123456789' * 500,
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(resp['body'], '0123456789' * 500, 'keep-alive 1')
|
self.assertEqual(resp['body'], '0123456789' * 500, 'keep-alive 1')
|
||||||
|
|
||||||
resp = self.post(headers={
|
resp = self.post(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Content-Type': 'text/html',
|
'Content-Type': 'text/html',
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
}, sock=sock, body='0123456789')
|
},
|
||||||
|
sock=sock,
|
||||||
|
body='0123456789',
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(resp['body'], '0123456789', 'keep-alive 2')
|
self.assertEqual(resp['body'], '0123456789', 'keep-alive 2')
|
||||||
|
|
||||||
def test_go_application_cookies(self):
|
def test_go_application_cookies(self):
|
||||||
self.load('cookies')
|
self.load('cookies')
|
||||||
|
|
||||||
resp = self.get(headers={
|
resp = self.get(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Cookie': 'var1=val1; var2=val2',
|
'Cookie': 'var1=val1; var2=val2',
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
})
|
}
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(resp['headers']['X-Cookie-1'], 'val1', 'cookie 1')
|
self.assertEqual(resp['headers']['X-Cookie-1'], 'val1', 'cookie 1')
|
||||||
self.assertEqual(resp['headers']['X-Cookie-2'], 'val2', 'cookie 2')
|
self.assertEqual(resp['headers']['X-Cookie-2'], 'val2', 'cookie 2')
|
||||||
@@ -106,15 +130,22 @@ class TestUnitGoApplication(unit.TestUnitApplicationGo):
|
|||||||
def test_go_application_command_line_arguments_type(self):
|
def test_go_application_command_line_arguments_type(self):
|
||||||
self.load('command_line_arguments')
|
self.load('command_line_arguments')
|
||||||
|
|
||||||
self.assertIn('error', self.conf(''"a b c",
|
self.assertIn(
|
||||||
'applications/command_line_arguments/arguments'), 'arguments type')
|
'error',
|
||||||
|
self.conf(
|
||||||
|
'' "a b c", 'applications/command_line_arguments/arguments'
|
||||||
|
),
|
||||||
|
'arguments type',
|
||||||
|
)
|
||||||
|
|
||||||
def test_go_application_command_line_arguments_0(self):
|
def test_go_application_command_line_arguments_0(self):
|
||||||
self.load('command_line_arguments')
|
self.load('command_line_arguments')
|
||||||
|
|
||||||
self.assertEqual(self.get()['headers']['X-Arg-0'],
|
self.assertEqual(
|
||||||
|
self.get()['headers']['X-Arg-0'],
|
||||||
self.conf_get('applications/command_line_arguments/executable'),
|
self.conf_get('applications/command_line_arguments/executable'),
|
||||||
'argument 0')
|
'argument 0',
|
||||||
|
)
|
||||||
|
|
||||||
def test_go_application_command_line_arguments(self):
|
def test_go_application_command_line_arguments(self):
|
||||||
self.load('command_line_arguments')
|
self.load('command_line_arguments')
|
||||||
@@ -123,11 +154,14 @@ class TestUnitGoApplication(unit.TestUnitApplicationGo):
|
|||||||
arg2 = '--cc-opt=\'-O0 -DNXT_DEBUG_MEMORY=1 -fsanitize=address\''
|
arg2 = '--cc-opt=\'-O0 -DNXT_DEBUG_MEMORY=1 -fsanitize=address\''
|
||||||
arg3 = '--debug'
|
arg3 = '--debug'
|
||||||
|
|
||||||
self.conf('["' + arg1 + '", "' + arg2 + '", "' + arg3 + '"]',
|
self.conf(
|
||||||
'applications/command_line_arguments/arguments')
|
'["' + arg1 + '", "' + arg2 + '", "' + arg3 + '"]',
|
||||||
|
'applications/command_line_arguments/arguments',
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(self.get()['body'], arg1 + ',' + arg2 + ',' + arg3,
|
self.assertEqual(
|
||||||
'arguments')
|
self.get()['body'], arg1 + ',' + arg2 + ',' + arg3, 'arguments'
|
||||||
|
)
|
||||||
|
|
||||||
def test_go_application_command_line_arguments_change(self):
|
def test_go_application_command_line_arguments_change(self):
|
||||||
self.load('command_line_arguments')
|
self.load('command_line_arguments')
|
||||||
@@ -144,8 +178,10 @@ class TestUnitGoApplication(unit.TestUnitApplicationGo):
|
|||||||
|
|
||||||
self.conf('[]', args_path)
|
self.conf('[]', args_path)
|
||||||
|
|
||||||
self.assertEqual(self.get()['headers']['Content-Length'], '0',
|
self.assertEqual(
|
||||||
'arguments empty')
|
self.get()['headers']['Content-Length'], '0', 'arguments empty'
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
if __name__ == '__main__':
|
if __name__ == '__main__':
|
||||||
TestUnitGoApplication.main()
|
TestUnitGoApplication.main()
|
||||||
|
|||||||
@@ -1,216 +1,302 @@
|
|||||||
import unittest
|
import unittest
|
||||||
import unit
|
import unit
|
||||||
|
|
||||||
class TestUnitHTTPHeader(unit.TestUnitApplicationPython):
|
|
||||||
|
|
||||||
|
class TestUnitHTTPHeader(unit.TestUnitApplicationPython):
|
||||||
def setUpClass():
|
def setUpClass():
|
||||||
unit.TestUnit().check_modules('python')
|
unit.TestUnit().check_modules('python')
|
||||||
|
|
||||||
def test_http_header_value_leading_sp(self):
|
def test_http_header_value_leading_sp(self):
|
||||||
self.load('custom_header')
|
self.load('custom_header')
|
||||||
|
|
||||||
resp = self.get(headers={
|
resp = self.get(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Custom-Header': ' ,',
|
'Custom-Header': ' ,',
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
})
|
}
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(resp['status'], 200, 'value leading sp status')
|
self.assertEqual(resp['status'], 200, 'value leading sp status')
|
||||||
self.assertEqual(resp['headers']['Custom-Header'], ',',
|
self.assertEqual(
|
||||||
'value leading sp custom header')
|
resp['headers']['Custom-Header'],
|
||||||
|
',',
|
||||||
|
'value leading sp custom header',
|
||||||
|
)
|
||||||
|
|
||||||
def test_http_header_value_leading_htab(self):
|
def test_http_header_value_leading_htab(self):
|
||||||
self.load('custom_header')
|
self.load('custom_header')
|
||||||
|
|
||||||
resp = self.get(headers={
|
resp = self.get(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Custom-Header': '\t,',
|
'Custom-Header': '\t,',
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
})
|
}
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(resp['status'], 200, 'value leading htab status')
|
self.assertEqual(resp['status'], 200, 'value leading htab status')
|
||||||
self.assertEqual(resp['headers']['Custom-Header'], ',',
|
self.assertEqual(
|
||||||
'value leading htab custom header')
|
resp['headers']['Custom-Header'],
|
||||||
|
',',
|
||||||
|
'value leading htab custom header',
|
||||||
|
)
|
||||||
|
|
||||||
def test_http_header_value_trailing_sp(self):
|
def test_http_header_value_trailing_sp(self):
|
||||||
self.load('custom_header')
|
self.load('custom_header')
|
||||||
|
|
||||||
resp = self.get(headers={
|
resp = self.get(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Custom-Header': ', ',
|
'Custom-Header': ', ',
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
})
|
}
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(resp['status'], 200, 'value trailing sp status')
|
self.assertEqual(resp['status'], 200, 'value trailing sp status')
|
||||||
self.assertEqual(resp['headers']['Custom-Header'], ',',
|
self.assertEqual(
|
||||||
'value trailing sp custom header')
|
resp['headers']['Custom-Header'],
|
||||||
|
',',
|
||||||
|
'value trailing sp custom header',
|
||||||
|
)
|
||||||
|
|
||||||
def test_http_header_value_trailing_htab(self):
|
def test_http_header_value_trailing_htab(self):
|
||||||
self.load('custom_header')
|
self.load('custom_header')
|
||||||
|
|
||||||
resp = self.get(headers={
|
resp = self.get(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Custom-Header': ',\t',
|
'Custom-Header': ',\t',
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
})
|
}
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(resp['status'], 200, 'value trailing htab status')
|
self.assertEqual(resp['status'], 200, 'value trailing htab status')
|
||||||
self.assertEqual(resp['headers']['Custom-Header'], ',',
|
self.assertEqual(
|
||||||
'value trailing htab custom header')
|
resp['headers']['Custom-Header'],
|
||||||
|
',',
|
||||||
|
'value trailing htab custom header',
|
||||||
|
)
|
||||||
|
|
||||||
def test_http_header_value_both_sp(self):
|
def test_http_header_value_both_sp(self):
|
||||||
self.load('custom_header')
|
self.load('custom_header')
|
||||||
|
|
||||||
resp = self.get(headers={
|
resp = self.get(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Custom-Header': ' , ',
|
'Custom-Header': ' , ',
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
})
|
}
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(resp['status'], 200, 'value both sp status')
|
self.assertEqual(resp['status'], 200, 'value both sp status')
|
||||||
self.assertEqual(resp['headers']['Custom-Header'], ',',
|
self.assertEqual(
|
||||||
'value both sp custom header')
|
resp['headers']['Custom-Header'],
|
||||||
|
',',
|
||||||
|
'value both sp custom header',
|
||||||
|
)
|
||||||
|
|
||||||
def test_http_header_value_both_htab(self):
|
def test_http_header_value_both_htab(self):
|
||||||
self.load('custom_header')
|
self.load('custom_header')
|
||||||
|
|
||||||
resp = self.get(headers={
|
resp = self.get(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Custom-Header': '\t,\t',
|
'Custom-Header': '\t,\t',
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
})
|
}
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(resp['status'], 200, 'value both htab status')
|
self.assertEqual(resp['status'], 200, 'value both htab status')
|
||||||
self.assertEqual(resp['headers']['Custom-Header'], ',',
|
self.assertEqual(
|
||||||
'value both htab custom header')
|
resp['headers']['Custom-Header'],
|
||||||
|
',',
|
||||||
|
'value both htab custom header',
|
||||||
|
)
|
||||||
|
|
||||||
def test_http_header_value_chars(self):
|
def test_http_header_value_chars(self):
|
||||||
self.load('custom_header')
|
self.load('custom_header')
|
||||||
|
|
||||||
resp = self.get(headers={
|
resp = self.get(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Custom-Header': '(),/:;<=>?@[\]{}\t !#$%&\'*+-.^_`|~',
|
'Custom-Header': '(),/:;<=>?@[\]{}\t !#$%&\'*+-.^_`|~',
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
})
|
}
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(resp['status'], 200, 'value chars status')
|
self.assertEqual(resp['status'], 200, 'value chars status')
|
||||||
self.assertEqual(resp['headers']['Custom-Header'],
|
self.assertEqual(
|
||||||
'(),/:;<=>?@[\]{}\t !#$%&\'*+-.^_`|~', 'value chars custom header')
|
resp['headers']['Custom-Header'],
|
||||||
|
'(),/:;<=>?@[\]{}\t !#$%&\'*+-.^_`|~',
|
||||||
|
'value chars custom header',
|
||||||
|
)
|
||||||
|
|
||||||
def test_http_header_value_chars_edge(self):
|
def test_http_header_value_chars_edge(self):
|
||||||
self.load('custom_header')
|
self.load('custom_header')
|
||||||
|
|
||||||
resp = self.http(b"""GET / HTTP/1.1
|
resp = self.http(
|
||||||
|
b"""GET / HTTP/1.1
|
||||||
Host: localhost
|
Host: localhost
|
||||||
Custom-Header: \x20\xFF
|
Custom-Header: \x20\xFF
|
||||||
Connection: close
|
Connection: close
|
||||||
|
|
||||||
""", raw=True, encoding='latin1')
|
""",
|
||||||
|
raw=True,
|
||||||
|
encoding='latin1',
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(resp['status'], 200, 'value chars edge status')
|
self.assertEqual(resp['status'], 200, 'value chars edge status')
|
||||||
self.assertEqual(resp['headers']['Custom-Header'], '\xFF',
|
self.assertEqual(
|
||||||
'value chars edge')
|
resp['headers']['Custom-Header'], '\xFF', 'value chars edge'
|
||||||
|
)
|
||||||
|
|
||||||
def test_http_header_value_chars_below(self):
|
def test_http_header_value_chars_below(self):
|
||||||
self.load('custom_header')
|
self.load('custom_header')
|
||||||
|
|
||||||
resp = self.http(b"""GET / HTTP/1.1
|
resp = self.http(
|
||||||
|
b"""GET / HTTP/1.1
|
||||||
Host: localhost
|
Host: localhost
|
||||||
Custom-Header: \x1F
|
Custom-Header: \x1F
|
||||||
Connection: close
|
Connection: close
|
||||||
|
|
||||||
""", raw=True)
|
""",
|
||||||
|
raw=True,
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(resp['status'], 400, 'value chars below')
|
self.assertEqual(resp['status'], 400, 'value chars below')
|
||||||
|
|
||||||
def test_http_header_field_leading_sp(self):
|
def test_http_header_field_leading_sp(self):
|
||||||
self.load('empty')
|
self.load('empty')
|
||||||
|
|
||||||
resp = self.get(headers={
|
resp = self.get(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
' Custom-Header': 'blah',
|
' Custom-Header': 'blah',
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
})
|
}
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(resp['status'], 400, 'field leading sp')
|
self.assertEqual(resp['status'], 400, 'field leading sp')
|
||||||
|
|
||||||
def test_http_header_field_leading_htab(self):
|
def test_http_header_field_leading_htab(self):
|
||||||
self.load('empty')
|
self.load('empty')
|
||||||
|
|
||||||
resp = self.get(headers={
|
resp = self.get(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'\tCustom-Header': 'blah',
|
'\tCustom-Header': 'blah',
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
})
|
}
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(resp['status'], 400, 'field leading htab')
|
self.assertEqual(resp['status'], 400, 'field leading htab')
|
||||||
|
|
||||||
def test_http_header_field_trailing_sp(self):
|
def test_http_header_field_trailing_sp(self):
|
||||||
self.load('empty')
|
self.load('empty')
|
||||||
|
|
||||||
resp = self.get(headers={
|
resp = self.get(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Custom-Header ': 'blah',
|
'Custom-Header ': 'blah',
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
})
|
}
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(resp['status'], 400, 'field trailing sp')
|
self.assertEqual(resp['status'], 400, 'field trailing sp')
|
||||||
|
|
||||||
def test_http_header_field_trailing_htab(self):
|
def test_http_header_field_trailing_htab(self):
|
||||||
self.load('empty')
|
self.load('empty')
|
||||||
|
|
||||||
resp = self.get(headers={
|
resp = self.get(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Custom-Header\t': 'blah',
|
'Custom-Header\t': 'blah',
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
})
|
}
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(resp['status'], 400, 'field trailing htab')
|
self.assertEqual(resp['status'], 400, 'field trailing htab')
|
||||||
|
|
||||||
def test_http_header_content_length_big(self):
|
def test_http_header_content_length_big(self):
|
||||||
self.load('empty')
|
self.load('empty')
|
||||||
|
|
||||||
self.assertEqual(self.post(headers={
|
self.assertEqual(
|
||||||
|
self.post(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Content-Length': str(2 ** 64),
|
'Content-Length': str(2 ** 64),
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
}, body='X' * 1000)['status'], 400, 'Content-Length big')
|
},
|
||||||
|
body='X' * 1000,
|
||||||
|
)['status'],
|
||||||
|
400,
|
||||||
|
'Content-Length big',
|
||||||
|
)
|
||||||
|
|
||||||
def test_http_header_content_length_negative(self):
|
def test_http_header_content_length_negative(self):
|
||||||
self.load('empty')
|
self.load('empty')
|
||||||
|
|
||||||
self.assertEqual(self.post(headers={
|
self.assertEqual(
|
||||||
|
self.post(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Content-Length': '-100',
|
'Content-Length': '-100',
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
}, body='X' * 1000)['status'], 400, 'Content-Length negative')
|
},
|
||||||
|
body='X' * 1000,
|
||||||
|
)['status'],
|
||||||
|
400,
|
||||||
|
'Content-Length negative',
|
||||||
|
)
|
||||||
|
|
||||||
def test_http_header_content_length_text(self):
|
def test_http_header_content_length_text(self):
|
||||||
self.load('empty')
|
self.load('empty')
|
||||||
|
|
||||||
self.assertEqual(self.post(headers={
|
self.assertEqual(
|
||||||
|
self.post(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Content-Length': 'blah',
|
'Content-Length': 'blah',
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
}, body='X' * 1000)['status'], 400, 'Content-Length text')
|
},
|
||||||
|
body='X' * 1000,
|
||||||
|
)['status'],
|
||||||
|
400,
|
||||||
|
'Content-Length text',
|
||||||
|
)
|
||||||
|
|
||||||
def test_http_header_content_length_multiple_values(self):
|
def test_http_header_content_length_multiple_values(self):
|
||||||
self.load('empty')
|
self.load('empty')
|
||||||
|
|
||||||
self.assertEqual(self.post(headers={
|
self.assertEqual(
|
||||||
|
self.post(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Content-Length': '41, 42',
|
'Content-Length': '41, 42',
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
}, body='X' * 1000)['status'], 400, 'Content-Length multiple value')
|
},
|
||||||
|
body='X' * 1000,
|
||||||
|
)['status'],
|
||||||
|
400,
|
||||||
|
'Content-Length multiple value',
|
||||||
|
)
|
||||||
|
|
||||||
def test_http_header_content_length_multiple_fields(self):
|
def test_http_header_content_length_multiple_fields(self):
|
||||||
self.load('empty')
|
self.load('empty')
|
||||||
|
|
||||||
self.assertEqual(self.post(headers={
|
self.assertEqual(
|
||||||
|
self.post(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Content-Length': ['41', '42'],
|
'Content-Length': ['41', '42'],
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
}, body='X' * 1000)['status'], 400, 'Content-Length multiple fields')
|
},
|
||||||
|
body='X' * 1000,
|
||||||
|
)['status'],
|
||||||
|
400,
|
||||||
|
'Content-Length multiple fields',
|
||||||
|
)
|
||||||
|
|
||||||
def test_http_header_host_absent(self):
|
def test_http_header_host_absent(self):
|
||||||
self.load('host')
|
self.load('host')
|
||||||
@@ -218,146 +304,182 @@ Connection: close
|
|||||||
resp = self.get(headers={'Connection': 'close'})
|
resp = self.get(headers={'Connection': 'close'})
|
||||||
|
|
||||||
self.assertEqual(resp['status'], 200, 'Host absent status')
|
self.assertEqual(resp['status'], 200, 'Host absent status')
|
||||||
self.assertNotEqual(resp['headers']['X-Server-Name'], '',
|
self.assertNotEqual(
|
||||||
'Host absent SERVER_NAME')
|
resp['headers']['X-Server-Name'], '', 'Host absent SERVER_NAME'
|
||||||
|
)
|
||||||
|
|
||||||
def test_http_header_host_empty(self):
|
def test_http_header_host_empty(self):
|
||||||
self.load('host')
|
self.load('host')
|
||||||
|
|
||||||
resp = self.get(headers={
|
resp = self.get(headers={'Host': '', 'Connection': 'close'})
|
||||||
'Host': '',
|
|
||||||
'Connection': 'close'
|
|
||||||
})
|
|
||||||
|
|
||||||
self.assertEqual(resp['status'], 200, 'Host empty status')
|
self.assertEqual(resp['status'], 200, 'Host empty status')
|
||||||
self.assertNotEqual(resp['headers']['X-Server-Name'], '',
|
self.assertNotEqual(
|
||||||
'Host empty SERVER_NAME')
|
resp['headers']['X-Server-Name'], '', 'Host empty SERVER_NAME'
|
||||||
|
)
|
||||||
|
|
||||||
def test_http_header_host_big(self):
|
def test_http_header_host_big(self):
|
||||||
self.load('empty')
|
self.load('empty')
|
||||||
|
|
||||||
self.assertEqual(self.get(headers={
|
self.assertEqual(
|
||||||
'Host': 'X' * 10000,
|
self.get(headers={'Host': 'X' * 10000, 'Connection': 'close'})[
|
||||||
'Connection': 'close'
|
'status'
|
||||||
})['status'], 431, 'Host big')
|
],
|
||||||
|
431,
|
||||||
|
'Host big',
|
||||||
|
)
|
||||||
|
|
||||||
def test_http_header_host_port(self):
|
def test_http_header_host_port(self):
|
||||||
self.load('host')
|
self.load('host')
|
||||||
|
|
||||||
resp = self.get(headers={
|
resp = self.get(
|
||||||
'Host': 'exmaple.com:7080',
|
headers={'Host': 'exmaple.com:7080', 'Connection': 'close'}
|
||||||
'Connection': 'close'
|
)
|
||||||
})
|
|
||||||
|
|
||||||
self.assertEqual(resp['status'], 200, 'Host port status')
|
self.assertEqual(resp['status'], 200, 'Host port status')
|
||||||
self.assertEqual(resp['headers']['X-Server-Name'], 'exmaple.com',
|
self.assertEqual(
|
||||||
'Host port SERVER_NAME')
|
resp['headers']['X-Server-Name'],
|
||||||
self.assertEqual(resp['headers']['X-Http-Host'], 'exmaple.com:7080',
|
'exmaple.com',
|
||||||
'Host port HTTP_HOST')
|
'Host port SERVER_NAME',
|
||||||
|
)
|
||||||
|
self.assertEqual(
|
||||||
|
resp['headers']['X-Http-Host'],
|
||||||
|
'exmaple.com:7080',
|
||||||
|
'Host port HTTP_HOST',
|
||||||
|
)
|
||||||
|
|
||||||
def test_http_header_host_port_empty(self):
|
def test_http_header_host_port_empty(self):
|
||||||
self.load('host')
|
self.load('host')
|
||||||
|
|
||||||
resp = self.get(headers={
|
resp = self.get(
|
||||||
'Host': 'exmaple.com:',
|
headers={'Host': 'exmaple.com:', 'Connection': 'close'}
|
||||||
'Connection': 'close'
|
)
|
||||||
})
|
|
||||||
|
|
||||||
self.assertEqual(resp['status'], 200, 'Host port empty status')
|
self.assertEqual(resp['status'], 200, 'Host port empty status')
|
||||||
self.assertEqual(resp['headers']['X-Server-Name'], 'exmaple.com',
|
self.assertEqual(
|
||||||
'Host port empty SERVER_NAME')
|
resp['headers']['X-Server-Name'],
|
||||||
self.assertEqual(resp['headers']['X-Http-Host'], 'exmaple.com:',
|
'exmaple.com',
|
||||||
'Host port empty HTTP_HOST')
|
'Host port empty SERVER_NAME',
|
||||||
|
)
|
||||||
|
self.assertEqual(
|
||||||
|
resp['headers']['X-Http-Host'],
|
||||||
|
'exmaple.com:',
|
||||||
|
'Host port empty HTTP_HOST',
|
||||||
|
)
|
||||||
|
|
||||||
def test_http_header_host_literal(self):
|
def test_http_header_host_literal(self):
|
||||||
self.load('host')
|
self.load('host')
|
||||||
|
|
||||||
resp = self.get(headers={
|
resp = self.get(headers={'Host': '127.0.0.1', 'Connection': 'close'})
|
||||||
'Host': '127.0.0.1',
|
|
||||||
'Connection': 'close'
|
|
||||||
})
|
|
||||||
|
|
||||||
self.assertEqual(resp['status'], 200, 'Host literal status')
|
self.assertEqual(resp['status'], 200, 'Host literal status')
|
||||||
self.assertEqual(resp['headers']['X-Server-Name'], '127.0.0.1',
|
self.assertEqual(
|
||||||
'Host literal SERVER_NAME')
|
resp['headers']['X-Server-Name'],
|
||||||
|
'127.0.0.1',
|
||||||
|
'Host literal SERVER_NAME',
|
||||||
|
)
|
||||||
|
|
||||||
def test_http_header_host_literal_ipv6(self):
|
def test_http_header_host_literal_ipv6(self):
|
||||||
self.load('host')
|
self.load('host')
|
||||||
|
|
||||||
resp = self.get(headers={
|
resp = self.get(headers={'Host': '[::1]:7080', 'Connection': 'close'})
|
||||||
'Host': '[::1]:7080',
|
|
||||||
'Connection': 'close'
|
|
||||||
})
|
|
||||||
|
|
||||||
self.assertEqual(resp['status'], 200, 'Host literal ipv6 status')
|
self.assertEqual(resp['status'], 200, 'Host literal ipv6 status')
|
||||||
self.assertEqual(resp['headers']['X-Server-Name'], '[::1]',
|
self.assertEqual(
|
||||||
'Host literal ipv6 SERVER_NAME')
|
resp['headers']['X-Server-Name'],
|
||||||
self.assertEqual(resp['headers']['X-Http-Host'], '[::1]:7080',
|
'[::1]',
|
||||||
'Host literal ipv6 HTTP_HOST')
|
'Host literal ipv6 SERVER_NAME',
|
||||||
|
)
|
||||||
|
self.assertEqual(
|
||||||
|
resp['headers']['X-Http-Host'],
|
||||||
|
'[::1]:7080',
|
||||||
|
'Host literal ipv6 HTTP_HOST',
|
||||||
|
)
|
||||||
|
|
||||||
def test_http_header_host_trailing_period(self):
|
def test_http_header_host_trailing_period(self):
|
||||||
self.load('host')
|
self.load('host')
|
||||||
|
|
||||||
resp = self.get(headers={
|
resp = self.get(headers={'Host': '127.0.0.1.', 'Connection': 'close'})
|
||||||
'Host': '127.0.0.1.',
|
|
||||||
'Connection': 'close'
|
|
||||||
})
|
|
||||||
|
|
||||||
self.assertEqual(resp['status'], 200, 'Host trailing period status')
|
self.assertEqual(resp['status'], 200, 'Host trailing period status')
|
||||||
self.assertEqual(resp['headers']['X-Server-Name'], '127.0.0.1',
|
self.assertEqual(
|
||||||
'Host trailing period SERVER_NAME')
|
resp['headers']['X-Server-Name'],
|
||||||
self.assertEqual(resp['headers']['X-Http-Host'], '127.0.0.1.',
|
'127.0.0.1',
|
||||||
'Host trailing period HTTP_HOST')
|
'Host trailing period SERVER_NAME',
|
||||||
|
)
|
||||||
|
self.assertEqual(
|
||||||
|
resp['headers']['X-Http-Host'],
|
||||||
|
'127.0.0.1.',
|
||||||
|
'Host trailing period HTTP_HOST',
|
||||||
|
)
|
||||||
|
|
||||||
def test_http_header_host_trailing_period_2(self):
|
def test_http_header_host_trailing_period_2(self):
|
||||||
self.load('host')
|
self.load('host')
|
||||||
|
|
||||||
resp = self.get(headers={
|
resp = self.get(
|
||||||
'Host': 'EXAMPLE.COM.',
|
headers={'Host': 'EXAMPLE.COM.', 'Connection': 'close'}
|
||||||
'Connection': 'close'
|
)
|
||||||
})
|
|
||||||
|
|
||||||
self.assertEqual(resp['status'], 200, 'Host trailing period 2 status')
|
self.assertEqual(resp['status'], 200, 'Host trailing period 2 status')
|
||||||
self.assertEqual(resp['headers']['X-Server-Name'], 'example.com',
|
self.assertEqual(
|
||||||
'Host trailing period 2 SERVER_NAME')
|
resp['headers']['X-Server-Name'],
|
||||||
self.assertEqual(resp['headers']['X-Http-Host'], 'EXAMPLE.COM.',
|
'example.com',
|
||||||
'Host trailing period 2 HTTP_HOST')
|
'Host trailing period 2 SERVER_NAME',
|
||||||
|
)
|
||||||
|
self.assertEqual(
|
||||||
|
resp['headers']['X-Http-Host'],
|
||||||
|
'EXAMPLE.COM.',
|
||||||
|
'Host trailing period 2 HTTP_HOST',
|
||||||
|
)
|
||||||
|
|
||||||
def test_http_header_host_case_insensitive(self):
|
def test_http_header_host_case_insensitive(self):
|
||||||
self.load('host')
|
self.load('host')
|
||||||
|
|
||||||
resp = self.get(headers={
|
resp = self.get(headers={'Host': 'EXAMPLE.COM', 'Connection': 'close'})
|
||||||
'Host': 'EXAMPLE.COM',
|
|
||||||
'Connection': 'close'
|
|
||||||
})
|
|
||||||
|
|
||||||
self.assertEqual(resp['status'], 200, 'Host case insensitive')
|
self.assertEqual(resp['status'], 200, 'Host case insensitive')
|
||||||
self.assertEqual(resp['headers']['X-Server-Name'], 'example.com',
|
self.assertEqual(
|
||||||
'Host case insensitive SERVER_NAME')
|
resp['headers']['X-Server-Name'],
|
||||||
|
'example.com',
|
||||||
|
'Host case insensitive SERVER_NAME',
|
||||||
|
)
|
||||||
|
|
||||||
def test_http_header_host_double_dot(self):
|
def test_http_header_host_double_dot(self):
|
||||||
self.load('empty')
|
self.load('empty')
|
||||||
|
|
||||||
self.assertEqual(self.get(headers={
|
self.assertEqual(
|
||||||
'Host': '127.0.0..1',
|
self.get(headers={'Host': '127.0.0..1', 'Connection': 'close'})[
|
||||||
'Connection': 'close'
|
'status'
|
||||||
})['status'], 400, 'Host double dot')
|
],
|
||||||
|
400,
|
||||||
|
'Host double dot',
|
||||||
|
)
|
||||||
|
|
||||||
def test_http_header_host_slash(self):
|
def test_http_header_host_slash(self):
|
||||||
self.load('empty')
|
self.load('empty')
|
||||||
|
|
||||||
self.assertEqual(self.get(headers={
|
self.assertEqual(
|
||||||
'Host': '/localhost',
|
self.get(headers={'Host': '/localhost', 'Connection': 'close'})[
|
||||||
'Connection': 'close'
|
'status'
|
||||||
})['status'], 400, 'Host slash')
|
],
|
||||||
|
400,
|
||||||
|
'Host slash',
|
||||||
|
)
|
||||||
|
|
||||||
def test_http_header_host_multiple_fields(self):
|
def test_http_header_host_multiple_fields(self):
|
||||||
self.load('empty')
|
self.load('empty')
|
||||||
|
|
||||||
self.assertEqual(self.get(headers={
|
self.assertEqual(
|
||||||
|
self.get(
|
||||||
|
headers={
|
||||||
'Host': ['localhost', 'example.com'],
|
'Host': ['localhost', 'example.com'],
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
})['status'], 400, 'Host multiple fields')
|
}
|
||||||
|
)['status'],
|
||||||
|
400,
|
||||||
|
'Host multiple fields',
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
if __name__ == '__main__':
|
if __name__ == '__main__':
|
||||||
TestUnitHTTPHeader.main()
|
TestUnitHTTPHeader.main()
|
||||||
|
|||||||
File diff suppressed because it is too large
Load Diff
@@ -1,8 +1,8 @@
|
|||||||
import unittest
|
import unittest
|
||||||
import unit
|
import unit
|
||||||
|
|
||||||
class TestUnitNodeApplication(unit.TestUnitApplicationNode):
|
|
||||||
|
|
||||||
|
class TestUnitNodeApplication(unit.TestUnitApplicationNode):
|
||||||
def setUpClass():
|
def setUpClass():
|
||||||
u = unit.TestUnit().check_modules('node')
|
u = unit.TestUnit().check_modules('node')
|
||||||
|
|
||||||
@@ -10,8 +10,9 @@ class TestUnitNodeApplication(unit.TestUnitApplicationNode):
|
|||||||
self.load('basic')
|
self.load('basic')
|
||||||
|
|
||||||
resp = self.get()
|
resp = self.get()
|
||||||
self.assertEqual(resp['headers']['Content-Type'], 'text/plain',
|
self.assertEqual(
|
||||||
'basic header')
|
resp['headers']['Content-Type'], 'text/plain', 'basic header'
|
||||||
|
)
|
||||||
self.assertEqual(resp['body'], 'Hello World\n', 'basic body')
|
self.assertEqual(resp['body'], 'Hello World\n', 'basic body')
|
||||||
|
|
||||||
def test_node_application_seq(self):
|
def test_node_application_seq(self):
|
||||||
@@ -25,12 +26,15 @@ class TestUnitNodeApplication(unit.TestUnitApplicationNode):
|
|||||||
|
|
||||||
body = 'Test body string.'
|
body = 'Test body string.'
|
||||||
|
|
||||||
resp = self.post(headers={
|
resp = self.post(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Content-Type': 'text/html',
|
'Content-Type': 'text/html',
|
||||||
'Custom-Header': 'blah',
|
'Custom-Header': 'blah',
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
}, body=body)
|
},
|
||||||
|
body=body,
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(resp['status'], 200, 'status')
|
self.assertEqual(resp['status'], 200, 'status')
|
||||||
headers = resp['headers']
|
headers = resp['headers']
|
||||||
@@ -39,15 +43,24 @@ class TestUnitNodeApplication(unit.TestUnitApplicationNode):
|
|||||||
|
|
||||||
date = headers.pop('Date')
|
date = headers.pop('Date')
|
||||||
self.assertEqual(date[-4:], ' GMT', 'date header timezone')
|
self.assertEqual(date[-4:], ' GMT', 'date header timezone')
|
||||||
self.assertLess(abs(self.date_to_sec_epoch(date) - self.sec_epoch()), 5,
|
self.assertLess(
|
||||||
'date header')
|
abs(self.date_to_sec_epoch(date) - self.sec_epoch()),
|
||||||
|
5,
|
||||||
|
'date header',
|
||||||
|
)
|
||||||
|
|
||||||
raw_headers = headers.pop('Request-Raw-Headers')
|
raw_headers = headers.pop('Request-Raw-Headers')
|
||||||
self.assertRegex(raw_headers, r'^(?:Host|localhost|Content-Type|' \
|
self.assertRegex(
|
||||||
'text\/html|Custom-Header|blah|Content-Length|17|Connection|' \
|
raw_headers,
|
||||||
'close|,)+$', 'raw headers')
|
r'^(?:Host|localhost|Content-Type|'
|
||||||
|
'text\/html|Custom-Header|blah|Content-Length|17|Connection|'
|
||||||
|
'close|,)+$',
|
||||||
|
'raw headers',
|
||||||
|
)
|
||||||
|
|
||||||
self.assertDictEqual(headers, {
|
self.assertDictEqual(
|
||||||
|
headers,
|
||||||
|
{
|
||||||
'Connection': 'close',
|
'Connection': 'close',
|
||||||
'Content-Length': str(len(body)),
|
'Content-Length': str(len(body)),
|
||||||
'Content-Type': 'text/html',
|
'Content-Type': 'text/html',
|
||||||
@@ -55,8 +68,10 @@ class TestUnitNodeApplication(unit.TestUnitApplicationNode):
|
|||||||
'Request-Uri': '/',
|
'Request-Uri': '/',
|
||||||
'Http-Host': 'localhost',
|
'Http-Host': 'localhost',
|
||||||
'Server-Protocol': 'HTTP/1.1',
|
'Server-Protocol': 'HTTP/1.1',
|
||||||
'Custom-Header': 'blah'
|
'Custom-Header': 'blah',
|
||||||
}, 'headers')
|
},
|
||||||
|
'headers',
|
||||||
|
)
|
||||||
self.assertEqual(resp['body'], body, 'body')
|
self.assertEqual(resp['body'], body, 'body')
|
||||||
|
|
||||||
def test_node_application_get_variables(self):
|
def test_node_application_get_variables(self):
|
||||||
@@ -70,11 +85,14 @@ class TestUnitNodeApplication(unit.TestUnitApplicationNode):
|
|||||||
def test_node_application_post_variables(self):
|
def test_node_application_post_variables(self):
|
||||||
self.load('post_variables')
|
self.load('post_variables')
|
||||||
|
|
||||||
resp = self.post(headers={
|
resp = self.post(
|
||||||
|
headers={
|
||||||
'Content-Type': 'application/x-www-form-urlencoded',
|
'Content-Type': 'application/x-www-form-urlencoded',
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
}, body='var1=val1&var2=&var3')
|
},
|
||||||
|
body='var1=val1&var2=&var3',
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(resp['headers']['X-Var-1'], 'val1', 'POST variables')
|
self.assertEqual(resp['headers']['X-Var-1'], 'val1', 'POST variables')
|
||||||
self.assertEqual(resp['headers']['X-Var-2'], '', 'POST variables 2')
|
self.assertEqual(resp['headers']['X-Var-2'], '', 'POST variables 2')
|
||||||
@@ -86,41 +104,56 @@ class TestUnitNodeApplication(unit.TestUnitApplicationNode):
|
|||||||
resp = self.get()
|
resp = self.get()
|
||||||
|
|
||||||
self.assertEqual(resp['status'], 404, '404 status')
|
self.assertEqual(resp['status'], 404, '404 status')
|
||||||
self.assertRegex(resp['body'], r'<title>404 Not Found</title>',
|
self.assertRegex(
|
||||||
'404 body')
|
resp['body'], r'<title>404 Not Found</title>', '404 body'
|
||||||
|
)
|
||||||
|
|
||||||
def test_node_keepalive_body(self):
|
def test_node_keepalive_body(self):
|
||||||
self.load('mirror')
|
self.load('mirror')
|
||||||
|
|
||||||
(resp, sock) = self.post(headers={
|
(resp, sock) = self.post(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Connection': 'keep-alive',
|
'Connection': 'keep-alive',
|
||||||
'Content-Type': 'text/html'
|
'Content-Type': 'text/html',
|
||||||
}, start=True, body='0123456789' * 500)
|
},
|
||||||
|
start=True,
|
||||||
|
body='0123456789' * 500,
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(resp['body'], '0123456789' * 500, 'keep-alive 1')
|
self.assertEqual(resp['body'], '0123456789' * 500, 'keep-alive 1')
|
||||||
|
|
||||||
resp = self.post(headers={
|
resp = self.post(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Connection': 'close',
|
'Connection': 'close',
|
||||||
'Content-Type': 'text/html'
|
'Content-Type': 'text/html',
|
||||||
}, sock=sock, body='0123456789')
|
},
|
||||||
|
sock=sock,
|
||||||
|
body='0123456789',
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(resp['body'], '0123456789', 'keep-alive 2')
|
self.assertEqual(resp['body'], '0123456789', 'keep-alive 2')
|
||||||
|
|
||||||
def test_node_application_write_buffer(self):
|
def test_node_application_write_buffer(self):
|
||||||
self.load('write_buffer')
|
self.load('write_buffer')
|
||||||
|
|
||||||
self.assertEqual(self.get()['body'], '6\r\nbuffer\r\n0\r\n\r\n',
|
self.assertEqual(
|
||||||
'write buffer')
|
self.get()['body'], '6\r\nbuffer\r\n0\r\n\r\n', 'write buffer'
|
||||||
|
)
|
||||||
|
|
||||||
def test_node_application_write_callback(self):
|
def test_node_application_write_callback(self):
|
||||||
self.load('write_callback')
|
self.load('write_callback')
|
||||||
|
|
||||||
self.assertEqual(self.get()['body'],
|
self.assertEqual(
|
||||||
'5\r\nhello\r\n5\r\nworld\r\n0\r\n\r\n', 'write callback order')
|
self.get()['body'],
|
||||||
self.assertTrue(self.waitforfiles(self.testdir + '/node/callback'),
|
'5\r\nhello\r\n5\r\nworld\r\n0\r\n\r\n',
|
||||||
'write callback')
|
'write callback order',
|
||||||
|
)
|
||||||
|
self.assertTrue(
|
||||||
|
self.waitforfiles(self.testdir + '/node/callback'),
|
||||||
|
'write callback',
|
||||||
|
)
|
||||||
|
|
||||||
def test_node_application_write_before_write_head(self):
|
def test_node_application_write_before_write_head(self):
|
||||||
self.load('write_before_write_head')
|
self.load('write_before_write_head')
|
||||||
@@ -136,17 +169,22 @@ class TestUnitNodeApplication(unit.TestUnitApplicationNode):
|
|||||||
def test_node_application_write_return(self):
|
def test_node_application_write_return(self):
|
||||||
self.load('write_return')
|
self.load('write_return')
|
||||||
|
|
||||||
self.assertEqual(self.get()['body'],
|
self.assertEqual(
|
||||||
'4\r\nbody\r\n4\r\ntrue\r\n0\r\n\r\n', 'write return')
|
self.get()['body'],
|
||||||
|
'4\r\nbody\r\n4\r\ntrue\r\n0\r\n\r\n',
|
||||||
|
'write return',
|
||||||
|
)
|
||||||
|
|
||||||
def test_node_application_remove_header(self):
|
def test_node_application_remove_header(self):
|
||||||
self.load('remove_header')
|
self.load('remove_header')
|
||||||
|
|
||||||
resp = self.get(headers={
|
resp = self.get(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'X-Remove': 'X-Header',
|
'X-Remove': 'X-Header',
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
})
|
}
|
||||||
|
)
|
||||||
self.assertEqual(resp['headers']['Was-Header'], 'true', 'was header')
|
self.assertEqual(resp['headers']['Was-Header'], 'true', 'was header')
|
||||||
self.assertEqual(resp['headers']['Has-Header'], 'false', 'has header')
|
self.assertEqual(resp['headers']['Has-Header'], 'false', 'has header')
|
||||||
self.assertFalse('X-Header' in resp['headers'], 'remove header')
|
self.assertFalse('X-Header' in resp['headers'], 'remove header')
|
||||||
@@ -154,35 +192,48 @@ class TestUnitNodeApplication(unit.TestUnitApplicationNode):
|
|||||||
def test_node_application_remove_header_nonexisting(self):
|
def test_node_application_remove_header_nonexisting(self):
|
||||||
self.load('remove_header')
|
self.load('remove_header')
|
||||||
|
|
||||||
self.assertEqual(self.get(headers={
|
self.assertEqual(
|
||||||
|
self.get(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'X-Remove': 'blah',
|
'X-Remove': 'blah',
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
})['headers']['Has-Header'], 'true', 'remove header nonexisting')
|
}
|
||||||
|
)['headers']['Has-Header'],
|
||||||
|
'true',
|
||||||
|
'remove header nonexisting',
|
||||||
|
)
|
||||||
|
|
||||||
def test_node_application_update_header(self):
|
def test_node_application_update_header(self):
|
||||||
self.load('update_header')
|
self.load('update_header')
|
||||||
|
|
||||||
self.assertEqual(self.get()['headers']['X-Header'], 'new',
|
self.assertEqual(
|
||||||
'update header')
|
self.get()['headers']['X-Header'], 'new', 'update header'
|
||||||
|
)
|
||||||
|
|
||||||
def test_node_application_set_header_array(self):
|
def test_node_application_set_header_array(self):
|
||||||
self.load('set_header_array')
|
self.load('set_header_array')
|
||||||
|
|
||||||
self.assertListEqual(self.get()['headers']['Set-Cookie'],
|
self.assertListEqual(
|
||||||
['tc=one,two,three', 'tc=four,five,six'], 'set header array')
|
self.get()['headers']['Set-Cookie'],
|
||||||
|
['tc=one,two,three', 'tc=four,five,six'],
|
||||||
|
'set header array',
|
||||||
|
)
|
||||||
|
|
||||||
@unittest.expectedFailure
|
@unittest.expectedFailure
|
||||||
def test_node_application_status_message(self):
|
def test_node_application_status_message(self):
|
||||||
self.load('status_message')
|
self.load('status_message')
|
||||||
|
|
||||||
self.assertRegex(self.get(raw_resp=True), r'200 blah', 'status message')
|
self.assertRegex(
|
||||||
|
self.get(raw_resp=True), r'200 blah', 'status message'
|
||||||
|
)
|
||||||
|
|
||||||
def test_node_application_get_header_type(self):
|
def test_node_application_get_header_type(self):
|
||||||
self.load('get_header_type')
|
self.load('get_header_type')
|
||||||
|
|
||||||
self.assertEqual(self.get()['headers']['X-Type'], 'number',
|
self.assertEqual(
|
||||||
'get header type')
|
self.get()['headers']['X-Type'], 'number', 'get header type'
|
||||||
|
)
|
||||||
|
|
||||||
def test_node_application_header_name_case(self):
|
def test_node_application_header_name_case(self):
|
||||||
self.load('header_name_case')
|
self.load('header_name_case')
|
||||||
@@ -196,56 +247,89 @@ class TestUnitNodeApplication(unit.TestUnitApplicationNode):
|
|||||||
def test_node_application_promise_handler(self):
|
def test_node_application_promise_handler(self):
|
||||||
self.load('promise_handler')
|
self.load('promise_handler')
|
||||||
|
|
||||||
self.assertEqual(self.post(headers={
|
self.assertEqual(
|
||||||
|
self.post(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Content-Type': 'text/html',
|
'Content-Type': 'text/html',
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
}, body='callback')['status'], 200, 'promise handler request')
|
},
|
||||||
self.assertTrue(self.waitforfiles(self.testdir + '/node/callback'),
|
body='callback',
|
||||||
'promise handler')
|
)['status'],
|
||||||
|
200,
|
||||||
|
'promise handler request',
|
||||||
|
)
|
||||||
|
self.assertTrue(
|
||||||
|
self.waitforfiles(self.testdir + '/node/callback'),
|
||||||
|
'promise handler',
|
||||||
|
)
|
||||||
|
|
||||||
def test_node_application_promise_handler_write_after_end(self):
|
def test_node_application_promise_handler_write_after_end(self):
|
||||||
self.load('promise_handler')
|
self.load('promise_handler')
|
||||||
|
|
||||||
self.assertEqual(self.post(headers={
|
self.assertEqual(
|
||||||
|
self.post(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Content-Type': 'text/html',
|
'Content-Type': 'text/html',
|
||||||
'X-Write-Call': '1',
|
'X-Write-Call': '1',
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
}, body='callback')['status'], 200,
|
},
|
||||||
'promise handler request write after end')
|
body='callback',
|
||||||
|
)['status'],
|
||||||
|
200,
|
||||||
|
'promise handler request write after end',
|
||||||
|
)
|
||||||
|
|
||||||
def test_node_application_promise_end(self):
|
def test_node_application_promise_end(self):
|
||||||
self.load('promise_end')
|
self.load('promise_end')
|
||||||
|
|
||||||
self.assertEqual(self.post(headers={
|
self.assertEqual(
|
||||||
|
self.post(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Content-Type': 'text/html',
|
'Content-Type': 'text/html',
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
}, body='end')['status'], 200, 'promise end request')
|
},
|
||||||
self.assertTrue(self.waitforfiles(self.testdir + '/node/callback'),
|
body='end',
|
||||||
'promise end')
|
)['status'],
|
||||||
|
200,
|
||||||
|
'promise end request',
|
||||||
|
)
|
||||||
|
self.assertTrue(
|
||||||
|
self.waitforfiles(self.testdir + '/node/callback'), 'promise end'
|
||||||
|
)
|
||||||
|
|
||||||
def test_node_application_promise_multiple_calls(self):
|
def test_node_application_promise_multiple_calls(self):
|
||||||
self.load('promise_handler')
|
self.load('promise_handler')
|
||||||
|
|
||||||
self.post(headers={
|
self.post(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Content-Type': 'text/html',
|
'Content-Type': 'text/html',
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
}, body='callback1')
|
},
|
||||||
|
body='callback1',
|
||||||
|
)
|
||||||
|
|
||||||
self.assertTrue(self.waitforfiles(self.testdir + '/node/callback1'),
|
self.assertTrue(
|
||||||
'promise first call')
|
self.waitforfiles(self.testdir + '/node/callback1'),
|
||||||
|
'promise first call',
|
||||||
|
)
|
||||||
|
|
||||||
self.post(headers={
|
self.post(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Content-Type': 'text/html',
|
'Content-Type': 'text/html',
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
}, body='callback2')
|
},
|
||||||
|
body='callback2',
|
||||||
|
)
|
||||||
|
|
||||||
self.assertTrue(self.waitforfiles(self.testdir + '/node/callback2'),
|
self.assertTrue(
|
||||||
'promise second call')
|
self.waitforfiles(self.testdir + '/node/callback2'),
|
||||||
|
'promise second call',
|
||||||
|
)
|
||||||
|
|
||||||
@unittest.expectedFailure
|
@unittest.expectedFailure
|
||||||
def test_node_application_header_name_valid(self):
|
def test_node_application_header_name_valid(self):
|
||||||
@@ -261,28 +345,46 @@ class TestUnitNodeApplication(unit.TestUnitApplicationNode):
|
|||||||
def test_node_application_get_header_names(self):
|
def test_node_application_get_header_names(self):
|
||||||
self.load('get_header_names')
|
self.load('get_header_names')
|
||||||
|
|
||||||
self.assertListEqual(self.get()['headers']['X-Names'],
|
self.assertListEqual(
|
||||||
['date', 'x-header'], 'get header names')
|
self.get()['headers']['X-Names'],
|
||||||
|
['date', 'x-header'],
|
||||||
|
'get header names',
|
||||||
|
)
|
||||||
|
|
||||||
def test_node_application_has_header(self):
|
def test_node_application_has_header(self):
|
||||||
self.load('has_header')
|
self.load('has_header')
|
||||||
|
|
||||||
self.assertEqual(self.get(headers={
|
self.assertEqual(
|
||||||
|
self.get(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'X-Header': 'length',
|
'X-Header': 'length',
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
})['headers']['X-Has-Header'], 'false', 'has header length')
|
}
|
||||||
|
)['headers']['X-Has-Header'],
|
||||||
|
'false',
|
||||||
|
'has header length',
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(self.get(headers={
|
self.assertEqual(
|
||||||
|
self.get(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'X-Header': 'Date',
|
'X-Header': 'Date',
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
})['headers']['X-Has-Header'], 'false', 'has header date')
|
}
|
||||||
|
)['headers']['X-Has-Header'],
|
||||||
|
'false',
|
||||||
|
'has header date',
|
||||||
|
)
|
||||||
|
|
||||||
def test_node_application_write_multiple(self):
|
def test_node_application_write_multiple(self):
|
||||||
self.load('write_multiple')
|
self.load('write_multiple')
|
||||||
|
|
||||||
self.assertEqual(self.get()['body'], 'writewrite2end', 'write multiple')
|
self.assertEqual(
|
||||||
|
self.get()['body'], 'writewrite2end', 'write multiple'
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
if __name__ == '__main__':
|
if __name__ == '__main__':
|
||||||
TestUnitNodeApplication.main()
|
TestUnitNodeApplication.main()
|
||||||
|
|||||||
@@ -1,8 +1,8 @@
|
|||||||
import unittest
|
import unittest
|
||||||
import unit
|
import unit
|
||||||
|
|
||||||
class TestUnitPerlApplication(unit.TestUnitApplicationPerl):
|
|
||||||
|
|
||||||
|
class TestUnitPerlApplication(unit.TestUnitApplicationPerl):
|
||||||
def setUpClass():
|
def setUpClass():
|
||||||
unit.TestUnit().check_modules('perl')
|
unit.TestUnit().check_modules('perl')
|
||||||
|
|
||||||
@@ -11,26 +11,37 @@ class TestUnitPerlApplication(unit.TestUnitApplicationPerl):
|
|||||||
|
|
||||||
body = 'Test body string.'
|
body = 'Test body string.'
|
||||||
|
|
||||||
resp = self.post(headers={
|
resp = self.post(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Content-Type': 'text/html',
|
'Content-Type': 'text/html',
|
||||||
'Custom-Header': 'blah',
|
'Custom-Header': 'blah',
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
}, body=body)
|
},
|
||||||
|
body=body,
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(resp['status'], 200, 'status')
|
self.assertEqual(resp['status'], 200, 'status')
|
||||||
headers = resp['headers']
|
headers = resp['headers']
|
||||||
header_server = headers.pop('Server')
|
header_server = headers.pop('Server')
|
||||||
self.assertRegex(header_server, r'Unit/[\d\.]+', 'server header')
|
self.assertRegex(header_server, r'Unit/[\d\.]+', 'server header')
|
||||||
self.assertEqual(headers.pop('Server-Software'), header_server,
|
self.assertEqual(
|
||||||
'server software header')
|
headers.pop('Server-Software'),
|
||||||
|
header_server,
|
||||||
|
'server software header',
|
||||||
|
)
|
||||||
|
|
||||||
date = headers.pop('Date')
|
date = headers.pop('Date')
|
||||||
self.assertEqual(date[-4:], ' GMT', 'date header timezone')
|
self.assertEqual(date[-4:], ' GMT', 'date header timezone')
|
||||||
self.assertLess(abs(self.date_to_sec_epoch(date) - self.sec_epoch()), 5,
|
self.assertLess(
|
||||||
'date header')
|
abs(self.date_to_sec_epoch(date) - self.sec_epoch()),
|
||||||
|
5,
|
||||||
|
'date header',
|
||||||
|
)
|
||||||
|
|
||||||
self.assertDictEqual(headers, {
|
self.assertDictEqual(
|
||||||
|
headers,
|
||||||
|
{
|
||||||
'Connection': 'close',
|
'Connection': 'close',
|
||||||
'Content-Length': str(len(body)),
|
'Content-Length': str(len(body)),
|
||||||
'Content-Type': 'text/html',
|
'Content-Type': 'text/html',
|
||||||
@@ -45,8 +56,10 @@ class TestUnitPerlApplication(unit.TestUnitApplicationPerl):
|
|||||||
'Psgi-Multiprocess': '1',
|
'Psgi-Multiprocess': '1',
|
||||||
'Psgi-Run-Once': '',
|
'Psgi-Run-Once': '',
|
||||||
'Psgi-Nonblocking': '',
|
'Psgi-Nonblocking': '',
|
||||||
'Psgi-Streaming': '1'
|
'Psgi-Streaming': '1',
|
||||||
}, 'headers')
|
},
|
||||||
|
'headers',
|
||||||
|
)
|
||||||
self.assertEqual(resp['body'], body, 'body')
|
self.assertEqual(resp['body'], body, 'body')
|
||||||
|
|
||||||
def test_perl_application_query_string(self):
|
def test_perl_application_query_string(self):
|
||||||
@@ -54,8 +67,11 @@ class TestUnitPerlApplication(unit.TestUnitApplicationPerl):
|
|||||||
|
|
||||||
resp = self.get(url='/?var1=val1&var2=val2')
|
resp = self.get(url='/?var1=val1&var2=val2')
|
||||||
|
|
||||||
self.assertEqual(resp['headers']['Query-String'], 'var1=val1&var2=val2',
|
self.assertEqual(
|
||||||
'Query-String header')
|
resp['headers']['Query-String'],
|
||||||
|
'var1=val1&var2=val2',
|
||||||
|
'Query-String header',
|
||||||
|
)
|
||||||
|
|
||||||
def test_perl_application_query_string_empty(self):
|
def test_perl_application_query_string_empty(self):
|
||||||
self.load('query_string')
|
self.load('query_string')
|
||||||
@@ -63,8 +79,9 @@ class TestUnitPerlApplication(unit.TestUnitApplicationPerl):
|
|||||||
resp = self.get(url='/?')
|
resp = self.get(url='/?')
|
||||||
|
|
||||||
self.assertEqual(resp['status'], 200, 'query string empty status')
|
self.assertEqual(resp['status'], 200, 'query string empty status')
|
||||||
self.assertEqual(resp['headers']['Query-String'], '',
|
self.assertEqual(
|
||||||
'query string empty')
|
resp['headers']['Query-String'], '', 'query string empty'
|
||||||
|
)
|
||||||
|
|
||||||
@unittest.expectedFailure
|
@unittest.expectedFailure
|
||||||
def test_perl_application_query_string_absent(self):
|
def test_perl_application_query_string_absent(self):
|
||||||
@@ -73,15 +90,17 @@ class TestUnitPerlApplication(unit.TestUnitApplicationPerl):
|
|||||||
resp = self.get()
|
resp = self.get()
|
||||||
|
|
||||||
self.assertEqual(resp['status'], 200, 'query string absent status')
|
self.assertEqual(resp['status'], 200, 'query string absent status')
|
||||||
self.assertEqual(resp['headers']['Query-String'], '',
|
self.assertEqual(
|
||||||
'query string absent')
|
resp['headers']['Query-String'], '', 'query string absent'
|
||||||
|
)
|
||||||
|
|
||||||
@unittest.expectedFailure
|
@unittest.expectedFailure
|
||||||
def test_perl_application_server_port(self):
|
def test_perl_application_server_port(self):
|
||||||
self.load('server_port')
|
self.load('server_port')
|
||||||
|
|
||||||
self.assertEqual(self.get()['headers']['Server-Port'], '7080',
|
self.assertEqual(
|
||||||
'Server-Port header')
|
self.get()['headers']['Server-Port'], '7080', 'Server-Port header'
|
||||||
|
)
|
||||||
|
|
||||||
def test_perl_application_input_read_empty(self):
|
def test_perl_application_input_read_empty(self):
|
||||||
self.load('input_read_empty')
|
self.load('input_read_empty')
|
||||||
@@ -91,15 +110,19 @@ class TestUnitPerlApplication(unit.TestUnitApplicationPerl):
|
|||||||
def test_perl_application_input_read_parts(self):
|
def test_perl_application_input_read_parts(self):
|
||||||
self.load('input_read_parts')
|
self.load('input_read_parts')
|
||||||
|
|
||||||
self.assertEqual(self.post(body='0123456789')['body'], '0123456789',
|
self.assertEqual(
|
||||||
'input read parts')
|
self.post(body='0123456789')['body'],
|
||||||
|
'0123456789',
|
||||||
|
'input read parts',
|
||||||
|
)
|
||||||
|
|
||||||
@unittest.expectedFailure
|
@unittest.expectedFailure
|
||||||
def test_perl_application_input_read_offset(self):
|
def test_perl_application_input_read_offset(self):
|
||||||
self.load('input_read_offset')
|
self.load('input_read_offset')
|
||||||
|
|
||||||
self.assertEqual(self.post(body='0123456789')['body'], '4567',
|
self.assertEqual(
|
||||||
'read offset')
|
self.post(body='0123456789')['body'], '4567', 'read offset'
|
||||||
|
)
|
||||||
|
|
||||||
def test_perl_application_input_copy(self):
|
def test_perl_application_input_copy(self):
|
||||||
self.load('input_copy')
|
self.load('input_copy')
|
||||||
@@ -116,13 +139,17 @@ class TestUnitPerlApplication(unit.TestUnitApplicationPerl):
|
|||||||
|
|
||||||
self.assertIsNotNone(
|
self.assertIsNotNone(
|
||||||
self.search_in_log(r'\[error\].+Error in application'),
|
self.search_in_log(r'\[error\].+Error in application'),
|
||||||
'errors print')
|
'errors print',
|
||||||
|
)
|
||||||
|
|
||||||
def test_perl_application_header_equal_names(self):
|
def test_perl_application_header_equal_names(self):
|
||||||
self.load('header_equal_names')
|
self.load('header_equal_names')
|
||||||
|
|
||||||
self.assertListEqual(self.get()['headers']['Set-Cookie'],
|
self.assertListEqual(
|
||||||
['tc=one,two,three', 'tc=four,five,six'], 'header equal names')
|
self.get()['headers']['Set-Cookie'],
|
||||||
|
['tc=one,two,three', 'tc=four,five,six'],
|
||||||
|
'header equal names',
|
||||||
|
)
|
||||||
|
|
||||||
def test_perl_application_header_pairs(self):
|
def test_perl_application_header_pairs(self):
|
||||||
self.load('header_pairs')
|
self.load('header_pairs')
|
||||||
@@ -160,10 +187,9 @@ class TestUnitPerlApplication(unit.TestUnitApplicationPerl):
|
|||||||
|
|
||||||
@unittest.expectedFailure
|
@unittest.expectedFailure
|
||||||
def test_perl_application_syntax_error(self):
|
def test_perl_application_syntax_error(self):
|
||||||
self.skip_alerts.extend([
|
self.skip_alerts.extend(
|
||||||
r'PSGI: Failed to parse script',
|
[r'PSGI: Failed to parse script', r'process \d+ exited on signal']
|
||||||
r'process \d+ exited on signal'
|
)
|
||||||
])
|
|
||||||
self.load('syntax_error')
|
self.load('syntax_error')
|
||||||
|
|
||||||
self.assertEqual(self.get()['status'], 500, 'syntax error')
|
self.assertEqual(self.get()['status'], 500, 'syntax error')
|
||||||
@@ -171,19 +197,27 @@ class TestUnitPerlApplication(unit.TestUnitApplicationPerl):
|
|||||||
def test_perl_keepalive_body(self):
|
def test_perl_keepalive_body(self):
|
||||||
self.load('variables')
|
self.load('variables')
|
||||||
|
|
||||||
(resp, sock) = self.post(headers={
|
(resp, sock) = self.post(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Connection': 'keep-alive',
|
'Connection': 'keep-alive',
|
||||||
'Content-Type': 'text/html'
|
'Content-Type': 'text/html',
|
||||||
}, start=True, body='0123456789' * 500)
|
},
|
||||||
|
start=True,
|
||||||
|
body='0123456789' * 500,
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(resp['body'], '0123456789' * 500, 'keep-alive 1')
|
self.assertEqual(resp['body'], '0123456789' * 500, 'keep-alive 1')
|
||||||
|
|
||||||
resp = self.post(headers={
|
resp = self.post(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Connection': 'close',
|
'Connection': 'close',
|
||||||
'Content-Type': 'text/html'
|
'Content-Type': 'text/html',
|
||||||
}, sock=sock, body='0123456789')
|
},
|
||||||
|
sock=sock,
|
||||||
|
body='0123456789',
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(resp['body'], '0123456789', 'keep-alive 2')
|
self.assertEqual(resp['body'], '0123456789', 'keep-alive 2')
|
||||||
|
|
||||||
@@ -194,11 +228,13 @@ class TestUnitPerlApplication(unit.TestUnitApplicationPerl):
|
|||||||
|
|
||||||
self.assertIsNotNone(
|
self.assertIsNotNone(
|
||||||
self.search_in_log(r'\[error\].+IOFake getline\(\) \$\/ is \d+'),
|
self.search_in_log(r'\[error\].+IOFake getline\(\) \$\/ is \d+'),
|
||||||
'body io fake $/ value')
|
'body io fake $/ value',
|
||||||
|
)
|
||||||
|
|
||||||
self.assertIsNotNone(
|
self.assertIsNotNone(
|
||||||
self.search_in_log(r'\[error\].+IOFake close\(\) called'),
|
self.search_in_log(r'\[error\].+IOFake close\(\) called'),
|
||||||
'body io fake close')
|
'body io fake close',
|
||||||
|
)
|
||||||
|
|
||||||
def test_perl_delayed_response(self):
|
def test_perl_delayed_response(self):
|
||||||
self.load('delayed_response')
|
self.load('delayed_response')
|
||||||
@@ -216,5 +252,6 @@ class TestUnitPerlApplication(unit.TestUnitApplicationPerl):
|
|||||||
self.assertEqual(resp['status'], 200, 'status')
|
self.assertEqual(resp['status'], 200, 'status')
|
||||||
self.assertEqual(resp['body'], 'Hello World!', 'body')
|
self.assertEqual(resp['body'], 'Hello World!', 'body')
|
||||||
|
|
||||||
|
|
||||||
if __name__ == '__main__':
|
if __name__ == '__main__':
|
||||||
TestUnitPerlApplication.main()
|
TestUnitPerlApplication.main()
|
||||||
|
|||||||
@@ -2,8 +2,8 @@ import unittest
|
|||||||
import unit
|
import unit
|
||||||
import re
|
import re
|
||||||
|
|
||||||
class TestUnitPHPApplication(unit.TestUnitApplicationPHP):
|
|
||||||
|
|
||||||
|
class TestUnitPHPApplication(unit.TestUnitApplicationPHP):
|
||||||
def setUpClass():
|
def setUpClass():
|
||||||
unit.TestUnit().check_modules('php')
|
unit.TestUnit().check_modules('php')
|
||||||
|
|
||||||
@@ -18,38 +18,51 @@ class TestUnitPHPApplication(unit.TestUnitApplicationPHP):
|
|||||||
|
|
||||||
body = 'Test body string.'
|
body = 'Test body string.'
|
||||||
|
|
||||||
resp = self.post(headers={
|
resp = self.post(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Content-Type': 'text/html',
|
'Content-Type': 'text/html',
|
||||||
'Custom-Header': 'blah',
|
'Custom-Header': 'blah',
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
}, body=body)
|
},
|
||||||
|
body=body,
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(resp['status'], 200, 'status')
|
self.assertEqual(resp['status'], 200, 'status')
|
||||||
headers = resp['headers']
|
headers = resp['headers']
|
||||||
header_server = headers.pop('Server')
|
header_server = headers.pop('Server')
|
||||||
self.assertRegex(header_server, r'Unit/[\d\.]+', 'server header')
|
self.assertRegex(header_server, r'Unit/[\d\.]+', 'server header')
|
||||||
self.assertEqual(headers.pop('Server-Software'), header_server,
|
self.assertEqual(
|
||||||
'server software header')
|
headers.pop('Server-Software'),
|
||||||
|
header_server,
|
||||||
|
'server software header',
|
||||||
|
)
|
||||||
|
|
||||||
date = headers.pop('Date')
|
date = headers.pop('Date')
|
||||||
self.assertEqual(date[-4:], ' GMT', 'date header timezone')
|
self.assertEqual(date[-4:], ' GMT', 'date header timezone')
|
||||||
self.assertLess(abs(self.date_to_sec_epoch(date) - self.sec_epoch()), 5,
|
self.assertLess(
|
||||||
'date header')
|
abs(self.date_to_sec_epoch(date) - self.sec_epoch()),
|
||||||
|
5,
|
||||||
|
'date header',
|
||||||
|
)
|
||||||
|
|
||||||
if 'X-Powered-By' in headers:
|
if 'X-Powered-By' in headers:
|
||||||
headers.pop('X-Powered-By')
|
headers.pop('X-Powered-By')
|
||||||
|
|
||||||
headers.pop('Content-type')
|
headers.pop('Content-type')
|
||||||
self.assertDictEqual(headers, {
|
self.assertDictEqual(
|
||||||
|
headers,
|
||||||
|
{
|
||||||
'Connection': 'close',
|
'Connection': 'close',
|
||||||
'Content-Length': str(len(body)),
|
'Content-Length': str(len(body)),
|
||||||
'Request-Method': 'POST',
|
'Request-Method': 'POST',
|
||||||
'Request-Uri': '/',
|
'Request-Uri': '/',
|
||||||
'Http-Host': 'localhost',
|
'Http-Host': 'localhost',
|
||||||
'Server-Protocol': 'HTTP/1.1',
|
'Server-Protocol': 'HTTP/1.1',
|
||||||
'Custom-Header': 'blah'
|
'Custom-Header': 'blah',
|
||||||
}, 'headers')
|
},
|
||||||
|
'headers',
|
||||||
|
)
|
||||||
self.assertEqual(resp['body'], body, 'body')
|
self.assertEqual(resp['body'], body, 'body')
|
||||||
|
|
||||||
def test_php_application_query_string(self):
|
def test_php_application_query_string(self):
|
||||||
@@ -57,8 +70,11 @@ class TestUnitPHPApplication(unit.TestUnitApplicationPHP):
|
|||||||
|
|
||||||
resp = self.get(url='/?var1=val1&var2=val2')
|
resp = self.get(url='/?var1=val1&var2=val2')
|
||||||
|
|
||||||
self.assertEqual(resp['headers']['Query-String'], 'var1=val1&var2=val2',
|
self.assertEqual(
|
||||||
'query string')
|
resp['headers']['Query-String'],
|
||||||
|
'var1=val1&var2=val2',
|
||||||
|
'query string',
|
||||||
|
)
|
||||||
|
|
||||||
def test_php_application_query_string_empty(self):
|
def test_php_application_query_string_empty(self):
|
||||||
self.load('query_string')
|
self.load('query_string')
|
||||||
@@ -66,8 +82,9 @@ class TestUnitPHPApplication(unit.TestUnitApplicationPHP):
|
|||||||
resp = self.get(url='/?')
|
resp = self.get(url='/?')
|
||||||
|
|
||||||
self.assertEqual(resp['status'], 200, 'query string empty status')
|
self.assertEqual(resp['status'], 200, 'query string empty status')
|
||||||
self.assertEqual(resp['headers']['Query-String'], '',
|
self.assertEqual(
|
||||||
'query string empty')
|
resp['headers']['Query-String'], '', 'query string empty'
|
||||||
|
)
|
||||||
|
|
||||||
@unittest.expectedFailure
|
@unittest.expectedFailure
|
||||||
def test_php_application_query_string_absent(self):
|
def test_php_application_query_string_absent(self):
|
||||||
@@ -76,8 +93,9 @@ class TestUnitPHPApplication(unit.TestUnitApplicationPHP):
|
|||||||
resp = self.get()
|
resp = self.get()
|
||||||
|
|
||||||
self.assertEqual(resp['status'], 200, 'query string absent status')
|
self.assertEqual(resp['status'], 200, 'query string absent status')
|
||||||
self.assertEqual(resp['headers']['Query-String'], '',
|
self.assertEqual(
|
||||||
'query string absent')
|
resp['headers']['Query-String'], '', 'query string absent'
|
||||||
|
)
|
||||||
|
|
||||||
def test_php_application_phpinfo(self):
|
def test_php_application_phpinfo(self):
|
||||||
self.load('phpinfo')
|
self.load('phpinfo')
|
||||||
@@ -93,25 +111,34 @@ class TestUnitPHPApplication(unit.TestUnitApplicationPHP):
|
|||||||
resp = self.get()
|
resp = self.get()
|
||||||
|
|
||||||
self.assertEqual(resp['status'], 404, '404 status')
|
self.assertEqual(resp['status'], 404, '404 status')
|
||||||
self.assertRegex(resp['body'], r'<title>404 Not Found</title>',
|
self.assertRegex(
|
||||||
'404 body')
|
resp['body'], r'<title>404 Not Found</title>', '404 body'
|
||||||
|
)
|
||||||
|
|
||||||
def test_php_application_keepalive_body(self):
|
def test_php_application_keepalive_body(self):
|
||||||
self.load('mirror')
|
self.load('mirror')
|
||||||
|
|
||||||
(resp, sock) = self.post(headers={
|
(resp, sock) = self.post(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Connection': 'keep-alive',
|
'Connection': 'keep-alive',
|
||||||
'Content-Type': 'text/html'
|
'Content-Type': 'text/html',
|
||||||
}, start=True, body='0123456789' * 500)
|
},
|
||||||
|
start=True,
|
||||||
|
body='0123456789' * 500,
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(resp['body'], '0123456789' * 500, 'keep-alive 1')
|
self.assertEqual(resp['body'], '0123456789' * 500, 'keep-alive 1')
|
||||||
|
|
||||||
resp = self.post(headers={
|
resp = self.post(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Connection': 'close',
|
'Connection': 'close',
|
||||||
'Content-Type': 'text/html'
|
'Content-Type': 'text/html',
|
||||||
}, sock=sock, body='0123456789')
|
},
|
||||||
|
sock=sock,
|
||||||
|
body='0123456789',
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(resp['body'], '0123456789', 'keep-alive 2')
|
self.assertEqual(resp['body'], '0123456789', 'keep-alive 2')
|
||||||
|
|
||||||
@@ -133,11 +160,14 @@ class TestUnitPHPApplication(unit.TestUnitApplicationPHP):
|
|||||||
def test_php_application_post_variables(self):
|
def test_php_application_post_variables(self):
|
||||||
self.load('post_variables')
|
self.load('post_variables')
|
||||||
|
|
||||||
resp = self.post(headers={
|
resp = self.post(
|
||||||
|
headers={
|
||||||
'Content-Type': 'application/x-www-form-urlencoded',
|
'Content-Type': 'application/x-www-form-urlencoded',
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
}, body='var1=val1&var2=')
|
},
|
||||||
|
body='var1=val1&var2=',
|
||||||
|
)
|
||||||
self.assertEqual(resp['headers']['X-Var-1'], 'val1', 'POST variables')
|
self.assertEqual(resp['headers']['X-Var-1'], 'val1', 'POST variables')
|
||||||
self.assertEqual(resp['headers']['X-Var-2'], '1', 'POST variables 2')
|
self.assertEqual(resp['headers']['X-Var-2'], '1', 'POST variables 2')
|
||||||
self.assertEqual(resp['headers']['X-Var-3'], '', 'POST variables 3')
|
self.assertEqual(resp['headers']['X-Var-3'], '', 'POST variables 3')
|
||||||
@@ -145,11 +175,13 @@ class TestUnitPHPApplication(unit.TestUnitApplicationPHP):
|
|||||||
def test_php_application_cookies(self):
|
def test_php_application_cookies(self):
|
||||||
self.load('cookies')
|
self.load('cookies')
|
||||||
|
|
||||||
resp = self.get(headers={
|
resp = self.get(
|
||||||
|
headers={
|
||||||
'Cookie': 'var=val; var2=val2',
|
'Cookie': 'var=val; var2=val2',
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
})
|
}
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(resp['headers']['X-Cookie-1'], 'val', 'cookie')
|
self.assertEqual(resp['headers']['X-Cookie-1'], 'val', 'cookie')
|
||||||
self.assertEqual(resp['headers']['X-Cookie-2'], 'val2', 'cookie')
|
self.assertEqual(resp['headers']['X-Cookie-2'], 'val2', 'cookie')
|
||||||
@@ -157,96 +189,129 @@ class TestUnitPHPApplication(unit.TestUnitApplicationPHP):
|
|||||||
def test_php_application_ini_precision(self):
|
def test_php_application_ini_precision(self):
|
||||||
self.load('ini_precision')
|
self.load('ini_precision')
|
||||||
|
|
||||||
self.assertNotEqual(self.get()['headers']['X-Precision'], '4',
|
self.assertNotEqual(
|
||||||
'ini value default')
|
self.get()['headers']['X-Precision'], '4', 'ini value default'
|
||||||
|
)
|
||||||
|
|
||||||
self.conf({"file": "ini/php.ini"}, 'applications/ini_precision/options')
|
self.conf(
|
||||||
|
{"file": "ini/php.ini"}, 'applications/ini_precision/options'
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(self.get()['headers']['X-File'],
|
self.assertEqual(
|
||||||
self.current_dir + '/php/ini_precision/ini/php.ini', 'ini file')
|
self.get()['headers']['X-File'],
|
||||||
self.assertEqual(self.get()['headers']['X-Precision'], '4', 'ini value')
|
self.current_dir + '/php/ini_precision/ini/php.ini',
|
||||||
|
'ini file',
|
||||||
|
)
|
||||||
|
self.assertEqual(
|
||||||
|
self.get()['headers']['X-Precision'], '4', 'ini value'
|
||||||
|
)
|
||||||
|
|
||||||
@unittest.expectedFailure
|
@unittest.expectedFailure
|
||||||
def test_php_application_ini_admin_user(self):
|
def test_php_application_ini_admin_user(self):
|
||||||
self.load('ini_precision')
|
self.load('ini_precision')
|
||||||
|
|
||||||
self.assertIn('error', self.conf({
|
self.assertIn(
|
||||||
"user": { "precision": "4" },
|
'error',
|
||||||
"admin": { "precision": "5" }
|
self.conf(
|
||||||
}, 'applications/ini_precision/options'), 'ini admin user')
|
{"user": {"precision": "4"}, "admin": {"precision": "5"}},
|
||||||
|
'applications/ini_precision/options',
|
||||||
|
),
|
||||||
|
'ini admin user',
|
||||||
|
)
|
||||||
|
|
||||||
def test_php_application_ini_admin(self):
|
def test_php_application_ini_admin(self):
|
||||||
self.load('ini_precision')
|
self.load('ini_precision')
|
||||||
|
|
||||||
self.conf({
|
self.conf(
|
||||||
"file": "php.ini",
|
{"file": "php.ini", "admin": {"precision": "5"}},
|
||||||
"admin": { "precision": "5" }
|
'applications/ini_precision/options',
|
||||||
}, 'applications/ini_precision/options')
|
)
|
||||||
|
|
||||||
self.assertEqual(self.get()['headers']['X-Precision'], '5',
|
self.assertEqual(
|
||||||
'ini value admin')
|
self.get()['headers']['X-Precision'], '5', 'ini value admin'
|
||||||
|
)
|
||||||
|
|
||||||
def test_php_application_ini_user(self):
|
def test_php_application_ini_user(self):
|
||||||
self.load('ini_precision')
|
self.load('ini_precision')
|
||||||
|
|
||||||
self.conf({
|
self.conf(
|
||||||
"file": "php.ini",
|
{"file": "php.ini", "user": {"precision": "5"}},
|
||||||
"user": { "precision": "5" }
|
'applications/ini_precision/options',
|
||||||
}, 'applications/ini_precision/options')
|
)
|
||||||
|
|
||||||
self.assertEqual(self.get()['headers']['X-Precision'], '5',
|
self.assertEqual(
|
||||||
'ini value user')
|
self.get()['headers']['X-Precision'], '5', 'ini value user'
|
||||||
|
)
|
||||||
|
|
||||||
def test_php_application_ini_user_2(self):
|
def test_php_application_ini_user_2(self):
|
||||||
self.load('ini_precision')
|
self.load('ini_precision')
|
||||||
|
|
||||||
self.conf({"file": "ini/php.ini"}, 'applications/ini_precision/options')
|
self.conf(
|
||||||
|
{"file": "ini/php.ini"}, 'applications/ini_precision/options'
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(self.get()['headers']['X-Precision'], '4',
|
self.assertEqual(
|
||||||
'ini user file')
|
self.get()['headers']['X-Precision'], '4', 'ini user file'
|
||||||
|
)
|
||||||
|
|
||||||
self.conf({ "precision": "5" },
|
self.conf(
|
||||||
'applications/ini_precision/options/user')
|
{"precision": "5"}, 'applications/ini_precision/options/user'
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(self.get()['headers']['X-Precision'], '5',
|
self.assertEqual(
|
||||||
'ini value user')
|
self.get()['headers']['X-Precision'], '5', 'ini value user'
|
||||||
|
)
|
||||||
|
|
||||||
def test_php_application_ini_set_admin(self):
|
def test_php_application_ini_set_admin(self):
|
||||||
self.load('ini_precision')
|
self.load('ini_precision')
|
||||||
|
|
||||||
self.conf({"admin": { "precision": "5" }},
|
self.conf(
|
||||||
'applications/ini_precision/options')
|
{"admin": {"precision": "5"}}, 'applications/ini_precision/options'
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(self.get(url='/?precision=6')['headers']['X-Precision'],
|
self.assertEqual(
|
||||||
'5', 'ini set admin')
|
self.get(url='/?precision=6')['headers']['X-Precision'],
|
||||||
|
'5',
|
||||||
|
'ini set admin',
|
||||||
|
)
|
||||||
|
|
||||||
def test_php_application_ini_set_user(self):
|
def test_php_application_ini_set_user(self):
|
||||||
self.load('ini_precision')
|
self.load('ini_precision')
|
||||||
|
|
||||||
self.conf({"user": { "precision": "5" }},
|
self.conf(
|
||||||
'applications/ini_precision/options')
|
{"user": {"precision": "5"}}, 'applications/ini_precision/options'
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(self.get(url='/?precision=6')['headers']['X-Precision'],
|
self.assertEqual(
|
||||||
'6', 'ini set user')
|
self.get(url='/?precision=6')['headers']['X-Precision'],
|
||||||
|
'6',
|
||||||
|
'ini set user',
|
||||||
|
)
|
||||||
|
|
||||||
def test_php_application_ini_repeat(self):
|
def test_php_application_ini_repeat(self):
|
||||||
self.load('ini_precision')
|
self.load('ini_precision')
|
||||||
|
|
||||||
self.conf({"user": { "precision": "5" }},
|
self.conf(
|
||||||
'applications/ini_precision/options')
|
{"user": {"precision": "5"}}, 'applications/ini_precision/options'
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(self.get()['headers']['X-Precision'], '5', 'ini value')
|
self.assertEqual(
|
||||||
|
self.get()['headers']['X-Precision'], '5', 'ini value'
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(self.get()['headers']['X-Precision'], '5',
|
self.assertEqual(
|
||||||
'ini value repeat')
|
self.get()['headers']['X-Precision'], '5', 'ini value repeat'
|
||||||
|
)
|
||||||
|
|
||||||
def test_php_application_disable_functions_exec(self):
|
def test_php_application_disable_functions_exec(self):
|
||||||
self.load('time_exec')
|
self.load('time_exec')
|
||||||
|
|
||||||
self.before_disable_functions()
|
self.before_disable_functions()
|
||||||
|
|
||||||
self.conf({"admin": { "disable_functions": "exec" }},
|
self.conf(
|
||||||
'applications/time_exec/options')
|
{"admin": {"disable_functions": "exec"}},
|
||||||
|
'applications/time_exec/options',
|
||||||
|
)
|
||||||
|
|
||||||
body = self.get()['body']
|
body = self.get()['body']
|
||||||
|
|
||||||
@@ -258,80 +323,103 @@ class TestUnitPHPApplication(unit.TestUnitApplicationPHP):
|
|||||||
|
|
||||||
self.before_disable_functions()
|
self.before_disable_functions()
|
||||||
|
|
||||||
self.conf({"admin": { "disable_functions": "exec,time" }},
|
self.conf(
|
||||||
'applications/time_exec/options')
|
{"admin": {"disable_functions": "exec,time"}},
|
||||||
|
'applications/time_exec/options',
|
||||||
|
)
|
||||||
|
|
||||||
body = self.get()['body']
|
body = self.get()['body']
|
||||||
|
|
||||||
self.assertNotRegex(body, r'time: \d+', 'disable_functions comma time')
|
self.assertNotRegex(body, r'time: \d+', 'disable_functions comma time')
|
||||||
self.assertNotRegex(body, r'exec: \/\w+',
|
self.assertNotRegex(
|
||||||
'disable_functions comma exec')
|
body, r'exec: \/\w+', 'disable_functions comma exec'
|
||||||
|
)
|
||||||
|
|
||||||
def test_php_application_disable_functions_space(self):
|
def test_php_application_disable_functions_space(self):
|
||||||
self.load('time_exec')
|
self.load('time_exec')
|
||||||
|
|
||||||
self.before_disable_functions()
|
self.before_disable_functions()
|
||||||
|
|
||||||
self.conf({"admin": { "disable_functions": "exec time" }},
|
self.conf(
|
||||||
'applications/time_exec/options')
|
{"admin": {"disable_functions": "exec time"}},
|
||||||
|
'applications/time_exec/options',
|
||||||
|
)
|
||||||
|
|
||||||
body = self.get()['body']
|
body = self.get()['body']
|
||||||
|
|
||||||
self.assertNotRegex(body, r'time: \d+', 'disable_functions space time')
|
self.assertNotRegex(body, r'time: \d+', 'disable_functions space time')
|
||||||
self.assertNotRegex(body, r'exec: \/\w+',
|
self.assertNotRegex(
|
||||||
'disable_functions space exec')
|
body, r'exec: \/\w+', 'disable_functions space exec'
|
||||||
|
)
|
||||||
|
|
||||||
def test_php_application_disable_functions_user(self):
|
def test_php_application_disable_functions_user(self):
|
||||||
self.load('time_exec')
|
self.load('time_exec')
|
||||||
|
|
||||||
self.before_disable_functions()
|
self.before_disable_functions()
|
||||||
|
|
||||||
self.conf({"user": { "disable_functions": "exec" }},
|
self.conf(
|
||||||
'applications/time_exec/options')
|
{"user": {"disable_functions": "exec"}},
|
||||||
|
'applications/time_exec/options',
|
||||||
|
)
|
||||||
|
|
||||||
body = self.get()['body']
|
body = self.get()['body']
|
||||||
|
|
||||||
self.assertRegex(body, r'time: \d+', 'disable_functions user time')
|
self.assertRegex(body, r'time: \d+', 'disable_functions user time')
|
||||||
self.assertNotRegex(body, r'exec: \/\w+', 'disable_functions user exec')
|
self.assertNotRegex(
|
||||||
|
body, r'exec: \/\w+', 'disable_functions user exec'
|
||||||
|
)
|
||||||
|
|
||||||
def test_php_application_disable_functions_nonexistent(self):
|
def test_php_application_disable_functions_nonexistent(self):
|
||||||
self.load('time_exec')
|
self.load('time_exec')
|
||||||
|
|
||||||
self.before_disable_functions()
|
self.before_disable_functions()
|
||||||
|
|
||||||
self.conf({"admin": { "disable_functions": "blah" }},
|
self.conf(
|
||||||
'applications/time_exec/options')
|
{"admin": {"disable_functions": "blah"}},
|
||||||
|
'applications/time_exec/options',
|
||||||
|
)
|
||||||
|
|
||||||
body = self.get()['body']
|
body = self.get()['body']
|
||||||
|
|
||||||
self.assertRegex(body, r'time: \d+',
|
self.assertRegex(
|
||||||
'disable_functions nonexistent time')
|
body, r'time: \d+', 'disable_functions nonexistent time'
|
||||||
self.assertRegex(body, r'exec: \/\w+',
|
)
|
||||||
'disable_functions nonexistent exec')
|
self.assertRegex(
|
||||||
|
body, r'exec: \/\w+', 'disable_functions nonexistent exec'
|
||||||
|
)
|
||||||
|
|
||||||
def test_php_application_disable_classes(self):
|
def test_php_application_disable_classes(self):
|
||||||
self.load('date_time')
|
self.load('date_time')
|
||||||
|
|
||||||
self.assertRegex(self.get()['body'], r'012345',
|
self.assertRegex(
|
||||||
'disable_classes before')
|
self.get()['body'], r'012345', 'disable_classes before'
|
||||||
|
)
|
||||||
|
|
||||||
self.conf({"admin": { "disable_classes": "DateTime" }},
|
self.conf(
|
||||||
'applications/date_time/options')
|
{"admin": {"disable_classes": "DateTime"}},
|
||||||
|
'applications/date_time/options',
|
||||||
|
)
|
||||||
|
|
||||||
self.assertNotRegex(self.get()['body'], r'012345',
|
self.assertNotRegex(
|
||||||
'disable_classes before')
|
self.get()['body'], r'012345', 'disable_classes before'
|
||||||
|
)
|
||||||
|
|
||||||
def test_php_application_disable_classes_user(self):
|
def test_php_application_disable_classes_user(self):
|
||||||
self.load('date_time')
|
self.load('date_time')
|
||||||
|
|
||||||
self.assertRegex(self.get()['body'], r'012345',
|
self.assertRegex(
|
||||||
'disable_classes before')
|
self.get()['body'], r'012345', 'disable_classes before'
|
||||||
|
)
|
||||||
|
|
||||||
self.conf({"user": { "disable_classes": "DateTime" }},
|
self.conf(
|
||||||
'applications/date_time/options')
|
{"user": {"disable_classes": "DateTime"}},
|
||||||
|
'applications/date_time/options',
|
||||||
|
)
|
||||||
|
|
||||||
|
self.assertNotRegex(
|
||||||
|
self.get()['body'], r'012345', 'disable_classes before'
|
||||||
|
)
|
||||||
|
|
||||||
self.assertNotRegex(self.get()['body'], r'012345',
|
|
||||||
'disable_classes before')
|
|
||||||
|
|
||||||
if __name__ == '__main__':
|
if __name__ == '__main__':
|
||||||
TestUnitPHPApplication.main()
|
TestUnitPHPApplication.main()
|
||||||
|
|||||||
@@ -1,27 +1,23 @@
|
|||||||
import unittest
|
import unittest
|
||||||
import unit
|
import unit
|
||||||
|
|
||||||
class TestUnitPHPBasic(unit.TestUnitControl):
|
|
||||||
|
|
||||||
|
class TestUnitPHPBasic(unit.TestUnitControl):
|
||||||
def setUpClass():
|
def setUpClass():
|
||||||
unit.TestUnit().check_modules('php')
|
unit.TestUnit().check_modules('php')
|
||||||
|
|
||||||
conf_app = {
|
conf_app = {
|
||||||
"app": {
|
"app": {
|
||||||
"type": "php",
|
"type": "php",
|
||||||
"processes": { "spare": 0 },
|
"processes": {"spare": 0},
|
||||||
"root": "/app",
|
"root": "/app",
|
||||||
"index": "index.php"
|
"index": "index.php",
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
conf_basic = {
|
conf_basic = {
|
||||||
"listeners": {
|
"listeners": {"*:7080": {"application": "app"}},
|
||||||
"*:7080": {
|
"applications": conf_app,
|
||||||
"application": "app"
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"applications": conf_app
|
|
||||||
}
|
}
|
||||||
|
|
||||||
def test_php_get_applications(self):
|
def test_php_get_applications(self):
|
||||||
@@ -30,113 +26,146 @@ class TestUnitPHPBasic(unit.TestUnitControl):
|
|||||||
conf = self.conf_get()
|
conf = self.conf_get()
|
||||||
|
|
||||||
self.assertEqual(conf['listeners'], {}, 'listeners')
|
self.assertEqual(conf['listeners'], {}, 'listeners')
|
||||||
self.assertEqual(conf['applications'],
|
self.assertEqual(
|
||||||
|
conf['applications'],
|
||||||
{
|
{
|
||||||
"app": {
|
"app": {
|
||||||
"type": "php",
|
"type": "php",
|
||||||
"processes": { "spare": 0 },
|
"processes": {"spare": 0},
|
||||||
"root": "/app",
|
"root": "/app",
|
||||||
"index": "index.php"
|
"index": "index.php",
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
'applications')
|
'applications',
|
||||||
|
)
|
||||||
|
|
||||||
def test_php_get_applications_prefix(self):
|
def test_php_get_applications_prefix(self):
|
||||||
self.conf(self.conf_app, 'applications')
|
self.conf(self.conf_app, 'applications')
|
||||||
|
|
||||||
self.assertEqual(self.conf_get('applications'),
|
self.assertEqual(
|
||||||
|
self.conf_get('applications'),
|
||||||
{
|
{
|
||||||
"app": {
|
"app": {
|
||||||
"type": "php",
|
"type": "php",
|
||||||
"processes": { "spare": 0 },
|
"processes": {"spare": 0},
|
||||||
"root": "/app",
|
"root": "/app",
|
||||||
"index": "index.php"
|
"index": "index.php",
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
'applications prefix')
|
'applications prefix',
|
||||||
|
)
|
||||||
|
|
||||||
def test_php_get_applications_prefix_2(self):
|
def test_php_get_applications_prefix_2(self):
|
||||||
self.conf(self.conf_app, 'applications')
|
self.conf(self.conf_app, 'applications')
|
||||||
|
|
||||||
self.assertEqual(self.conf_get('applications/app'),
|
self.assertEqual(
|
||||||
|
self.conf_get('applications/app'),
|
||||||
{
|
{
|
||||||
"type": "php",
|
"type": "php",
|
||||||
"processes": { "spare": 0 },
|
"processes": {"spare": 0},
|
||||||
"root": "/app",
|
"root": "/app",
|
||||||
"index": "index.php"
|
"index": "index.php",
|
||||||
},
|
},
|
||||||
'applications prefix 2')
|
'applications prefix 2',
|
||||||
|
)
|
||||||
|
|
||||||
def test_php_get_applications_prefix_3(self):
|
def test_php_get_applications_prefix_3(self):
|
||||||
self.conf(self.conf_app, 'applications')
|
self.conf(self.conf_app, 'applications')
|
||||||
|
|
||||||
self.assertEqual(self.conf_get('applications/app/type'), 'php',
|
self.assertEqual(self.conf_get('applications/app/type'), 'php', 'type')
|
||||||
'type')
|
self.assertEqual(
|
||||||
self.assertEqual(self.conf_get('applications/app/processes/spare'), 0,
|
self.conf_get('applications/app/processes/spare'),
|
||||||
'spare processes')
|
0,
|
||||||
|
'spare processes',
|
||||||
|
)
|
||||||
|
|
||||||
def test_php_get_listeners(self):
|
def test_php_get_listeners(self):
|
||||||
self.conf(self.conf_basic)
|
self.conf(self.conf_basic)
|
||||||
|
|
||||||
self.assertEqual(self.conf_get()['listeners'],
|
self.assertEqual(
|
||||||
{"*:7080":{"application":"app"}}, 'listeners')
|
self.conf_get()['listeners'],
|
||||||
|
{"*:7080": {"application": "app"}},
|
||||||
|
'listeners',
|
||||||
|
)
|
||||||
|
|
||||||
def test_php_get_listeners_prefix(self):
|
def test_php_get_listeners_prefix(self):
|
||||||
self.conf(self.conf_basic)
|
self.conf(self.conf_basic)
|
||||||
|
|
||||||
self.assertEqual(self.conf_get('listeners'),
|
self.assertEqual(
|
||||||
{"*:7080":{"application":"app"}}, 'listeners prefix')
|
self.conf_get('listeners'),
|
||||||
|
{"*:7080": {"application": "app"}},
|
||||||
|
'listeners prefix',
|
||||||
|
)
|
||||||
|
|
||||||
def test_php_get_listeners_prefix_2(self):
|
def test_php_get_listeners_prefix_2(self):
|
||||||
self.conf(self.conf_basic)
|
self.conf(self.conf_basic)
|
||||||
|
|
||||||
self.assertEqual(self.conf_get('listeners/*:7080'),
|
self.assertEqual(
|
||||||
{"application":"app"}, 'listeners prefix 2')
|
self.conf_get('listeners/*:7080'),
|
||||||
|
{"application": "app"},
|
||||||
|
'listeners prefix 2',
|
||||||
|
)
|
||||||
|
|
||||||
def test_php_change_listener(self):
|
def test_php_change_listener(self):
|
||||||
self.conf(self.conf_basic)
|
self.conf(self.conf_basic)
|
||||||
self.conf({"*:7081":{"application":"app"}}, 'listeners')
|
self.conf({"*:7081": {"application": "app"}}, 'listeners')
|
||||||
|
|
||||||
self.assertEqual(self.conf_get('listeners'),
|
self.assertEqual(
|
||||||
{"*:7081": {"application":"app"}}, 'change listener')
|
self.conf_get('listeners'),
|
||||||
|
{"*:7081": {"application": "app"}},
|
||||||
|
'change listener',
|
||||||
|
)
|
||||||
|
|
||||||
def test_php_add_listener(self):
|
def test_php_add_listener(self):
|
||||||
self.conf(self.conf_basic)
|
self.conf(self.conf_basic)
|
||||||
self.conf({"application":"app"}, 'listeners/*:7082')
|
self.conf({"application": "app"}, 'listeners/*:7082')
|
||||||
|
|
||||||
self.assertEqual(self.conf_get('listeners'),
|
self.assertEqual(
|
||||||
|
self.conf_get('listeners'),
|
||||||
{
|
{
|
||||||
"*:7080": {
|
"*:7080": {"application": "app"},
|
||||||
"application": "app"
|
"*:7082": {"application": "app"},
|
||||||
},
|
},
|
||||||
"*:7082": {
|
'add listener',
|
||||||
"application": "app"
|
)
|
||||||
}
|
|
||||||
},
|
|
||||||
'add listener')
|
|
||||||
|
|
||||||
def test_php_change_application(self):
|
def test_php_change_application(self):
|
||||||
self.conf(self.conf_basic)
|
self.conf(self.conf_basic)
|
||||||
|
|
||||||
self.conf('30', 'applications/app/processes/max')
|
self.conf('30', 'applications/app/processes/max')
|
||||||
self.assertEqual(self.conf_get('applications/app/processes/max'), 30,
|
self.assertEqual(
|
||||||
'change application max')
|
self.conf_get('applications/app/processes/max'),
|
||||||
|
30,
|
||||||
|
'change application max',
|
||||||
|
)
|
||||||
|
|
||||||
self.conf('"/www"', 'applications/app/root')
|
self.conf('"/www"', 'applications/app/root')
|
||||||
self.assertEqual(self.conf_get('applications/app/root'), '/www',
|
self.assertEqual(
|
||||||
'change application root')
|
self.conf_get('applications/app/root'),
|
||||||
|
'/www',
|
||||||
|
'change application root',
|
||||||
|
)
|
||||||
|
|
||||||
def test_php_delete(self):
|
def test_php_delete(self):
|
||||||
self.conf(self.conf_basic)
|
self.conf(self.conf_basic)
|
||||||
|
|
||||||
self.assertIn('error', self.conf_delete('applications/app'),
|
self.assertIn(
|
||||||
'delete app before listener')
|
'error',
|
||||||
self.assertIn('success', self.conf_delete('listeners/*:7080'),
|
self.conf_delete('applications/app'),
|
||||||
'delete listener')
|
'delete app before listener',
|
||||||
self.assertIn('success', self.conf_delete('applications/app'),
|
)
|
||||||
'delete app after listener')
|
self.assertIn(
|
||||||
self.assertIn('error', self.conf_delete('applications/app'),
|
'success', self.conf_delete('listeners/*:7080'), 'delete listener'
|
||||||
'delete app again')
|
)
|
||||||
|
self.assertIn(
|
||||||
|
'success',
|
||||||
|
self.conf_delete('applications/app'),
|
||||||
|
'delete app after listener',
|
||||||
|
)
|
||||||
|
self.assertIn(
|
||||||
|
'error', self.conf_delete('applications/app'), 'delete app again'
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
if __name__ == '__main__':
|
if __name__ == '__main__':
|
||||||
TestUnitPHPBasic.main()
|
TestUnitPHPBasic.main()
|
||||||
|
|||||||
@@ -2,8 +2,8 @@ import time
|
|||||||
import unittest
|
import unittest
|
||||||
import unit
|
import unit
|
||||||
|
|
||||||
class TestUnitPythonApplication(unit.TestUnitApplicationPython):
|
|
||||||
|
|
||||||
|
class TestUnitPythonApplication(unit.TestUnitApplicationPython):
|
||||||
def setUpClass():
|
def setUpClass():
|
||||||
unit.TestUnit().check_modules('python')
|
unit.TestUnit().check_modules('python')
|
||||||
|
|
||||||
@@ -12,26 +12,37 @@ class TestUnitPythonApplication(unit.TestUnitApplicationPython):
|
|||||||
|
|
||||||
body = 'Test body string.'
|
body = 'Test body string.'
|
||||||
|
|
||||||
resp = self.post(headers={
|
resp = self.post(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Content-Type': 'text/html',
|
'Content-Type': 'text/html',
|
||||||
'Custom-Header': 'blah',
|
'Custom-Header': 'blah',
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
}, body=body)
|
},
|
||||||
|
body=body,
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(resp['status'], 200, 'status')
|
self.assertEqual(resp['status'], 200, 'status')
|
||||||
headers = resp['headers']
|
headers = resp['headers']
|
||||||
header_server = headers.pop('Server')
|
header_server = headers.pop('Server')
|
||||||
self.assertRegex(header_server, r'Unit/[\d\.]+', 'server header')
|
self.assertRegex(header_server, r'Unit/[\d\.]+', 'server header')
|
||||||
self.assertEqual(headers.pop('Server-Software'), header_server,
|
self.assertEqual(
|
||||||
'server software header')
|
headers.pop('Server-Software'),
|
||||||
|
header_server,
|
||||||
|
'server software header',
|
||||||
|
)
|
||||||
|
|
||||||
date = headers.pop('Date')
|
date = headers.pop('Date')
|
||||||
self.assertEqual(date[-4:], ' GMT', 'date header timezone')
|
self.assertEqual(date[-4:], ' GMT', 'date header timezone')
|
||||||
self.assertLess(abs(self.date_to_sec_epoch(date) - self.sec_epoch()), 5,
|
self.assertLess(
|
||||||
'date header')
|
abs(self.date_to_sec_epoch(date) - self.sec_epoch()),
|
||||||
|
5,
|
||||||
|
'date header',
|
||||||
|
)
|
||||||
|
|
||||||
self.assertDictEqual(headers, {
|
self.assertDictEqual(
|
||||||
|
headers,
|
||||||
|
{
|
||||||
'Connection': 'close',
|
'Connection': 'close',
|
||||||
'Content-Length': str(len(body)),
|
'Content-Length': str(len(body)),
|
||||||
'Content-Type': 'text/html',
|
'Content-Type': 'text/html',
|
||||||
@@ -44,8 +55,10 @@ class TestUnitPythonApplication(unit.TestUnitApplicationPython):
|
|||||||
'Wsgi-Url-Scheme': 'http',
|
'Wsgi-Url-Scheme': 'http',
|
||||||
'Wsgi-Multithread': 'False',
|
'Wsgi-Multithread': 'False',
|
||||||
'Wsgi-Multiprocess': 'True',
|
'Wsgi-Multiprocess': 'True',
|
||||||
'Wsgi-Run-Once': 'False'
|
'Wsgi-Run-Once': 'False',
|
||||||
}, 'headers')
|
},
|
||||||
|
'headers',
|
||||||
|
)
|
||||||
self.assertEqual(resp['body'], body, 'body')
|
self.assertEqual(resp['body'], body, 'body')
|
||||||
|
|
||||||
def test_python_application_query_string(self):
|
def test_python_application_query_string(self):
|
||||||
@@ -53,8 +66,11 @@ class TestUnitPythonApplication(unit.TestUnitApplicationPython):
|
|||||||
|
|
||||||
resp = self.get(url='/?var1=val1&var2=val2')
|
resp = self.get(url='/?var1=val1&var2=val2')
|
||||||
|
|
||||||
self.assertEqual(resp['headers']['Query-String'], 'var1=val1&var2=val2',
|
self.assertEqual(
|
||||||
'Query-String header')
|
resp['headers']['Query-String'],
|
||||||
|
'var1=val1&var2=val2',
|
||||||
|
'Query-String header',
|
||||||
|
)
|
||||||
|
|
||||||
def test_python_application_query_string_empty(self):
|
def test_python_application_query_string_empty(self):
|
||||||
self.load('query_string')
|
self.load('query_string')
|
||||||
@@ -62,8 +78,9 @@ class TestUnitPythonApplication(unit.TestUnitApplicationPython):
|
|||||||
resp = self.get(url='/?')
|
resp = self.get(url='/?')
|
||||||
|
|
||||||
self.assertEqual(resp['status'], 200, 'query string empty status')
|
self.assertEqual(resp['status'], 200, 'query string empty status')
|
||||||
self.assertEqual(resp['headers']['Query-String'], '',
|
self.assertEqual(
|
||||||
'query string empty')
|
resp['headers']['Query-String'], '', 'query string empty'
|
||||||
|
)
|
||||||
|
|
||||||
def test_python_application_query_string_absent(self):
|
def test_python_application_query_string_absent(self):
|
||||||
self.load('query_string')
|
self.load('query_string')
|
||||||
@@ -71,71 +88,87 @@ class TestUnitPythonApplication(unit.TestUnitApplicationPython):
|
|||||||
resp = self.get()
|
resp = self.get()
|
||||||
|
|
||||||
self.assertEqual(resp['status'], 200, 'query string absent status')
|
self.assertEqual(resp['status'], 200, 'query string absent status')
|
||||||
self.assertEqual(resp['headers']['Query-String'], '',
|
self.assertEqual(
|
||||||
'query string absent')
|
resp['headers']['Query-String'], '', 'query string absent'
|
||||||
|
)
|
||||||
|
|
||||||
@unittest.expectedFailure
|
@unittest.expectedFailure
|
||||||
def test_python_application_server_port(self):
|
def test_python_application_server_port(self):
|
||||||
self.load('server_port')
|
self.load('server_port')
|
||||||
|
|
||||||
self.assertEqual(self.get()['headers']['Server-Port'], '7080',
|
self.assertEqual(
|
||||||
'Server-Port header')
|
self.get()['headers']['Server-Port'], '7080', 'Server-Port header'
|
||||||
|
)
|
||||||
|
|
||||||
def test_python_application_204_transfer_encoding(self):
|
def test_python_application_204_transfer_encoding(self):
|
||||||
self.load('204_no_content')
|
self.load('204_no_content')
|
||||||
|
|
||||||
self.assertNotIn('Transfer-Encoding', self.get()['headers'],
|
self.assertNotIn(
|
||||||
'204 header transfer encoding')
|
'Transfer-Encoding',
|
||||||
|
self.get()['headers'],
|
||||||
|
'204 header transfer encoding',
|
||||||
|
)
|
||||||
|
|
||||||
def test_python_application_ctx_iter_atexit(self):
|
def test_python_application_ctx_iter_atexit(self):
|
||||||
self.load('ctx_iter_atexit')
|
self.load('ctx_iter_atexit')
|
||||||
|
|
||||||
resp = self.post(headers={
|
resp = self.post(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Connection': 'close',
|
'Connection': 'close',
|
||||||
'Content-Type': 'text/html'
|
'Content-Type': 'text/html',
|
||||||
}, body='0123456789')
|
},
|
||||||
|
body='0123456789',
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(resp['status'], 200, 'ctx iter status')
|
self.assertEqual(resp['status'], 200, 'ctx iter status')
|
||||||
self.assertEqual(resp['body'], '0123456789', 'ctx iter body')
|
self.assertEqual(resp['body'], '0123456789', 'ctx iter body')
|
||||||
|
|
||||||
self.conf({
|
self.conf({"listeners": {}, "applications": {}})
|
||||||
"listeners": {},
|
|
||||||
"applications": {}
|
|
||||||
})
|
|
||||||
|
|
||||||
self.stop()
|
self.stop()
|
||||||
|
|
||||||
time.sleep(0.2)
|
time.sleep(0.2)
|
||||||
|
|
||||||
self.assertIsNotNone(self.search_in_log(r'RuntimeError'),
|
self.assertIsNotNone(
|
||||||
'ctx iter atexit')
|
self.search_in_log(r'RuntimeError'), 'ctx iter atexit'
|
||||||
|
)
|
||||||
|
|
||||||
def test_python_keepalive_body(self):
|
def test_python_keepalive_body(self):
|
||||||
self.load('mirror')
|
self.load('mirror')
|
||||||
|
|
||||||
(resp, sock) = self.post(headers={
|
(resp, sock) = self.post(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Connection': 'keep-alive',
|
'Connection': 'keep-alive',
|
||||||
'Content-Type': 'text/html'
|
'Content-Type': 'text/html',
|
||||||
}, start=True, body='0123456789' * 500)
|
},
|
||||||
|
start=True,
|
||||||
|
body='0123456789' * 500,
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(resp['body'], '0123456789' * 500, 'keep-alive 1')
|
self.assertEqual(resp['body'], '0123456789' * 500, 'keep-alive 1')
|
||||||
|
|
||||||
resp = self.post(headers={
|
resp = self.post(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Connection': 'close',
|
'Connection': 'close',
|
||||||
'Content-Type': 'text/html'
|
'Content-Type': 'text/html',
|
||||||
}, sock=sock, body='0123456789')
|
},
|
||||||
|
sock=sock,
|
||||||
|
body='0123456789',
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(resp['body'], '0123456789', 'keep-alive 2')
|
self.assertEqual(resp['body'], '0123456789', 'keep-alive 2')
|
||||||
|
|
||||||
def test_python_keepalive_reconfigure(self):
|
def test_python_keepalive_reconfigure(self):
|
||||||
self.skip_alerts.extend([
|
self.skip_alerts.extend(
|
||||||
|
[
|
||||||
r'pthread_mutex.+failed',
|
r'pthread_mutex.+failed',
|
||||||
r'failed to apply',
|
r'failed to apply',
|
||||||
r'process \d+ exited on signal'
|
r'process \d+ exited on signal',
|
||||||
])
|
]
|
||||||
|
)
|
||||||
self.load('mirror')
|
self.load('mirror')
|
||||||
|
|
||||||
body = '0123456789'
|
body = '0123456789'
|
||||||
@@ -143,74 +176,109 @@ class TestUnitPythonApplication(unit.TestUnitApplicationPython):
|
|||||||
socks = []
|
socks = []
|
||||||
|
|
||||||
for i in range(conns):
|
for i in range(conns):
|
||||||
(resp, sock) = self.post(headers={
|
(resp, sock) = self.post(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Connection': 'keep-alive',
|
'Connection': 'keep-alive',
|
||||||
'Content-Type': 'text/html'
|
'Content-Type': 'text/html',
|
||||||
}, start=True, body=body)
|
},
|
||||||
|
start=True,
|
||||||
|
body=body,
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(resp['body'], body, 'keep-alive open')
|
self.assertEqual(resp['body'], body, 'keep-alive open')
|
||||||
self.assertIn('success', self.conf({
|
self.assertIn(
|
||||||
"spare": i % 4,
|
'success',
|
||||||
"max": (i % 4) + 1
|
self.conf(
|
||||||
}, 'applications/mirror/processes'), 'reconfigure')
|
str(i + 1),
|
||||||
|
'applications/mirror/processes',
|
||||||
|
),
|
||||||
|
'reconfigure',
|
||||||
|
)
|
||||||
|
|
||||||
socks.append(sock)
|
socks.append(sock)
|
||||||
|
|
||||||
for i in range(conns):
|
for i in range(conns):
|
||||||
(resp, sock) = self.post(headers={
|
(resp, sock) = self.post(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Connection': 'keep-alive',
|
'Connection': 'keep-alive',
|
||||||
'Content-Type': 'text/html'
|
'Content-Type': 'text/html',
|
||||||
}, start=True, sock=socks[i], body=body)
|
},
|
||||||
|
start=True,
|
||||||
|
sock=socks[i],
|
||||||
|
body=body,
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(resp['body'], body, 'keep-alive request')
|
self.assertEqual(resp['body'], body, 'keep-alive request')
|
||||||
self.assertIn('success', self.conf({
|
self.assertIn(
|
||||||
"spare": i % 4,
|
'success',
|
||||||
"max": (i % 4) + 1
|
self.conf(
|
||||||
}, 'applications/mirror/processes'), 'reconfigure 2')
|
str(i + 1),
|
||||||
|
'applications/mirror/processes',
|
||||||
|
),
|
||||||
|
'reconfigure 2',
|
||||||
|
)
|
||||||
|
|
||||||
for i in range(conns):
|
for i in range(conns):
|
||||||
resp = self.post(headers={
|
resp = self.post(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Connection': 'close',
|
'Connection': 'close',
|
||||||
'Content-Type': 'text/html'
|
'Content-Type': 'text/html',
|
||||||
}, sock=socks[i], body=body)
|
},
|
||||||
|
sock=socks[i],
|
||||||
|
body=body,
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(resp['body'], body, 'keep-alive close')
|
self.assertEqual(resp['body'], body, 'keep-alive close')
|
||||||
self.assertIn('success', self.conf({
|
self.assertIn(
|
||||||
"spare": i % 4,
|
'success',
|
||||||
"max": (i % 4) + 1
|
self.conf(
|
||||||
}, 'applications/mirror/processes'), 'reconfigure 3')
|
str(i + 1),
|
||||||
|
'applications/mirror/processes',
|
||||||
|
),
|
||||||
|
'reconfigure 3',
|
||||||
|
)
|
||||||
|
|
||||||
def test_python_keepalive_reconfigure_2(self):
|
def test_python_keepalive_reconfigure_2(self):
|
||||||
self.load('mirror')
|
self.load('mirror')
|
||||||
|
|
||||||
body = '0123456789'
|
body = '0123456789'
|
||||||
|
|
||||||
(resp, sock) = self.post(headers={
|
(resp, sock) = self.post(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Connection': 'keep-alive',
|
'Connection': 'keep-alive',
|
||||||
'Content-Type': 'text/html'
|
'Content-Type': 'text/html',
|
||||||
}, start=True, body=body)
|
},
|
||||||
|
start=True,
|
||||||
|
body=body,
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(resp['body'], body, 'reconfigure 2 keep-alive 1')
|
self.assertEqual(resp['body'], body, 'reconfigure 2 keep-alive 1')
|
||||||
|
|
||||||
self.load('empty')
|
self.load('empty')
|
||||||
|
|
||||||
(resp, sock) = self.post(headers={
|
(resp, sock) = self.post(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Connection': 'close',
|
'Connection': 'close',
|
||||||
'Content-Type': 'text/html'
|
'Content-Type': 'text/html',
|
||||||
}, start=True, sock=sock, body=body)
|
},
|
||||||
|
start=True,
|
||||||
|
sock=sock,
|
||||||
|
body=body,
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(resp['status'], 200, 'reconfigure 2 keep-alive 2')
|
self.assertEqual(resp['status'], 200, 'reconfigure 2 keep-alive 2')
|
||||||
self.assertEqual(resp['body'], '', 'reconfigure 2 keep-alive 2 body')
|
self.assertEqual(resp['body'], '', 'reconfigure 2 keep-alive 2 body')
|
||||||
|
|
||||||
self.assertIn('success', self.conf({
|
self.assertIn(
|
||||||
"listeners": {},
|
'success',
|
||||||
"applications": {}
|
self.conf({"listeners": {}, "applications": {}}),
|
||||||
}), 'reconfigure 2 clear configuration')
|
'reconfigure 2 clear configuration',
|
||||||
|
)
|
||||||
|
|
||||||
resp = self.get(sock=sock)
|
resp = self.get(sock=sock)
|
||||||
|
|
||||||
@@ -219,18 +287,27 @@ class TestUnitPythonApplication(unit.TestUnitApplicationPython):
|
|||||||
def test_python_keepalive_reconfigure_3(self):
|
def test_python_keepalive_reconfigure_3(self):
|
||||||
self.load('empty')
|
self.load('empty')
|
||||||
|
|
||||||
(resp, sock) = self.http(b"""GET / HTTP/1.1
|
(resp, sock) = self.http(
|
||||||
""", start=True, raw=True)
|
b"""GET / HTTP/1.1
|
||||||
|
""",
|
||||||
|
start=True,
|
||||||
|
raw=True,
|
||||||
|
)
|
||||||
|
|
||||||
self.assertIn('success', self.conf({
|
self.assertIn(
|
||||||
"listeners": {},
|
'success',
|
||||||
"applications": {}
|
self.conf({"listeners": {}, "applications": {}}),
|
||||||
}), 'reconfigure 3 clear configuration')
|
'reconfigure 3 clear configuration',
|
||||||
|
)
|
||||||
|
|
||||||
resp = self.http(b"""Host: localhost
|
resp = self.http(
|
||||||
|
b"""Host: localhost
|
||||||
Connection: close
|
Connection: close
|
||||||
|
|
||||||
""", sock=sock, raw=True)
|
""",
|
||||||
|
sock=sock,
|
||||||
|
raw=True,
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(resp['status'], 200, 'reconfigure 3')
|
self.assertEqual(resp['status'], 200, 'reconfigure 3')
|
||||||
|
|
||||||
@@ -239,10 +316,7 @@ Connection: close
|
|||||||
|
|
||||||
self.get()
|
self.get()
|
||||||
|
|
||||||
self.conf({
|
self.conf({"listeners": {}, "applications": {}})
|
||||||
"listeners": {},
|
|
||||||
"applications": {}
|
|
||||||
})
|
|
||||||
|
|
||||||
self.stop()
|
self.stop()
|
||||||
|
|
||||||
@@ -267,35 +341,47 @@ Connection: close
|
|||||||
|
|
||||||
body = '0123456789'
|
body = '0123456789'
|
||||||
|
|
||||||
resp = self.post(headers={
|
resp = self.post(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Input-Length': '5',
|
'Input-Length': '5',
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
}, body=body)
|
},
|
||||||
|
body=body,
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(resp['body'], body[:5], 'input read length lt body')
|
self.assertEqual(resp['body'], body[:5], 'input read length lt body')
|
||||||
|
|
||||||
resp = self.post(headers={
|
resp = self.post(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Input-Length': '15',
|
'Input-Length': '15',
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
}, body=body)
|
},
|
||||||
|
body=body,
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(resp['body'], body, 'input read length gt body')
|
self.assertEqual(resp['body'], body, 'input read length gt body')
|
||||||
|
|
||||||
resp = self.post(headers={
|
resp = self.post(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Input-Length': '0',
|
'Input-Length': '0',
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
}, body=body)
|
},
|
||||||
|
body=body,
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(resp['body'], '', 'input read length zero')
|
self.assertEqual(resp['body'], '', 'input read length zero')
|
||||||
|
|
||||||
resp = self.post(headers={
|
resp = self.post(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Input-Length': '-1',
|
'Input-Length': '-1',
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
}, body=body)
|
},
|
||||||
|
body=body,
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(resp['body'], body, 'input read length negative')
|
self.assertEqual(resp['body'], body, 'input read length negative')
|
||||||
|
|
||||||
@@ -309,7 +395,8 @@ Connection: close
|
|||||||
|
|
||||||
self.assertIsNotNone(
|
self.assertIsNotNone(
|
||||||
self.search_in_log(r'\[error\].+Error in application\.'),
|
self.search_in_log(r'\[error\].+Error in application\.'),
|
||||||
'errors write')
|
'errors write',
|
||||||
|
)
|
||||||
|
|
||||||
def test_python_application_body_array(self):
|
def test_python_application_body_array(self):
|
||||||
self.load('body_array')
|
self.load('body_array')
|
||||||
@@ -349,8 +436,9 @@ Connection: close
|
|||||||
|
|
||||||
self.stop()
|
self.stop()
|
||||||
|
|
||||||
self.assertIsNotNone(self.search_in_log(r'Close called\.'),
|
self.assertIsNotNone(
|
||||||
'close error')
|
self.search_in_log(r'Close called\.'), 'close error'
|
||||||
|
)
|
||||||
|
|
||||||
def test_python_application_not_iterable(self):
|
def test_python_application_not_iterable(self):
|
||||||
self.load('not_iterable')
|
self.load('not_iterable')
|
||||||
@@ -359,14 +447,18 @@ Connection: close
|
|||||||
|
|
||||||
self.stop()
|
self.stop()
|
||||||
|
|
||||||
self.assertIsNotNone(self.search_in_log(
|
self.assertIsNotNone(
|
||||||
r'\[error\].+the application returned not an iterable object'),
|
self.search_in_log(
|
||||||
'not iterable')
|
r'\[error\].+the application returned not an iterable object'
|
||||||
|
),
|
||||||
|
'not iterable',
|
||||||
|
)
|
||||||
|
|
||||||
def test_python_application_write(self):
|
def test_python_application_write(self):
|
||||||
self.load('write')
|
self.load('write')
|
||||||
|
|
||||||
self.assertEqual(self.get()['body'], '0123456789', 'write')
|
self.assertEqual(self.get()['body'], '0123456789', 'write')
|
||||||
|
|
||||||
|
|
||||||
if __name__ == '__main__':
|
if __name__ == '__main__':
|
||||||
TestUnitPythonApplication.main()
|
TestUnitPythonApplication.main()
|
||||||
|
|||||||
@@ -1,38 +1,37 @@
|
|||||||
import unittest
|
import unittest
|
||||||
import unit
|
import unit
|
||||||
|
|
||||||
class TestUnitPythonBasic(unit.TestUnitControl):
|
|
||||||
|
|
||||||
|
class TestUnitPythonBasic(unit.TestUnitControl):
|
||||||
def setUpClass():
|
def setUpClass():
|
||||||
unit.TestUnit().check_modules('python')
|
unit.TestUnit().check_modules('python')
|
||||||
|
|
||||||
conf_app = {
|
conf_app = {
|
||||||
"app": {
|
"app": {
|
||||||
"type": "python",
|
"type": "python",
|
||||||
"processes": { "spare": 0 },
|
"processes": {"spare": 0},
|
||||||
"path": "/app",
|
"path": "/app",
|
||||||
"module": "wsgi"
|
"module": "wsgi",
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
conf_basic = {
|
conf_basic = {
|
||||||
"listeners": {
|
"listeners": {"*:7080": {"application": "app"}},
|
||||||
"*:7080": {
|
"applications": conf_app,
|
||||||
"application": "app"
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"applications": conf_app
|
|
||||||
}
|
}
|
||||||
|
|
||||||
def test_python_get_empty(self):
|
def test_python_get_empty(self):
|
||||||
self.assertEqual(self.conf_get(),
|
self.assertEqual(
|
||||||
{'listeners': {}, 'applications': {}}, 'empty')
|
self.conf_get(), {'listeners': {}, 'applications': {}}, 'empty'
|
||||||
|
)
|
||||||
|
|
||||||
def test_python_get_prefix_listeners(self):
|
def test_python_get_prefix_listeners(self):
|
||||||
self.assertEqual(self.conf_get('listeners'), {}, 'listeners prefix')
|
self.assertEqual(self.conf_get('listeners'), {}, 'listeners prefix')
|
||||||
|
|
||||||
def test_python_get_prefix_applications(self):
|
def test_python_get_prefix_applications(self):
|
||||||
self.assertEqual(self.conf_get('applications'), {}, 'applications prefix')
|
self.assertEqual(
|
||||||
|
self.conf_get('applications'), {}, 'applications prefix'
|
||||||
|
)
|
||||||
|
|
||||||
def test_python_get_applications(self):
|
def test_python_get_applications(self):
|
||||||
self.conf(self.conf_app, 'applications')
|
self.conf(self.conf_app, 'applications')
|
||||||
@@ -40,113 +39,146 @@ class TestUnitPythonBasic(unit.TestUnitControl):
|
|||||||
conf = self.conf_get()
|
conf = self.conf_get()
|
||||||
|
|
||||||
self.assertEqual(conf['listeners'], {}, 'listeners')
|
self.assertEqual(conf['listeners'], {}, 'listeners')
|
||||||
self.assertEqual(conf['applications'],
|
self.assertEqual(
|
||||||
|
conf['applications'],
|
||||||
{
|
{
|
||||||
"app": {
|
"app": {
|
||||||
"type": "python",
|
"type": "python",
|
||||||
"processes": { "spare": 0 },
|
"processes": {"spare": 0},
|
||||||
"path": "/app",
|
"path": "/app",
|
||||||
"module": "wsgi"
|
"module": "wsgi",
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
'applications')
|
'applications',
|
||||||
|
)
|
||||||
|
|
||||||
def test_python_get_applications_prefix(self):
|
def test_python_get_applications_prefix(self):
|
||||||
self.conf(self.conf_app, 'applications')
|
self.conf(self.conf_app, 'applications')
|
||||||
|
|
||||||
self.assertEqual(self.conf_get('applications'),
|
self.assertEqual(
|
||||||
|
self.conf_get('applications'),
|
||||||
{
|
{
|
||||||
"app": {
|
"app": {
|
||||||
"type": "python",
|
"type": "python",
|
||||||
"processes": { "spare": 0 },
|
"processes": {"spare": 0},
|
||||||
"path": "/app",
|
"path": "/app",
|
||||||
"module":"wsgi"
|
"module": "wsgi",
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
'applications prefix')
|
'applications prefix',
|
||||||
|
)
|
||||||
|
|
||||||
def test_python_get_applications_prefix_2(self):
|
def test_python_get_applications_prefix_2(self):
|
||||||
self.conf(self.conf_app, 'applications')
|
self.conf(self.conf_app, 'applications')
|
||||||
|
|
||||||
self.assertEqual(self.conf_get('applications/app'),
|
self.assertEqual(
|
||||||
|
self.conf_get('applications/app'),
|
||||||
{
|
{
|
||||||
"type": "python",
|
"type": "python",
|
||||||
"processes": { "spare": 0 },
|
"processes": {"spare": 0},
|
||||||
"path": "/app",
|
"path": "/app",
|
||||||
"module": "wsgi"
|
"module": "wsgi",
|
||||||
},
|
},
|
||||||
'applications prefix 2')
|
'applications prefix 2',
|
||||||
|
)
|
||||||
|
|
||||||
def test_python_get_applications_prefix_3(self):
|
def test_python_get_applications_prefix_3(self):
|
||||||
self.conf(self.conf_app, 'applications')
|
self.conf(self.conf_app, 'applications')
|
||||||
|
|
||||||
self.assertEqual(self.conf_get('applications/app/type'), 'python',
|
self.assertEqual(
|
||||||
'type')
|
self.conf_get('applications/app/type'), 'python', 'type'
|
||||||
self.assertEqual(self.conf_get('applications/app/processes/spare'), 0,
|
)
|
||||||
'spare')
|
self.assertEqual(
|
||||||
|
self.conf_get('applications/app/processes/spare'), 0, 'spare'
|
||||||
|
)
|
||||||
|
|
||||||
def test_python_get_listeners(self):
|
def test_python_get_listeners(self):
|
||||||
self.conf(self.conf_basic)
|
self.conf(self.conf_basic)
|
||||||
|
|
||||||
self.assertEqual(self.conf_get()['listeners'],
|
self.assertEqual(
|
||||||
{"*:7080":{"application":"app"}}, 'listeners')
|
self.conf_get()['listeners'],
|
||||||
|
{"*:7080": {"application": "app"}},
|
||||||
|
'listeners',
|
||||||
|
)
|
||||||
|
|
||||||
def test_python_get_listeners_prefix(self):
|
def test_python_get_listeners_prefix(self):
|
||||||
self.conf(self.conf_basic)
|
self.conf(self.conf_basic)
|
||||||
|
|
||||||
self.assertEqual(self.conf_get('listeners'),
|
self.assertEqual(
|
||||||
{"*:7080":{"application":"app"}}, 'listeners prefix')
|
self.conf_get('listeners'),
|
||||||
|
{"*:7080": {"application": "app"}},
|
||||||
|
'listeners prefix',
|
||||||
|
)
|
||||||
|
|
||||||
def test_python_get_listeners_prefix_2(self):
|
def test_python_get_listeners_prefix_2(self):
|
||||||
self.conf(self.conf_basic)
|
self.conf(self.conf_basic)
|
||||||
|
|
||||||
self.assertEqual(self.conf_get('listeners/*:7080'),
|
self.assertEqual(
|
||||||
{"application":"app"}, 'listeners prefix 2')
|
self.conf_get('listeners/*:7080'),
|
||||||
|
{"application": "app"},
|
||||||
|
'listeners prefix 2',
|
||||||
|
)
|
||||||
|
|
||||||
def test_python_change_listener(self):
|
def test_python_change_listener(self):
|
||||||
self.conf(self.conf_basic)
|
self.conf(self.conf_basic)
|
||||||
self.conf({"*:7081":{"application":"app"}}, 'listeners')
|
self.conf({"*:7081": {"application": "app"}}, 'listeners')
|
||||||
|
|
||||||
self.assertEqual(self.conf_get('listeners'),
|
self.assertEqual(
|
||||||
{"*:7081": {"application":"app"}}, 'change listener')
|
self.conf_get('listeners'),
|
||||||
|
{"*:7081": {"application": "app"}},
|
||||||
|
'change listener',
|
||||||
|
)
|
||||||
|
|
||||||
def test_python_add_listener(self):
|
def test_python_add_listener(self):
|
||||||
self.conf(self.conf_basic)
|
self.conf(self.conf_basic)
|
||||||
self.conf({"application":"app"}, 'listeners/*:7082')
|
self.conf({"application": "app"}, 'listeners/*:7082')
|
||||||
|
|
||||||
self.assertEqual(self.conf_get('listeners'),
|
self.assertEqual(
|
||||||
|
self.conf_get('listeners'),
|
||||||
{
|
{
|
||||||
"*:7080": {
|
"*:7080": {"application": "app"},
|
||||||
"application": "app"
|
"*:7082": {"application": "app"},
|
||||||
},
|
},
|
||||||
"*:7082": {
|
'add listener',
|
||||||
"application": "app"
|
)
|
||||||
}
|
|
||||||
},
|
|
||||||
'add listener')
|
|
||||||
|
|
||||||
def test_python_change_application(self):
|
def test_python_change_application(self):
|
||||||
self.conf(self.conf_basic)
|
self.conf(self.conf_basic)
|
||||||
|
|
||||||
self.conf('30', 'applications/app/processes/max')
|
self.conf('30', 'applications/app/processes/max')
|
||||||
self.assertEqual(self.conf_get('applications/app/processes/max'), 30,
|
self.assertEqual(
|
||||||
'change application max')
|
self.conf_get('applications/app/processes/max'),
|
||||||
|
30,
|
||||||
|
'change application max',
|
||||||
|
)
|
||||||
|
|
||||||
self.conf('"/www"', 'applications/app/path')
|
self.conf('"/www"', 'applications/app/path')
|
||||||
self.assertEqual(self.conf_get('applications/app/path'), '/www',
|
self.assertEqual(
|
||||||
'change application path')
|
self.conf_get('applications/app/path'),
|
||||||
|
'/www',
|
||||||
|
'change application path',
|
||||||
|
)
|
||||||
|
|
||||||
def test_python_delete(self):
|
def test_python_delete(self):
|
||||||
self.conf(self.conf_basic)
|
self.conf(self.conf_basic)
|
||||||
|
|
||||||
self.assertIn('error', self.conf_delete('applications/app'),
|
self.assertIn(
|
||||||
'delete app before listener')
|
'error',
|
||||||
self.assertIn('success', self.conf_delete('listeners/*:7080'),
|
self.conf_delete('applications/app'),
|
||||||
'delete listener')
|
'delete app before listener',
|
||||||
self.assertIn('success', self.conf_delete('applications/app'),
|
)
|
||||||
'delete app after listener')
|
self.assertIn(
|
||||||
self.assertIn('error', self.conf_delete('applications/app'),
|
'success', self.conf_delete('listeners/*:7080'), 'delete listener'
|
||||||
'delete app again')
|
)
|
||||||
|
self.assertIn(
|
||||||
|
'success',
|
||||||
|
self.conf_delete('applications/app'),
|
||||||
|
'delete app after listener',
|
||||||
|
)
|
||||||
|
self.assertIn(
|
||||||
|
'error', self.conf_delete('applications/app'), 'delete app again'
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
if __name__ == '__main__':
|
if __name__ == '__main__':
|
||||||
TestUnitPythonBasic.main()
|
TestUnitPythonBasic.main()
|
||||||
|
|||||||
@@ -1,128 +1,181 @@
|
|||||||
import unittest
|
import unittest
|
||||||
import unit
|
import unit
|
||||||
|
|
||||||
class TestUnitPythonEnvironment(unit.TestUnitApplicationPython):
|
|
||||||
|
|
||||||
|
class TestUnitPythonEnvironment(unit.TestUnitApplicationPython):
|
||||||
def setUpClass():
|
def setUpClass():
|
||||||
unit.TestUnit().check_modules('python')
|
unit.TestUnit().check_modules('python')
|
||||||
|
|
||||||
def test_python_environment_name_null(self):
|
def test_python_environment_name_null(self):
|
||||||
self.load('environment')
|
self.load('environment')
|
||||||
|
|
||||||
self.assertIn('error', self.conf({
|
self.assertIn(
|
||||||
"va\0r": "val1"
|
'error',
|
||||||
}, 'applications/environment/environment'), 'name null')
|
self.conf(
|
||||||
|
{"va\0r": "val1"}, 'applications/environment/environment'
|
||||||
|
),
|
||||||
|
'name null',
|
||||||
|
)
|
||||||
|
|
||||||
def test_python_environment_name_equals(self):
|
def test_python_environment_name_equals(self):
|
||||||
self.load('environment')
|
self.load('environment')
|
||||||
|
|
||||||
self.assertIn('error', self.conf({
|
self.assertIn(
|
||||||
"var=": "val1"
|
'error',
|
||||||
}, 'applications/environment/environment'), 'name equals')
|
self.conf(
|
||||||
|
{"var=": "val1"}, 'applications/environment/environment'
|
||||||
|
),
|
||||||
|
'name equals',
|
||||||
|
)
|
||||||
|
|
||||||
def test_python_environment_value_null(self):
|
def test_python_environment_value_null(self):
|
||||||
self.load('environment')
|
self.load('environment')
|
||||||
|
|
||||||
self.assertIn('error', self.conf({
|
self.assertIn(
|
||||||
"var": "\0val"
|
'error',
|
||||||
}, 'applications/environment/environment'), 'value null')
|
self.conf(
|
||||||
|
{"var": "\0val"}, 'applications/environment/environment'
|
||||||
|
),
|
||||||
|
'value null',
|
||||||
|
)
|
||||||
|
|
||||||
def test_python_environment_update(self):
|
def test_python_environment_update(self):
|
||||||
self.load('environment')
|
self.load('environment')
|
||||||
|
|
||||||
self.conf({
|
self.conf({"var": "val1"}, 'applications/environment/environment')
|
||||||
"var": "val1"
|
|
||||||
}, 'applications/environment/environment')
|
|
||||||
|
|
||||||
self.assertEqual(self.get(headers={
|
self.assertEqual(
|
||||||
|
self.get(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'X-Variables': 'var',
|
'X-Variables': 'var',
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
})['body'], 'val1,', 'set')
|
}
|
||||||
|
)['body'],
|
||||||
|
'val1,',
|
||||||
|
'set',
|
||||||
|
)
|
||||||
|
|
||||||
self.conf({
|
self.conf({"var": "val2"}, 'applications/environment/environment')
|
||||||
"var": "val2"
|
|
||||||
}, 'applications/environment/environment')
|
|
||||||
|
|
||||||
self.assertEqual(self.get(headers={
|
self.assertEqual(
|
||||||
|
self.get(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'X-Variables': 'var',
|
'X-Variables': 'var',
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
})['body'], 'val2,', 'update')
|
}
|
||||||
|
)['body'],
|
||||||
|
'val2,',
|
||||||
|
'update',
|
||||||
|
)
|
||||||
|
|
||||||
def test_python_environment_replace(self):
|
def test_python_environment_replace(self):
|
||||||
self.load('environment')
|
self.load('environment')
|
||||||
|
|
||||||
self.conf({
|
self.conf({"var1": "val1"}, 'applications/environment/environment')
|
||||||
"var1": "val1"
|
|
||||||
}, 'applications/environment/environment')
|
|
||||||
|
|
||||||
self.assertEqual(self.get(headers={
|
self.assertEqual(
|
||||||
|
self.get(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'X-Variables': 'var1',
|
'X-Variables': 'var1',
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
})['body'], 'val1,', 'set')
|
}
|
||||||
|
)['body'],
|
||||||
|
'val1,',
|
||||||
|
'set',
|
||||||
|
)
|
||||||
|
|
||||||
self.conf({
|
self.conf({"var2": "val2"}, 'applications/environment/environment')
|
||||||
"var2": "val2"
|
|
||||||
}, 'applications/environment/environment')
|
|
||||||
|
|
||||||
self.assertEqual(self.get(headers={
|
self.assertEqual(
|
||||||
|
self.get(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'X-Variables': 'var1,var2',
|
'X-Variables': 'var1,var2',
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
})['body'], 'val2,', 'replace')
|
}
|
||||||
|
)['body'],
|
||||||
|
'val2,',
|
||||||
|
'replace',
|
||||||
|
)
|
||||||
|
|
||||||
def test_python_environment_clear(self):
|
def test_python_environment_clear(self):
|
||||||
self.load('environment')
|
self.load('environment')
|
||||||
|
|
||||||
self.conf({
|
self.conf(
|
||||||
"var1": "val1",
|
{"var1": "val1", "var2": "val2"},
|
||||||
"var2": "val2"
|
'applications/environment/environment',
|
||||||
}, 'applications/environment/environment')
|
)
|
||||||
|
|
||||||
self.assertEqual(self.get(headers={
|
self.assertEqual(
|
||||||
|
self.get(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'X-Variables': 'var1,var2',
|
'X-Variables': 'var1,var2',
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
})['body'], 'val1,val2,', 'set')
|
}
|
||||||
|
)['body'],
|
||||||
|
'val1,val2,',
|
||||||
|
'set',
|
||||||
|
)
|
||||||
|
|
||||||
self.conf({}, 'applications/environment/environment')
|
self.conf({}, 'applications/environment/environment')
|
||||||
|
|
||||||
self.assertEqual(self.get(headers={
|
self.assertEqual(
|
||||||
|
self.get(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'X-Variables': 'var1,var2',
|
'X-Variables': 'var1,var2',
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
})['body'], '', 'clear')
|
}
|
||||||
|
)['body'],
|
||||||
|
'',
|
||||||
|
'clear',
|
||||||
|
)
|
||||||
|
|
||||||
def test_python_environment_replace_default(self):
|
def test_python_environment_replace_default(self):
|
||||||
self.load('environment')
|
self.load('environment')
|
||||||
|
|
||||||
pwd_default = self.get(headers={
|
pwd_default = self.get(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'X-Variables': 'PWD',
|
'X-Variables': 'PWD',
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
})['body']
|
}
|
||||||
|
)['body']
|
||||||
|
|
||||||
self.assertGreater(len(pwd_default), 1, 'get default')
|
self.assertGreater(len(pwd_default), 1, 'get default')
|
||||||
|
|
||||||
self.conf({
|
self.conf({"PWD": "new/pwd"}, 'applications/environment/environment')
|
||||||
"PWD": "new/pwd"
|
|
||||||
}, 'applications/environment/environment')
|
|
||||||
|
|
||||||
self.assertEqual(self.get(headers={
|
self.assertEqual(
|
||||||
|
self.get(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'X-Variables': 'PWD',
|
'X-Variables': 'PWD',
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
})['body'], 'new/pwd,', 'replace default')
|
}
|
||||||
|
)['body'],
|
||||||
|
'new/pwd,',
|
||||||
|
'replace default',
|
||||||
|
)
|
||||||
|
|
||||||
self.conf({}, 'applications/environment/environment')
|
self.conf({}, 'applications/environment/environment')
|
||||||
|
|
||||||
self.assertEqual(self.get(headers={
|
self.assertEqual(
|
||||||
|
self.get(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'X-Variables': 'PWD',
|
'X-Variables': 'PWD',
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
})['body'], pwd_default, 'restore default')
|
}
|
||||||
|
)['body'],
|
||||||
|
pwd_default,
|
||||||
|
'restore default',
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
if __name__ == '__main__':
|
if __name__ == '__main__':
|
||||||
TestUnitPythonEnvironment.main()
|
TestUnitPythonEnvironment.main()
|
||||||
|
|||||||
@@ -4,8 +4,8 @@ import subprocess
|
|||||||
import unittest
|
import unittest
|
||||||
import unit
|
import unit
|
||||||
|
|
||||||
class TestUnitPythonProcman(unit.TestUnitApplicationPython):
|
|
||||||
|
|
||||||
|
class TestUnitPythonProcman(unit.TestUnitApplicationPython):
|
||||||
def setUpClass():
|
def setUpClass():
|
||||||
unit.TestUnit().check_modules('python')
|
unit.TestUnit().check_modules('python')
|
||||||
|
|
||||||
@@ -29,55 +29,88 @@ class TestUnitPythonProcman(unit.TestUnitApplicationPython):
|
|||||||
def test_python_processes_access(self):
|
def test_python_processes_access(self):
|
||||||
self.conf('1', 'applications/' + self.app_name + '/processes')
|
self.conf('1', 'applications/' + self.app_name + '/processes')
|
||||||
|
|
||||||
self.assertIn('error', self.conf_get('/applications/' + self.app_name +
|
self.assertIn(
|
||||||
'/processes/max'), 'max no access')
|
'error',
|
||||||
self.assertIn('error', self.conf_get('/applications/' + self.app_name +
|
self.conf_get('/applications/' + self.app_name + '/processes/max'),
|
||||||
'/processes/spare'), 'spare no access')
|
'max no access',
|
||||||
self.assertIn('error', self.conf_get('/applications/' + self.app_name +
|
)
|
||||||
'/processes/idle_timeout'), 'idle_timeout no access')
|
self.assertIn(
|
||||||
|
'error',
|
||||||
|
self.conf_get(
|
||||||
|
'/applications/' + self.app_name + '/processes/spare'
|
||||||
|
),
|
||||||
|
'spare no access',
|
||||||
|
)
|
||||||
|
self.assertIn(
|
||||||
|
'error',
|
||||||
|
self.conf_get(
|
||||||
|
'/applications/' + self.app_name + '/processes/idle_timeout'
|
||||||
|
),
|
||||||
|
'idle_timeout no access',
|
||||||
|
)
|
||||||
|
|
||||||
def test_python_processes_spare_negative(self):
|
def test_python_processes_spare_negative(self):
|
||||||
self.assertIn('error', self.conf({
|
self.assertIn(
|
||||||
"spare": -1
|
'error',
|
||||||
}, 'applications/' + self.app_name + '/processes'), 'negative spare')
|
self.conf(
|
||||||
|
{"spare": -1}, 'applications/' + self.app_name + '/processes'
|
||||||
|
),
|
||||||
|
'negative spare',
|
||||||
|
)
|
||||||
|
|
||||||
def test_python_processes_max_negative(self):
|
def test_python_processes_max_negative(self):
|
||||||
self.assertIn('error', self.conf({
|
self.assertIn(
|
||||||
"max": -1
|
'error',
|
||||||
}, 'applications/' + self.app_name + '/processes'), 'negative max')
|
self.conf(
|
||||||
|
{"max": -1}, 'applications/' + self.app_name + '/processes'
|
||||||
|
),
|
||||||
|
'negative max',
|
||||||
|
)
|
||||||
|
|
||||||
def test_python_processes_idle_timeout_negative(self):
|
def test_python_processes_idle_timeout_negative(self):
|
||||||
self.assertIn('error', self.conf({
|
self.assertIn(
|
||||||
"idle_timeout": -1
|
'error',
|
||||||
}, 'applications/' + self.app_name + '/processes'),
|
self.conf(
|
||||||
'negative idle_timeout')
|
{"idle_timeout": -1},
|
||||||
|
'applications/' + self.app_name + '/processes',
|
||||||
|
),
|
||||||
|
'negative idle_timeout',
|
||||||
|
)
|
||||||
|
|
||||||
def test_python_processes_spare_gt_max_default(self):
|
def test_python_processes_spare_gt_max_default(self):
|
||||||
self.assertIn('error', self.conf({"spare": 2},
|
self.assertIn(
|
||||||
'applications/' + self.app_name + '/processes'),
|
'error',
|
||||||
'spare greater than max default')
|
self.conf(
|
||||||
|
{"spare": 2}, 'applications/' + self.app_name + '/processes'
|
||||||
|
),
|
||||||
|
'spare greater than max default',
|
||||||
|
)
|
||||||
|
|
||||||
def test_python_processes_spare_gt_max(self):
|
def test_python_processes_spare_gt_max(self):
|
||||||
self.assertIn('error', self.conf({
|
self.assertIn(
|
||||||
"spare": 2,
|
'error',
|
||||||
"max": 1,
|
self.conf(
|
||||||
"idle_timeout": 1
|
{"spare": 2, "max": 1, "idle_timeout": 1},
|
||||||
}, '/applications/' + self.app_name + '/processes'),
|
'/applications/' + self.app_name + '/processes',
|
||||||
'spare greater than max')
|
),
|
||||||
|
'spare greater than max',
|
||||||
|
)
|
||||||
|
|
||||||
def test_python_processes_max_zero(self):
|
def test_python_processes_max_zero(self):
|
||||||
self.assertIn('error', self.conf({
|
self.assertIn(
|
||||||
"spare": 0,
|
'error',
|
||||||
"max": 0,
|
self.conf(
|
||||||
"idle_timeout": 1
|
{"spare": 0, "max": 0, "idle_timeout": 1},
|
||||||
}, 'applications/' + self.app_name + '/processes'), 'max 0')
|
'applications/' + self.app_name + '/processes',
|
||||||
|
),
|
||||||
|
'max 0',
|
||||||
|
)
|
||||||
|
|
||||||
def test_python_processes_idle_timeout_zero(self):
|
def test_python_processes_idle_timeout_zero(self):
|
||||||
self.conf({
|
self.conf(
|
||||||
"spare": 0,
|
{"spare": 0, "max": 2, "idle_timeout": 0},
|
||||||
"max": 2,
|
'applications/' + self.app_name + '/processes',
|
||||||
"idle_timeout": 0
|
)
|
||||||
}, 'applications/' + self.app_name + '/processes')
|
|
||||||
|
|
||||||
self.get()
|
self.get()
|
||||||
self.assertEqual(len(self.pids_for_process()), 0, 'idle timeout 0')
|
self.assertEqual(len(self.pids_for_process()), 0, 'idle timeout 0')
|
||||||
@@ -114,11 +147,10 @@ class TestUnitPythonProcman(unit.TestUnitApplicationPython):
|
|||||||
self.assertTrue(pids.issubset(pids_new), 'prefork same processes')
|
self.assertTrue(pids.issubset(pids_new), 'prefork same processes')
|
||||||
|
|
||||||
def test_python_ondemand(self):
|
def test_python_ondemand(self):
|
||||||
self.conf({
|
self.conf(
|
||||||
"spare": 0,
|
{"spare": 0, "max": 8, "idle_timeout": 1},
|
||||||
"max": 8,
|
'applications/' + self.app_name + '/processes',
|
||||||
"idle_timeout": 1
|
)
|
||||||
}, 'applications/' + self.app_name + '/processes')
|
|
||||||
|
|
||||||
self.assertEqual(len(self.pids_for_process()), 0, 'on-demand 0')
|
self.assertEqual(len(self.pids_for_process()), 0, 'on-demand 0')
|
||||||
|
|
||||||
@@ -131,16 +163,17 @@ class TestUnitPythonProcman(unit.TestUnitApplicationPython):
|
|||||||
|
|
||||||
time.sleep(1)
|
time.sleep(1)
|
||||||
|
|
||||||
self.assertEqual(len(self.pids_for_process()), 0, 'on-demand stop idle')
|
self.assertEqual(
|
||||||
|
len(self.pids_for_process()), 0, 'on-demand stop idle'
|
||||||
|
)
|
||||||
|
|
||||||
self.stop_all()
|
self.stop_all()
|
||||||
|
|
||||||
def test_python_scale_updown(self):
|
def test_python_scale_updown(self):
|
||||||
self.conf({
|
self.conf(
|
||||||
"spare": 2,
|
{"spare": 2, "max": 8, "idle_timeout": 1},
|
||||||
"max": 8,
|
'applications/' + self.app_name + '/processes',
|
||||||
"idle_timeout": 1
|
)
|
||||||
}, 'applications/' + self.app_name + '/processes')
|
|
||||||
|
|
||||||
pids = self.pids_for_process()
|
pids = self.pids_for_process()
|
||||||
self.assertEqual(len(pids), 2, 'updown 2')
|
self.assertEqual(len(pids), 2, 'updown 2')
|
||||||
@@ -151,7 +184,9 @@ class TestUnitPythonProcman(unit.TestUnitApplicationPython):
|
|||||||
self.assertTrue(pids.issubset(pids_new), 'updown 3 only 1 new')
|
self.assertTrue(pids.issubset(pids_new), 'updown 3 only 1 new')
|
||||||
|
|
||||||
self.get()
|
self.get()
|
||||||
self.assertSetEqual(self.pids_for_process(), pids_new, 'updown still 3')
|
self.assertSetEqual(
|
||||||
|
self.pids_for_process(), pids_new, 'updown still 3'
|
||||||
|
)
|
||||||
|
|
||||||
time.sleep(1)
|
time.sleep(1)
|
||||||
|
|
||||||
@@ -166,11 +201,10 @@ class TestUnitPythonProcman(unit.TestUnitApplicationPython):
|
|||||||
self.stop_all()
|
self.stop_all()
|
||||||
|
|
||||||
def test_python_reconfigure(self):
|
def test_python_reconfigure(self):
|
||||||
self.conf({
|
self.conf(
|
||||||
"spare": 2,
|
{"spare": 2, "max": 6, "idle_timeout": 1},
|
||||||
"max": 6,
|
'applications/' + self.app_name + '/processes',
|
||||||
"idle_timeout": 1
|
)
|
||||||
}, 'applications/' + self.app_name + '/processes')
|
|
||||||
|
|
||||||
pids = self.pids_for_process()
|
pids = self.pids_for_process()
|
||||||
self.assertEqual(len(pids), 2, 'reconf 2')
|
self.assertEqual(len(pids), 2, 'reconf 2')
|
||||||
@@ -191,11 +225,10 @@ class TestUnitPythonProcman(unit.TestUnitApplicationPython):
|
|||||||
self.stop_all()
|
self.stop_all()
|
||||||
|
|
||||||
def test_python_idle_timeout(self):
|
def test_python_idle_timeout(self):
|
||||||
self.conf({
|
self.conf(
|
||||||
"spare": 0,
|
{"spare": 0, "max": 6, "idle_timeout": 2},
|
||||||
"max": 6,
|
'applications/' + self.app_name + '/processes',
|
||||||
"idle_timeout": 2
|
)
|
||||||
}, 'applications/' + self.app_name + '/processes')
|
|
||||||
|
|
||||||
self.get()
|
self.get()
|
||||||
pids = self.pids_for_process()
|
pids = self.pids_for_process()
|
||||||
@@ -209,40 +242,42 @@ class TestUnitPythonProcman(unit.TestUnitApplicationPython):
|
|||||||
|
|
||||||
pids_new = self.pids_for_process()
|
pids_new = self.pids_for_process()
|
||||||
self.assertEqual(len(pids_new), 1, 'idle timeout still 1')
|
self.assertEqual(len(pids_new), 1, 'idle timeout still 1')
|
||||||
self.assertSetEqual(self.pids_for_process(), pids,
|
self.assertSetEqual(
|
||||||
'idle timeout still 1 same pid')
|
self.pids_for_process(), pids, 'idle timeout still 1 same pid'
|
||||||
|
)
|
||||||
|
|
||||||
time.sleep(1)
|
time.sleep(1)
|
||||||
|
|
||||||
self.assertEqual(len(self.pids_for_process()), 0, 'idle timed out')
|
self.assertEqual(len(self.pids_for_process()), 0, 'idle timed out')
|
||||||
|
|
||||||
def test_python_processes_connection_keepalive(self):
|
def test_python_processes_connection_keepalive(self):
|
||||||
self.conf({
|
self.conf(
|
||||||
"spare": 0,
|
{"spare": 0, "max": 6, "idle_timeout": 2},
|
||||||
"max": 6,
|
'applications/' + self.app_name + '/processes',
|
||||||
"idle_timeout": 2
|
)
|
||||||
}, 'applications/' + self.app_name + '/processes')
|
|
||||||
|
|
||||||
(resp, sock) = self.get(headers={
|
(resp, sock) = self.get(
|
||||||
'Host': 'localhost',
|
headers={'Host': 'localhost', 'Connection': 'keep-alive'},
|
||||||
'Connection': 'keep-alive'
|
start=True,
|
||||||
}, start=True, read_timeout=1)
|
read_timeout=1,
|
||||||
self.assertEqual(len(self.pids_for_process()), 1,
|
)
|
||||||
'keepalive connection 1')
|
self.assertEqual(
|
||||||
|
len(self.pids_for_process()), 1, 'keepalive connection 1'
|
||||||
|
)
|
||||||
|
|
||||||
time.sleep(2)
|
time.sleep(2)
|
||||||
|
|
||||||
self.assertEqual(len(self.pids_for_process()), 0, 'keepalive connection 0')
|
self.assertEqual(
|
||||||
|
len(self.pids_for_process()), 0, 'keepalive connection 0'
|
||||||
|
)
|
||||||
|
|
||||||
sock.close()
|
sock.close()
|
||||||
|
|
||||||
def stop_all(self):
|
def stop_all(self):
|
||||||
self.conf({
|
self.conf({"listeners": {}, "applications": {}})
|
||||||
"listeners": {},
|
|
||||||
"applications": {}
|
|
||||||
})
|
|
||||||
|
|
||||||
self.assertEqual(len(self.pids_for_process()), 0, 'stop all')
|
self.assertEqual(len(self.pids_for_process()), 0, 'stop all')
|
||||||
|
|
||||||
|
|
||||||
if __name__ == '__main__':
|
if __name__ == '__main__':
|
||||||
TestUnitPythonProcman.main()
|
TestUnitPythonProcman.main()
|
||||||
|
|||||||
File diff suppressed because it is too large
Load Diff
@@ -1,8 +1,8 @@
|
|||||||
import unittest
|
import unittest
|
||||||
import unit
|
import unit
|
||||||
|
|
||||||
class TestUnitRubyApplication(unit.TestUnitApplicationRuby):
|
|
||||||
|
|
||||||
|
class TestUnitRubyApplication(unit.TestUnitApplicationRuby):
|
||||||
def setUpClass():
|
def setUpClass():
|
||||||
unit.TestUnit().check_modules('ruby')
|
unit.TestUnit().check_modules('ruby')
|
||||||
|
|
||||||
@@ -11,26 +11,37 @@ class TestUnitRubyApplication(unit.TestUnitApplicationRuby):
|
|||||||
|
|
||||||
body = 'Test body string.'
|
body = 'Test body string.'
|
||||||
|
|
||||||
resp = self.post(headers={
|
resp = self.post(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Content-Type': 'text/html',
|
'Content-Type': 'text/html',
|
||||||
'Custom-Header': 'blah',
|
'Custom-Header': 'blah',
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
}, body=body)
|
},
|
||||||
|
body=body,
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(resp['status'], 200, 'status')
|
self.assertEqual(resp['status'], 200, 'status')
|
||||||
headers = resp['headers']
|
headers = resp['headers']
|
||||||
header_server = headers.pop('Server')
|
header_server = headers.pop('Server')
|
||||||
self.assertRegex(header_server, r'Unit/[\d\.]+', 'server header')
|
self.assertRegex(header_server, r'Unit/[\d\.]+', 'server header')
|
||||||
self.assertEqual(headers.pop('Server-Software'), header_server,
|
self.assertEqual(
|
||||||
'server software header')
|
headers.pop('Server-Software'),
|
||||||
|
header_server,
|
||||||
|
'server software header',
|
||||||
|
)
|
||||||
|
|
||||||
date = headers.pop('Date')
|
date = headers.pop('Date')
|
||||||
self.assertEqual(date[-4:], ' GMT', 'date header timezone')
|
self.assertEqual(date[-4:], ' GMT', 'date header timezone')
|
||||||
self.assertLess(abs(self.date_to_sec_epoch(date) - self.sec_epoch()), 5,
|
self.assertLess(
|
||||||
'date header')
|
abs(self.date_to_sec_epoch(date) - self.sec_epoch()),
|
||||||
|
5,
|
||||||
|
'date header',
|
||||||
|
)
|
||||||
|
|
||||||
self.assertDictEqual(headers, {
|
self.assertDictEqual(
|
||||||
|
headers,
|
||||||
|
{
|
||||||
'Connection': 'close',
|
'Connection': 'close',
|
||||||
'Content-Length': str(len(body)),
|
'Content-Length': str(len(body)),
|
||||||
'Content-Type': 'text/html',
|
'Content-Type': 'text/html',
|
||||||
@@ -46,8 +57,10 @@ class TestUnitRubyApplication(unit.TestUnitApplicationRuby):
|
|||||||
'Rack-Run-Once': 'false',
|
'Rack-Run-Once': 'false',
|
||||||
'Rack-Hijack-Q': 'false',
|
'Rack-Hijack-Q': 'false',
|
||||||
'Rack-Hijack': '',
|
'Rack-Hijack': '',
|
||||||
'Rack-Hijack-IO': ''
|
'Rack-Hijack-IO': '',
|
||||||
}, 'headers')
|
},
|
||||||
|
'headers',
|
||||||
|
)
|
||||||
self.assertEqual(resp['body'], body, 'body')
|
self.assertEqual(resp['body'], body, 'body')
|
||||||
|
|
||||||
def test_ruby_application_query_string(self):
|
def test_ruby_application_query_string(self):
|
||||||
@@ -55,8 +68,11 @@ class TestUnitRubyApplication(unit.TestUnitApplicationRuby):
|
|||||||
|
|
||||||
resp = self.get(url='/?var1=val1&var2=val2')
|
resp = self.get(url='/?var1=val1&var2=val2')
|
||||||
|
|
||||||
self.assertEqual(resp['headers']['Query-String'], 'var1=val1&var2=val2',
|
self.assertEqual(
|
||||||
'Query-String header')
|
resp['headers']['Query-String'],
|
||||||
|
'var1=val1&var2=val2',
|
||||||
|
'Query-String header',
|
||||||
|
)
|
||||||
|
|
||||||
def test_ruby_application_query_string_empty(self):
|
def test_ruby_application_query_string_empty(self):
|
||||||
self.load('query_string')
|
self.load('query_string')
|
||||||
@@ -64,8 +80,9 @@ class TestUnitRubyApplication(unit.TestUnitApplicationRuby):
|
|||||||
resp = self.get(url='/?')
|
resp = self.get(url='/?')
|
||||||
|
|
||||||
self.assertEqual(resp['status'], 200, 'query string empty status')
|
self.assertEqual(resp['status'], 200, 'query string empty status')
|
||||||
self.assertEqual(resp['headers']['Query-String'], '',
|
self.assertEqual(
|
||||||
'query string empty')
|
resp['headers']['Query-String'], '', 'query string empty'
|
||||||
|
)
|
||||||
|
|
||||||
@unittest.expectedFailure
|
@unittest.expectedFailure
|
||||||
def test_ruby_application_query_string_absent(self):
|
def test_ruby_application_query_string_absent(self):
|
||||||
@@ -74,15 +91,17 @@ class TestUnitRubyApplication(unit.TestUnitApplicationRuby):
|
|||||||
resp = self.get()
|
resp = self.get()
|
||||||
|
|
||||||
self.assertEqual(resp['status'], 200, 'query string absent status')
|
self.assertEqual(resp['status'], 200, 'query string absent status')
|
||||||
self.assertEqual(resp['headers']['Query-String'], '',
|
self.assertEqual(
|
||||||
'query string absent')
|
resp['headers']['Query-String'], '', 'query string absent'
|
||||||
|
)
|
||||||
|
|
||||||
@unittest.expectedFailure
|
@unittest.expectedFailure
|
||||||
def test_ruby_application_server_port(self):
|
def test_ruby_application_server_port(self):
|
||||||
self.load('server_port')
|
self.load('server_port')
|
||||||
|
|
||||||
self.assertEqual(self.get()['headers']['Server-Port'], '7080',
|
self.assertEqual(
|
||||||
'Server-Port header')
|
self.get()['headers']['Server-Port'], '7080', 'Server-Port header'
|
||||||
|
)
|
||||||
|
|
||||||
def test_ruby_application_status_int(self):
|
def test_ruby_application_status_int(self):
|
||||||
self.load('status_int')
|
self.load('status_int')
|
||||||
@@ -97,20 +116,29 @@ class TestUnitRubyApplication(unit.TestUnitApplicationRuby):
|
|||||||
def test_ruby_application_input_read_parts(self):
|
def test_ruby_application_input_read_parts(self):
|
||||||
self.load('input_read_parts')
|
self.load('input_read_parts')
|
||||||
|
|
||||||
self.assertEqual(self.post(body='0123456789')['body'], '012345678',
|
self.assertEqual(
|
||||||
'input read parts')
|
self.post(body='0123456789')['body'],
|
||||||
|
'012345678',
|
||||||
|
'input read parts',
|
||||||
|
)
|
||||||
|
|
||||||
def test_ruby_application_input_read_buffer(self):
|
def test_ruby_application_input_read_buffer(self):
|
||||||
self.load('input_read_buffer')
|
self.load('input_read_buffer')
|
||||||
|
|
||||||
self.assertEqual(self.post(body='0123456789')['body'], '0123456789',
|
self.assertEqual(
|
||||||
'input read buffer')
|
self.post(body='0123456789')['body'],
|
||||||
|
'0123456789',
|
||||||
|
'input read buffer',
|
||||||
|
)
|
||||||
|
|
||||||
def test_ruby_application_input_read_buffer_not_empty(self):
|
def test_ruby_application_input_read_buffer_not_empty(self):
|
||||||
self.load('input_read_buffer_not_empty')
|
self.load('input_read_buffer_not_empty')
|
||||||
|
|
||||||
self.assertEqual(self.post(body='0123456789')['body'], '0123456789',
|
self.assertEqual(
|
||||||
'input read buffer not empty')
|
self.post(body='0123456789')['body'],
|
||||||
|
'0123456789',
|
||||||
|
'input read buffer not empty',
|
||||||
|
)
|
||||||
|
|
||||||
def test_ruby_application_input_gets(self):
|
def test_ruby_application_input_gets(self):
|
||||||
self.load('input_gets')
|
self.load('input_gets')
|
||||||
@@ -122,8 +150,9 @@ class TestUnitRubyApplication(unit.TestUnitApplicationRuby):
|
|||||||
def test_ruby_application_input_gets_2(self):
|
def test_ruby_application_input_gets_2(self):
|
||||||
self.load('input_gets')
|
self.load('input_gets')
|
||||||
|
|
||||||
self.assertEqual(self.post(body='01234\n56789\n')['body'], '01234\n',
|
self.assertEqual(
|
||||||
'input gets 2')
|
self.post(body='01234\n56789\n')['body'], '01234\n', 'input gets 2'
|
||||||
|
)
|
||||||
|
|
||||||
def test_ruby_application_input_gets_all(self):
|
def test_ruby_application_input_gets_all(self):
|
||||||
self.load('input_gets_all')
|
self.load('input_gets_all')
|
||||||
@@ -149,12 +178,14 @@ class TestUnitRubyApplication(unit.TestUnitApplicationRuby):
|
|||||||
|
|
||||||
@unittest.expectedFailure
|
@unittest.expectedFailure
|
||||||
def test_ruby_application_syntax_error(self):
|
def test_ruby_application_syntax_error(self):
|
||||||
self.skip_alerts.extend([
|
self.skip_alerts.extend(
|
||||||
|
[
|
||||||
r'Failed to parse rack script',
|
r'Failed to parse rack script',
|
||||||
r'syntax error',
|
r'syntax error',
|
||||||
r'new_from_string',
|
r'new_from_string',
|
||||||
r'parse_file'
|
r'parse_file',
|
||||||
])
|
]
|
||||||
|
)
|
||||||
self.load('syntax_error')
|
self.load('syntax_error')
|
||||||
|
|
||||||
self.assertEqual(self.get()['status'], 500, 'syntax error')
|
self.assertEqual(self.get()['status'], 500, 'syntax error')
|
||||||
@@ -168,7 +199,8 @@ class TestUnitRubyApplication(unit.TestUnitApplicationRuby):
|
|||||||
|
|
||||||
self.assertIsNotNone(
|
self.assertIsNotNone(
|
||||||
self.search_in_log(r'\[error\].+Error in application'),
|
self.search_in_log(r'\[error\].+Error in application'),
|
||||||
'errors puts')
|
'errors puts',
|
||||||
|
)
|
||||||
|
|
||||||
def test_ruby_application_errors_puts_int(self):
|
def test_ruby_application_errors_puts_int(self):
|
||||||
self.load('errors_puts_int')
|
self.load('errors_puts_int')
|
||||||
@@ -178,8 +210,8 @@ class TestUnitRubyApplication(unit.TestUnitApplicationRuby):
|
|||||||
self.stop()
|
self.stop()
|
||||||
|
|
||||||
self.assertIsNotNone(
|
self.assertIsNotNone(
|
||||||
self.search_in_log(r'\[error\].+1234567890'),
|
self.search_in_log(r'\[error\].+1234567890'), 'errors puts int'
|
||||||
'errors puts int')
|
)
|
||||||
|
|
||||||
def test_ruby_application_errors_write(self):
|
def test_ruby_application_errors_write(self):
|
||||||
self.load('errors_write')
|
self.load('errors_write')
|
||||||
@@ -190,13 +222,13 @@ class TestUnitRubyApplication(unit.TestUnitApplicationRuby):
|
|||||||
|
|
||||||
self.assertIsNotNone(
|
self.assertIsNotNone(
|
||||||
self.search_in_log(r'\[error\].+Error in application'),
|
self.search_in_log(r'\[error\].+Error in application'),
|
||||||
'errors write')
|
'errors write',
|
||||||
|
)
|
||||||
|
|
||||||
def test_ruby_application_errors_write_to_s_custom(self):
|
def test_ruby_application_errors_write_to_s_custom(self):
|
||||||
self.load('errors_write_to_s_custom')
|
self.load('errors_write_to_s_custom')
|
||||||
|
|
||||||
self.assertEqual(self.get()['status'], 200,
|
self.assertEqual(self.get()['status'], 200, 'errors write to_s custom')
|
||||||
'errors write to_s custom')
|
|
||||||
|
|
||||||
def test_ruby_application_errors_write_int(self):
|
def test_ruby_application_errors_write_int(self):
|
||||||
self.load('errors_write_int')
|
self.load('errors_write_int')
|
||||||
@@ -206,38 +238,40 @@ class TestUnitRubyApplication(unit.TestUnitApplicationRuby):
|
|||||||
self.stop()
|
self.stop()
|
||||||
|
|
||||||
self.assertIsNotNone(
|
self.assertIsNotNone(
|
||||||
self.search_in_log(r'\[error\].+1234567890'),
|
self.search_in_log(r'\[error\].+1234567890'), 'errors write int'
|
||||||
'errors write int')
|
)
|
||||||
|
|
||||||
def test_ruby_application_at_exit(self):
|
def test_ruby_application_at_exit(self):
|
||||||
self.load('at_exit')
|
self.load('at_exit')
|
||||||
|
|
||||||
self.get()
|
self.get()
|
||||||
|
|
||||||
self.conf({
|
self.conf({"listeners": {}, "applications": {}})
|
||||||
"listeners": {},
|
|
||||||
"applications": {}
|
|
||||||
})
|
|
||||||
|
|
||||||
self.stop()
|
self.stop()
|
||||||
|
|
||||||
self.assertIsNotNone(
|
self.assertIsNotNone(
|
||||||
self.search_in_log(r'\[error\].+At exit called\.'), 'at exit')
|
self.search_in_log(r'\[error\].+At exit called\.'), 'at exit'
|
||||||
|
)
|
||||||
|
|
||||||
def test_ruby_application_header_custom(self):
|
def test_ruby_application_header_custom(self):
|
||||||
self.load('header_custom')
|
self.load('header_custom')
|
||||||
|
|
||||||
resp = self.post(body="\ntc=one,two\ntc=three,four,\n\n")
|
resp = self.post(body="\ntc=one,two\ntc=three,four,\n\n")
|
||||||
|
|
||||||
self.assertEqual(resp['headers']['Custom-Header'],
|
self.assertEqual(
|
||||||
['', 'tc=one,two', 'tc=three,four,', '', ''], 'header custom')
|
resp['headers']['Custom-Header'],
|
||||||
|
['', 'tc=one,two', 'tc=three,four,', '', ''],
|
||||||
|
'header custom',
|
||||||
|
)
|
||||||
|
|
||||||
@unittest.expectedFailure
|
@unittest.expectedFailure
|
||||||
def test_ruby_application_header_custom_non_printable(self):
|
def test_ruby_application_header_custom_non_printable(self):
|
||||||
self.load('header_custom')
|
self.load('header_custom')
|
||||||
|
|
||||||
self.assertEqual(self.post(body='\b')['status'], 500,
|
self.assertEqual(
|
||||||
'header custom non printable')
|
self.post(body='\b')['status'], 500, 'header custom non printable'
|
||||||
|
)
|
||||||
|
|
||||||
def test_ruby_application_header_status(self):
|
def test_ruby_application_header_status(self):
|
||||||
self.load('header_status')
|
self.load('header_status')
|
||||||
@@ -277,7 +311,8 @@ class TestUnitRubyApplication(unit.TestUnitApplicationRuby):
|
|||||||
|
|
||||||
self.assertIsNotNone(
|
self.assertIsNotNone(
|
||||||
self.search_in_log(r'\[error\].+Failed to run ruby script'),
|
self.search_in_log(r'\[error\].+Failed to run ruby script'),
|
||||||
'body each error')
|
'body each error',
|
||||||
|
)
|
||||||
|
|
||||||
def test_ruby_application_body_file(self):
|
def test_ruby_application_body_file(self):
|
||||||
self.load('body_file')
|
self.load('body_file')
|
||||||
@@ -287,21 +322,30 @@ class TestUnitRubyApplication(unit.TestUnitApplicationRuby):
|
|||||||
def test_ruby_keepalive_body(self):
|
def test_ruby_keepalive_body(self):
|
||||||
self.load('mirror')
|
self.load('mirror')
|
||||||
|
|
||||||
(resp, sock) = self.post(headers={
|
(resp, sock) = self.post(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Connection': 'keep-alive',
|
'Connection': 'keep-alive',
|
||||||
'Content-Type': 'text/html'
|
'Content-Type': 'text/html',
|
||||||
}, start=True, body='0123456789' * 500)
|
},
|
||||||
|
start=True,
|
||||||
|
body='0123456789' * 500,
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(resp['body'], '0123456789' * 500, 'keep-alive 1')
|
self.assertEqual(resp['body'], '0123456789' * 500, 'keep-alive 1')
|
||||||
|
|
||||||
resp = self.post(headers={
|
resp = self.post(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Connection': 'close',
|
'Connection': 'close',
|
||||||
'Content-Type': 'text/html'
|
'Content-Type': 'text/html',
|
||||||
}, sock=sock, body='0123456789')
|
},
|
||||||
|
sock=sock,
|
||||||
|
body='0123456789',
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(resp['body'], '0123456789', 'keep-alive 2')
|
self.assertEqual(resp['body'], '0123456789', 'keep-alive 2')
|
||||||
|
|
||||||
|
|
||||||
if __name__ == '__main__':
|
if __name__ == '__main__':
|
||||||
TestUnitRubyApplication.main()
|
TestUnitRubyApplication.main()
|
||||||
|
|||||||
@@ -3,45 +3,73 @@ import socket
|
|||||||
import unittest
|
import unittest
|
||||||
import unit
|
import unit
|
||||||
|
|
||||||
class TestUnitSettings(unit.TestUnitApplicationPython):
|
|
||||||
|
|
||||||
|
class TestUnitSettings(unit.TestUnitApplicationPython):
|
||||||
def setUpClass():
|
def setUpClass():
|
||||||
unit.TestUnit().check_modules('python')
|
unit.TestUnit().check_modules('python')
|
||||||
|
|
||||||
def test_settings_header_read_timeout(self):
|
def test_settings_header_read_timeout(self):
|
||||||
self.load('empty')
|
self.load('empty')
|
||||||
|
|
||||||
self.conf({'http': { 'header_read_timeout': 2 }}, 'settings')
|
self.conf({'http': {'header_read_timeout': 2}}, 'settings')
|
||||||
|
|
||||||
(resp, sock) = self.http(b"""GET / HTTP/1.1
|
(resp, sock) = self.http(
|
||||||
""", start=True, read_timeout=1, raw=True)
|
b"""GET / HTTP/1.1
|
||||||
|
""",
|
||||||
|
start=True,
|
||||||
|
read_timeout=1,
|
||||||
|
raw=True,
|
||||||
|
)
|
||||||
|
|
||||||
time.sleep(3)
|
time.sleep(3)
|
||||||
|
|
||||||
resp = self.http(b"""Host: localhost
|
resp = self.http(
|
||||||
|
b"""Host: localhost
|
||||||
Connection: close
|
Connection: close
|
||||||
|
|
||||||
""", sock=sock, raw=True)
|
""",
|
||||||
|
sock=sock,
|
||||||
|
raw=True,
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(resp['status'], 408, 'status header read timeout')
|
self.assertEqual(resp['status'], 408, 'status header read timeout')
|
||||||
|
|
||||||
def test_settings_header_read_timeout_update(self):
|
def test_settings_header_read_timeout_update(self):
|
||||||
self.load('empty')
|
self.load('empty')
|
||||||
|
|
||||||
self.conf({'http': { 'header_read_timeout': 4 }}, 'settings')
|
self.conf({'http': {'header_read_timeout': 4}}, 'settings')
|
||||||
|
|
||||||
(resp, sock) = self.http(b"""GET / HTTP/1.1
|
(resp, sock) = self.http(
|
||||||
""", start=True, read_timeout=1, raw=True, no_recv=True)
|
b"""GET / HTTP/1.1
|
||||||
|
""",
|
||||||
|
start=True,
|
||||||
|
read_timeout=1,
|
||||||
|
raw=True,
|
||||||
|
no_recv=True,
|
||||||
|
)
|
||||||
|
|
||||||
time.sleep(2)
|
time.sleep(2)
|
||||||
|
|
||||||
(resp, sock) = self.http(b"""Host: localhost
|
(resp, sock) = self.http(
|
||||||
""", start=True, sock=sock, read_timeout=1, raw=True, no_recv=True)
|
b"""Host: localhost
|
||||||
|
""",
|
||||||
|
start=True,
|
||||||
|
sock=sock,
|
||||||
|
read_timeout=1,
|
||||||
|
raw=True,
|
||||||
|
no_recv=True,
|
||||||
|
)
|
||||||
|
|
||||||
time.sleep(2)
|
time.sleep(2)
|
||||||
|
|
||||||
(resp, sock) = self.http(b"""X-Blah: blah
|
(resp, sock) = self.http(
|
||||||
""", start=True, sock=sock, read_timeout=1, raw=True)
|
b"""X-Blah: blah
|
||||||
|
""",
|
||||||
|
start=True,
|
||||||
|
sock=sock,
|
||||||
|
read_timeout=1,
|
||||||
|
raw=True,
|
||||||
|
)
|
||||||
|
|
||||||
if len(resp) != 0:
|
if len(resp) != 0:
|
||||||
sock.close()
|
sock.close()
|
||||||
@@ -49,24 +77,35 @@ Connection: close
|
|||||||
else:
|
else:
|
||||||
time.sleep(2)
|
time.sleep(2)
|
||||||
|
|
||||||
resp = self.http(b"""Connection: close
|
resp = self.http(
|
||||||
|
b"""Connection: close
|
||||||
|
|
||||||
""", sock=sock, raw=True)
|
""",
|
||||||
|
sock=sock,
|
||||||
|
raw=True,
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(resp['status'], 408,
|
self.assertEqual(
|
||||||
'status header read timeout update')
|
resp['status'], 408, 'status header read timeout update'
|
||||||
|
)
|
||||||
|
|
||||||
def test_settings_body_read_timeout(self):
|
def test_settings_body_read_timeout(self):
|
||||||
self.load('empty')
|
self.load('empty')
|
||||||
|
|
||||||
self.conf({'http': { 'body_read_timeout': 2 }}, 'settings')
|
self.conf({'http': {'body_read_timeout': 2}}, 'settings')
|
||||||
|
|
||||||
(resp, sock) = self.http(b"""POST / HTTP/1.1
|
(resp, sock) = self.http(
|
||||||
|
b"""POST / HTTP/1.1
|
||||||
Host: localhost
|
Host: localhost
|
||||||
Content-Length: 10
|
Content-Length: 10
|
||||||
Connection: close
|
Connection: close
|
||||||
|
|
||||||
""", start=True, raw_resp=True, read_timeout=1, raw=True)
|
""",
|
||||||
|
start=True,
|
||||||
|
raw_resp=True,
|
||||||
|
read_timeout=1,
|
||||||
|
raw=True,
|
||||||
|
)
|
||||||
|
|
||||||
time.sleep(3)
|
time.sleep(3)
|
||||||
|
|
||||||
@@ -77,37 +116,46 @@ Connection: close
|
|||||||
def test_settings_body_read_timeout_update(self):
|
def test_settings_body_read_timeout_update(self):
|
||||||
self.load('empty')
|
self.load('empty')
|
||||||
|
|
||||||
self.conf({'http': { 'body_read_timeout': 4 }}, 'settings')
|
self.conf({'http': {'body_read_timeout': 4}}, 'settings')
|
||||||
|
|
||||||
(resp, sock) = self.http(b"""POST / HTTP/1.1
|
(resp, sock) = self.http(
|
||||||
|
b"""POST / HTTP/1.1
|
||||||
Host: localhost
|
Host: localhost
|
||||||
Content-Length: 10
|
Content-Length: 10
|
||||||
Connection: close
|
Connection: close
|
||||||
|
|
||||||
""", start=True, read_timeout=1, raw=True)
|
""",
|
||||||
|
start=True,
|
||||||
|
read_timeout=1,
|
||||||
|
raw=True,
|
||||||
|
)
|
||||||
|
|
||||||
time.sleep(2)
|
time.sleep(2)
|
||||||
|
|
||||||
(resp, sock) = self.http(b"""012""", start=True, sock=sock,
|
(resp, sock) = self.http(
|
||||||
read_timeout=1, raw=True)
|
b"""012""", start=True, sock=sock, read_timeout=1, raw=True
|
||||||
|
)
|
||||||
|
|
||||||
time.sleep(2)
|
time.sleep(2)
|
||||||
|
|
||||||
(resp, sock) = self.http(b"""345""", start=True, sock=sock,
|
(resp, sock) = self.http(
|
||||||
read_timeout=1, raw=True)
|
b"""345""", start=True, sock=sock, read_timeout=1, raw=True
|
||||||
|
)
|
||||||
|
|
||||||
time.sleep(2)
|
time.sleep(2)
|
||||||
|
|
||||||
resp = self.http(b"""6789""", sock=sock, raw=True)
|
resp = self.http(b"""6789""", sock=sock, raw=True)
|
||||||
|
|
||||||
self.assertEqual(resp['status'], 200, 'status body read timeout update')
|
self.assertEqual(
|
||||||
|
resp['status'], 200, 'status body read timeout update'
|
||||||
|
)
|
||||||
|
|
||||||
def test_settings_send_timeout(self):
|
def test_settings_send_timeout(self):
|
||||||
self.load('mirror')
|
self.load('mirror')
|
||||||
|
|
||||||
data_len = 1048576
|
data_len = 1048576
|
||||||
|
|
||||||
self.conf({'http': { 'send_timeout': 1 }}, 'settings')
|
self.conf({'http': {'send_timeout': 1}}, 'settings')
|
||||||
|
|
||||||
addr = self.testdir + '/sock'
|
addr = self.testdir + '/sock'
|
||||||
|
|
||||||
@@ -122,7 +170,9 @@ Content-Type: text/html
|
|||||||
Content-Length: %d
|
Content-Length: %d
|
||||||
Connection: close
|
Connection: close
|
||||||
|
|
||||||
""" % data_len + ('X' * data_len)
|
""" % data_len + (
|
||||||
|
'X' * data_len
|
||||||
|
)
|
||||||
|
|
||||||
sock.sendall(req.encode())
|
sock.sendall(req.encode())
|
||||||
|
|
||||||
@@ -140,35 +190,40 @@ Connection: close
|
|||||||
def test_settings_idle_timeout(self):
|
def test_settings_idle_timeout(self):
|
||||||
self.load('empty')
|
self.load('empty')
|
||||||
|
|
||||||
self.conf({'http': { 'idle_timeout': 2 }}, 'settings')
|
self.conf({'http': {'idle_timeout': 2}}, 'settings')
|
||||||
|
|
||||||
(resp, sock) = self.get(headers={
|
(resp, sock) = self.get(
|
||||||
'Host': 'localhost',
|
headers={'Host': 'localhost', 'Connection': 'keep-alive'},
|
||||||
'Connection': 'keep-alive'
|
start=True,
|
||||||
}, start=True, read_timeout=1)
|
read_timeout=1,
|
||||||
|
)
|
||||||
|
|
||||||
time.sleep(3)
|
time.sleep(3)
|
||||||
|
|
||||||
resp = self.get(headers={
|
resp = self.get(
|
||||||
'Host': 'localhost',
|
headers={'Host': 'localhost', 'Connection': 'close'}, sock=sock
|
||||||
'Connection': 'close'
|
)
|
||||||
}, sock=sock)
|
|
||||||
|
|
||||||
self.assertEqual(resp['status'], 408, 'status idle timeout')
|
self.assertEqual(resp['status'], 408, 'status idle timeout')
|
||||||
|
|
||||||
def test_settings_max_body_size(self):
|
def test_settings_max_body_size(self):
|
||||||
self.load('empty')
|
self.load('empty')
|
||||||
|
|
||||||
self.conf({'http': { 'max_body_size': 5 }}, 'settings')
|
self.conf({'http': {'max_body_size': 5}}, 'settings')
|
||||||
|
|
||||||
self.assertEqual(self.post(body='01234')['status'], 200, 'status size')
|
self.assertEqual(self.post(body='01234')['status'], 200, 'status size')
|
||||||
self.assertEqual(self.post(body='012345')['status'], 413,
|
self.assertEqual(
|
||||||
'status size max')
|
self.post(body='012345')['status'], 413, 'status size max'
|
||||||
|
)
|
||||||
|
|
||||||
@unittest.expectedFailure
|
@unittest.expectedFailure
|
||||||
def test_settings_negative_value(self):
|
def test_settings_negative_value(self):
|
||||||
self.assertIn('error', self.conf({'http': { 'max_body_size': -1 }},
|
self.assertIn(
|
||||||
'settings'), 'settings negative value')
|
'error',
|
||||||
|
self.conf({'http': {'max_body_size': -1}}, 'settings'),
|
||||||
|
'settings negative value',
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
if __name__ == '__main__':
|
if __name__ == '__main__':
|
||||||
TestUnitSettings.main()
|
TestUnitSettings.main()
|
||||||
|
|||||||
403
test/test_tls.py
403
test/test_tls.py
@@ -5,8 +5,8 @@ import subprocess
|
|||||||
import unittest
|
import unittest
|
||||||
import unit
|
import unit
|
||||||
|
|
||||||
class TestUnitTLS(unit.TestUnitApplicationTLS):
|
|
||||||
|
|
||||||
|
class TestUnitTLS(unit.TestUnitApplicationTLS):
|
||||||
def setUpClass():
|
def setUpClass():
|
||||||
unit.TestUnit().check_modules('python', 'openssl')
|
unit.TestUnit().check_modules('python', 'openssl')
|
||||||
|
|
||||||
@@ -26,17 +26,13 @@ class TestUnitTLS(unit.TestUnitApplicationTLS):
|
|||||||
return self.date_to_sec_epoch(date, '%b %d %H:%M:%S %Y %Z')
|
return self.date_to_sec_epoch(date, '%b %d %H:%M:%S %Y %Z')
|
||||||
|
|
||||||
def add_tls(self, application='empty', cert='default', port=7080):
|
def add_tls(self, application='empty', cert='default', port=7080):
|
||||||
self.conf({
|
self.conf(
|
||||||
"application": application,
|
{"application": application, "tls": {"certificate": cert}},
|
||||||
"tls": {
|
'listeners/*:' + str(port),
|
||||||
"certificate": cert
|
)
|
||||||
}
|
|
||||||
}, 'listeners/*:' + str(port))
|
|
||||||
|
|
||||||
def remove_tls(self, application='empty', port=7080):
|
def remove_tls(self, application='empty', port=7080):
|
||||||
self.conf({
|
self.conf({"application": application}, 'listeners/*:' + str(port))
|
||||||
"application": application
|
|
||||||
}, 'listeners/*:' + str(port))
|
|
||||||
|
|
||||||
def test_tls_listener_option_add(self):
|
def test_tls_listener_option_add(self):
|
||||||
self.load('empty')
|
self.load('empty')
|
||||||
@@ -65,8 +61,11 @@ class TestUnitTLS(unit.TestUnitApplicationTLS):
|
|||||||
|
|
||||||
self.certificate()
|
self.certificate()
|
||||||
|
|
||||||
self.assertIn('success', self.conf_delete('/certificates/default'),
|
self.assertIn(
|
||||||
'remove certificate')
|
'success',
|
||||||
|
self.conf_delete('/certificates/default'),
|
||||||
|
'remove certificate',
|
||||||
|
)
|
||||||
|
|
||||||
def test_tls_certificate_remove_used(self):
|
def test_tls_certificate_remove_used(self):
|
||||||
self.load('empty')
|
self.load('empty')
|
||||||
@@ -75,8 +74,11 @@ class TestUnitTLS(unit.TestUnitApplicationTLS):
|
|||||||
|
|
||||||
self.add_tls()
|
self.add_tls()
|
||||||
|
|
||||||
self.assertIn('error', self.conf_delete('/certificates/default'),
|
self.assertIn(
|
||||||
'remove certificate')
|
'error',
|
||||||
|
self.conf_delete('/certificates/default'),
|
||||||
|
'remove certificate',
|
||||||
|
)
|
||||||
|
|
||||||
def test_tls_certificate_remove_nonexisting(self):
|
def test_tls_certificate_remove_nonexisting(self):
|
||||||
self.load('empty')
|
self.load('empty')
|
||||||
@@ -85,8 +87,11 @@ class TestUnitTLS(unit.TestUnitApplicationTLS):
|
|||||||
|
|
||||||
self.add_tls()
|
self.add_tls()
|
||||||
|
|
||||||
self.assertIn('error', self.conf_delete('/certificates/blah'),
|
self.assertIn(
|
||||||
'remove nonexistings certificate')
|
'error',
|
||||||
|
self.conf_delete('/certificates/blah'),
|
||||||
|
'remove nonexistings certificate',
|
||||||
|
)
|
||||||
|
|
||||||
@unittest.expectedFailure
|
@unittest.expectedFailure
|
||||||
def test_tls_certificate_update(self):
|
def test_tls_certificate_update(self):
|
||||||
@@ -100,8 +105,9 @@ class TestUnitTLS(unit.TestUnitApplicationTLS):
|
|||||||
|
|
||||||
self.certificate()
|
self.certificate()
|
||||||
|
|
||||||
self.assertNotEqual(cert_old, self.get_server_certificate(),
|
self.assertNotEqual(
|
||||||
'update certificate')
|
cert_old, self.get_server_certificate(), 'update certificate'
|
||||||
|
)
|
||||||
|
|
||||||
@unittest.expectedFailure
|
@unittest.expectedFailure
|
||||||
def test_tls_certificate_key_incorrect(self):
|
def test_tls_certificate_key_incorrect(self):
|
||||||
@@ -110,8 +116,9 @@ class TestUnitTLS(unit.TestUnitApplicationTLS):
|
|||||||
self.certificate('first', False)
|
self.certificate('first', False)
|
||||||
self.certificate('second', False)
|
self.certificate('second', False)
|
||||||
|
|
||||||
self.assertIn('error', self.certificate_load('first', 'second'),
|
self.assertIn(
|
||||||
'key incorrect')
|
'error', self.certificate_load('first', 'second'), 'key incorrect'
|
||||||
|
)
|
||||||
|
|
||||||
def test_tls_certificate_change(self):
|
def test_tls_certificate_change(self):
|
||||||
self.load('empty')
|
self.load('empty')
|
||||||
@@ -125,33 +132,53 @@ class TestUnitTLS(unit.TestUnitApplicationTLS):
|
|||||||
|
|
||||||
self.add_tls(cert='new')
|
self.add_tls(cert='new')
|
||||||
|
|
||||||
self.assertNotEqual(cert_old, self.get_server_certificate(),
|
self.assertNotEqual(
|
||||||
'change certificate')
|
cert_old, self.get_server_certificate(), 'change certificate'
|
||||||
|
)
|
||||||
|
|
||||||
def test_tls_certificate_key_rsa(self):
|
def test_tls_certificate_key_rsa(self):
|
||||||
self.load('empty')
|
self.load('empty')
|
||||||
|
|
||||||
self.certificate()
|
self.certificate()
|
||||||
|
|
||||||
self.assertEqual(self.conf_get('/certificates/default/key'),
|
self.assertEqual(
|
||||||
'RSA (1024 bits)', 'certificate key rsa')
|
self.conf_get('/certificates/default/key'),
|
||||||
|
'RSA (1024 bits)',
|
||||||
|
'certificate key rsa',
|
||||||
|
)
|
||||||
|
|
||||||
def test_tls_certificate_key_ec(self):
|
def test_tls_certificate_key_ec(self):
|
||||||
self.load('empty')
|
self.load('empty')
|
||||||
|
|
||||||
subprocess.call(['openssl', 'ecparam', '-noout', '-genkey',
|
subprocess.call(
|
||||||
|
[
|
||||||
|
'openssl',
|
||||||
|
'ecparam',
|
||||||
|
'-noout',
|
||||||
|
'-genkey',
|
||||||
'-out', self.testdir + '/ec.key',
|
'-out', self.testdir + '/ec.key',
|
||||||
'-name', 'prime256v1'])
|
'-name', 'prime256v1',
|
||||||
|
]
|
||||||
|
)
|
||||||
|
|
||||||
subprocess.call(['openssl', 'req', '-x509', '-new',
|
subprocess.call(
|
||||||
|
[
|
||||||
|
'openssl',
|
||||||
|
'req',
|
||||||
|
'-x509',
|
||||||
|
'-new',
|
||||||
|
'-subj', '/CN=ec/',
|
||||||
'-config', self.testdir + '/openssl.conf',
|
'-config', self.testdir + '/openssl.conf',
|
||||||
'-key', self.testdir + '/ec.key', '-subj', '/CN=ec/',
|
'-key', self.testdir + '/ec.key',
|
||||||
'-out', self.testdir + '/ec.crt'])
|
'-out', self.testdir + '/ec.crt',
|
||||||
|
]
|
||||||
|
)
|
||||||
|
|
||||||
self.certificate_load('ec')
|
self.certificate_load('ec')
|
||||||
|
|
||||||
self.assertEqual(self.conf_get('/certificates/ec/key'), 'ECDH',
|
self.assertEqual(
|
||||||
'certificate key ec')
|
self.conf_get('/certificates/ec/key'), 'ECDH', 'certificate key ec'
|
||||||
|
)
|
||||||
|
|
||||||
def test_tls_certificate_chain_options(self):
|
def test_tls_certificate_chain_options(self):
|
||||||
self.load('empty')
|
self.load('empty')
|
||||||
@@ -164,36 +191,64 @@ class TestUnitTLS(unit.TestUnitApplicationTLS):
|
|||||||
|
|
||||||
cert = chain[0]
|
cert = chain[0]
|
||||||
|
|
||||||
self.assertEqual(cert['subject']['common_name'], 'default',
|
|
||||||
'certificate subject common name')
|
|
||||||
self.assertEqual(cert['issuer']['common_name'], 'default',
|
|
||||||
'certificate issuer common name')
|
|
||||||
|
|
||||||
self.assertLess(abs(self.sec_epoch() -
|
|
||||||
self.openssl_date_to_sec_epoch(cert['validity']['since'])), 5,
|
|
||||||
'certificate validity since')
|
|
||||||
self.assertEqual(
|
self.assertEqual(
|
||||||
self.openssl_date_to_sec_epoch(cert['validity']['until']) -
|
cert['subject']['common_name'],
|
||||||
self.openssl_date_to_sec_epoch(cert['validity']['since']), 2592000,
|
'default',
|
||||||
'certificate validity until')
|
'certificate subject common name',
|
||||||
|
)
|
||||||
|
self.assertEqual(
|
||||||
|
cert['issuer']['common_name'],
|
||||||
|
'default',
|
||||||
|
'certificate issuer common name',
|
||||||
|
)
|
||||||
|
|
||||||
|
self.assertLess(
|
||||||
|
abs(
|
||||||
|
self.sec_epoch()
|
||||||
|
- self.openssl_date_to_sec_epoch(cert['validity']['since'])
|
||||||
|
),
|
||||||
|
5,
|
||||||
|
'certificate validity since',
|
||||||
|
)
|
||||||
|
self.assertEqual(
|
||||||
|
self.openssl_date_to_sec_epoch(cert['validity']['until'])
|
||||||
|
- self.openssl_date_to_sec_epoch(cert['validity']['since']),
|
||||||
|
2592000,
|
||||||
|
'certificate validity until',
|
||||||
|
)
|
||||||
|
|
||||||
def test_tls_certificate_chain(self):
|
def test_tls_certificate_chain(self):
|
||||||
self.load('empty')
|
self.load('empty')
|
||||||
|
|
||||||
self.certificate('root', False)
|
self.certificate('root', False)
|
||||||
|
|
||||||
subprocess.call(['openssl', 'req', '-new', '-config',
|
subprocess.call(
|
||||||
self.testdir + '/openssl.conf', '-subj', '/CN=int/',
|
[
|
||||||
|
'openssl',
|
||||||
|
'req',
|
||||||
|
'-new',
|
||||||
|
'-subj', '/CN=int/',
|
||||||
|
'-config', self.testdir + '/openssl.conf',
|
||||||
'-out', self.testdir + '/int.csr',
|
'-out', self.testdir + '/int.csr',
|
||||||
'-keyout', self.testdir + '/int.key'])
|
'-keyout', self.testdir + '/int.key',
|
||||||
|
]
|
||||||
|
)
|
||||||
|
|
||||||
subprocess.call(['openssl', 'req', '-new', '-config',
|
subprocess.call(
|
||||||
self.testdir + '/openssl.conf', '-subj', '/CN=end/',
|
[
|
||||||
|
'openssl',
|
||||||
|
'req',
|
||||||
|
'-new',
|
||||||
|
'-subj', '/CN=end/',
|
||||||
|
'-config', self.testdir + '/openssl.conf',
|
||||||
'-out', self.testdir + '/end.csr',
|
'-out', self.testdir + '/end.csr',
|
||||||
'-keyout', self.testdir + '/end.key'])
|
'-keyout', self.testdir + '/end.key',
|
||||||
|
]
|
||||||
|
)
|
||||||
|
|
||||||
with open(self.testdir + '/ca.conf', 'w') as f:
|
with open(self.testdir + '/ca.conf', 'w') as f:
|
||||||
f.write("""[ ca ]
|
f.write(
|
||||||
|
"""[ ca ]
|
||||||
default_ca = myca
|
default_ca = myca
|
||||||
|
|
||||||
[ myca ]
|
[ myca ]
|
||||||
@@ -209,11 +264,13 @@ x509_extensions = myca_extensions
|
|||||||
commonName = supplied
|
commonName = supplied
|
||||||
|
|
||||||
[ myca_extensions ]
|
[ myca_extensions ]
|
||||||
basicConstraints = critical,CA:TRUE""" % {
|
basicConstraints = critical,CA:TRUE"""
|
||||||
|
% {
|
||||||
'dir': self.testdir,
|
'dir': self.testdir,
|
||||||
'database': self.testdir + '/certindex',
|
'database': self.testdir + '/certindex',
|
||||||
'certserial': self.testdir + '/certserial'
|
'certserial': self.testdir + '/certserial',
|
||||||
})
|
}
|
||||||
|
)
|
||||||
|
|
||||||
with open(self.testdir + '/certserial', 'w') as f:
|
with open(self.testdir + '/certserial', 'w') as f:
|
||||||
f.write('1000')
|
f.write('1000')
|
||||||
@@ -221,25 +278,41 @@ basicConstraints = critical,CA:TRUE""" % {
|
|||||||
with open(self.testdir + '/certindex', 'w') as f:
|
with open(self.testdir + '/certindex', 'w') as f:
|
||||||
f.write('')
|
f.write('')
|
||||||
|
|
||||||
subprocess.call(['openssl', 'ca', '-batch',
|
subprocess.call(
|
||||||
|
[
|
||||||
|
'openssl',
|
||||||
|
'ca',
|
||||||
|
'-batch',
|
||||||
|
'-subj', '/CN=int/',
|
||||||
'-config', self.testdir + '/ca.conf',
|
'-config', self.testdir + '/ca.conf',
|
||||||
'-keyfile', self.testdir + '/root.key',
|
'-keyfile', self.testdir + '/root.key',
|
||||||
'-cert', self.testdir + '/root.crt',
|
'-cert', self.testdir + '/root.crt',
|
||||||
'-subj', '/CN=int/',
|
|
||||||
'-in', self.testdir + '/int.csr',
|
'-in', self.testdir + '/int.csr',
|
||||||
'-out', self.testdir + '/int.crt'])
|
'-out', self.testdir + '/int.crt',
|
||||||
|
]
|
||||||
|
)
|
||||||
|
|
||||||
subprocess.call(['openssl', 'ca', '-batch',
|
subprocess.call(
|
||||||
|
[
|
||||||
|
'openssl',
|
||||||
|
'ca',
|
||||||
|
'-batch',
|
||||||
|
'-subj', '/CN=end/',
|
||||||
'-config', self.testdir + '/ca.conf',
|
'-config', self.testdir + '/ca.conf',
|
||||||
'-keyfile', self.testdir + '/int.key',
|
'-keyfile', self.testdir + '/int.key',
|
||||||
'-cert', self.testdir + '/int.crt',
|
'-cert', self.testdir + '/int.crt',
|
||||||
'-subj', '/CN=end/',
|
|
||||||
'-in', self.testdir + '/end.csr',
|
'-in', self.testdir + '/end.csr',
|
||||||
'-out', self.testdir + '/end.crt'])
|
'-out', self.testdir + '/end.crt',
|
||||||
|
]
|
||||||
|
)
|
||||||
|
|
||||||
with open(self.testdir + '/end-int.crt', 'wb') as crt, \
|
crt_path = self.testdir + '/end-int.crt'
|
||||||
open(self.testdir + '/end.crt', 'rb') as end, \
|
end_path = self.testdir + '/end.crt'
|
||||||
open(self.testdir + '/int.crt', 'rb') as int:
|
int_path = self.testdir + '/int.crt'
|
||||||
|
|
||||||
|
with open(crt_path, 'wb') as crt, \
|
||||||
|
open(end_path, 'rb') as end, \
|
||||||
|
open(int_path, 'rb') as int:
|
||||||
crt.write(end.read() + int.read())
|
crt.write(end.read() + int.read())
|
||||||
|
|
||||||
self.context = ssl.create_default_context()
|
self.context = ssl.create_default_context()
|
||||||
@@ -249,15 +322,24 @@ basicConstraints = critical,CA:TRUE""" % {
|
|||||||
|
|
||||||
# incomplete chain
|
# incomplete chain
|
||||||
|
|
||||||
self.assertIn('success', self.certificate_load('end', 'end'),
|
self.assertIn(
|
||||||
'certificate chain end upload')
|
'success',
|
||||||
|
self.certificate_load('end', 'end'),
|
||||||
|
'certificate chain end upload',
|
||||||
|
)
|
||||||
|
|
||||||
chain = self.conf_get('/certificates/end/chain')
|
chain = self.conf_get('/certificates/end/chain')
|
||||||
self.assertEqual(len(chain), 1, 'certificate chain end length')
|
self.assertEqual(len(chain), 1, 'certificate chain end length')
|
||||||
self.assertEqual(chain[0]['subject']['common_name'], 'end',
|
self.assertEqual(
|
||||||
'certificate chain end subject common name')
|
chain[0]['subject']['common_name'],
|
||||||
self.assertEqual(chain[0]['issuer']['common_name'], 'int',
|
'end',
|
||||||
'certificate chain end issuer common name')
|
'certificate chain end subject common name',
|
||||||
|
)
|
||||||
|
self.assertEqual(
|
||||||
|
chain[0]['issuer']['common_name'],
|
||||||
|
'int',
|
||||||
|
'certificate chain end issuer common name',
|
||||||
|
)
|
||||||
|
|
||||||
self.add_tls(cert='end')
|
self.add_tls(cert='end')
|
||||||
|
|
||||||
@@ -270,41 +352,69 @@ basicConstraints = critical,CA:TRUE""" % {
|
|||||||
|
|
||||||
# intermediate
|
# intermediate
|
||||||
|
|
||||||
self.assertIn('success', self.certificate_load('int', 'int'),
|
self.assertIn(
|
||||||
'certificate chain int upload')
|
'success',
|
||||||
|
self.certificate_load('int', 'int'),
|
||||||
|
'certificate chain int upload',
|
||||||
|
)
|
||||||
|
|
||||||
chain = self.conf_get('/certificates/int/chain')
|
chain = self.conf_get('/certificates/int/chain')
|
||||||
self.assertEqual(len(chain), 1, 'certificate chain int length')
|
self.assertEqual(len(chain), 1, 'certificate chain int length')
|
||||||
self.assertEqual(chain[0]['subject']['common_name'], 'int',
|
self.assertEqual(
|
||||||
'certificate chain int subject common name')
|
chain[0]['subject']['common_name'],
|
||||||
self.assertEqual(chain[0]['issuer']['common_name'], 'root',
|
'int',
|
||||||
'certificate chain int issuer common name')
|
'certificate chain int subject common name',
|
||||||
|
)
|
||||||
|
self.assertEqual(
|
||||||
|
chain[0]['issuer']['common_name'],
|
||||||
|
'root',
|
||||||
|
'certificate chain int issuer common name',
|
||||||
|
)
|
||||||
|
|
||||||
self.add_tls(cert='int')
|
self.add_tls(cert='int')
|
||||||
|
|
||||||
self.assertEqual(self.get_ssl()['status'], 200,
|
self.assertEqual(
|
||||||
'certificate chain intermediate')
|
self.get_ssl()['status'], 200, 'certificate chain intermediate'
|
||||||
|
)
|
||||||
|
|
||||||
# intermediate server
|
# intermediate server
|
||||||
|
|
||||||
self.assertIn('success', self.certificate_load('end-int', 'end'),
|
self.assertIn(
|
||||||
'certificate chain end-int upload')
|
'success',
|
||||||
|
self.certificate_load('end-int', 'end'),
|
||||||
|
'certificate chain end-int upload',
|
||||||
|
)
|
||||||
|
|
||||||
chain = self.conf_get('/certificates/end-int/chain')
|
chain = self.conf_get('/certificates/end-int/chain')
|
||||||
self.assertEqual(len(chain), 2, 'certificate chain end-int length')
|
self.assertEqual(len(chain), 2, 'certificate chain end-int length')
|
||||||
self.assertEqual(chain[0]['subject']['common_name'], 'end',
|
self.assertEqual(
|
||||||
'certificate chain end-int int subject common name')
|
chain[0]['subject']['common_name'],
|
||||||
self.assertEqual(chain[0]['issuer']['common_name'], 'int',
|
'end',
|
||||||
'certificate chain end-int int issuer common name')
|
'certificate chain end-int int subject common name',
|
||||||
self.assertEqual(chain[1]['subject']['common_name'], 'int',
|
)
|
||||||
'certificate chain end-int end subject common name')
|
self.assertEqual(
|
||||||
self.assertEqual(chain[1]['issuer']['common_name'], 'root',
|
chain[0]['issuer']['common_name'],
|
||||||
'certificate chain end-int end issuer common name')
|
'int',
|
||||||
|
'certificate chain end-int int issuer common name',
|
||||||
|
)
|
||||||
|
self.assertEqual(
|
||||||
|
chain[1]['subject']['common_name'],
|
||||||
|
'int',
|
||||||
|
'certificate chain end-int end subject common name',
|
||||||
|
)
|
||||||
|
self.assertEqual(
|
||||||
|
chain[1]['issuer']['common_name'],
|
||||||
|
'root',
|
||||||
|
'certificate chain end-int end issuer common name',
|
||||||
|
)
|
||||||
|
|
||||||
self.add_tls(cert='end-int')
|
self.add_tls(cert='end-int')
|
||||||
|
|
||||||
self.assertEqual(self.get_ssl()['status'], 200,
|
self.assertEqual(
|
||||||
'certificate chain intermediate server')
|
self.get_ssl()['status'],
|
||||||
|
200,
|
||||||
|
'certificate chain intermediate server',
|
||||||
|
)
|
||||||
|
|
||||||
@unittest.expectedFailure
|
@unittest.expectedFailure
|
||||||
def test_tls_reconfigure(self):
|
def test_tls_reconfigure(self):
|
||||||
@@ -312,19 +422,21 @@ basicConstraints = critical,CA:TRUE""" % {
|
|||||||
|
|
||||||
self.certificate()
|
self.certificate()
|
||||||
|
|
||||||
(resp, sock) = self.get(headers={
|
(resp, sock) = self.get(
|
||||||
'Host': 'localhost',
|
headers={'Host': 'localhost', 'Connection': 'keep-alive'},
|
||||||
'Connection': 'keep-alive'
|
start=True,
|
||||||
}, start=True)
|
)
|
||||||
|
|
||||||
self.assertEqual(resp['status'], 200, 'initial status')
|
self.assertEqual(resp['status'], 200, 'initial status')
|
||||||
|
|
||||||
self.add_tls()
|
self.add_tls()
|
||||||
|
|
||||||
self.assertEqual(self.get(sock=sock)['status'], 200,
|
self.assertEqual(
|
||||||
'reconfigure status')
|
self.get(sock=sock)['status'], 200, 'reconfigure status'
|
||||||
self.assertEqual(self.get_ssl()['status'], 200,
|
)
|
||||||
'reconfigure tls status')
|
self.assertEqual(
|
||||||
|
self.get_ssl()['status'], 200, 'reconfigure tls status'
|
||||||
|
)
|
||||||
|
|
||||||
def test_tls_keepalive(self):
|
def test_tls_keepalive(self):
|
||||||
self.load('mirror')
|
self.load('mirror')
|
||||||
@@ -333,19 +445,27 @@ basicConstraints = critical,CA:TRUE""" % {
|
|||||||
|
|
||||||
self.add_tls(application='mirror')
|
self.add_tls(application='mirror')
|
||||||
|
|
||||||
(resp, sock) = self.post_ssl(headers={
|
(resp, sock) = self.post_ssl(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Connection': 'keep-alive',
|
'Connection': 'keep-alive',
|
||||||
'Content-Type': 'text/html'
|
'Content-Type': 'text/html',
|
||||||
}, start=True, body='0123456789')
|
},
|
||||||
|
start=True,
|
||||||
|
body='0123456789',
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(resp['body'], '0123456789', 'keepalive 1')
|
self.assertEqual(resp['body'], '0123456789', 'keepalive 1')
|
||||||
|
|
||||||
resp = self.post_ssl(headers={
|
resp = self.post_ssl(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Connection': 'close',
|
'Connection': 'close',
|
||||||
'Content-Type': 'text/html'
|
'Content-Type': 'text/html',
|
||||||
}, sock=sock, body='0123456789')
|
},
|
||||||
|
sock=sock,
|
||||||
|
body='0123456789',
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(resp['body'], '0123456789', 'keepalive 2')
|
self.assertEqual(resp['body'], '0123456789', 'keepalive 2')
|
||||||
|
|
||||||
@@ -357,21 +477,18 @@ basicConstraints = critical,CA:TRUE""" % {
|
|||||||
|
|
||||||
self.add_tls()
|
self.add_tls()
|
||||||
|
|
||||||
(resp, sock) = self.get_ssl(headers={
|
(resp, sock) = self.get_ssl(
|
||||||
'Host': 'localhost',
|
headers={'Host': 'localhost', 'Connection': 'keep-alive'},
|
||||||
'Connection': 'keep-alive'
|
start=True,
|
||||||
}, start=True)
|
)
|
||||||
|
|
||||||
self.conf({
|
self.conf({"application": "empty"}, 'listeners/*:7080')
|
||||||
"application": "empty"
|
|
||||||
}, 'listeners/*:7080')
|
|
||||||
self.conf_delete('/certificates/default')
|
self.conf_delete('/certificates/default')
|
||||||
|
|
||||||
try:
|
try:
|
||||||
resp = self.get_ssl(headers={
|
resp = self.get_ssl(
|
||||||
'Host': 'localhost',
|
headers={'Host': 'localhost', 'Connection': 'close'}, sock=sock
|
||||||
'Connection': 'close'
|
)
|
||||||
}, sock=sock)
|
|
||||||
except:
|
except:
|
||||||
resp = None
|
resp = None
|
||||||
|
|
||||||
@@ -383,8 +500,11 @@ basicConstraints = critical,CA:TRUE""" % {
|
|||||||
|
|
||||||
self.certificate()
|
self.certificate()
|
||||||
|
|
||||||
self.assertIn('success', self.conf_delete('/certificates'),
|
self.assertIn(
|
||||||
'remove all certificates')
|
'success',
|
||||||
|
self.conf_delete('/certificates'),
|
||||||
|
'remove all certificates',
|
||||||
|
)
|
||||||
|
|
||||||
def test_tls_application_respawn(self):
|
def test_tls_application_respawn(self):
|
||||||
self.skip_alerts.append(r'process \d+ exited on signal 9')
|
self.skip_alerts.append(r'process \d+ exited on signal 9')
|
||||||
@@ -396,48 +516,73 @@ basicConstraints = critical,CA:TRUE""" % {
|
|||||||
|
|
||||||
self.add_tls(application='mirror')
|
self.add_tls(application='mirror')
|
||||||
|
|
||||||
(resp, sock) = self.post_ssl(headers={
|
(resp, sock) = self.post_ssl(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Connection': 'keep-alive',
|
'Connection': 'keep-alive',
|
||||||
'Content-Type': 'text/html'
|
'Content-Type': 'text/html',
|
||||||
}, start=True, body='0123456789')
|
},
|
||||||
|
start=True,
|
||||||
|
body='0123456789',
|
||||||
|
)
|
||||||
|
|
||||||
app_id = self.findall(r'(\d+)#\d+ "mirror" application started')[0]
|
app_id = self.findall(r'(\d+)#\d+ "mirror" application started')[0]
|
||||||
|
|
||||||
subprocess.call(['kill', '-9', app_id])
|
subprocess.call(['kill', '-9', app_id])
|
||||||
|
|
||||||
self.wait_for_record(re.compile(' (?!' + app_id +
|
self.wait_for_record(
|
||||||
'#)(\d+)#\d+ "mirror" application started'))
|
re.compile(
|
||||||
|
' (?!' + app_id + '#)(\d+)#\d+ "mirror" application started'
|
||||||
|
)
|
||||||
|
)
|
||||||
|
|
||||||
resp = self.post_ssl(headers={
|
resp = self.post_ssl(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Connection': 'close',
|
'Connection': 'close',
|
||||||
'Content-Type': 'text/html'
|
'Content-Type': 'text/html',
|
||||||
}, sock=sock, body='0123456789')
|
},
|
||||||
|
sock=sock,
|
||||||
|
body='0123456789',
|
||||||
|
)
|
||||||
|
|
||||||
self.assertEqual(resp['status'], 200, 'application respawn status')
|
self.assertEqual(resp['status'], 200, 'application respawn status')
|
||||||
self.assertEqual(resp['body'], '0123456789', 'application respawn body')
|
self.assertEqual(
|
||||||
|
resp['body'], '0123456789', 'application respawn body'
|
||||||
|
)
|
||||||
|
|
||||||
def test_tls_url_scheme(self):
|
def test_tls_url_scheme(self):
|
||||||
self.load('variables')
|
self.load('variables')
|
||||||
|
|
||||||
self.assertEqual(self.post(headers={
|
self.assertEqual(
|
||||||
|
self.post(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Content-Type': 'text/html',
|
'Content-Type': 'text/html',
|
||||||
'Custom-Header': '',
|
'Custom-Header': '',
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
})['headers']['Wsgi-Url-Scheme'], 'http', 'url scheme http')
|
}
|
||||||
|
)['headers']['Wsgi-Url-Scheme'],
|
||||||
|
'http',
|
||||||
|
'url scheme http',
|
||||||
|
)
|
||||||
|
|
||||||
self.certificate()
|
self.certificate()
|
||||||
|
|
||||||
self.add_tls(application='variables')
|
self.add_tls(application='variables')
|
||||||
|
|
||||||
self.assertEqual(self.post_ssl(headers={
|
self.assertEqual(
|
||||||
|
self.post_ssl(
|
||||||
|
headers={
|
||||||
'Host': 'localhost',
|
'Host': 'localhost',
|
||||||
'Content-Type': 'text/html',
|
'Content-Type': 'text/html',
|
||||||
'Custom-Header': '',
|
'Custom-Header': '',
|
||||||
'Connection': 'close'
|
'Connection': 'close',
|
||||||
})['headers']['Wsgi-Url-Scheme'], 'https', 'url scheme https')
|
}
|
||||||
|
)['headers']['Wsgi-Url-Scheme'],
|
||||||
|
'https',
|
||||||
|
'url scheme https',
|
||||||
|
)
|
||||||
|
|
||||||
if __name__ == '__main__':
|
if __name__ == '__main__':
|
||||||
TestUnitTLS.main()
|
TestUnitTLS.main()
|
||||||
|
|||||||
374
test/unit.py
374
test/unit.py
@@ -14,9 +14,12 @@ import unittest
|
|||||||
import subprocess
|
import subprocess
|
||||||
from multiprocessing import Process
|
from multiprocessing import Process
|
||||||
|
|
||||||
|
|
||||||
class TestUnit(unittest.TestCase):
|
class TestUnit(unittest.TestCase):
|
||||||
|
|
||||||
pardir = os.path.abspath(os.path.join(os.path.dirname(__file__), os.pardir))
|
pardir = os.path.abspath(
|
||||||
|
os.path.join(os.path.dirname(__file__), os.pardir)
|
||||||
|
)
|
||||||
architecture = platform.architecture()[0]
|
architecture = platform.architecture()[0]
|
||||||
maxDiff = None
|
maxDiff = None
|
||||||
|
|
||||||
@@ -61,16 +64,19 @@ class TestUnit(unittest.TestCase):
|
|||||||
result = self.defaultTestResult()
|
result = self.defaultTestResult()
|
||||||
self._feedErrorsToResult(result, self._outcome.errors)
|
self._feedErrorsToResult(result, self._outcome.errors)
|
||||||
else:
|
else:
|
||||||
result = getattr(self, '_outcomeForDoCleanups',
|
result = getattr(
|
||||||
self._resultForDoCleanups)
|
self, '_outcomeForDoCleanups', self._resultForDoCleanups
|
||||||
|
)
|
||||||
|
|
||||||
success = not list2reason(result.errors) \
|
success = not list2reason(result.errors) and not list2reason(
|
||||||
and not list2reason(result.failures)
|
result.failures
|
||||||
|
)
|
||||||
|
|
||||||
# check unit.log for alerts
|
# check unit.log for alerts
|
||||||
|
|
||||||
with open(self.testdir + '/unit.log', 'r', encoding='utf-8',
|
unit_log = self.testdir + '/unit.log'
|
||||||
errors='ignore') as f:
|
|
||||||
|
with open(unit_log, 'r', encoding='utf-8', errors='ignore') as f:
|
||||||
self._check_alerts(f.read())
|
self._check_alerts(f.read())
|
||||||
|
|
||||||
# remove unit.log
|
# remove unit.log
|
||||||
@@ -107,9 +113,16 @@ class TestUnit(unittest.TestCase):
|
|||||||
env['GOPATH'] = self.pardir + '/go'
|
env['GOPATH'] = self.pardir + '/go'
|
||||||
|
|
||||||
try:
|
try:
|
||||||
process = subprocess.Popen(['go', 'build', '-o',
|
process = subprocess.Popen(
|
||||||
|
[
|
||||||
|
'go',
|
||||||
|
'build',
|
||||||
|
'-o',
|
||||||
self.testdir + '/go/check_module',
|
self.testdir + '/go/check_module',
|
||||||
current_dir + '/go/empty/app.go'], env=env)
|
current_dir + '/go/empty/app.go',
|
||||||
|
],
|
||||||
|
env=env,
|
||||||
|
)
|
||||||
process.communicate()
|
process.communicate()
|
||||||
|
|
||||||
m = module if process.returncode == 0 else None
|
m = module if process.returncode == 0 else None
|
||||||
@@ -127,9 +140,10 @@ class TestUnit(unittest.TestCase):
|
|||||||
try:
|
try:
|
||||||
subprocess.check_output(['which', 'openssl'])
|
subprocess.check_output(['which', 'openssl'])
|
||||||
|
|
||||||
output = subprocess.check_output([
|
output = subprocess.check_output(
|
||||||
self.pardir + '/build/unitd', '--version'],
|
[self.pardir + '/build/unitd', '--version'],
|
||||||
stderr=subprocess.STDOUT)
|
stderr=subprocess.STDOUT,
|
||||||
|
)
|
||||||
|
|
||||||
m = re.search('--openssl', output.decode())
|
m = re.search('--openssl', output.decode())
|
||||||
|
|
||||||
@@ -162,25 +176,35 @@ class TestUnit(unittest.TestCase):
|
|||||||
print()
|
print()
|
||||||
|
|
||||||
def _run_unit():
|
def _run_unit():
|
||||||
subprocess.call([self.pardir + '/build/unitd',
|
subprocess.call(
|
||||||
|
[
|
||||||
|
self.pardir + '/build/unitd',
|
||||||
'--no-daemon',
|
'--no-daemon',
|
||||||
'--modules', self.pardir + '/build',
|
'--modules', self.pardir + '/build',
|
||||||
'--state', self.testdir + '/state',
|
'--state', self.testdir + '/state',
|
||||||
'--pid', self.testdir + '/unit.pid',
|
'--pid', self.testdir + '/unit.pid',
|
||||||
'--log', self.testdir + '/unit.log',
|
'--log', self.testdir + '/unit.log',
|
||||||
'--control', 'unix:' + self.testdir + '/control.unit.sock'])
|
'--control', 'unix:' + self.testdir + '/control.unit.sock',
|
||||||
|
]
|
||||||
|
)
|
||||||
|
|
||||||
self._p = Process(target=_run_unit)
|
self._p = Process(target=_run_unit)
|
||||||
self._p.start()
|
self._p.start()
|
||||||
|
|
||||||
if not self.waitforfiles(self.testdir + '/unit.pid',
|
if not self.waitforfiles(
|
||||||
self.testdir + '/unit.log', self.testdir + '/control.unit.sock'):
|
self.testdir + '/unit.pid',
|
||||||
|
self.testdir + '/unit.log',
|
||||||
|
self.testdir + '/control.unit.sock',
|
||||||
|
):
|
||||||
exit("Could not start unit")
|
exit("Could not start unit")
|
||||||
|
|
||||||
self._started = True
|
self._started = True
|
||||||
|
|
||||||
self.skip_alerts = [r'read signalfd\(4\) failed', r'sendmsg.+failed',
|
self.skip_alerts = [
|
||||||
r'recvmsg.+failed']
|
r'read signalfd\(4\) failed',
|
||||||
|
r'sendmsg.+failed',
|
||||||
|
r'recvmsg.+failed',
|
||||||
|
]
|
||||||
self.skip_sanitizer = False
|
self.skip_sanitizer = False
|
||||||
|
|
||||||
def _stop(self):
|
def _stop(self):
|
||||||
@@ -264,10 +288,20 @@ class TestUnit(unittest.TestCase):
|
|||||||
def _parse_args():
|
def _parse_args():
|
||||||
parser = argparse.ArgumentParser(add_help=False)
|
parser = argparse.ArgumentParser(add_help=False)
|
||||||
|
|
||||||
parser.add_argument('-d', '--detailed', dest='detailed',
|
parser.add_argument(
|
||||||
action='store_true', help='Detailed output for tests')
|
'-d',
|
||||||
parser.add_argument('-l', '--log', dest='save_log',
|
'--detailed',
|
||||||
action='store_true', help='Save unit.log after the test execution')
|
dest='detailed',
|
||||||
|
action='store_true',
|
||||||
|
help='Detailed output for tests',
|
||||||
|
)
|
||||||
|
parser.add_argument(
|
||||||
|
'-l',
|
||||||
|
'--log',
|
||||||
|
dest='save_log',
|
||||||
|
action='store_true',
|
||||||
|
help='Save unit.log after the test execution',
|
||||||
|
)
|
||||||
|
|
||||||
return parser.parse_known_args()
|
return parser.parse_known_args()
|
||||||
|
|
||||||
@@ -279,18 +313,21 @@ class TestUnit(unittest.TestCase):
|
|||||||
def _print_path_to_log(self):
|
def _print_path_to_log(self):
|
||||||
print('Path to unit.log:\n' + self.testdir + '/unit.log')
|
print('Path to unit.log:\n' + self.testdir + '/unit.log')
|
||||||
|
|
||||||
class TestUnitHTTP(TestUnit):
|
|
||||||
|
|
||||||
|
class TestUnitHTTP(TestUnit):
|
||||||
def http(self, start_str, **kwargs):
|
def http(self, start_str, **kwargs):
|
||||||
sock_type = 'ipv4' if 'sock_type' not in kwargs else kwargs['sock_type']
|
sock_type = (
|
||||||
|
'ipv4' if 'sock_type' not in kwargs else kwargs['sock_type']
|
||||||
|
)
|
||||||
port = 7080 if 'port' not in kwargs else kwargs['port']
|
port = 7080 if 'port' not in kwargs else kwargs['port']
|
||||||
url = '/' if 'url' not in kwargs else kwargs['url']
|
url = '/' if 'url' not in kwargs else kwargs['url']
|
||||||
http = 'HTTP/1.0' if 'http_10' in kwargs else 'HTTP/1.1'
|
http = 'HTTP/1.0' if 'http_10' in kwargs else 'HTTP/1.1'
|
||||||
|
|
||||||
headers = ({
|
headers = (
|
||||||
'Host': 'localhost',
|
{'Host': 'localhost', 'Connection': 'close'}
|
||||||
'Connection': 'close'
|
if 'headers' not in kwargs
|
||||||
} if 'headers' not in kwargs else kwargs['headers'])
|
else kwargs['headers']
|
||||||
|
)
|
||||||
|
|
||||||
body = b'' if 'body' not in kwargs else kwargs['body']
|
body = b'' if 'body' not in kwargs else kwargs['body']
|
||||||
crlf = '\r\n'
|
crlf = '\r\n'
|
||||||
@@ -303,13 +340,16 @@ class TestUnitHTTP(TestUnit):
|
|||||||
sock_types = {
|
sock_types = {
|
||||||
'ipv4': socket.AF_INET,
|
'ipv4': socket.AF_INET,
|
||||||
'ipv6': socket.AF_INET6,
|
'ipv6': socket.AF_INET6,
|
||||||
'unix': socket.AF_UNIX
|
'unix': socket.AF_UNIX,
|
||||||
}
|
}
|
||||||
|
|
||||||
if 'sock' not in kwargs:
|
if 'sock' not in kwargs:
|
||||||
sock = socket.socket(sock_types[sock_type], socket.SOCK_STREAM)
|
sock = socket.socket(sock_types[sock_type], socket.SOCK_STREAM)
|
||||||
|
|
||||||
if sock_type == sock_types['ipv4'] or sock_type == sock_types['ipv6']:
|
if (
|
||||||
|
sock_type == sock_types['ipv4']
|
||||||
|
or sock_type == sock_types['ipv6']
|
||||||
|
):
|
||||||
sock.setsockopt(socket.IPPROTO_TCP, socket.TCP_NODELAY, 1)
|
sock.setsockopt(socket.IPPROTO_TCP, socket.TCP_NODELAY, 1)
|
||||||
|
|
||||||
if 'wrapper' in kwargs:
|
if 'wrapper' in kwargs:
|
||||||
@@ -357,7 +397,9 @@ class TestUnitHTTP(TestUnit):
|
|||||||
|
|
||||||
if 'no_recv' not in kwargs:
|
if 'no_recv' not in kwargs:
|
||||||
enc = 'utf-8' if 'encoding' not in kwargs else kwargs['encoding']
|
enc = 'utf-8' if 'encoding' not in kwargs else kwargs['encoding']
|
||||||
read_timeout = 5 if 'read_timeout' not in kwargs else kwargs['read_timeout']
|
read_timeout = (
|
||||||
|
5 if 'read_timeout' not in kwargs else kwargs['read_timeout']
|
||||||
|
)
|
||||||
resp = self.recvall(sock, read_timeout=read_timeout).decode(enc)
|
resp = self.recvall(sock, read_timeout=read_timeout).decode(enc)
|
||||||
|
|
||||||
if TestUnit.detailed:
|
if TestUnit.detailed:
|
||||||
@@ -410,7 +452,9 @@ class TestUnitHTTP(TestUnit):
|
|||||||
p = re.compile('(.*?)\x0d\x0a?', re.M | re.S)
|
p = re.compile('(.*?)\x0d\x0a?', re.M | re.S)
|
||||||
headers_lines = p.findall(headers_text)
|
headers_lines = p.findall(headers_text)
|
||||||
|
|
||||||
status = re.search('^HTTP\/\d\.\d\s(\d+)|$', headers_lines.pop(0)).group(1)
|
status = re.search(
|
||||||
|
'^HTTP\/\d\.\d\s(\d+)|$', headers_lines.pop(0)
|
||||||
|
).group(1)
|
||||||
|
|
||||||
headers = {}
|
headers = {}
|
||||||
for line in headers_lines:
|
for line in headers_lines:
|
||||||
@@ -418,16 +462,15 @@ class TestUnitHTTP(TestUnit):
|
|||||||
|
|
||||||
if m.group(1) not in headers:
|
if m.group(1) not in headers:
|
||||||
headers[m.group(1)] = m.group(2)
|
headers[m.group(1)] = m.group(2)
|
||||||
|
|
||||||
elif isinstance(headers[m.group(1)], list):
|
elif isinstance(headers[m.group(1)], list):
|
||||||
headers[m.group(1)].append(m.group(2))
|
headers[m.group(1)].append(m.group(2))
|
||||||
|
|
||||||
else:
|
else:
|
||||||
headers[m.group(1)] = [headers[m.group(1)], m.group(2)]
|
headers[m.group(1)] = [headers[m.group(1)], m.group(2)]
|
||||||
|
|
||||||
return {
|
return {'status': int(status), 'headers': headers, 'body': body}
|
||||||
'status': int(status),
|
|
||||||
'headers': headers,
|
|
||||||
'body': body
|
|
||||||
}
|
|
||||||
|
|
||||||
class TestUnitControl(TestUnitHTTP):
|
class TestUnitControl(TestUnitHTTP):
|
||||||
|
|
||||||
@@ -441,32 +484,39 @@ class TestUnitControl(TestUnitHTTP):
|
|||||||
if path[:1] != '/':
|
if path[:1] != '/':
|
||||||
path = '/config/' + path
|
path = '/config/' + path
|
||||||
|
|
||||||
return json.loads(self.put(
|
return json.loads(
|
||||||
|
self.put(
|
||||||
url=path,
|
url=path,
|
||||||
body=conf,
|
body=conf,
|
||||||
sock_type='unix',
|
sock_type='unix',
|
||||||
addr=self.testdir + '/control.unit.sock'
|
addr=self.testdir + '/control.unit.sock',
|
||||||
)['body'])
|
)['body']
|
||||||
|
)
|
||||||
|
|
||||||
def conf_get(self, path='/config'):
|
def conf_get(self, path='/config'):
|
||||||
if path[:1] != '/':
|
if path[:1] != '/':
|
||||||
path = '/config/' + path
|
path = '/config/' + path
|
||||||
|
|
||||||
return json.loads(self.get(
|
return json.loads(
|
||||||
|
self.get(
|
||||||
url=path,
|
url=path,
|
||||||
sock_type='unix',
|
sock_type='unix',
|
||||||
addr=self.testdir + '/control.unit.sock'
|
addr=self.testdir + '/control.unit.sock',
|
||||||
)['body'])
|
)['body']
|
||||||
|
)
|
||||||
|
|
||||||
def conf_delete(self, path='/config'):
|
def conf_delete(self, path='/config'):
|
||||||
if path[:1] != '/':
|
if path[:1] != '/':
|
||||||
path = '/config/' + path
|
path = '/config/' + path
|
||||||
|
|
||||||
return json.loads(self.delete(
|
return json.loads(
|
||||||
|
self.delete(
|
||||||
url=path,
|
url=path,
|
||||||
sock_type='unix',
|
sock_type='unix',
|
||||||
addr=self.testdir + '/control.unit.sock'
|
addr=self.testdir + '/control.unit.sock',
|
||||||
)['body'])
|
)['body']
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
class TestUnitApplicationProto(TestUnitControl):
|
class TestUnitApplicationProto(TestUnitControl):
|
||||||
|
|
||||||
@@ -482,64 +532,68 @@ class TestUnitApplicationProto(TestUnitControl):
|
|||||||
with open(self.testdir + '/unit.log', 'r', errors='ignore') as f:
|
with open(self.testdir + '/unit.log', 'r', errors='ignore') as f:
|
||||||
return re.search(pattern, f.read())
|
return re.search(pattern, f.read())
|
||||||
|
|
||||||
|
|
||||||
class TestUnitApplicationPython(TestUnitApplicationProto):
|
class TestUnitApplicationPython(TestUnitApplicationProto):
|
||||||
def load(self, script, name=None):
|
def load(self, script, name=None):
|
||||||
if name is None:
|
if name is None:
|
||||||
name = script
|
name = script
|
||||||
|
|
||||||
self.conf({
|
script_path = self.current_dir + '/python/' + script
|
||||||
"listeners": {
|
|
||||||
"*:7080": {
|
self.conf(
|
||||||
"application": name
|
{
|
||||||
}
|
"listeners": {"*:7080": {"application": name}},
|
||||||
},
|
|
||||||
"applications": {
|
"applications": {
|
||||||
name: {
|
name: {
|
||||||
"type": "python",
|
"type": "python",
|
||||||
"processes": { "spare": 0 },
|
"processes": {"spare": 0},
|
||||||
"path": self.current_dir + '/python/' + script,
|
"path": script_path,
|
||||||
"working_directory": self.current_dir + '/python/' + script,
|
"working_directory": script_path,
|
||||||
"module": "wsgi"
|
"module": "wsgi",
|
||||||
}
|
}
|
||||||
|
},
|
||||||
}
|
}
|
||||||
})
|
)
|
||||||
|
|
||||||
|
|
||||||
class TestUnitApplicationRuby(TestUnitApplicationProto):
|
class TestUnitApplicationRuby(TestUnitApplicationProto):
|
||||||
def load(self, script, name='config.ru'):
|
def load(self, script, name='config.ru'):
|
||||||
self.conf({
|
script_path = self.current_dir + '/ruby/' + script
|
||||||
"listeners": {
|
|
||||||
"*:7080": {
|
self.conf(
|
||||||
"application": script
|
{
|
||||||
}
|
"listeners": {"*:7080": {"application": script}},
|
||||||
},
|
|
||||||
"applications": {
|
"applications": {
|
||||||
script: {
|
script: {
|
||||||
"type": "ruby",
|
"type": "ruby",
|
||||||
"processes": { "spare": 0 },
|
"processes": {"spare": 0},
|
||||||
"working_directory": self.current_dir + '/ruby/' + script,
|
"working_directory": script_path,
|
||||||
"script": self.current_dir + '/ruby/' + script + '/' + name
|
"script": script_path + '/' + name,
|
||||||
}
|
}
|
||||||
|
},
|
||||||
}
|
}
|
||||||
})
|
)
|
||||||
|
|
||||||
|
|
||||||
class TestUnitApplicationPHP(TestUnitApplicationProto):
|
class TestUnitApplicationPHP(TestUnitApplicationProto):
|
||||||
def load(self, script, name='index.php'):
|
def load(self, script, name='index.php'):
|
||||||
self.conf({
|
script_path = self.current_dir + '/php/' + script
|
||||||
"listeners": {
|
|
||||||
"*:7080": {
|
self.conf(
|
||||||
"application": script
|
{
|
||||||
}
|
"listeners": {"*:7080": {"application": script}},
|
||||||
},
|
|
||||||
"applications": {
|
"applications": {
|
||||||
script: {
|
script: {
|
||||||
"type": "php",
|
"type": "php",
|
||||||
"processes": { "spare": 0 },
|
"processes": {"spare": 0},
|
||||||
"root": self.current_dir + '/php/' + script,
|
"root": script_path,
|
||||||
"working_directory": self.current_dir + '/php/' + script,
|
"working_directory": script_path,
|
||||||
"index": name
|
"index": name,
|
||||||
}
|
}
|
||||||
|
},
|
||||||
}
|
}
|
||||||
})
|
)
|
||||||
|
|
||||||
|
|
||||||
class TestUnitApplicationGo(TestUnitApplicationProto):
|
class TestUnitApplicationGo(TestUnitApplicationProto):
|
||||||
def load(self, script, name='app'):
|
def load(self, script, name='app'):
|
||||||
@@ -547,58 +601,67 @@ class TestUnitApplicationGo(TestUnitApplicationProto):
|
|||||||
if not os.path.isdir(self.testdir + '/go'):
|
if not os.path.isdir(self.testdir + '/go'):
|
||||||
os.mkdir(self.testdir + '/go')
|
os.mkdir(self.testdir + '/go')
|
||||||
|
|
||||||
|
go_app_path = self.current_dir + '/go/'
|
||||||
|
|
||||||
env = os.environ.copy()
|
env = os.environ.copy()
|
||||||
env['GOPATH'] = self.pardir + '/go'
|
env['GOPATH'] = self.pardir + '/go'
|
||||||
process = subprocess.Popen(['go', 'build', '-o',
|
process = subprocess.Popen(
|
||||||
|
[
|
||||||
|
'go',
|
||||||
|
'build',
|
||||||
|
'-o',
|
||||||
self.testdir + '/go/' + name,
|
self.testdir + '/go/' + name,
|
||||||
self.current_dir + '/go/' + script + '/' + name + '.go'],
|
go_app_path + script + '/' + name + '.go',
|
||||||
env=env)
|
],
|
||||||
|
env=env,
|
||||||
|
)
|
||||||
process.communicate()
|
process.communicate()
|
||||||
|
|
||||||
self.conf({
|
self.conf(
|
||||||
"listeners": {
|
{
|
||||||
"*:7080": {
|
"listeners": {"*:7080": {"application": script}},
|
||||||
"application": script
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"applications": {
|
"applications": {
|
||||||
script: {
|
script: {
|
||||||
"type": "external",
|
"type": "external",
|
||||||
"processes": { "spare": 0 },
|
"processes": {"spare": 0},
|
||||||
"working_directory": self.current_dir + '/go/' + script,
|
"working_directory": go_app_path + script,
|
||||||
"executable": self.testdir + '/go/' + name
|
"executable": self.testdir + '/go/' + name,
|
||||||
}
|
}
|
||||||
|
},
|
||||||
}
|
}
|
||||||
})
|
)
|
||||||
|
|
||||||
|
|
||||||
class TestUnitApplicationNode(TestUnitApplicationProto):
|
class TestUnitApplicationNode(TestUnitApplicationProto):
|
||||||
def load(self, script, name='app.js'):
|
def load(self, script, name='app.js'):
|
||||||
|
|
||||||
# copy application
|
# copy application
|
||||||
|
|
||||||
shutil.copytree(self.current_dir + '/node/' + script,
|
shutil.copytree(
|
||||||
self.testdir + '/node')
|
self.current_dir + '/node/' + script, self.testdir + '/node'
|
||||||
|
)
|
||||||
|
|
||||||
# link modules
|
# link modules
|
||||||
|
|
||||||
os.symlink(self.pardir + '/node/node_modules',
|
os.symlink(
|
||||||
self.testdir + '/node/node_modules')
|
self.pardir + '/node/node_modules',
|
||||||
|
self.testdir + '/node/node_modules',
|
||||||
|
)
|
||||||
|
|
||||||
self.conf({
|
self.conf(
|
||||||
"listeners": {
|
{
|
||||||
"*:7080": {
|
"listeners": {"*:7080": {"application": script}},
|
||||||
"application": script
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"applications": {
|
"applications": {
|
||||||
script: {
|
script: {
|
||||||
"type": "external",
|
"type": "external",
|
||||||
"processes": { "spare": 0 },
|
"processes": {"spare": 0},
|
||||||
"working_directory": self.testdir + '/node',
|
"working_directory": self.testdir + '/node',
|
||||||
"executable": name
|
"executable": name,
|
||||||
}
|
}
|
||||||
|
},
|
||||||
}
|
}
|
||||||
})
|
)
|
||||||
|
|
||||||
|
|
||||||
class TestUnitApplicationJava(TestUnitApplicationProto):
|
class TestUnitApplicationJava(TestUnitApplicationProto):
|
||||||
def load(self, script, name='app'):
|
def load(self, script, name='app'):
|
||||||
@@ -641,48 +704,53 @@ class TestUnitApplicationJava(TestUnitApplicationProto):
|
|||||||
if not os.path.isdir(classes_path):
|
if not os.path.isdir(classes_path):
|
||||||
os.makedirs(classes_path)
|
os.makedirs(classes_path)
|
||||||
|
|
||||||
javac = ['javac', '-encoding', 'utf-8', '-d', classes_path,
|
tomcat_jar = self.pardir + '/build/tomcat-servlet-api-9.0.13.jar'
|
||||||
'-classpath',
|
|
||||||
self.pardir + '/build/tomcat-servlet-api-9.0.13.jar']
|
javac = [
|
||||||
|
'javac',
|
||||||
|
'-encoding', 'utf-8',
|
||||||
|
'-d', classes_path,
|
||||||
|
'-classpath', tomcat_jar,
|
||||||
|
]
|
||||||
javac.extend(src)
|
javac.extend(src)
|
||||||
|
|
||||||
process = subprocess.Popen(javac)
|
process = subprocess.Popen(javac)
|
||||||
process.communicate()
|
process.communicate()
|
||||||
|
|
||||||
self.conf({
|
self.conf(
|
||||||
"listeners": {
|
{
|
||||||
"*:7080": {
|
"listeners": {"*:7080": {"application": script}},
|
||||||
"application": script
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"applications": {
|
"applications": {
|
||||||
script: {
|
script: {
|
||||||
"unit_jars": self.pardir + '/build',
|
"unit_jars": self.pardir + '/build',
|
||||||
"type": "java",
|
"type": "java",
|
||||||
"processes": { "spare": 0 },
|
"processes": {"spare": 0},
|
||||||
"working_directory": script_path,
|
"working_directory": script_path,
|
||||||
"webapp": app_path
|
"webapp": app_path,
|
||||||
}
|
}
|
||||||
|
},
|
||||||
}
|
}
|
||||||
})
|
)
|
||||||
|
|
||||||
|
|
||||||
class TestUnitApplicationPerl(TestUnitApplicationProto):
|
class TestUnitApplicationPerl(TestUnitApplicationProto):
|
||||||
def load(self, script, name='psgi.pl'):
|
def load(self, script, name='psgi.pl'):
|
||||||
self.conf({
|
script_path = self.current_dir + '/perl/' + script
|
||||||
"listeners": {
|
|
||||||
"*:7080": {
|
self.conf(
|
||||||
"application": script
|
{
|
||||||
}
|
"listeners": {"*:7080": {"application": script}},
|
||||||
},
|
|
||||||
"applications": {
|
"applications": {
|
||||||
script: {
|
script: {
|
||||||
"type": "perl",
|
"type": "perl",
|
||||||
"processes": { "spare": 0 },
|
"processes": {"spare": 0},
|
||||||
"working_directory": self.current_dir + '/perl/' + script,
|
"working_directory": script_path,
|
||||||
"script": self.current_dir + '/perl/' + script + '/' + name
|
"script": script_path + '/' + name,
|
||||||
}
|
}
|
||||||
|
},
|
||||||
}
|
}
|
||||||
})
|
)
|
||||||
|
|
||||||
|
|
||||||
class TestUnitApplicationTLS(TestUnitApplicationProto):
|
class TestUnitApplicationTLS(TestUnitApplicationProto):
|
||||||
def __init__(self, test):
|
def __init__(self, test):
|
||||||
@@ -693,10 +761,18 @@ class TestUnitApplicationTLS(TestUnitApplicationProto):
|
|||||||
self.context.verify_mode = ssl.CERT_NONE
|
self.context.verify_mode = ssl.CERT_NONE
|
||||||
|
|
||||||
def certificate(self, name='default', load=True):
|
def certificate(self, name='default', load=True):
|
||||||
subprocess.call(['openssl', 'req', '-x509', '-new', '-config',
|
subprocess.call(
|
||||||
self.testdir + '/openssl.conf', '-subj', '/CN=' + name + '/',
|
[
|
||||||
|
'openssl',
|
||||||
|
'req',
|
||||||
|
'-x509',
|
||||||
|
'-new',
|
||||||
|
'-subj', '/CN=' + name + '/',
|
||||||
|
'-config', self.testdir + '/openssl.conf',
|
||||||
'-out', self.testdir + '/' + name + '.crt',
|
'-out', self.testdir + '/' + name + '.crt',
|
||||||
'-keyout', self.testdir + '/' + name + '.key'])
|
'-keyout', self.testdir + '/' + name + '.key',
|
||||||
|
]
|
||||||
|
)
|
||||||
|
|
||||||
if load:
|
if load:
|
||||||
self.certificate_load(name)
|
self.certificate_load(name)
|
||||||
@@ -705,17 +781,17 @@ class TestUnitApplicationTLS(TestUnitApplicationProto):
|
|||||||
if key is None:
|
if key is None:
|
||||||
key = crt
|
key = crt
|
||||||
|
|
||||||
with open(self.testdir + '/' + key + '.key', 'rb') as k, \
|
key_path = self.testdir + '/' + key + '.key'
|
||||||
open(self.testdir + '/' + crt + '.crt', 'rb') as c:
|
crt_path = self.testdir + '/' + crt + '.crt'
|
||||||
|
|
||||||
|
with open(key_path, 'rb') as k, open(crt_path, 'rb') as c:
|
||||||
return self.conf(k.read() + c.read(), '/certificates/' + crt)
|
return self.conf(k.read() + c.read(), '/certificates/' + crt)
|
||||||
|
|
||||||
def get_ssl(self, **kwargs):
|
def get_ssl(self, **kwargs):
|
||||||
return self.get(wrapper=self.context.wrap_socket,
|
return self.get(wrapper=self.context.wrap_socket, **kwargs)
|
||||||
**kwargs)
|
|
||||||
|
|
||||||
def post_ssl(self, **kwargs):
|
def post_ssl(self, **kwargs):
|
||||||
return self.post(wrapper=self.context.wrap_socket,
|
return self.post(wrapper=self.context.wrap_socket, **kwargs)
|
||||||
**kwargs)
|
|
||||||
|
|
||||||
def get_server_certificate(self, addr=('127.0.0.1', 7080)):
|
def get_server_certificate(self, addr=('127.0.0.1', 7080)):
|
||||||
|
|
||||||
@@ -739,25 +815,27 @@ class TestUnitApplicationTLS(TestUnitApplicationProto):
|
|||||||
# create default openssl configuration
|
# create default openssl configuration
|
||||||
|
|
||||||
with open(self.testdir + '/openssl.conf', 'w') as f:
|
with open(self.testdir + '/openssl.conf', 'w') as f:
|
||||||
f.write("""[ req ]
|
f.write(
|
||||||
|
"""[ req ]
|
||||||
default_bits = 1024
|
default_bits = 1024
|
||||||
encrypt_key = no
|
encrypt_key = no
|
||||||
distinguished_name = req_distinguished_name
|
distinguished_name = req_distinguished_name
|
||||||
[ req_distinguished_name ]""")
|
[ req_distinguished_name ]"""
|
||||||
|
)
|
||||||
|
|
||||||
self.conf({
|
script_path = self.current_dir + '/python/' + script
|
||||||
"listeners": {
|
|
||||||
"*:7080": {
|
self.conf(
|
||||||
"application": name
|
{
|
||||||
}
|
"listeners": {"*:7080": {"application": name}},
|
||||||
},
|
|
||||||
"applications": {
|
"applications": {
|
||||||
name: {
|
name: {
|
||||||
"type": "python",
|
"type": "python",
|
||||||
"processes": { "spare": 0 },
|
"processes": {"spare": 0},
|
||||||
"path": self.current_dir + '/python/' + script,
|
"path": script_path,
|
||||||
"working_directory": self.current_dir + '/python/' + script,
|
"working_directory": script_path,
|
||||||
"module": "wsgi"
|
"module": "wsgi",
|
||||||
}
|
}
|
||||||
|
},
|
||||||
}
|
}
|
||||||
})
|
)
|
||||||
|
|||||||
Reference in New Issue
Block a user