def logging_level(request): """ Configure the structlog level. For integration tests this also sets the geth verbosity. """ # disable pytest's built in log capture, otherwise logs are printed twice request.config.option.showcapture = "no" if request.config.option.log_cli_level: level = request.config.option.log_cli_level elif request.config.option.verbose > 3: level = "DEBUG" elif request.config.option.verbose > 1: level = "INFO" else: level = "WARNING" if request.config.option.log_config: config_converter = LogLevelConfigType() logging_levels = config_converter.convert( value=request.config.option.log_config, param=None, ctx=None) else: logging_levels = {"": level} time = datetime.datetime.utcnow().isoformat() debug_path = os.path.join(tempfile.gettempdir(), f"raiden-debug_{time}.log") configure_logging( logging_levels, colorize=not request.config.option.plain_log, log_file=request.config.option.log_file, cache_logger_on_first_use=False, debug_log_file_name=debug_path, )
def logging_level(request): """ Configure the structlog level. For integration tests this also sets the geth verbosity. """ # disable pytest's built in log capture, otherwise logs are printed twice request.config.option.showcapture = 'no' if request.config.option.log_cli_level: level = request.config.option.log_cli_level elif request.config.option.verbose > 3: level = 'DEBUG' elif request.config.option.verbose > 1: level = 'INFO' else: level = 'WARNING' if request.config.option.log_config: config_converter = LogLevelConfigType() logging_levels = config_converter.convert( value=request.config.option.log_config, param=None, ctx=None, ) else: logging_levels = {'': level} configure_logging( logging_levels, colorize=not request.config.option.plain_log, log_file=request.config.option.log_file, )
def logging_level(request): """ Configure the structlog level. For integration tests this also sets the geth verbosity. """ if request.config.option.log_cli_level: level = request.config.option.log_cli_level elif request.config.option.verbose > 3: level = 'DEBUG' elif request.config.option.verbose > 1: level = 'INFO' else: level = 'WARNING' if request.config.option.log_config: config_converter = LogLevelConfigType() logging_levels = config_converter.convert( value=request.config.option.log_config, param=None, ctx=None, ) else: logging_levels = {'': level} configure_logging( logging_levels, colorize=not request.config.option.plain_log, log_file=request.config.option.log_file, )
def main(own_server: str, interval: int, credentials_file: TextIO, log_level: str) -> None: configure_logging( {"": log_level, "raiden": log_level, "__main__": log_level}, disable_debug_logfile=True ) known_servers_url = os.environ.get(ENV_KEY_KNOWN_SERVERS) try: credentials = json.loads(credentials_file.read()) username = credentials["username"] password = credentials["password"] except (JSONDecodeError, UnicodeDecodeError, OSError, KeyError): log.exception("Invalid credentials file") sys.exit(1) while True: try: room_ensurer = RoomEnsurer(username, password, own_server, known_servers_url) except RuntimeError as ex: log.exception(ex) gevent.sleep(60) continue try: room_ensurer.ensure_rooms() except EnsurerError: log.error("Retrying in 60s.") gevent.sleep(60) continue if interval == 0: break log.info("Run finished, sleeping.", duration=interval) gevent.sleep(interval)
def report(report_path=None, disable_debug_logfile=True): if report_path is None: report_file = tempfile.mktemp(suffix=".log") else: report_file = report_path click.secho(f"Report file: {report_file}", fg="yellow") configure_logging( logger_level_config={ "": "INFO", "raiden": "DEBUG", "scenario_player": "DEBUG" }, log_file=report_file, disable_debug_logfile=disable_debug_logfile, ) def append_report(subject: str, data: Optional[AnyStr] = None) -> None: with open(report_file, "a", encoding="UTF-8") as handler: handler.write(f'{f" {subject.upper()} ":=^80}{os.linesep}') if data is not None: write_data: str if isinstance(data, bytes): write_data = data.decode() else: write_data = data handler.writelines([write_data + os.linesep]) yield report_file, append_report
def logging_level(request): """ Configure the structlog level. For integration tests this also sets the geth verbosity. """ # disable pytest's built in log capture, otherwise logs are printed twice request.config.option.showcapture = 'no' if request.config.option.log_cli_level: level = request.config.option.log_cli_level elif request.config.option.verbose > 3: level = 'DEBUG' elif request.config.option.verbose > 1: level = 'INFO' else: level = 'WARNING' if request.config.option.log_config: config_converter = LogLevelConfigType() logging_levels = config_converter.convert( value=request.config.option.log_config, param=None, ctx=None, ) else: logging_levels = {'': level} configure_logging( logging_levels, colorize=not request.config.option.plain_log, log_file=request.config.option.log_file, cache_logger_on_first_use=False, )
def configure_logging_for_subcommand(log_file_name): Path(log_file_name).parent.mkdir(exist_ok=True, parents=True) click.secho(f"Writing log to {log_file_name}", fg="yellow") configure_logging( {"": "INFO", "raiden": "DEBUG", "scenario_player": "DEBUG"}, debug_log_file_name=log_file_name, _first_party_packages=_FIRST_PARTY_PACKAGES | frozenset(["scenario_player"]), _debug_log_file_additional_level_filters={"scenario_player": "DEBUG"}, )
def run(self): configure_logging( self._options['log_config'], log_json=self._options['log_json'], log_file=self._options['log_file'], disable_debug_logfile=self._options['disable_debug_logfile'], ) if self._options['config_file']: log.debug('Using config file', config_file=self._options['config_file'])
def run(self): configure_logging( self._options['log_config'], log_json=self._options['log_json'], log_file=self._options['log_file'], disable_debug_logfile=self._options['disable_debug_logfile'], ) log.info('Starting Raiden', **get_system_spec()) if self._options['config_file']: log.debug('Using config file', config_file=self._options['config_file'])
def run(self): configure_logging( self._options['log_config'], log_json=self._options['log_json'], log_file=self._options['log_file'], disable_debug_logfile=self._options['disable_debug_logfile'], ) log.info('Starting Raiden', **get_system_spec()) if self._options['config_file']: log.debug('Using config file', config_file=self._options['config_file'])
def run(self): configure_logging( self._options["log_config"], log_json=self._options["log_json"], log_file=self._options["log_file"], disable_debug_logfile=self._options["disable_debug_logfile"], debug_log_file_name=self._options["debug_logfile_name"], ) log.info("Starting Raiden", **get_system_spec()) if self._options["config_file"]: log.debug("Using config file", config_file=self._options["config_file"])
def test_redacted_request(capsys, tmpdir): configure_logging({"": "DEBUG"}, debug_log_file_name=str(tmpdir / "raiden-debug.log")) token = "my_access_token123" # use logging, as 'urllib3/requests' log = logging.getLogger("urllib3.connectionpool") log.debug("Starting new HTTPS connection (1): example.org:443") log.debug(f'https://example.org:443 "GET /endpoint?access_token={token} HTTP/1.1" 200 403') captured = capsys.readouterr() assert token not in captured.err assert "access_token=<redacted>" in captured.err
def test_redacted_request(capsys): configure_logging({'': 'DEBUG'}) token = 'my_access_token123' # use logging, as 'urllib3/requests' log = logging.getLogger('urllib3.connectionpool') log.debug('Starting new HTTPS connection (1): example.org:443') log.debug(f'https://example.org:443 "GET /endpoint?access_token={token} HTTP/1.1" 200 403') captured = capsys.readouterr() assert token not in captured.err assert 'access_token=<redacted>' in captured.err
def test_basic_logging(capsys, module, level, logger): configure_logging({module: level}) log = structlog.get_logger(logger).bind(foo='bar') log.debug('test event', key='value') captured = capsys.readouterr() no_log = level != 'DEBUG' or module not in logger if no_log: assert captured.err == '' else: assert 'test event' in captured.err assert 'key=value' in captured.err assert 'foo=bar' in captured.err
def test_redacted_traceback(capsys): configure_logging({'': 'DEBUG'}) token = 'my_access_token123' try: assert False, f'Failed acessing /endpoint?accessToken={token}' except AssertionError: traceback.print_exc() captured = capsys.readouterr() assert token not in captured.err assert 'accessToken=<redacted>' in captured.err
def test_that_secret_is_redacted(capsys, tmpdir): configure_logging({"": "DEBUG"}, debug_log_file_path=str(tmpdir / "raiden-debug.log")) log = structlog.get_logger("raiden.network.transport.matrix.transport") secret = "0x74564b5d217c3430713e7c6b643b5b244c6d617a4e350945303960723a7b2d4c" data = f"""{{"secret": "{secret}", "signature": "0x274ec0589b47a85fa8645a4b7fa9f021b3ba7b81e41ab47278c6269089bad7b26f41f233236d994dd86b495791c95e433710365224d390aeb9f7ee427eddb5081b", "message_identifier": "3887369794757038169", "type": "RevealSecret"}}""" # noqa log.debug("Send raw", data=data.replace("\n", "\\n")) captured = capsys.readouterr() assert secret not in captured.err assert f'"secret": "<redacted>"' in captured.err
def test_redacted_traceback(capsys, tmpdir): configure_logging({"": "DEBUG"}, debug_log_file_name=str(tmpdir / "raiden-debug.log")) token = "my_access_token123" try: assert False, f"Failed acessing /endpoint?accessToken={token}" except AssertionError: traceback.print_exc() captured = capsys.readouterr() assert token not in captured.err assert "accessToken=<redacted>" in captured.err
def logging_level(request): """ Configure the structlog level. For integration tests this also sets the geth verbosity. """ if request.config.option.verbose > 3: level = 'DEBUG' elif request.config.option.verbose > 1: level = 'INFO' else: level = 'WARNING' if request.config.option.log_cli_level: level = request.config.option.log_cli_level configure_logging({'': level}, colorize=not request.config.option.plain_log, log_file=request.config.option.log_file)
def test_redacted_request(capsys, tmpdir): configure_logging( {'': 'DEBUG'}, debug_log_file_name=str(tmpdir / 'raiden-debug.log'), ) token = 'my_access_token123' # use logging, as 'urllib3/requests' log = logging.getLogger('urllib3.connectionpool') log.debug('Starting new HTTPS connection (1): example.org:443') log.debug(f'https://example.org:443 "GET /endpoint?access_token={token} HTTP/1.1" 200 403') captured = capsys.readouterr() assert token not in captured.err assert 'access_token=<redacted>' in captured.err
def test_redacted_traceback(capsys, tmpdir): configure_logging( {'': 'DEBUG'}, debug_log_file_name=str(tmpdir / 'raiden-debug.log'), ) token = 'my_access_token123' try: assert False, f'Failed acessing /endpoint?accessToken={token}' except AssertionError: traceback.print_exc() captured = capsys.readouterr() assert token not in captured.err assert 'accessToken=<redacted>' in captured.err
def test_redacted_traceback(capsys, tmpdir): configure_logging( {'': 'DEBUG'}, debug_log_file_name=str(tmpdir / 'raiden-debug.log'), ) token = 'my_access_token123' try: assert False, f'Failed acessing /endpoint?accessToken={token}' except AssertionError: traceback.print_exc() captured = capsys.readouterr() assert token not in captured.err assert 'accessToken=<redacted>' in captured.err
def test_basic_logging(capsys, module, level, logger, disabled_debug, tmpdir): configure_logging( {module: level}, disable_debug_logfile=disabled_debug, debug_log_file_name=str(tmpdir / 'raiden-debug.log'), ) log = structlog.get_logger(logger).bind(foo='bar') log.debug('test event', key='value') captured = capsys.readouterr() no_log = level != 'DEBUG' or module not in logger if no_log: assert captured.err == '' else: assert 'test event' in captured.err assert 'key=value' in captured.err assert 'foo=bar' in captured.err
def test_basic_logging(capsys, module, level, logger, disabled_debug, tmpdir): configure_logging( {module: level}, disable_debug_logfile=disabled_debug, debug_log_file_name=str(tmpdir / "raiden-debug.log"), ) log = structlog.get_logger(logger).bind(foo="bar") log.debug("test event", key="value") captured = capsys.readouterr() no_log = level != "DEBUG" or module not in logger if no_log: assert captured.err == "" else: assert "test event" in captured.err assert "key=value" in captured.err assert "foo=bar" in captured.err
def test_basic_logging(capsys, module, level, logger, disabled_debug, tmpdir): configure_logging( {module: level}, disable_debug_logfile=disabled_debug, debug_log_file_name=str(tmpdir / 'raiden-debug.log'), ) log = structlog.get_logger(logger).bind(foo='bar') log.debug('test event', key='value') captured = capsys.readouterr() no_log = level != 'DEBUG' or module not in logger if no_log: assert captured.err == '' else: assert 'test event' in captured.err assert 'key=value' in captured.err assert 'foo=bar' in captured.err
def main(keystore_path, pretty, gas_price, port): configure_logging({'': 'DEBUG'}, colorize=True) privatekey_hex = get_privatekey_hex(keystore_path) privatekey = decode_hex(privatekey_hex) gas_price_in_wei = gas_price * 1000000000 patch_deploy_solidity_contract() host = '127.0.0.1' client = JSONRPCClient( host, port, privatekey, gas_price_in_wei, ) deployed = deploy_all(client) print(json.dumps(deployed, indent=2 if pretty else None))
def main(keystore_path, pretty, gas_price, port): configure_logging({'': 'DEBUG'}, colorize=True) privatekey = get_privatekey(keystore_path) gas_price_in_wei = gas_price * 1000000000 patch_deploy_solidity_contract() host = '127.0.0.1' client = JSONRPCClient( host, port, privatekey, gas_price_in_wei, ) deployed = deploy_contracts(client) print(json.dumps({ name: to_checksum_address(address) for name, address in deployed.items() }, indent=2 if pretty else None))
def logging_level(request): """ Configure the structlog level. For integration tests this also sets the geth verbosity. """ # disable pytest's built in log capture, otherwise logs are printed twice request.config.option.showcapture = 'no' if request.config.option.log_cli_level: level = request.config.option.log_cli_level elif request.config.option.verbose > 3: level = 'DEBUG' elif request.config.option.verbose > 1: level = 'INFO' else: level = 'WARNING' if request.config.option.log_config: config_converter = LogLevelConfigType() logging_levels = config_converter.convert( value=request.config.option.log_config, param=None, ctx=None, ) else: logging_levels = {'': level} time = datetime.datetime.utcnow().isoformat() debug_path = os.path.join( tempfile.gettempdir(), f'raiden-debug_{time}.log', ) configure_logging( logging_levels, colorize=not request.config.option.plain_log, log_file=request.config.option.log_file, cache_logger_on_first_use=False, debug_log_file_name=debug_path, )
def test_redacted_state_change(capsys, tmpdir): configure_logging({"": "DEBUG"}, debug_log_file_name=str(tmpdir / "raiden-debug.log")) auth_token = ( "MDAxZGxvY2F0aW9uIGxvY2FsaG9zdDo2NDAzMwowMDEzaWRlbnRpZmllciBrZXkKMDAxMGNpZCBnZW4gPSAxCjAwN" "GVjaWQgdXNlcl9pZCA9IEAweDYyNjRkYThmMmViOGQ4MDM3NjM2OTEwYzFlYzAzODA0MzhmNGVmZWU6bG9jYWxob3" "N0OjY0MDMzCjAwMTZjaWQgdHlwZSA9IGFjY2VzcwowMDIxY2lkIG5vbmNlID0gSlhjfjI4YVA9clZmbzZUSQowMDJ" "mc2lnbmF0dXJlIKQ1WCUJ-1Mv6rN6yjnb2w5R2BqH7iew7RwFiKuMcYosCg") auth_user = "******" state_changes = [{ "auth_data": f"{auth_user}/{auth_token}", "_type": "raiden.transfer.state_change.ActionUpdateTransportAuthData", }] log = structlog.get_logger("raiden.raiden_service") log.debug("State changes", state_changes=state_changes) captured = capsys.readouterr() assert auth_token not in captured.err assert f"{auth_user}/<redacted>" in captured.err
def logging_level(request, logs_storage): """ Configure the structlog level. For integration tests this also sets the geth verbosity. """ # disable pytest's built in log capture, otherwise logs are printed twice request.config.option.showcapture = "stdout" if request.config.option.log_cli_level: level = request.config.option.log_cli_level elif request.config.option.verbose > 3: level = "DEBUG" elif request.config.option.verbose > 1: level = "INFO" else: level = "WARNING" if request.config.option.log_config: config_converter = LogLevelConfigType() logging_levels = config_converter.convert( value=request.config.option.log_config, param=None, ctx=None ) else: logging_levels = {"": level} # configure_logging requires the path to exist os.makedirs(logs_storage, exist_ok=True) time = datetime.datetime.utcnow().isoformat() debug_path = os.path.join(logs_storage, f"raiden-debug_{time}.log") configure_logging( logging_levels, colorize=not request.config.option.plain_log, log_file=request.config.option.log_file, cache_logger_on_first_use=False, debug_log_file_path=debug_path, ) log.info("Running test", nodeid=request.node.nodeid)
def main(keystore_path, pretty, gas_price, port): configure_logging({'': 'DEBUG'}, colorize=True) privatekey = get_privatekey(keystore_path) gas_price_in_wei = gas_price * 1000000000 patch_deploy_solidity_contract() host = '127.0.0.1' client = JSONRPCClient( host, port, privatekey, gas_price_in_wei, ) deployed = deploy_all(client) deployed['EndpointRegistry.sol:EndpointRegistry'] = to_checksum_address( deployed['EndpointRegistry.sol:EndpointRegistry'], ) deployed['Registry.sol:Registry'] = to_checksum_address( deployed['Registry.sol:Registry'], ) print(json.dumps(deployed, indent=2 if pretty else None))
def main( ctx, scenario_file, keystore_file, password, chains, data_path, auth, mailgun_api_key, ): gevent.get_hub().exception_stream = DummyStream() is_subcommand = ctx.invoked_subcommand is not None if not is_subcommand and scenario_file is None: ctx.fail('No scenario definition file provided') if is_subcommand: log_file_name = ( f'scenario-player-{ctx.invoked_subcommand}_{datetime.now():%Y-%m-%dT%H:%M:%S}.log' ) else: scenario_basename = basename(scenario_file.name) log_file_name = ( f'scenario-player_{scenario_basename}_{datetime.now():%Y-%m-%dT%H:%M:%S}.log' ) click.secho(f'Writing log to {log_file_name}', fg='yellow') configure_logging( {'': 'INFO', 'raiden': 'DEBUG', 'scenario_player': 'DEBUG'}, debug_log_file_name=log_file_name, _first_party_packages=_FIRST_PARTY_PACKAGES | frozenset(['scenario_player']), ) log_buffer = None if sys.stdout.isatty() and not is_subcommand: log_buffer = UrwidLogWalker([]) for handler in logging.getLogger('').handlers: if isinstance(handler, logging.StreamHandler): handler.terminator = None handler.formatter = NonStringifyingProcessorFormatter( UrwidLogRenderer(), foreign_pre_chain=LOGGING_PROCESSORS, ) handler.stream = log_buffer break chain_rpc_urls = defaultdict(list) for chain_name, chain_rpc_url in chains: chain_rpc_urls[chain_name].append(chain_rpc_url) with open(keystore_file, 'r') as keystore: account = Account(json.load(keystore), password, keystore_file) log.info("Using account", account=to_checksum_address(account.address)) if is_subcommand: ctx.obj = dict( account=account, chain_rpc_urls=chain_rpc_urls, data_path=data_path, ) return # Collect tasks collect_tasks(tasks) runner = ScenarioRunner(account, chain_rpc_urls, auth, Path(data_path), scenario_file) ui = ScenarioUI(runner, log_buffer, log_file_name) ui_greenlet = ui.run() success = False try: try: runner.run_scenario() success = True log.info('Run finished', result='success') send_notification_mail( runner.notification_email, f'Scenario successful {scenario_file.name}', 'Success', mailgun_api_key, ) except ScenarioAssertionError as ex: log.error('Run finished', result='assertion errors') send_notification_mail( runner.notification_email, f'Assertion mismatch in {scenario_file.name}', str(ex), mailgun_api_key, ) except ScenarioError: log.exception('Run finished', result='scenario error') send_notification_mail( runner.notification_email, f'Invalid scenario {scenario_file.name}', traceback.format_exc(), mailgun_api_key, ) except Exception: log.exception('Exception while running scenario') send_notification_mail( runner.notification_email, f'Error running scenario {scenario_file.name}', traceback.format_exc(), mailgun_api_key, ) finally: try: if sys.stdout.isatty(): ui.set_success(success) log.warning('Press q to exit') while not ui_greenlet.dead: gevent.sleep(1) finally: if runner.is_managed: runner.node_controller.stop() if not ui_greenlet.dead: ui_greenlet.kill(ExitMainLoop) ui_greenlet.join()
def smoketest( ctx: Context, debug: bool, eth_client: EthClient, report_path: Optional[str] ) -> None: """ Test, that the raiden installation is sane. """ from raiden.tests.utils.smoketest import ( setup_raiden, run_smoketest, setup_matrix_for_smoketest, setup_testchain_for_smoketest, ) from raiden.tests.utils.transport import make_requests_insecure, ParsedURL step_count = 8 step = 0 stdout = sys.stdout raiden_stdout = StringIO() assert ctx.parent, MYPY_ANNOTATION environment_type = ctx.parent.params["environment_type"] transport = ctx.parent.params["transport"] disable_debug_logfile = ctx.parent.params["disable_debug_logfile"] matrix_server = ctx.parent.params["matrix_server"] if transport != "matrix": raise RuntimeError(f"Invalid transport type '{transport}'") if report_path is None: report_file = mktemp(suffix=".log") else: report_file = report_path make_requests_insecure() urllib3.disable_warnings(InsecureRequestWarning) click.secho(f"Report file: {report_file}", fg="yellow") configure_logging( logger_level_config={"": "DEBUG"}, log_file=report_file, disable_debug_logfile=disable_debug_logfile, ) def append_report(subject: str, data: Optional[AnyStr] = None) -> None: with open(report_file, "a", encoding="UTF-8") as handler: handler.write(f'{f" {subject.upper()} ":=^80}{os.linesep}') if data is not None: write_data: str if isinstance(data, bytes): write_data = data.decode() else: write_data = data handler.writelines([write_data + os.linesep]) append_report("Raiden version", json.dumps(get_system_spec())) append_report("Raiden log") def print_step(description: str, error: bool = False) -> None: nonlocal step step += 1 click.echo( "{} {}".format( click.style(f"[{step}/{step_count}]", fg="blue"), click.style(description, fg="green" if not error else "red"), ), file=stdout, ) contracts_version = RAIDEN_CONTRACT_VERSION try: free_port_generator = get_free_port() ethereum_nodes = None datadir = mkdtemp() testchain_manager: ContextManager[Dict[str, Any]] = setup_testchain_for_smoketest( eth_client=eth_client, print_step=print_step, free_port_generator=free_port_generator, base_datadir=datadir, base_logdir=datadir, ) matrix_manager: ContextManager[ List[Tuple[ParsedURL, HTTPExecutor]] ] = setup_matrix_for_smoketest( print_step=print_step, free_port_generator=free_port_generator, broadcast_rooms_aliases=[ make_room_alias(NETWORKNAME_TO_ID["smoketest"], DISCOVERY_DEFAULT_ROOM), make_room_alias(NETWORKNAME_TO_ID["smoketest"], PATH_FINDING_BROADCASTING_ROOM), ], ) # Do not redirect the stdout on a debug session, otherwise the REPL # will also be redirected if debug: stdout_manager = contextlib.nullcontext() else: stdout_manager = contextlib.redirect_stdout(raiden_stdout) with stdout_manager, testchain_manager as testchain, matrix_manager as server_urls: result = setup_raiden( transport=transport, matrix_server=matrix_server, print_step=print_step, contracts_version=contracts_version, eth_client=testchain["eth_client"], eth_rpc_endpoint=testchain["eth_rpc_endpoint"], web3=testchain["web3"], base_datadir=testchain["base_datadir"], keystore=testchain["keystore"], ) args = result["args"] contract_addresses = result["contract_addresses"] ethereum_nodes = testchain["node_executors"] token = result["token"] port = next(free_port_generator) args["api_address"] = f"localhost:{port}" args["environment_type"] = environment_type # Matrix server # TODO: do we need more than one here? first_server = server_urls[0] args["matrix_server"] = first_server[0] args["one_to_n_contract_address"] = "0x" + "1" * 40 args["routing_mode"] = RoutingMode.LOCAL args["flat_fee"] = () args["proportional_fee"] = () args["proportional_imbalance_fee"] = () for option_ in run.params: if option_.name in args.keys(): args[option_.name] = option_.process_value(ctx, args[option_.name]) else: args[option_.name] = option_.default try: run_smoketest( print_step=print_step, args=args, contract_addresses=contract_addresses, token=token, ) finally: if ethereum_nodes: for node_executor in ethereum_nodes: node = node_executor.process node.send_signal(signal.SIGINT) try: node.wait(10) except TimeoutExpired: print_step("Ethereum node shutdown unclean, check log!", error=True) node.kill() if isinstance(node_executor.stdio, tuple): logfile = node_executor.stdio[1] logfile.flush() logfile.seek(0) append_report("Ethereum Node log output", logfile.read()) append_report("Raiden Node stdout", raiden_stdout.getvalue()) except: # noqa pylint: disable=bare-except if debug: import pdb pdb.post_mortem() # pylint: disable=no-member error = traceback.format_exc() append_report("Smoketest execution error", error) print_step("Smoketest execution error", error=True) success = False else: print_step(f"Smoketest successful") success = True if not success: sys.exit(1)
def smoketest(ctx, debug, eth_client): """ Test, that the raiden installation is sane. """ from raiden.tests.utils.smoketest import setup_testchain_and_raiden, run_smoketest from raiden.tests.utils.transport import make_requests_insecure, matrix_server_starter report_file = mktemp(suffix=".log") configure_logging( logger_level_config={"": "DEBUG"}, log_file=report_file, disable_debug_logfile=ctx.parent.params["disable_debug_logfile"], ) free_port_generator = get_free_port() click.secho(f"Report file: {report_file}", fg="yellow") def append_report(subject: str, data: Optional[AnyStr] = None): with open(report_file, "a", encoding="UTF-8") as handler: handler.write(f'{f" {subject.upper()} ":=^80}{os.linesep}') if data is not None: write_data: str if isinstance(data, bytes): write_data = data.decode() else: write_data = data handler.writelines([write_data + os.linesep]) append_report("Raiden version", json.dumps(get_system_spec())) append_report("Raiden log") step_count = 7 if ctx.parent.params["transport"] == "matrix": step_count = 8 step = 0 stdout = sys.stdout def print_step(description: str, error: bool = False) -> None: nonlocal step step += 1 click.echo( "{} {}".format( click.style(f"[{step}/{step_count}]", fg="blue"), click.style(description, fg="green" if not error else "red"), ), file=stdout, ) print_step("Getting smoketest configuration") contracts_version = environment_type_to_contracts_version( ctx.parent.params["environment_type"]) with setup_testchain_and_raiden( transport=ctx.parent.params["transport"], eth_client=eth_client, matrix_server=ctx.parent.params["matrix_server"], contracts_version=contracts_version, print_step=print_step, free_port_generator=free_port_generator, ) as result: args = result["args"] contract_addresses = result["contract_addresses"] token = result["token"] ethereum_nodes = result["ethereum_nodes"] # Also respect environment type args["environment_type"] = ctx.parent.params["environment_type"] for option_ in run.params: if option_.name in args.keys(): args[option_.name] = option_.process_value( ctx, args[option_.name]) else: args[option_.name] = option_.default port = next(free_port_generator) args["api_address"] = "localhost:" + str(port) if args["transport"] == "udp": with SocketFactory("127.0.0.1", port, strategy="none") as mapped_socket: args["mapped_socket"] = mapped_socket success = run_smoketest( print_step=print_step, append_report=append_report, args=args, contract_addresses=contract_addresses, token=token, debug=debug, ethereum_nodes=ethereum_nodes, ) elif args["transport"] == "matrix": args["mapped_socket"] = None print_step("Starting Matrix transport") try: with matrix_server_starter( free_port_generator=free_port_generator ) as server_urls: # Disable TLS verification so we can connect to the self signed certificate make_requests_insecure() urllib3.disable_warnings(InsecureRequestWarning) args["extra_config"] = { "transport": { "matrix": { "available_servers": server_urls } } } success = run_smoketest( print_step=print_step, append_report=append_report, args=args, contract_addresses=contract_addresses, token=token, debug=debug, ethereum_nodes=ethereum_nodes, ) except (PermissionError, ProcessExitedWithError, FileNotFoundError): append_report("Matrix server start exception", traceback.format_exc()) print_step( f"Error during smoketest setup, report was written to {report_file}", error=True, ) success = False else: # Shouldn't happen raise RuntimeError(f"Invalid transport type '{args['transport']}'") if not success: sys.exit(1)
def smoketest(ctx, debug, local_matrix, **kwargs): # pylint: disable=unused-argument """ Test, that the raiden installation is sane. """ import binascii from web3 import Web3, HTTPProvider from web3.middleware import geth_poa_middleware from raiden.api.python import RaidenAPI from raiden.tests.utils.geth import geth_wait_and_check from raiden.tests.integration.contracts.fixtures.contracts import deploy_token from raiden.tests.utils.smoketest import ( TEST_PARTNER_ADDRESS, TEST_DEPOSIT_AMOUNT, deploy_smoketest_contracts, get_private_key, load_smoketest_config, start_ethereum, run_smoketests, ) report_file = tempfile.mktemp(suffix='.log') configure_logging({'': 'DEBUG'}, log_file=report_file) def append_report(subject, data): with open(report_file, 'a', encoding='UTF-8') as handler: handler.write(f'{f" {subject.upper()} ":=^80}{os.linesep}') if data is not None: if isinstance(data, bytes): data = data.decode() handler.writelines([data + os.linesep]) append_report('Raiden version', json.dumps(get_system_spec())) append_report('Raiden log', None) step_count = 7 if ctx.parent.params['transport'] == 'matrix': step_count = 8 step = 0 def print_step(description, error=False): nonlocal step step += 1 click.echo( '{} {}'.format( click.style(f'[{step}/{step_count}]', fg='blue'), click.style(description, fg='green' if not error else 'red'), ), ) print_step('Getting smoketest configuration') smoketest_config = load_smoketest_config() if not smoketest_config: append_report( 'Smoketest configuration', 'Could not load the smoketest genesis configuration file.', ) print_step('Starting Ethereum node') ethereum, ethereum_config = start_ethereum(smoketest_config['genesis']) port = ethereum_config['rpc'] web3_client = Web3(HTTPProvider(f'http://0.0.0.0:{port}')) web3_client.middleware_stack.inject(geth_poa_middleware, layer=0) random_marker = binascii.hexlify(b'raiden').decode() privatekeys = [] geth_wait_and_check(web3_client, privatekeys, random_marker) print_step('Deploying Raiden contracts') host = '0.0.0.0' client = JSONRPCClient( host, ethereum_config['rpc'], get_private_key(), web3=web3_client, ) contract_addresses = deploy_smoketest_contracts(client, 627) token_contract = deploy_token(client) token = token_contract(1000, 0, 'TKN', 'TKN') registry = TokenNetworkRegistry(client, contract_addresses[CONTRACT_TOKEN_NETWORK_REGISTRY]) registry.add_token(to_canonical_address(token.contract.address)) print_step('Setting up Raiden') # setup cli arguments for starting raiden args = dict( discovery_contract_address=to_checksum_address( contract_addresses[CONTRACT_ENDPOINT_REGISTRY], ), registry_contract_address=to_checksum_address( contract_addresses[CONTRACT_TOKEN_NETWORK_REGISTRY], ), secret_registry_contract_address=to_checksum_address( contract_addresses[CONTRACT_SECRET_REGISTRY], ), eth_rpc_endpoint='http://127.0.0.1:{}'.format(port), keystore_path=ethereum_config['keystore'], address=ethereum_config['address'], network_id='627', transport=ctx.parent.params['transport'], matrix_server='http://localhost:8008' if ctx.parent.params['matrix_server'] == 'auto' else ctx.parent.params['matrix_server'], ) smoketest_config['transport'] = args['transport'] for option_ in app.params: if option_.name in args.keys(): args[option_.name] = option_.process_value(ctx, args[option_.name]) else: args[option_.name] = option_.default password_file = os.path.join(args['keystore_path'], 'password') with open(password_file, 'w') as handler: handler.write('password') port = next(get_free_port('127.0.0.1', 5001)) args['password_file'] = click.File()(password_file) args['datadir'] = args['keystore_path'] args['api_address'] = 'localhost:' + str(port) args['sync_check'] = False def _run_smoketest(): print_step('Starting Raiden') # invoke the raiden app app_ = ctx.invoke(app, **args) raiden_api = RaidenAPI(app_.raiden) rest_api = RestAPI(raiden_api) api_server = APIServer(rest_api) (api_host, api_port) = split_endpoint(args['api_address']) api_server.start(api_host, api_port) raiden_api.channel_open( contract_addresses[CONTRACT_TOKEN_NETWORK_REGISTRY], to_canonical_address(token.contract.address), to_canonical_address(TEST_PARTNER_ADDRESS), None, None, ) raiden_api.set_total_channel_deposit( contract_addresses[CONTRACT_TOKEN_NETWORK_REGISTRY], to_canonical_address(token.contract.address), to_canonical_address(TEST_PARTNER_ADDRESS), TEST_DEPOSIT_AMOUNT, ) smoketest_config['contracts']['registry_address'] = to_checksum_address( contract_addresses[CONTRACT_TOKEN_NETWORK_REGISTRY], ) smoketest_config['contracts']['secret_registry_address'] = to_checksum_address( contract_addresses[CONTRACT_SECRET_REGISTRY], ) smoketest_config['contracts']['discovery_address'] = to_checksum_address( contract_addresses[CONTRACT_ENDPOINT_REGISTRY], ) smoketest_config['contracts']['token_address'] = to_checksum_address( token.contract.address, ) success = False try: print_step('Running smoketest') error = run_smoketests(app_.raiden, smoketest_config, debug=debug) if error is not None: append_report('Smoketest assertion error', error) else: success = True finally: app_.stop() ethereum.send_signal(2) err, out = ethereum.communicate() append_report('Ethereum init stdout', ethereum_config['init_log_out'].decode('utf-8')) append_report('Ethereum init stderr', ethereum_config['init_log_err'].decode('utf-8')) append_report('Ethereum stdout', out) append_report('Ethereum stderr', err) append_report('Smoketest configuration', json.dumps(smoketest_config)) if success: print_step(f'Smoketest successful, report was written to {report_file}') else: print_step(f'Smoketest had errors, report was written to {report_file}', error=True) return success if args['transport'] == 'udp': with SocketFactory('127.0.0.1', port, strategy='none') as mapped_socket: args['mapped_socket'] = mapped_socket success = _run_smoketest() elif args['transport'] == 'matrix' and local_matrix.lower() != 'none': args['mapped_socket'] = None print_step('Starting Matrix transport') try: with HTTPExecutor( local_matrix, status=r'^[24]\d\d$', url=urljoin(args['matrix_server'], '/_matrix/client/versions'), shell=True, ): args['extra_config'] = { 'matrix': { 'discovery_room': {'server': 'matrix.local.raiden'}, 'server_name': 'matrix.local.raiden', }, } success = _run_smoketest() except (PermissionError, ProcessExitedWithError): append_report('Matrix server start exception', traceback.format_exc()) print_step( f'Error during smoketest setup, report was written to {report_file}', error=True, ) success = False elif args['transport'] == 'matrix' and local_matrix.lower() == "none": args['mapped_socket'] = None success = _run_smoketest() else: # Shouldn't happen raise RuntimeError(f"Invalid transport type '{args['transport']}'") if not success: sys.exit(1)
def smoketest(ctx, debug, **kwargs): # pylint: disable=unused-argument """ Test, that the raiden installation is sane. """ from raiden.api.python import RaidenAPI from raiden.tests.utils.smoketest import ( TEST_PARTNER_ADDRESS, TEST_DEPOSIT_AMOUNT, run_smoketests, setup_testchain_and_raiden, ) report_file = mktemp(suffix='.log') configure_logging( logger_level_config={'': 'DEBUG'}, log_file=report_file, disable_debug_logfile=ctx.parent.params['disable_debug_logfile'], ) click.secho( f'Report file: {report_file}', fg='yellow', ) def append_report(subject, data): with open(report_file, 'a', encoding='UTF-8') as handler: handler.write(f'{f" {subject.upper()} ":=^80}{os.linesep}') if data is not None: if isinstance(data, bytes): data = data.decode() handler.writelines([data + os.linesep]) append_report('Raiden version', json.dumps(get_system_spec())) append_report('Raiden log', None) step_count = 7 if ctx.parent.params['transport'] == 'matrix': step_count = 8 step = 0 def print_step(description, error=False): nonlocal step step += 1 click.echo( '{} {}'.format( click.style(f'[{step}/{step_count}]', fg='blue'), click.style(description, fg='green' if not error else 'red'), ), ) print_step('Getting smoketest configuration') result = setup_testchain_and_raiden( ctx.parent.params['transport'], ctx.parent.params['matrix_server'], print_step, 'pre_limits', # smoke test should work with pre-limits contract version ) args = result['args'] contract_addresses = result['contract_addresses'] token = result['token'] ethereum = result['ethereum'] for option_ in run.params: if option_.name in args.keys(): args[option_.name] = option_.process_value(ctx, args[option_.name]) else: args[option_.name] = option_.default port = next(get_free_port('127.0.0.1', 5001)) args['api_address'] = 'localhost:' + str(port) def _run_smoketest(): print_step('Starting Raiden') config = deepcopy(App.DEFAULT_CONFIG) if args.get('extra_config', dict()): merge_dict(config, args['extra_config']) del args['extra_config'] args['config'] = config raiden_stdout = StringIO() with contextlib.redirect_stdout(raiden_stdout): try: # invoke the raiden app app = run_app(**args) raiden_api = RaidenAPI(app.raiden) rest_api = RestAPI(raiden_api) api_server = APIServer(rest_api) (api_host, api_port) = split_endpoint(args['api_address']) api_server.start(api_host, api_port) raiden_api.channel_open( registry_address=contract_addresses[CONTRACT_TOKEN_NETWORK_REGISTRY], token_address=to_canonical_address(token.contract.address), partner_address=to_canonical_address(TEST_PARTNER_ADDRESS), ) raiden_api.set_total_channel_deposit( contract_addresses[CONTRACT_TOKEN_NETWORK_REGISTRY], to_canonical_address(token.contract.address), to_canonical_address(TEST_PARTNER_ADDRESS), TEST_DEPOSIT_AMOUNT, ) token_addresses = [to_checksum_address(token.contract.address)] success = False print_step('Running smoketest') error = run_smoketests( app.raiden, args['transport'], token_addresses, contract_addresses[CONTRACT_ENDPOINT_REGISTRY], debug=debug, ) if error is not None: append_report('Smoketest assertion error', error) else: success = True finally: app.stop() app.raiden.get() node = ethereum[0] node.send_signal(2) err, out = node.communicate() append_report('Ethereum stdout', out) append_report('Ethereum stderr', err) append_report('Raiden Node stdout', raiden_stdout.getvalue()) if success: print_step(f'Smoketest successful') else: print_step(f'Smoketest had errors', error=True) return success if args['transport'] == 'udp': with SocketFactory('127.0.0.1', port, strategy='none') as mapped_socket: args['mapped_socket'] = mapped_socket success = _run_smoketest() elif args['transport'] == 'matrix': args['mapped_socket'] = None print_step('Starting Matrix transport') try: with matrix_server_starter() as server_urls: # Disable TLS verification so we can connect to the self signed certificate make_requests_insecure() urllib3.disable_warnings(InsecureRequestWarning) args['extra_config'] = { 'transport': { 'matrix': { 'available_servers': server_urls, }, }, } success = _run_smoketest() except (PermissionError, ProcessExitedWithError, FileNotFoundError): append_report('Matrix server start exception', traceback.format_exc()) print_step( f'Error during smoketest setup, report was written to {report_file}', error=True, ) success = False else: # Shouldn't happen raise RuntimeError(f"Invalid transport type '{args['transport']}'") if not success: sys.exit(1)
def run(ctx, **kwargs): # pylint: disable=too-many-locals,too-many-branches,too-many-statements if ctx.invoked_subcommand is not None: # Pass parsed args on to subcommands. ctx.obj = kwargs return click.secho('Welcome to Raiden, version {}!'.format(get_system_spec()['raiden']), fg='green') click.secho( ''' ---------------------------------------------------------------------- | This is an Alpha version of experimental open source software | | released under the MIT license and may contain errors and/or bugs. | | Use of the software is at your own risk and discretion. No | | guarantee whatsoever is made regarding its suitability for your | | intended purposes and its compliance with applicable law and | | regulations. It is up to the user to determine the software´s | | quality and suitability and whether its use is compliant with its | | respective regulatory regime, especially in the case that you are | | operating in a commercial context. | ----------------------------------------------------------------------''', fg='yellow', ) from raiden.ui.console import Console from raiden.api.python import RaidenAPI if kwargs['config_file']: paramname_to_param = {param.name: param for param in run.params} path_params = { param.name for param in run.params if isinstance(param.type, (click.Path, click.File)) } config_file_path = Path(kwargs['config_file']) config_file_values = dict() try: with config_file_path.open() as config_file: config_file_values = pytoml.load(config_file) except OSError as ex: # Silently ignore if 'file not found' and the config file path is the default config_file_param = paramname_to_param['config_file'] config_file_default_path = Path( config_file_param.type.expand_default(config_file_param.get_default(ctx), kwargs), ) default_config_missing = ( ex.errno == errno.ENOENT and config_file_path.resolve() == config_file_default_path.resolve() ) if default_config_missing: kwargs['config_file'] = None else: click.secho(f"Error opening config file: {ex}", fg='red') sys.exit(2) except TomlError as ex: click.secho(f'Error loading config file: {ex}', fg='red') sys.exit(2) for config_name, config_value in config_file_values.items(): config_name_int = config_name.replace('-', '_') if config_name_int not in paramname_to_param: click.secho( f"Unknown setting '{config_name}' found in config file - ignoring.", fg='yellow', ) continue if config_name_int in path_params: # Allow users to use `~` in paths in the config file config_value = os.path.expanduser(config_value) if config_name_int == LOG_CONFIG_OPTION_NAME: # Uppercase log level names config_value = {k: v.upper() for k, v in config_value.items()} else: # Pipe config file values through cli converter to ensure correct types # We exclude `log-config` because it already is a dict when loading from toml try: config_value = paramname_to_param[config_name_int].type.convert( config_value, paramname_to_param[config_name_int], ctx, ) except click.BadParameter as ex: click.secho(f"Invalid config file setting '{config_name}': {ex}", fg='red') sys.exit(2) # Use the config file value if the value from the command line is the default if kwargs[config_name_int] == paramname_to_param[config_name_int].get_default(ctx): kwargs[config_name_int] = config_value configure_logging( kwargs['log_config'], log_json=kwargs['log_json'], log_file=kwargs['log_file'], ) # Do this here so logging is configured if kwargs['config_file']: log.debug('Using config file', config_file=kwargs['config_file']) # TODO: # - Ask for confirmation to quit if there are any locked transfers that did # not timeout. def _run_app(): # this catches exceptions raised when waiting for the stalecheck to complete try: app_ = ctx.invoke(app, **kwargs) except EthNodeCommunicationError: print( '\n' 'Could not contact the ethereum node through JSON-RPC.\n' 'Please make sure that JSON-RPC is enabled for these interfaces:\n' '\n' ' eth_*, net_*, web3_*\n' '\n' 'geth: https://github.com/ethereum/go-ethereum/wiki/Management-APIs\n', ) sys.exit(1) domain_list = [] if kwargs['rpccorsdomain']: if ',' in kwargs['rpccorsdomain']: for domain in kwargs['rpccorsdomain'].split(','): domain_list.append(str(domain)) else: domain_list.append(str(kwargs['rpccorsdomain'])) api_server = None if ctx.params['rpc']: raiden_api = RaidenAPI(app_.raiden) rest_api = RestAPI(raiden_api) api_server = APIServer( rest_api, cors_domain_list=domain_list, web_ui=ctx.params['web_ui'], eth_rpc_endpoint=ctx.params['eth_rpc_endpoint'], ) (api_host, api_port) = split_endpoint(kwargs['api_address']) try: api_server.start(api_host, api_port) except APIServerPortInUseError: print( 'ERROR: API Address %s:%s is in use. ' 'Use --api-address <host:port> to specify port to listen on.' % (api_host, api_port), ) sys.exit(1) print( 'The Raiden API RPC server is now running at http://{}:{}/.\n\n' 'See the Raiden documentation for all available endpoints at\n' 'http://raiden-network.readthedocs.io/en/stable/rest_api.html'.format( api_host, api_port, ), ) if ctx.params['console']: console = Console(app_) console.start() # spawning a thread to handle the version checking gevent.spawn(check_version) # wait for interrupt event = gevent.event.Event() gevent.signal(signal.SIGQUIT, event.set) gevent.signal(signal.SIGTERM, event.set) gevent.signal(signal.SIGINT, event.set) try: event.wait() print('Signal received. Shutting down ...') except RaidenError as ex: click.secho(f'FATAL: {ex}', fg='red') except Exception as ex: with NamedTemporaryFile( 'w', prefix='raiden-exception', suffix='.txt', delete=False, ) as traceback_file: traceback.print_exc(file=traceback_file) click.secho( f'FATAL: An unexpected exception occured.' f'A traceback has been written to {traceback_file.name}\n' f'{ex}', fg='red', ) if api_server: api_server.stop() return app_ # TODO: # - Ask for confirmation to quit if there are any locked transfers that did # not timeout. try: if kwargs['transport'] == 'udp': (listen_host, listen_port) = split_endpoint(kwargs['listen_address']) try: with SocketFactory( listen_host, listen_port, strategy=kwargs['nat'], ) as mapped_socket: kwargs['mapped_socket'] = mapped_socket app_ = _run_app() except RaidenServicePortInUseError: print( 'ERROR: Address %s:%s is in use. ' 'Use --listen-address <host:port> to specify port to listen on.' % (listen_host, listen_port), ) sys.exit(1) elif kwargs['transport'] == 'matrix': kwargs['mapped_socket'] = None app_ = _run_app() else: # Shouldn't happen raise RuntimeError(f"Invalid transport type '{kwargs['transport']}'") app_.stop(leave_channels=False) except ReplacementTransactionUnderpriced as e: print( '{}. Please make sure that this Raiden node is the ' 'only user of the selected account'.format(str(e)), ) sys.exit(1)
def run(self): click.secho(self._welcome_string, fg='green') click.secho( textwrap.dedent( '''\ ---------------------------------------------------------------------- | This is an Alpha version of experimental open source software | | released under the MIT license and may contain errors and/or bugs. | | Use of the software is at your own risk and discretion. No | | guarantee whatsoever is made regarding its suitability for your | | intended purposes and its compliance with applicable law and | | regulations. It is up to the user to determine the software´s | | quality and suitability and whether its use is compliant with its | | respective regulatory regime, especially in the case that you are | | operating in a commercial context. | ----------------------------------------------------------------------''', ), fg='yellow', ) configure_logging( self._options['log_config'], log_json=self._options['log_json'], log_file=self._options['log_file'], disable_debug_logfile=self._options['disable_debug_logfile'], ) if self._options['config_file']: log.debug('Using config file', config_file=self._options['config_file']) # TODO: # - Ask for confirmation to quit if there are any locked transfers that did # not timeout. try: if self._options['transport'] == 'udp': (listen_host, listen_port) = split_endpoint(self._options['listen_address']) try: with SocketFactory( listen_host, listen_port, strategy=self._options['nat'], ) as mapped_socket: self._options['mapped_socket'] = mapped_socket app = self._run_app() except RaidenServicePortInUseError: print( 'ERROR: Address %s:%s is in use. ' 'Use --listen-address <host:port> to specify port to listen on.' % (listen_host, listen_port), ) sys.exit(1) elif self._options['transport'] == 'matrix': self._options['mapped_socket'] = None app = self._run_app() else: # Shouldn't happen raise RuntimeError( f"Invalid transport type '{self._options['transport']}'") app.stop(leave_channels=False) except ReplacementTransactionUnderpriced as e: print( '{}. Please make sure that this Raiden node is the ' 'only user of the selected account'.format(str(e)), ) sys.exit(1)
def smoketest(ctx, debug, local_matrix, **kwargs): # pylint: disable=unused-argument """ Test, that the raiden installation is sane. """ from raiden.api.python import RaidenAPI from raiden.tests.utils.smoketest import ( TEST_PARTNER_ADDRESS, TEST_DEPOSIT_AMOUNT, load_smoketest_config, run_smoketests, setup_testchain_and_raiden, ) report_file = tempfile.mktemp(suffix='.log') configure_logging({'': 'DEBUG'}, log_file=report_file) def append_report(subject, data): with open(report_file, 'a', encoding='UTF-8') as handler: handler.write(f'{f" {subject.upper()} ":=^80}{os.linesep}') if data is not None: if isinstance(data, bytes): data = data.decode() handler.writelines([data + os.linesep]) append_report('Raiden version', json.dumps(get_system_spec())) append_report('Raiden log', None) step_count = 7 if ctx.parent.params['transport'] == 'matrix': step_count = 8 step = 0 def print_step(description, error=False): nonlocal step step += 1 click.echo( '{} {}'.format( click.style(f'[{step}/{step_count}]', fg='blue'), click.style(description, fg='green' if not error else 'red'), ), ) print_step('Getting smoketest configuration') smoketest_config = load_smoketest_config() if not smoketest_config: append_report( 'Smoketest configuration', 'Could not load the smoketest genesis configuration file.', ) result = setup_testchain_and_raiden( smoketest_config, ctx.parent.params['transport'], ctx.parent.params['matrix_server'], print_step, ) args = result['args'] contract_addresses = result['contract_addresses'] token = result['token'] ethereum = result['ethereum'] ethereum_config = result['ethereum_config'] smoketest_config['transport'] = args['transport'] for option_ in run.params: if option_.name in args.keys(): args[option_.name] = option_.process_value(ctx, args[option_.name]) else: args[option_.name] = option_.default port = next(get_free_port('127.0.0.1', 5001)) args['api_address'] = 'localhost:' + str(port) def _run_smoketest(): print_step('Starting Raiden') # invoke the raiden app app = run_app(**args) raiden_api = RaidenAPI(app.raiden) rest_api = RestAPI(raiden_api) api_server = APIServer(rest_api) (api_host, api_port) = split_endpoint(args['api_address']) api_server.start(api_host, api_port) raiden_api.channel_open( contract_addresses[CONTRACT_TOKEN_NETWORK_REGISTRY], to_canonical_address(token.contract.address), to_canonical_address(TEST_PARTNER_ADDRESS), None, None, ) raiden_api.set_total_channel_deposit( contract_addresses[CONTRACT_TOKEN_NETWORK_REGISTRY], to_canonical_address(token.contract.address), to_canonical_address(TEST_PARTNER_ADDRESS), TEST_DEPOSIT_AMOUNT, ) smoketest_config['contracts'][ 'registry_address'] = to_checksum_address( contract_addresses[CONTRACT_TOKEN_NETWORK_REGISTRY], ) smoketest_config['contracts'][ 'secret_registry_address'] = to_checksum_address( contract_addresses[CONTRACT_SECRET_REGISTRY], ) smoketest_config['contracts'][ 'discovery_address'] = to_checksum_address( contract_addresses[CONTRACT_ENDPOINT_REGISTRY], ) smoketest_config['contracts']['token_address'] = to_checksum_address( token.contract.address, ) success = False try: print_step('Running smoketest') error = run_smoketests(app.raiden, smoketest_config, debug=debug) if error is not None: append_report('Smoketest assertion error', error) else: success = True finally: app.stop() ethereum.send_signal(2) err, out = ethereum.communicate() append_report('Ethereum init stdout', ethereum_config['init_log_out'].decode('utf-8')) append_report('Ethereum init stderr', ethereum_config['init_log_err'].decode('utf-8')) append_report('Ethereum stdout', out) append_report('Ethereum stderr', err) append_report('Smoketest configuration', json.dumps(smoketest_config)) if success: print_step( f'Smoketest successful, report was written to {report_file}') else: print_step( f'Smoketest had errors, report was written to {report_file}', error=True) return success if args['transport'] == 'udp': with SocketFactory('127.0.0.1', port, strategy='none') as mapped_socket: args['mapped_socket'] = mapped_socket success = _run_smoketest() elif args['transport'] == 'matrix' and local_matrix.lower() != 'none': args['mapped_socket'] = None print_step('Starting Matrix transport') try: with HTTPExecutor( local_matrix, url=urljoin(args['matrix_server'], '/_matrix/client/versions'), method='GET', timeout=30, shell=True, ): args['extra_config'] = { 'transport': { 'matrix': { 'discovery_room': { 'server': 'matrix.local.raiden' }, 'server_name': 'matrix.local.raiden', }, }, } success = _run_smoketest() except (PermissionError, ProcessExitedWithError): append_report('Matrix server start exception', traceback.format_exc()) print_step( f'Error during smoketest setup, report was written to {report_file}', error=True, ) success = False elif args['transport'] == 'matrix' and local_matrix.lower() == "none": args['mapped_socket'] = None success = _run_smoketest() else: # Shouldn't happen raise RuntimeError(f"Invalid transport type '{args['transport']}'") if not success: sys.exit(1)
def smoketest(ctx, debug, **kwargs): # pylint: disable=unused-argument """ Test, that the raiden installation is sane. """ from raiden.api.python import RaidenAPI from raiden.tests.utils.smoketest import ( TEST_PARTNER_ADDRESS, TEST_DEPOSIT_AMOUNT, run_smoketests, setup_testchain_and_raiden, ) report_file = mktemp(suffix='.log') configure_logging( logger_level_config={'': 'DEBUG'}, log_file=report_file, disable_debug_logfile=ctx.parent.params['disable_debug_logfile'], ) click.secho( f'Report file: {report_file}', fg='yellow', ) def append_report(subject, data): with open(report_file, 'a', encoding='UTF-8') as handler: handler.write(f'{f" {subject.upper()} ":=^80}{os.linesep}') if data is not None: if isinstance(data, bytes): data = data.decode() handler.writelines([data + os.linesep]) append_report('Raiden version', json.dumps(get_system_spec())) append_report('Raiden log', None) step_count = 7 if ctx.parent.params['transport'] == 'matrix': step_count = 8 step = 0 def print_step(description, error=False): nonlocal step step += 1 click.echo( '{} {}'.format( click.style(f'[{step}/{step_count}]', fg='blue'), click.style(description, fg='green' if not error else 'red'), ), ) print_step('Getting smoketest configuration') result = setup_testchain_and_raiden( ctx.parent.params['transport'], ctx.parent.params['matrix_server'], print_step, 'pre_limits', # smoke test should work with pre-limits contract version ) args = result['args'] contract_addresses = result['contract_addresses'] token = result['token'] ethereum = result['ethereum'] for option_ in run.params: if option_.name in args.keys(): args[option_.name] = option_.process_value(ctx, args[option_.name]) else: args[option_.name] = option_.default port = next(get_free_port('127.0.0.1', 5001)) args['api_address'] = 'localhost:' + str(port) def _run_smoketest(): print_step('Starting Raiden') config = deepcopy(App.DEFAULT_CONFIG) if args.get('extra_config', dict()): merge_dict(config, args['extra_config']) del args['extra_config'] args['config'] = config raiden_stdout = StringIO() with contextlib.redirect_stdout(raiden_stdout): try: # invoke the raiden app app = run_app(**args) raiden_api = RaidenAPI(app.raiden) rest_api = RestAPI(raiden_api) api_server = APIServer(rest_api) (api_host, api_port) = split_endpoint(args['api_address']) api_server.start(api_host, api_port) raiden_api.channel_open( registry_address=contract_addresses[ CONTRACT_TOKEN_NETWORK_REGISTRY], token_address=to_canonical_address(token.contract.address), partner_address=to_canonical_address(TEST_PARTNER_ADDRESS), ) raiden_api.set_total_channel_deposit( contract_addresses[CONTRACT_TOKEN_NETWORK_REGISTRY], to_canonical_address(token.contract.address), to_canonical_address(TEST_PARTNER_ADDRESS), TEST_DEPOSIT_AMOUNT, ) token_addresses = [to_checksum_address(token.contract.address)] success = False print_step('Running smoketest') error = run_smoketests( app.raiden, args['transport'], token_addresses, contract_addresses[CONTRACT_ENDPOINT_REGISTRY], debug=debug, ) if error is not None: append_report('Smoketest assertion error', error) else: success = True finally: app.stop() app.raiden.get() node = ethereum[0] node.send_signal(2) err, out = node.communicate() append_report('Ethereum stdout', out) append_report('Ethereum stderr', err) append_report('Raiden Node stdout', raiden_stdout.getvalue()) if success: print_step(f'Smoketest successful') else: print_step(f'Smoketest had errors', error=True) return success if args['transport'] == 'udp': with SocketFactory('127.0.0.1', port, strategy='none') as mapped_socket: args['mapped_socket'] = mapped_socket success = _run_smoketest() elif args['transport'] == 'matrix': args['mapped_socket'] = None print_step('Starting Matrix transport') try: with matrix_server_starter() as server_urls: # Disable TLS verification so we can connect to the self signed certificate make_requests_insecure() urllib3.disable_warnings(InsecureRequestWarning) args['extra_config'] = { 'transport': { 'matrix': { 'available_servers': server_urls, }, }, } success = _run_smoketest() except (PermissionError, ProcessExitedWithError, FileNotFoundError): append_report('Matrix server start exception', traceback.format_exc()) print_step( f'Error during smoketest setup, report was written to {report_file}', error=True, ) success = False else: # Shouldn't happen raise RuntimeError(f"Invalid transport type '{args['transport']}'") if not success: sys.exit(1)
def test_debug_logfile_invalid_dir(): """Test that providing an invalid directory for the debug logfile throws an error""" with pytest.raises(ConfigurationError): configure_logging({"": "DEBUG"}, debug_log_file_path=os.path.join( "notarealdir", "raiden-debug.log"))