summaryrefslogtreecommitdiffhomepage
path: root/test/test_php_application.py
diff options
context:
space:
mode:
Diffstat (limited to 'test/test_php_application.py')
-rw-r--r--test/test_php_application.py1279
1 files changed, 655 insertions, 624 deletions
diff --git a/test/test_php_application.py b/test/test_php_application.py
index 6e1d190a..6c1f227b 100644
--- a/test/test_php_application.py
+++ b/test/test_php_application.py
@@ -7,822 +7,853 @@ import time
from pathlib import Path
import pytest
-from unit.applications.lang.php import TestApplicationPHP
+from unit.applications.lang.php import ApplicationPHP
from unit.option import option
+prerequisites = {'modules': {'php': 'all'}}
-class TestPHPApplication(TestApplicationPHP):
- prerequisites = {'modules': {'php': 'all'}}
+client = ApplicationPHP()
- def before_disable_functions(self):
- body = self.get()['body']
- assert re.search(r'time: \d+', body), 'disable_functions before time'
- assert re.search(r'exec: \/\w+', body), 'disable_functions before exec'
+def before_disable_functions():
+ body = client.get()['body']
- def check_opcache(self):
- resp = self.get()
- assert resp['status'] == 200, 'status'
+ assert re.search(r'time: \d+', body), 'disable_functions before time'
+ assert re.search(r'exec: \/\w+', body), 'disable_functions before exec'
- headers = resp['headers']
- if 'X-OPcache' in headers and headers['X-OPcache'] == '-1':
- pytest.skip('opcache is not supported')
- return resp
+def check_opcache():
+ resp = client.get()
+ assert resp['status'] == 200, 'status'
- def set_opcache(self, app, val):
- assert 'success' in self.conf(
- {"admin": {"opcache.enable": val, "opcache.enable_cli": val}},
- f'applications/{app}/options',
- )
+ headers = resp['headers']
+ if 'X-OPcache' in headers and headers['X-OPcache'] == '-1':
+ pytest.skip('opcache is not supported')
- r = self.check_opcache()
- assert r['headers']['X-OPcache'] == val, 'opcache value'
+ return resp
- def set_preload(self, preload):
- with open(f'{option.temp_dir}/php.ini', 'w') as f:
- f.write(
- f"""opcache.preload = {option.test_dir}/php/opcache/preload\
-/{preload}
-opcache.preload_user = {option.user or getpass.getuser()}
-"""
- )
- assert 'success' in self.conf(
- {"file": f"{option.temp_dir}/php.ini"},
- 'applications/opcache/options',
- )
+def run_php_application_cwd_root_tests():
+ assert 'success' in client.conf_delete('applications/cwd/working_directory')
- def test_php_application_variables(self):
- self.load('variables')
+ script_cwd = f'{option.test_dir}/php/cwd'
- body = 'Test body string.'
+ resp = client.get()
+ assert resp['status'] == 200, 'status ok'
+ assert resp['body'] == script_cwd, 'default cwd'
- resp = self.post(
- headers={
- 'Host': 'localhost',
- 'Content-Type': 'text/html',
- 'Custom-Header': 'blah',
- 'Connection': 'close',
- },
- body=body,
- url='/index.php/blah?var=val',
- )
+ assert 'success' in client.conf(
+ f'"{option.test_dir}"',
+ 'applications/cwd/working_directory',
+ )
- assert resp['status'] == 200, 'status'
- headers = resp['headers']
- header_server = headers.pop('Server')
- assert re.search(r'Unit/[\d\.]+', header_server), 'server header'
- assert (
- headers.pop('Server-Software') == header_server
- ), 'server software header'
-
- date = headers.pop('Date')
- assert date[-4:] == ' GMT', 'date header timezone'
- assert (
- abs(self.date_to_sec_epoch(date) - self.sec_epoch()) < 5
- ), 'date header'
-
- if 'X-Powered-By' in headers:
- headers.pop('X-Powered-By')
-
- headers.pop('Content-type')
- assert headers == {
- 'Connection': 'close',
- 'Content-Length': str(len(body)),
- 'Request-Method': 'POST',
- 'Path-Info': '/blah',
- 'Request-Uri': '/index.php/blah?var=val',
- 'Http-Host': 'localhost',
- 'Server-Protocol': 'HTTP/1.1',
- 'Custom-Header': 'blah',
- }, 'headers'
- assert resp['body'] == body, 'body'
+ resp = client.get()
+ assert resp['status'] == 200, 'status ok'
+ assert resp['body'] == script_cwd, 'wdir cwd'
- def test_php_application_query_string(self):
- self.load('query_string')
+ resp = client.get(url='/?chdir=/')
+ assert resp['status'] == 200, 'status ok'
+ assert resp['body'] == '/', 'cwd after chdir'
- resp = self.get(url='/?var1=val1&var2=val2')
+ # cwd must be restored
- assert (
- resp['headers']['Query-String'] == 'var1=val1&var2=val2'
- ), 'query string'
+ resp = client.get()
+ assert resp['status'] == 200, 'status ok'
+ assert resp['body'] == script_cwd, 'cwd restored'
- def test_php_application_query_string_empty(self):
- self.load('query_string')
+ resp = client.get(url='/subdir/')
+ assert resp['body'] == f'{script_cwd}/subdir', 'cwd subdir'
- resp = self.get(url='/?')
- assert resp['status'] == 200, 'query string empty status'
- assert resp['headers']['Query-String'] == '', 'query string empty'
+def run_php_application_cwd_script_tests():
+ client.load('cwd')
- def test_php_application_fastcgi_finish_request(self, unit_pid):
- self.load('fastcgi_finish_request')
+ script_cwd = f'{option.test_dir}/php/cwd'
- assert 'success' in self.conf(
- {"admin": {"auto_globals_jit": "1"}},
- 'applications/fastcgi_finish_request/options',
- )
+ assert 'success' in client.conf_delete('applications/cwd/working_directory')
- assert self.get()['body'] == '0123'
+ assert 'success' in client.conf('"index.php"', 'applications/cwd/script')
- os.kill(unit_pid, signal.SIGUSR1)
+ assert client.get()['body'] == script_cwd, 'default cwd'
- errs = self.findall(r'Error in fastcgi_finish_request')
+ assert client.get(url='/?chdir=/')['body'] == '/', 'cwd after chdir'
- assert len(errs) == 0, 'no error'
+ # cwd must be restored
+ assert client.get()['body'] == script_cwd, 'cwd restored'
- def test_php_application_fastcgi_finish_request_2(self, unit_pid):
- self.load('fastcgi_finish_request')
- assert 'success' in self.conf(
- {"admin": {"auto_globals_jit": "1"}},
- 'applications/fastcgi_finish_request/options',
+def set_opcache(app, val):
+ assert 'success' in client.conf(
+ {"admin": {"opcache.enable": val, "opcache.enable_cli": val}},
+ f'applications/{app}/options',
+ )
+
+ r = check_opcache()
+ assert r['headers']['X-OPcache'] == val, 'opcache value'
+
+
+def set_preload(preload):
+ with open(f'{option.temp_dir}/php.ini', 'w') as ini:
+ ini.write(
+ f"""opcache.preload = {option.test_dir}/php/opcache/preload\
+/{preload}
+opcache.preload_user = {option.user or getpass.getuser()}
+"""
)
- resp = self.get(url='/?skip')
- assert resp['status'] == 200
- assert resp['body'] == ''
+ assert 'success' in client.conf(
+ {"file": f"{option.temp_dir}/php.ini"},
+ 'applications/opcache/options',
+ )
- os.kill(unit_pid, signal.SIGUSR1)
- errs = self.findall(r'Error in fastcgi_finish_request')
+def test_php_application_variables(date_to_sec_epoch, sec_epoch):
+ client.load('variables')
- assert len(errs) == 0, 'no error'
+ body = 'Test body string.'
- def test_php_application_query_string_absent(self):
- self.load('query_string')
+ resp = client.post(
+ headers={
+ 'Host': 'localhost',
+ 'Content-Type': 'text/html',
+ 'Custom-Header': 'blah',
+ 'Connection': 'close',
+ },
+ body=body,
+ url='/index.php/blah?var=val',
+ )
- resp = self.get()
+ assert resp['status'] == 200, 'status'
+ headers = resp['headers']
+ header_server = headers.pop('Server')
+ assert re.search(r'Unit/[\d\.]+', header_server), 'server header'
+ assert (
+ headers.pop('Server-Software') == header_server
+ ), 'server software header'
- assert resp['status'] == 200, 'query string absent status'
- assert resp['headers']['Query-String'] == '', 'query string absent'
+ date = headers.pop('Date')
+ assert date[-4:] == ' GMT', 'date header timezone'
+ assert abs(date_to_sec_epoch(date) - sec_epoch) < 5, 'date header'
- def test_php_application_phpinfo(self):
- self.load('phpinfo')
+ if 'X-Powered-By' in headers:
+ headers.pop('X-Powered-By')
- resp = self.get()
+ headers.pop('Content-type')
+ assert headers == {
+ 'Connection': 'close',
+ 'Content-Length': str(len(body)),
+ 'Request-Method': 'POST',
+ 'Path-Info': '/blah',
+ 'Request-Uri': '/index.php/blah?var=val',
+ 'Http-Host': 'localhost',
+ 'Server-Protocol': 'HTTP/1.1',
+ 'Custom-Header': 'blah',
+ }, 'headers'
+ assert resp['body'] == body, 'body'
- assert resp['status'] == 200, 'status'
- assert resp['body'] != '', 'body not empty'
- def test_php_application_header_status(self):
- self.load('header')
+def test_php_application_query_string():
+ client.load('query_string')
- assert (
- self.get(
- headers={
- 'Host': 'localhost',
- 'Connection': 'close',
- 'X-Header': 'HTTP/1.1 404 Not Found',
- }
- )['status']
- == 404
- ), 'status'
-
- assert (
- self.get(
- headers={
- 'Host': 'localhost',
- 'Connection': 'close',
- 'X-Header': 'http/1.1 404 Not Found',
- }
- )['status']
- == 404
- ), 'status case insensitive'
-
- assert (
- self.get(
- headers={
- 'Host': 'localhost',
- 'Connection': 'close',
- 'X-Header': 'HTTP/ 404 Not Found',
- }
- )['status']
- == 404
- ), 'status version empty'
+ resp = client.get(url='/?var1=val1&var2=val2')
- def test_php_application_404(self):
- self.load('404')
+ assert (
+ resp['headers']['Query-String'] == 'var1=val1&var2=val2'
+ ), 'query string'
- resp = self.get()
- assert resp['status'] == 404, '404 status'
- assert re.search(
- r'<title>404 Not Found</title>', resp['body']
- ), '404 body'
+def test_php_application_query_string_empty():
+ client.load('query_string')
- def test_php_application_keepalive_body(self):
- self.load('mirror')
+ resp = client.get(url='/?')
- assert self.get()['status'] == 200, 'init'
+ assert resp['status'] == 200, 'query string empty status'
+ assert resp['headers']['Query-String'] == '', 'query string empty'
+
+
+def test_php_application_fastcgi_finish_request(findall, unit_pid):
+ client.load('fastcgi_finish_request')
+
+ assert 'success' in client.conf(
+ {"admin": {"auto_globals_jit": "1"}},
+ 'applications/fastcgi_finish_request/options',
+ )
+
+ assert client.get()['body'] == '0123'
+
+ os.kill(unit_pid, signal.SIGUSR1)
+
+ errs = findall(r'Error in fastcgi_finish_request')
+
+ assert len(errs) == 0, 'no error'
- body = '0123456789' * 500
- (resp, sock) = self.post(
- headers={
- 'Host': 'localhost',
- 'Connection': 'keep-alive',
- },
- start=True,
- body=body,
- read_timeout=1,
- )
- assert resp['body'] == body, 'keep-alive 1'
+def test_php_application_fastcgi_finish_request_2(findall, unit_pid):
+ client.load('fastcgi_finish_request')
- body = '0123456789'
- resp = self.post(sock=sock, body=body)
+ assert 'success' in client.conf(
+ {"admin": {"auto_globals_jit": "1"}},
+ 'applications/fastcgi_finish_request/options',
+ )
- assert resp['body'] == body, 'keep-alive 2'
+ resp = client.get(url='/?skip')
+ assert resp['status'] == 200
+ assert resp['body'] == ''
- def test_php_application_conditional(self):
- self.load('conditional')
+ os.kill(unit_pid, signal.SIGUSR1)
- assert re.search(r'True', self.get()['body']), 'conditional true'
- assert re.search(r'False', self.post()['body']), 'conditional false'
+ errs = findall(r'Error in fastcgi_finish_request')
- def test_php_application_get_variables(self):
- self.load('get_variables')
+ assert len(errs) == 0, 'no error'
- resp = self.get(url='/?var1=val1&var2=&var3')
- assert resp['headers']['X-Var-1'] == 'val1', 'GET variables'
- assert resp['headers']['X-Var-2'] == '', 'GET variables 2'
- assert resp['headers']['X-Var-3'] == '', 'GET variables 3'
- assert resp['headers']['X-Var-4'] == 'not set', 'GET variables 4'
- def test_php_application_post_variables(self):
- self.load('post_variables')
+def test_php_application_query_string_absent():
+ client.load('query_string')
- resp = self.post(
+ resp = client.get()
+
+ assert resp['status'] == 200, 'query string absent status'
+ assert resp['headers']['Query-String'] == '', 'query string absent'
+
+
+def test_php_application_phpinfo():
+ client.load('phpinfo')
+
+ resp = client.get()
+
+ assert resp['status'] == 200, 'status'
+ assert resp['body'] != '', 'body not empty'
+
+
+def test_php_application_header_status():
+ client.load('header')
+
+ assert (
+ client.get(
headers={
- 'Content-Type': 'application/x-www-form-urlencoded',
'Host': 'localhost',
'Connection': 'close',
- },
- body='var1=val1&var2=',
- )
- assert resp['headers']['X-Var-1'] == 'val1', 'POST variables'
- assert resp['headers']['X-Var-2'] == '', 'POST variables 2'
- assert resp['headers']['X-Var-3'] == 'not set', 'POST variables 3'
+ 'X-Header': 'HTTP/1.1 404 Not Found',
+ }
+ )['status']
+ == 404
+ ), 'status'
- def test_php_application_cookies(self):
- self.load('cookies')
+ assert (
+ client.get(
+ headers={
+ 'Host': 'localhost',
+ 'Connection': 'close',
+ 'X-Header': 'http/1.1 404 Not Found',
+ }
+ )['status']
+ == 404
+ ), 'status case insensitive'
- resp = self.get(
+ assert (
+ client.get(
headers={
- 'Cookie': 'var=val; var2=val2',
'Host': 'localhost',
'Connection': 'close',
+ 'X-Header': 'HTTP/ 404 Not Found',
}
- )
+ )['status']
+ == 404
+ ), 'status version empty'
- assert resp['headers']['X-Cookie-1'] == 'val', 'cookie'
- assert resp['headers']['X-Cookie-2'] == 'val2', 'cookie'
- def test_php_application_ini_precision(self):
- self.load('ini_precision')
+def test_php_application_404():
+ client.load('404')
- assert self.get()['headers']['X-Precision'] != '4', 'ini value default'
+ resp = client.get()
- assert 'success' in self.conf(
- {"file": "ini/php.ini"}, 'applications/ini_precision/options'
- )
+ assert resp['status'] == 404, '404 status'
+ assert re.search(r'<title>404 Not Found</title>', resp['body']), '404 body'
- assert (
- self.get()['headers']['X-File']
- == f'{option.test_dir}/php/ini_precision/ini/php.ini'
- ), 'ini file'
- assert self.get()['headers']['X-Precision'] == '4', 'ini value'
- @pytest.mark.skip('not yet')
- def test_php_application_ini_admin_user(self):
- self.load('ini_precision')
+def test_php_application_keepalive_body():
+ client.load('mirror')
- assert 'error' in self.conf(
- {"user": {"precision": "4"}, "admin": {"precision": "5"}},
- 'applications/ini_precision/options',
- ), 'ini admin user'
+ assert client.get()['status'] == 200, 'init'
- def test_php_application_ini_admin(self):
- self.load('ini_precision')
+ body = '0123456789' * 500
+ (resp, sock) = client.post(
+ headers={
+ 'Host': 'localhost',
+ 'Connection': 'keep-alive',
+ },
+ start=True,
+ body=body,
+ read_timeout=1,
+ )
- assert 'success' in self.conf(
- {"file": "ini/php.ini", "admin": {"precision": "5"}},
- 'applications/ini_precision/options',
- )
+ assert resp['body'] == body, 'keep-alive 1'
- assert (
- self.get()['headers']['X-File']
- == f'{option.test_dir}/php/ini_precision/ini/php.ini'
- ), 'ini file'
- assert self.get()['headers']['X-Precision'] == '5', 'ini value admin'
+ body = '0123456789'
+ resp = client.post(sock=sock, body=body)
- def test_php_application_ini_user(self):
- self.load('ini_precision')
+ assert resp['body'] == body, 'keep-alive 2'
- assert 'success' in self.conf(
- {"file": "ini/php.ini", "user": {"precision": "5"}},
- 'applications/ini_precision/options',
- )
- assert (
- self.get()['headers']['X-File']
- == f'{option.test_dir}/php/ini_precision/ini/php.ini'
- ), 'ini file'
- assert self.get()['headers']['X-Precision'] == '5', 'ini value user'
+def test_php_application_conditional():
+ client.load('conditional')
- def test_php_application_ini_user_2(self):
- self.load('ini_precision')
+ assert re.search(r'True', client.get()['body']), 'conditional true'
+ assert re.search(r'False', client.post()['body']), 'conditional false'
- assert 'success' in self.conf(
- {"file": "ini/php.ini"}, 'applications/ini_precision/options'
- )
- assert self.get()['headers']['X-Precision'] == '4', 'ini user file'
+def test_php_application_get_variables():
+ client.load('get_variables')
- assert 'success' in self.conf(
- {"precision": "5"}, 'applications/ini_precision/options/user'
- )
+ resp = client.get(url='/?var1=val1&var2=&var3')
+ assert resp['headers']['X-Var-1'] == 'val1', 'GET variables'
+ assert resp['headers']['X-Var-2'] == '', 'GET variables 2'
+ assert resp['headers']['X-Var-3'] == '', 'GET variables 3'
+ assert resp['headers']['X-Var-4'] == 'not set', 'GET variables 4'
- assert self.get()['headers']['X-Precision'] == '5', 'ini value user'
- def test_php_application_ini_set_admin(self):
- self.load('ini_precision')
+def test_php_application_post_variables():
+ client.load('post_variables')
- assert 'success' in self.conf(
- {"admin": {"precision": "5"}}, 'applications/ini_precision/options'
- )
+ resp = client.post(
+ headers={
+ 'Content-Type': 'application/x-www-form-urlencoded',
+ 'Host': 'localhost',
+ 'Connection': 'close',
+ },
+ body='var1=val1&var2=',
+ )
+ assert resp['headers']['X-Var-1'] == 'val1', 'POST variables'
+ assert resp['headers']['X-Var-2'] == '', 'POST variables 2'
+ assert resp['headers']['X-Var-3'] == 'not set', 'POST variables 3'
- assert (
- self.get(url='/?precision=6')['headers']['X-Precision'] == '5'
- ), 'ini set admin'
- def test_php_application_ini_set_user(self):
- self.load('ini_precision')
+def test_php_application_cookies():
+ client.load('cookies')
- assert 'success' in self.conf(
- {"user": {"precision": "5"}}, 'applications/ini_precision/options'
- )
+ resp = client.get(
+ headers={
+ 'Cookie': 'var=val; var2=val2',
+ 'Host': 'localhost',
+ 'Connection': 'close',
+ }
+ )
- assert (
- self.get(url='/?precision=6')['headers']['X-Precision'] == '6'
- ), 'ini set user'
+ assert resp['headers']['X-Cookie-1'] == 'val', 'cookie'
+ assert resp['headers']['X-Cookie-2'] == 'val2', 'cookie'
- def test_php_application_ini_repeat(self):
- self.load('ini_precision')
- assert 'success' in self.conf(
- {"user": {"precision": "5"}}, 'applications/ini_precision/options'
- )
+def test_php_application_ini_precision():
+ client.load('ini_precision')
- assert self.get()['headers']['X-Precision'] == '5', 'ini value'
+ assert client.get()['headers']['X-Precision'] != '4', 'ini value default'
- assert self.get()['headers']['X-Precision'] == '5', 'ini value repeat'
+ assert 'success' in client.conf(
+ {"file": "ini/php.ini"}, 'applications/ini_precision/options'
+ )
- def test_php_application_disable_functions_exec(self):
- self.load('time_exec')
+ assert (
+ client.get()['headers']['X-File']
+ == f'{option.test_dir}/php/ini_precision/ini/php.ini'
+ ), 'ini file'
+ assert client.get()['headers']['X-Precision'] == '4', 'ini value'
- self.before_disable_functions()
- assert 'success' in self.conf(
- {"admin": {"disable_functions": "exec"}},
- 'applications/time_exec/options',
- )
+@pytest.mark.skip('not yet')
+def test_php_application_ini_admin_user():
+ client.load('ini_precision')
- body = self.get()['body']
+ assert 'error' in client.conf(
+ {"user": {"precision": "4"}, "admin": {"precision": "5"}},
+ 'applications/ini_precision/options',
+ ), 'ini admin user'
- assert re.search(r'time: \d+', body), 'disable_functions time'
- assert not re.search(r'exec: \/\w+', body), 'disable_functions exec'
- def test_php_application_disable_functions_comma(self):
- self.load('time_exec')
+def test_php_application_ini_admin():
+ client.load('ini_precision')
- self.before_disable_functions()
+ assert 'success' in client.conf(
+ {"file": "ini/php.ini", "admin": {"precision": "5"}},
+ 'applications/ini_precision/options',
+ )
- assert 'success' in self.conf(
- {"admin": {"disable_functions": "exec,time"}},
- 'applications/time_exec/options',
- )
+ assert (
+ client.get()['headers']['X-File']
+ == f'{option.test_dir}/php/ini_precision/ini/php.ini'
+ ), 'ini file'
+ assert client.get()['headers']['X-Precision'] == '5', 'ini value admin'
- body = self.get()['body']
- assert not re.search(r'time: \d+', body), 'disable_functions comma time'
- assert not re.search(
- r'exec: \/\w+', body
- ), 'disable_functions comma exec'
+def test_php_application_ini_user():
+ client.load('ini_precision')
- def test_php_application_auth(self):
- self.load('auth')
+ assert 'success' in client.conf(
+ {"file": "ini/php.ini", "user": {"precision": "5"}},
+ 'applications/ini_precision/options',
+ )
- resp = self.get()
- assert resp['status'] == 200, 'status'
- assert resp['headers']['X-Digest'] == 'not set', 'digest'
- assert resp['headers']['X-User'] == 'not set', 'user'
- assert resp['headers']['X-Password'] == 'not set', 'password'
+ assert (
+ client.get()['headers']['X-File']
+ == f'{option.test_dir}/php/ini_precision/ini/php.ini'
+ ), 'ini file'
+ assert client.get()['headers']['X-Precision'] == '5', 'ini value user'
- resp = self.get(
- headers={
- 'Host': 'localhost',
- 'Authorization': 'Basic dXNlcjpwYXNzd29yZA==',
- 'Connection': 'close',
- }
- )
- assert resp['status'] == 200, 'basic status'
- assert resp['headers']['X-Digest'] == 'not set', 'basic digest'
- assert resp['headers']['X-User'] == 'user', 'basic user'
- assert resp['headers']['X-Password'] == 'password', 'basic password'
- resp = self.get(
+def test_php_application_ini_user_2():
+ client.load('ini_precision')
+
+ assert 'success' in client.conf(
+ {"file": "ini/php.ini"}, 'applications/ini_precision/options'
+ )
+
+ assert client.get()['headers']['X-Precision'] == '4', 'ini user file'
+
+ assert 'success' in client.conf(
+ {"precision": "5"}, 'applications/ini_precision/options/user'
+ )
+
+ assert client.get()['headers']['X-Precision'] == '5', 'ini value user'
+
+
+def test_php_application_ini_set_admin():
+ client.load('ini_precision')
+
+ assert 'success' in client.conf(
+ {"admin": {"precision": "5"}}, 'applications/ini_precision/options'
+ )
+
+ assert (
+ client.get(url='/?precision=6')['headers']['X-Precision'] == '5'
+ ), 'ini set admin'
+
+
+def test_php_application_ini_set_user():
+ client.load('ini_precision')
+
+ assert 'success' in client.conf(
+ {"user": {"precision": "5"}}, 'applications/ini_precision/options'
+ )
+
+ assert (
+ client.get(url='/?precision=6')['headers']['X-Precision'] == '6'
+ ), 'ini set user'
+
+
+def test_php_application_ini_repeat():
+ client.load('ini_precision')
+
+ assert 'success' in client.conf(
+ {"user": {"precision": "5"}}, 'applications/ini_precision/options'
+ )
+
+ assert client.get()['headers']['X-Precision'] == '5', 'ini value'
+
+ assert client.get()['headers']['X-Precision'] == '5', 'ini value repeat'
+
+
+def test_php_application_disable_functions_exec():
+ client.load('time_exec')
+
+ before_disable_functions()
+
+ assert 'success' in client.conf(
+ {"admin": {"disable_functions": "exec"}},
+ 'applications/time_exec/options',
+ )
+
+ body = client.get()['body']
+
+ assert re.search(r'time: \d+', body), 'disable_functions time'
+ assert not re.search(r'exec: \/\w+', body), 'disable_functions exec'
+
+
+def test_php_application_disable_functions_comma():
+ client.load('time_exec')
+
+ before_disable_functions()
+
+ assert 'success' in client.conf(
+ {"admin": {"disable_functions": "exec,time"}},
+ 'applications/time_exec/options',
+ )
+
+ body = client.get()['body']
+
+ assert not re.search(r'time: \d+', body), 'disable_functions comma time'
+ assert not re.search(r'exec: \/\w+', body), 'disable_functions comma exec'
+
+
+def test_php_application_auth():
+ client.load('auth')
+
+ resp = client.get()
+ assert resp['status'] == 200, 'status'
+ assert resp['headers']['X-Digest'] == 'not set', 'digest'
+ assert resp['headers']['X-User'] == 'not set', 'user'
+ assert resp['headers']['X-Password'] == 'not set', 'password'
+
+ resp = client.get(
+ headers={
+ 'Host': 'localhost',
+ 'Authorization': 'Basic dXNlcjpwYXNzd29yZA==',
+ 'Connection': 'close',
+ }
+ )
+ assert resp['status'] == 200, 'basic status'
+ assert resp['headers']['X-Digest'] == 'not set', 'basic digest'
+ assert resp['headers']['X-User'] == 'user', 'basic user'
+ assert resp['headers']['X-Password'] == 'password', 'basic password'
+
+ resp = client.get(
+ headers={
+ 'Host': 'localhost',
+ 'Authorization': 'Digest username="blah", realm="", uri="/"',
+ 'Connection': 'close',
+ }
+ )
+ assert resp['status'] == 200, 'digest status'
+ assert (
+ resp['headers']['X-Digest'] == 'username="blah", realm="", uri="/"'
+ ), 'digest digest'
+ assert resp['headers']['X-User'] == 'not set', 'digest user'
+ assert resp['headers']['X-Password'] == 'not set', 'digest password'
+
+
+def test_php_application_auth_invalid():
+ client.load('auth')
+
+ def check_auth(auth):
+ resp = client.get(
headers={
'Host': 'localhost',
- 'Authorization': 'Digest username="blah", realm="", uri="/"',
+ 'Authorization': auth,
'Connection': 'close',
}
)
- assert resp['status'] == 200, 'digest status'
- assert (
- resp['headers']['X-Digest'] == 'username="blah", realm="", uri="/"'
- ), 'digest digest'
- assert resp['headers']['X-User'] == 'not set', 'digest user'
- assert resp['headers']['X-Password'] == 'not set', 'digest password'
-
- def test_php_application_auth_invalid(self):
- self.load('auth')
-
- def check_auth(auth):
- resp = self.get(
- headers={
- 'Host': 'localhost',
- 'Authorization': auth,
- 'Connection': 'close',
- }
- )
- assert resp['status'] == 200, 'status'
- assert resp['headers']['X-Digest'] == 'not set', 'Digest'
- assert resp['headers']['X-User'] == 'not set', 'User'
- assert resp['headers']['X-Password'] == 'not set', 'Password'
+ assert resp['status'] == 200, 'status'
+ assert resp['headers']['X-Digest'] == 'not set', 'Digest'
+ assert resp['headers']['X-User'] == 'not set', 'User'
+ assert resp['headers']['X-Password'] == 'not set', 'Password'
- check_auth('Basic dXN%cjpwYXNzd29yZA==')
- check_auth('Basic XNlcjpwYXNzd29yZA==')
- check_auth('Basic DdXNlcjpwYXNzd29yZA==')
- check_auth('Basic blah')
- check_auth('Basic')
- check_auth('Digest')
- check_auth('blah')
+ check_auth('Basic dXN%cjpwYXNzd29yZA==')
+ check_auth('Basic XNlcjpwYXNzd29yZA==')
+ check_auth('Basic DdXNlcjpwYXNzd29yZA==')
+ check_auth('Basic blah')
+ check_auth('Basic')
+ check_auth('Digest')
+ check_auth('blah')
- def test_php_application_disable_functions_space(self):
- self.load('time_exec')
- self.before_disable_functions()
+def test_php_application_disable_functions_space():
+ client.load('time_exec')
- assert 'success' in self.conf(
- {"admin": {"disable_functions": "exec time"}},
- 'applications/time_exec/options',
- )
+ before_disable_functions()
- body = self.get()['body']
+ assert 'success' in client.conf(
+ {"admin": {"disable_functions": "exec time"}},
+ 'applications/time_exec/options',
+ )
- assert not re.search(r'time: \d+', body), 'disable_functions space time'
- assert not re.search(
- r'exec: \/\w+', body
- ), 'disable_functions space exec'
+ body = client.get()['body']
- def test_php_application_disable_functions_user(self):
- self.load('time_exec')
+ assert not re.search(r'time: \d+', body), 'disable_functions space time'
+ assert not re.search(r'exec: \/\w+', body), 'disable_functions space exec'
- self.before_disable_functions()
- assert 'success' in self.conf(
- {"user": {"disable_functions": "exec"}},
- 'applications/time_exec/options',
- )
+def test_php_application_disable_functions_user():
+ client.load('time_exec')
- body = self.get()['body']
+ before_disable_functions()
- assert re.search(r'time: \d+', body), 'disable_functions user time'
- assert not re.search(
- r'exec: \/\w+', body
- ), 'disable_functions user exec'
+ assert 'success' in client.conf(
+ {"user": {"disable_functions": "exec"}},
+ 'applications/time_exec/options',
+ )
- def test_php_application_disable_functions_nonexistent(self):
- self.load('time_exec')
+ body = client.get()['body']
- self.before_disable_functions()
+ assert re.search(r'time: \d+', body), 'disable_functions user time'
+ assert not re.search(r'exec: \/\w+', body), 'disable_functions user exec'
- assert 'success' in self.conf(
- {"admin": {"disable_functions": "blah"}},
- 'applications/time_exec/options',
- )
- body = self.get()['body']
+def test_php_application_disable_functions_nonexistent():
+ client.load('time_exec')
- assert re.search(
- r'time: \d+', body
- ), 'disable_functions nonexistent time'
- assert re.search(
- r'exec: \/\w+', body
- ), 'disable_functions nonexistent exec'
+ before_disable_functions()
- def test_php_application_disable_classes(self):
- self.load('date_time')
+ assert 'success' in client.conf(
+ {"admin": {"disable_functions": "blah"}},
+ 'applications/time_exec/options',
+ )
- assert re.search(
- r'012345', self.get()['body']
- ), 'disable_classes before'
+ body = client.get()['body']
- assert 'success' in self.conf(
- {"admin": {"disable_classes": "DateTime"}},
- 'applications/date_time/options',
- )
+ assert re.search(r'time: \d+', body), 'disable_functions nonexistent time'
+ assert re.search(r'exec: \/\w+', body), 'disable_functions nonexistent exec'
- assert not re.search(
- r'012345', self.get()['body']
- ), 'disable_classes before'
- def test_php_application_disable_classes_user(self):
- self.load('date_time')
+def test_php_application_disable_classes():
+ client.load('date_time')
- assert re.search(
- r'012345', self.get()['body']
- ), 'disable_classes before'
+ assert re.search(r'012345', client.get()['body']), 'disable_classes before'
- assert 'success' in self.conf(
- {"user": {"disable_classes": "DateTime"}},
- 'applications/date_time/options',
- )
+ assert 'success' in client.conf(
+ {"admin": {"disable_classes": "DateTime"}},
+ 'applications/date_time/options',
+ )
- assert not re.search(
- r'012345', self.get()['body']
- ), 'disable_classes before'
+ assert not re.search(
+ r'012345', client.get()['body']
+ ), 'disable_classes before'
- def test_php_application_error_log(self):
- self.load('error_log')
- assert self.get()['status'] == 200, 'status'
+def test_php_application_disable_classes_user():
+ client.load('date_time')
- time.sleep(1)
+ assert re.search(r'012345', client.get()['body']), 'disable_classes before'
- assert self.get()['status'] == 200, 'status 2'
+ assert 'success' in client.conf(
+ {"user": {"disable_classes": "DateTime"}},
+ 'applications/date_time/options',
+ )
- pattern = r'\d{4}\/\d\d\/\d\d\s\d\d:.+\[notice\].+Error in application'
+ assert not re.search(
+ r'012345', client.get()['body']
+ ), 'disable_classes before'
- assert self.wait_for_record(pattern) is not None, 'errors print'
- errs = self.findall(pattern)
+def test_php_application_error_log(findall, wait_for_record):
+ client.load('error_log')
- assert len(errs) == 2, 'error_log count'
+ assert client.get()['status'] == 200, 'status'
- date = errs[0].split('[')[0]
- date2 = errs[1].split('[')[0]
- assert date != date2, 'date diff'
+ time.sleep(1)
- def test_php_application_script(self):
- assert 'success' in self.conf(
- {
- "listeners": {"*:7080": {"pass": "applications/script"}},
- "applications": {
- "script": {
- "type": self.get_application_type(),
- "processes": {"spare": 0},
- "root": f"{option.test_dir}/php/script",
- "script": "phpinfo.php",
- }
- },
- }
- ), 'configure script'
+ assert client.get()['status'] == 200, 'status 2'
- resp = self.get()
+ pattern = r'\d{4}\/\d\d\/\d\d\s\d\d:.+\[notice\].+Error in application'
- assert resp['status'] == 200, 'status'
- assert resp['body'] != '', 'body not empty'
-
- def test_php_application_index_default(self):
- assert 'success' in self.conf(
- {
- "listeners": {"*:7080": {"pass": "applications/phpinfo"}},
- "applications": {
- "phpinfo": {
- "type": self.get_application_type(),
- "processes": {"spare": 0},
- "root": f"{option.test_dir}/php/phpinfo",
- }
- },
- }
- ), 'configure index default'
+ assert wait_for_record(pattern) is not None, 'errors print'
- resp = self.get()
+ errs = findall(pattern)
- assert resp['status'] == 200, 'status'
- assert resp['body'] != '', 'body not empty'
-
- def test_php_application_trailing_slash(self, temp_dir):
- new_root = f'{temp_dir}/php-root'
- os.makedirs(f'{new_root}/path')
-
- Path(f'{new_root}/path/index.php').write_text('<?php echo "OK\n"; ?>')
-
- addr = f'{temp_dir}/sock'
-
- assert 'success' in self.conf(
- {
- "listeners": {
- "*:7080": {"pass": "applications/php-path"},
- f'unix:{addr}': {"pass": "applications/php-path"},
- },
- "applications": {
- "php-path": {
- "type": self.get_application_type(),
- "processes": {"spare": 0},
- "root": new_root,
- }
- },
- }
- ), 'configure trailing slash'
+ assert len(errs) == 2, 'error_log count'
- assert self.get(url='/path/')['status'] == 200, 'uri with trailing /'
+ date = errs[0].split('[')[0]
+ date2 = errs[1].split('[')[0]
+ assert date != date2, 'date diff'
- resp = self.get(url='/path?q=a')
- assert resp['status'] == 301, 'uri without trailing /'
- assert (
- resp['headers']['Location'] == 'http://localhost:7080/path/?q=a'
- ), 'Location with query string'
- resp = self.get(
- sock_type='unix',
- addr=addr,
- url='/path',
- headers={'Host': 'foo', 'Connection': 'close'},
- )
- assert resp['status'] == 301, 'uri without trailing /'
- assert (
- resp['headers']['Location'] == 'http://foo/path/'
- ), 'Location with custom Host over UDS'
-
- def test_php_application_forbidden(self, temp_dir):
- new_root = f'{temp_dir}/php-root/path'
- os.makedirs(new_root)
- os.chmod(new_root, 0o000)
-
- assert 'success' in self.conf(
- {
- "listeners": {"*:7080": {"pass": "applications/php-path"}},
- "applications": {
- "php-path": {
- "type": self.get_application_type(),
- "processes": {"spare": 0},
- "root": f'{temp_dir}/php-root',
- }
- },
- }
- ), 'forbidden directory'
-
- assert self.get(url='/path/')['status'] == 403, 'access forbidden'
-
- def test_php_application_extension_check(self, temp_dir):
- self.load('phpinfo')
-
- assert self.get(url='/index.wrong')['status'] != 200, 'status'
-
- new_root = f'{temp_dir}/php'
- os.mkdir(new_root)
- shutil.copy(f'{option.test_dir}/php/phpinfo/index.wrong', new_root)
-
- assert 'success' in self.conf(
- {
- "listeners": {"*:7080": {"pass": "applications/phpinfo"}},
- "applications": {
- "phpinfo": {
- "type": self.get_application_type(),
- "processes": {"spare": 0},
- "root": new_root,
- "working_directory": new_root,
- }
- },
- }
- ), 'configure new root'
+def test_php_application_script():
+ assert 'success' in client.conf(
+ {
+ "listeners": {"*:7080": {"pass": "applications/script"}},
+ "applications": {
+ "script": {
+ "type": client.get_application_type(),
+ "processes": {"spare": 0},
+ "root": f"{option.test_dir}/php/script",
+ "script": "phpinfo.php",
+ }
+ },
+ }
+ ), 'configure script'
- resp = self.get()
- assert f'{resp["status"]}{resp["body"]}' != '200', 'status new root'
+ resp = client.get()
- def run_php_application_cwd_root_tests(self):
- assert 'success' in self.conf_delete(
- 'applications/cwd/working_directory'
- )
+ assert resp['status'] == 200, 'status'
+ assert resp['body'] != '', 'body not empty'
- script_cwd = f'{option.test_dir}/php/cwd'
- resp = self.get()
- assert resp['status'] == 200, 'status ok'
- assert resp['body'] == script_cwd, 'default cwd'
+def test_php_application_index_default():
+ assert 'success' in client.conf(
+ {
+ "listeners": {"*:7080": {"pass": "applications/phpinfo"}},
+ "applications": {
+ "phpinfo": {
+ "type": client.get_application_type(),
+ "processes": {"spare": 0},
+ "root": f"{option.test_dir}/php/phpinfo",
+ }
+ },
+ }
+ ), 'configure index default'
- assert 'success' in self.conf(
- f'"{option.test_dir}"',
- 'applications/cwd/working_directory',
- )
+ resp = client.get()
- resp = self.get()
- assert resp['status'] == 200, 'status ok'
- assert resp['body'] == script_cwd, 'wdir cwd'
+ assert resp['status'] == 200, 'status'
+ assert resp['body'] != '', 'body not empty'
- resp = self.get(url='/?chdir=/')
- assert resp['status'] == 200, 'status ok'
- assert resp['body'] == '/', 'cwd after chdir'
- # cwd must be restored
+def test_php_application_trailing_slash(temp_dir):
+ new_root = f'{temp_dir}/php-root'
+ os.makedirs(f'{new_root}/path')
- resp = self.get()
- assert resp['status'] == 200, 'status ok'
- assert resp['body'] == script_cwd, 'cwd restored'
+ Path(f'{new_root}/path/index.php').write_text('<?php echo "OK\n"; ?>')
- resp = self.get(url='/subdir/')
- assert resp['body'] == f'{script_cwd}/subdir', 'cwd subdir'
+ addr = f'{temp_dir}/sock'
- def test_php_application_cwd_root(self):
- self.load('cwd')
- self.run_php_application_cwd_root_tests()
+ assert 'success' in client.conf(
+ {
+ "listeners": {
+ "*:7080": {"pass": "applications/php-path"},
+ f'unix:{addr}': {"pass": "applications/php-path"},
+ },
+ "applications": {
+ "php-path": {
+ "type": client.get_application_type(),
+ "processes": {"spare": 0},
+ "root": new_root,
+ }
+ },
+ }
+ ), 'configure trailing slash'
+
+ assert client.get(url='/path/')['status'] == 200, 'uri with trailing /'
+
+ resp = client.get(url='/path?q=a')
+ assert resp['status'] == 301, 'uri without trailing /'
+ assert (
+ resp['headers']['Location'] == 'http://localhost:7080/path/?q=a'
+ ), 'Location with query string'
+
+ resp = client.get(
+ sock_type='unix',
+ addr=addr,
+ url='/path',
+ headers={'Host': 'foo', 'Connection': 'close'},
+ )
+ assert resp['status'] == 301, 'uri without trailing /'
+ assert (
+ resp['headers']['Location'] == 'http://foo/path/'
+ ), 'Location with custom Host over UDS'
+
+
+def test_php_application_forbidden(temp_dir):
+ new_root = f'{temp_dir}/php-root/path'
+ os.makedirs(new_root)
+ os.chmod(new_root, 0o000)
+
+ assert 'success' in client.conf(
+ {
+ "listeners": {"*:7080": {"pass": "applications/php-path"}},
+ "applications": {
+ "php-path": {
+ "type": client.get_application_type(),
+ "processes": {"spare": 0},
+ "root": f'{temp_dir}/php-root',
+ }
+ },
+ }
+ ), 'forbidden directory'
- def test_php_application_cwd_opcache_disabled(self):
- self.load('cwd')
- self.set_opcache('cwd', '0')
- self.run_php_application_cwd_root_tests()
+ assert client.get(url='/path/')['status'] == 403, 'access forbidden'
- def test_php_application_cwd_opcache_enabled(self):
- self.load('cwd')
- self.set_opcache('cwd', '1')
- self.run_php_application_cwd_root_tests()
- def run_php_application_cwd_script_tests(self):
- self.load('cwd')
+def test_php_application_extension_check(temp_dir):
+ client.load('phpinfo')
- script_cwd = f'{option.test_dir}/php/cwd'
+ assert client.get(url='/index.wrong')['status'] != 200, 'status'
+
+ new_root = f'{temp_dir}/php'
+ os.mkdir(new_root)
+ shutil.copy(f'{option.test_dir}/php/phpinfo/index.wrong', new_root)
+
+ assert 'success' in client.conf(
+ {
+ "listeners": {"*:7080": {"pass": "applications/phpinfo"}},
+ "applications": {
+ "phpinfo": {
+ "type": client.get_application_type(),
+ "processes": {"spare": 0},
+ "root": new_root,
+ "working_directory": new_root,
+ }
+ },
+ }
+ ), 'configure new root'
+
+ resp = client.get()
+ assert f'{resp["status"]}{resp["body"]}' != '200', 'status new root'
+
+
+def test_php_application_cwd_root():
+ client.load('cwd')
+ run_php_application_cwd_root_tests()
+
+
+def test_php_application_cwd_opcache_disabled():
+ client.load('cwd')
+ set_opcache('cwd', '0')
+ run_php_application_cwd_root_tests()
+
+
+def test_php_application_cwd_opcache_enabled():
+ client.load('cwd')
+ set_opcache('cwd', '1')
+ run_php_application_cwd_root_tests()
+
+
+def test_php_application_cwd_script():
+ client.load('cwd')
+ run_php_application_cwd_script_tests()
- assert 'success' in self.conf_delete(
- 'applications/cwd/working_directory'
- )
- assert 'success' in self.conf('"index.php"', 'applications/cwd/script')
+def test_php_application_cwd_script_opcache_disabled():
+ client.load('cwd')
+ set_opcache('cwd', '0')
+ run_php_application_cwd_script_tests()
- assert self.get()['body'] == script_cwd, 'default cwd'
- assert self.get(url='/?chdir=/')['body'] == '/', 'cwd after chdir'
+def test_php_application_cwd_script_opcache_enabled():
+ client.load('cwd')
+ set_opcache('cwd', '1')
+ run_php_application_cwd_script_tests()
- # cwd must be restored
- assert self.get()['body'] == script_cwd, 'cwd restored'
- def test_php_application_cwd_script(self):
- self.load('cwd')
- self.run_php_application_cwd_script_tests()
+def test_php_application_path_relative():
+ client.load('open')
- def test_php_application_cwd_script_opcache_disabled(self):
- self.load('cwd')
- self.set_opcache('cwd', '0')
- self.run_php_application_cwd_script_tests()
+ assert client.get()['body'] == 'test', 'relative path'
- def test_php_application_cwd_script_opcache_enabled(self):
- self.load('cwd')
- self.set_opcache('cwd', '1')
- self.run_php_application_cwd_script_tests()
+ assert (
+ client.get(url='/?chdir=/')['body'] != 'test'
+ ), 'relative path w/ chdir'
- def test_php_application_path_relative(self):
- self.load('open')
+ assert client.get()['body'] == 'test', 'relative path 2'
- assert self.get()['body'] == 'test', 'relative path'
- assert (
- self.get(url='/?chdir=/')['body'] != 'test'
- ), 'relative path w/ chdir'
+def test_php_application_shared_opcache():
+ client.load('opcache', limits={'requests': 1})
- assert self.get()['body'] == 'test', 'relative path 2'
+ r = check_opcache()
+ pid = r['headers']['X-Pid']
+ assert r['headers']['X-Cached'] == '0', 'not cached'
- def test_php_application_shared_opcache(self):
- self.load('opcache', limits={'requests': 1})
+ r = client.get()
- r = self.check_opcache()
- pid = r['headers']['X-Pid']
- assert r['headers']['X-Cached'] == '0', 'not cached'
+ assert r['headers']['X-Pid'] != pid, 'new instance'
+ assert r['headers']['X-Cached'] == '1', 'cached'
- r = self.get()
- assert r['headers']['X-Pid'] != pid, 'new instance'
- assert r['headers']['X-Cached'] == '1', 'cached'
+def test_php_application_opcache_preload_chdir():
+ client.load('opcache')
- def test_php_application_opcache_preload_chdir(self, temp_dir):
- self.load('opcache')
+ check_opcache()
- self.check_opcache()
+ set_preload('chdir.php')
- self.set_preload('chdir.php')
+ assert client.get()['headers']['X-Cached'] == '0', 'not cached'
+ assert client.get()['headers']['X-Cached'] == '1', 'cached'
- assert self.get()['headers']['X-Cached'] == '0', 'not cached'
- assert self.get()['headers']['X-Cached'] == '1', 'cached'
- def test_php_application_opcache_preload_ffr(self, temp_dir):
- self.load('opcache')
+def test_php_application_opcache_preload_ffr():
+ client.load('opcache')
- self.check_opcache()
+ check_opcache()
- self.set_preload('fastcgi_finish_request.php')
+ set_preload('fastcgi_finish_request.php')
- assert self.get()['headers']['X-Cached'] == '0', 'not cached'
- assert self.get()['headers']['X-Cached'] == '1', 'cached'
+ assert client.get()['headers']['X-Cached'] == '0', 'not cached'
+ assert client.get()['headers']['X-Cached'] == '1', 'cached'