# SPDX-License-Identifier: AGPL-3.0-or-later """ Tests for config module. """ import os from unittest.mock import MagicMock, patch import pytest from plinth import __main__ as plinth_main from plinth.modules.apache import uws_directory_of_user, uws_url_of_user from plinth.modules.config import (_home_page_scid2url, change_home_page, get_home_page, home_page_url2scid) from plinth.modules.config.forms import ConfigurationForm def test_hostname_field(): """Test that hostname field accepts only valid hostnames.""" valid_hostnames = [ 'a', '0a', 'a0', 'AAA', '00', '0-0', 'example-hostname', 'example', '012345678901234567890123456789012345678901234567890123456789012' ] invalid_hostnames = [ '', '-', '-a', 'a-', '.a', 'a.', 'a.a', '?', 'a?a', '0123456789012345678901234567890123456789012345678901234567890123' ] for hostname in valid_hostnames: form = ConfigurationForm({ 'hostname': hostname, 'domainname': 'example.com', 'logging_mode': 'volatile' }) assert form.is_valid() for hostname in invalid_hostnames: form = ConfigurationForm({ 'hostname': hostname, 'domainname': 'example.com', 'logging_mode': 'volatile' }) assert not form.is_valid() def test_domainname_field(): """Test that domainname field accepts only valid domainnames.""" valid_domainnames = [ '', 'a', '0a', 'a0', 'AAA', '00', '0-0', 'example-hostname', 'example', 'example.org', 'a.b.c.d', 'a-0.b-0.c-0', '012345678901234567890123456789012345678901234567890123456789012', ((('x' * 63) + '.') * 3) + 'x' * 61 ] invalid_domainnames = [ '-', '-a', 'a-', '.a', 'a.', '?', 'a?a', 'a..a', 'a.-a', '.', ((('x' * 63) + '.') * 3) + 'x' * 62, 'x' * 64 ] for domainname in valid_domainnames: form = ConfigurationForm({ 'hostname': 'example', 'domainname': domainname, 'logging_mode': 'volatile' }) assert form.is_valid() for domainname in invalid_domainnames: form = ConfigurationForm({ 'hostname': 'example', 'domainname': domainname, 'logging_mode': 'volatile' }) assert not form.is_valid() def test_homepage_mapping(): """Basic tests for homepage functions.""" func = home_page_url2scid assert func(None) is None assert func('/unknown/url') is None assert func('/plinth/') == 'plinth' assert func('/plinth') == 'plinth' assert func('plinth') == 'plinth' assert func('/index.html') == 'apache-default' assert func('/~user') == 'uws-user' assert func('/~user/whatever/else') == 'uws-user' func = _home_page_scid2url assert func(None) is None assert func('plinth') == '/plinth/' assert func('apache-default') == '/index.html' def test_homepage_mapping_skip_ci(): """Special tests for homepage functions.""" try: user = os.getlogin() except OSError: # See msg383161 in https://bugs.python.org/issue40821 reason = "Needs access to ~/ directory. " \ + "CI sandboxed workspace doesn't provide it." pytest.skip(reason) uws_directory = uws_directory_of_user(user) uws_url = uws_url_of_user(user) uws_scid = home_page_url2scid(uws_url) # Check test's precondition: if os.path.exists(uws_directory): # Don't blindly remove a pre-existing directory. Just skip the test. reason = "UWS directory {} exists already.".format(uws_directory) pytest.skip(reason) # AC: Return scid if UWS directory exists: try: os.mkdir(uws_directory) except Exception: reason = "Needs access to ~/ directory. " \ + "CI sandboxed workspace doesn't provide it." pytest.skip(reason) assert _home_page_scid2url(uws_scid) == uws_url # AC: Return None if it doesn't: os.rmdir(uws_directory) assert _home_page_scid2url(uws_scid) is None class Dict2Obj: """Mock object made out of any dict.""" def __init__(self, a_dict): self.__dict__ = a_dict @patch('plinth.frontpage.Shortcut.list', MagicMock(return_value=[ Dict2Obj({ 'url': 'url/for/' + id, 'component_id': id }) for id in ('a', 'b') ])) @pytest.mark.usefixtures('needs_root') def test_homepage_field(): """Test homepage changes. Test Cases: 1) FreedomBox Homepage (default), 2) Apache default, 3) A user's website of an... 3.1) unexisting user 3.2) existing user without a page 3.3) existing user page. 4) A FreedomBox App. 4.1) unknown app 4.2) uninstalled app 4.3) disabled app 4.4) enabled app Note: If run on a pristine unconfigured FreedomBox, this test will leave the homepage default-configured. (Imperfect cleanup in such case). Note: We take fbx as website user because of our testing container. Pending: - Specific test cases to distinguish 4.1,2,3. Currently they share the same test case. - Search for another valid user apart from fbx. """ user = 'fbx' uws_directory = uws_directory_of_user(user) uws_url = uws_url_of_user(user) uws_scid = home_page_url2scid(uws_url) default_home_page = 'plinth' original_home_page = get_home_page() or default_home_page # Check test's preconditions: if original_home_page not in (default_home_page, None): reason = "Unexpected home page {}.".format(original_home_page) pytest.skip(reason) if os.path.exists(uws_directory): # Don't blindly remove a pre-existing directory. Just skip the test. reason = "UWS directory {} exists already.".format(uws_directory) pytest.skip(reason) # AC: invalid changes fall back to default: for scid in ('uws-unexisting', uws_scid, 'missing_app'): change_home_page(scid) assert get_home_page() == default_home_page # AC: valid changes actually happen: try: os.mkdir(uws_directory) except Exception: reason = "Needs access to ~/ directory. " \ + "CI sandboxed workspace doesn't provide it." pytest.skip(reason) for scid in ('b', 'a', uws_scid, 'apache-default', 'plinth'): change_home_page(scid) assert get_home_page() == scid # cleanup: change_home_page(original_home_page) os.rmdir(uws_directory) assert get_home_page() == original_home_page def test_locale_path(): """ Test that the 'locale' directory is in the same folder as __main__.py. This is required for detecting translated languages. """ plinth_dir = os.path.dirname(plinth_main.__file__) locale_dir = os.path.join(plinth_dir, 'locale') assert os.path.isdir(locale_dir)