import functools import shutil import subprocess from typing import Optional, Type from irctest.basecontrollers import BaseServerController, DirectoryBasedController TEMPLATE_CONFIG = """ # Clients: {ssl_config} # Disable 'NOTICE #chan :*** foo invited bar into the channel- # Services: # Anope errors when missing # Atheme raises a warning when missing # Protocol: # for testing mute extbans # For multi-prefix # For userhost-in-names # HELP/HELPOP # for the HELP alias # Misc: """ TEMPLATE_SSL_CONFIG = """ """ @functools.lru_cache() def installed_version() -> int: output = subprocess.check_output(["inspircd", "--version"], universal_newlines=True) if output.startswith("InspIRCd-3"): return 3 if output.startswith("InspIRCd-4"): return 4 else: assert False, f"unexpected version: {output}" class InspircdController(BaseServerController, DirectoryBasedController): software_name = "InspIRCd" software_version = installed_version() supported_sasl_mechanisms = {"PLAIN"} supports_sts = False extban_mute_char = "m" def create_config(self) -> None: super().create_config() with self.open_file("server.conf"): pass def run( self, hostname: str, port: int, *, password: Optional[str], ssl: bool, run_services: bool, faketime: Optional[str] = None, ) -> None: assert self.proc is None self.port = port self.hostname = hostname self.create_config() (services_hostname, services_port) = self.get_hostname_and_port() password_field = 'password="{}"'.format(password) if password else "" if ssl: self.gen_ssl() ssl_config = TEMPLATE_SSL_CONFIG.format( key_path=self.key_path, pem_path=self.pem_path, dh_path=self.dh_path ) else: ssl_config = "" if installed_version() == 3: help_module_name = "helpop" elif installed_version() == 4: help_module_name = "help" else: assert False, f"unexpected version: {installed_version()}" with self.open_file("server.conf") as fd: fd.write( TEMPLATE_CONFIG.format( hostname=hostname, port=port, services_hostname=services_hostname, services_port=services_port, password_field=password_field, ssl_config=ssl_config, help_module_name=help_module_name, ) ) assert self.directory if faketime and shutil.which("faketime"): faketime_cmd = ["faketime", "-f", faketime] self.faketime_enabled = True else: faketime_cmd = [] self.proc = subprocess.Popen( [ *faketime_cmd, "inspircd", "--nofork", "--config", self.directory / "server.conf", ], stdout=subprocess.DEVNULL, ) if run_services: self.wait_for_port() self.services_controller = self.services_controller_class( self.test_config, self ) self.services_controller.run( protocol="inspircd3", server_hostname=services_hostname, server_port=services_port, ) def get_irctest_controller_class() -> Type[InspircdController]: return InspircdController