def main(channel_name: str, amqp_target: str, amqp_key: str, tx_versioner: TransactionVersioner, tx_queue: mp.Queue, properties: ModuleProcessProperties=None): if properties is not None: ModuleProcess.load_properties(properties, "txreceiver") logging.info(f"Channel TX Receiver start") tx_queue.cancel_join_thread() queue_name = conf.CHANNEL_TX_RECEIVER_QUEUE_NAME_FORMAT.format(channel_name=channel_name, amqp_key=amqp_key) service = ChannelTxReceiverInnerService(amqp_target, queue_name, conf.AMQP_USERNAME, conf.AMQP_PASSWORD, tx_versioner=tx_versioner, tx_queue=tx_queue) async def _stop_loop(): service.loop.stop() def _on_signal(signal_num): logging.error(f"Channel TX Receiver has been received signal({repr(signal_num)})") asyncio.run_coroutine_threadsafe(_stop_loop(), service.loop) service.loop.add_signal_handler(signal.SIGTERM, _on_signal, signal.SIGTERM) service.loop.add_signal_handler(signal.SIGINT, _on_signal, signal.SIGINT) service.serve(connection_attempts=conf.AMQP_CONNECTION_ATTEMPTS, retry_delay=conf.AMQP_RETRY_DELAY, exclusive=True) logging.info("ChannelTxReceiverInnerService: started") service.serve_all() service.loop.close() logging.info("ChannelTxReceiverInnerService: stopped")
def main(channel_name: str, amqp_target: str, amqp_key: str, peer_target: str, tx_versioner: TransactionVersioner, broadcast_queue: mp.Queue, properties: ModuleProcessProperties=None): if properties is not None: ModuleProcess.load_properties(properties, "txcreator") logging.info(f"Channel TX Creator start") broadcast_queue.cancel_join_thread() queue_name = conf.CHANNEL_TX_CREATOR_QUEUE_NAME_FORMAT.format(channel_name=channel_name, amqp_key=amqp_key) service = ChannelTxCreatorInnerService(broadcast_queue, amqp_target, queue_name, conf.AMQP_USERNAME, conf.AMQP_PASSWORD, channel_name=channel_name, peer_target=peer_target, tx_versioner=tx_versioner) def _on_signal(signal_num): logging.error(f"Channel TX Creator has been received signal({repr(signal_num)})") service.stop() service.loop.add_signal_handler(signal.SIGTERM, _on_signal, signal.SIGTERM) service.loop.add_signal_handler(signal.SIGINT, _on_signal, signal.SIGINT) service.serve(connection_attempts=conf.AMQP_CONNECTION_ATTEMPTS, retry_delay=conf.AMQP_RETRY_DELAY, exclusive=True) logging.info("ChannelTxCreatorInnerService: started") service.serve_all() service.cleanup() service.loop.close() logging.info("ChannelTxCreatorInnerService: stopped")
def __init__(self, channel: str, self_target: str = None): super().__init__() self.__channel = channel self.__self_target = self_target self.__process = ModuleProcess() self.__broadcast_queue = self.__process.Queue() self.__broadcast_queue.cancel_join_thread()
async def __handle_crash_sub_services(self, process: ModuleProcess): try: self.__sub_processes.remove(process) process.join() logging.critical(f"Channel sub process crash occurred. process={process}") async def _close(): if not self.__loop_for_sub_services.is_closed(): self._channel_service.close() asyncio.ensure_future(_close(), loop=self.__loop_for_sub_services) except ValueError: # Call this function by cleanup pass
def _main(broadcast_queue: mp.Queue, channel: str, self_target: str, properties: ModuleProcessProperties = None): if properties is not None: ModuleProcess.load_properties(properties, f"{channel}_broadcast") logging.info(f"BroadcastScheduler process({channel}) start") broadcast_queue.cancel_join_thread() broadcaster = _Broadcaster(channel, self_target) broadcaster.start() original_sigterm_handler = signal.getsignal(signal.SIGTERM) original_sigint_handler = signal.getsignal(signal.SIGINT) def _signal_handler(signal_num, frame): signal.signal(signal.SIGTERM, original_sigterm_handler) signal.signal(signal.SIGINT, original_sigint_handler) logging.error( f"BroadcastScheduler process({channel}) has been received signal({signal_num})" ) broadcast_queue.put((None, None)) broadcaster.stop() signal.signal(signal.SIGTERM, _signal_handler) signal.signal(signal.SIGINT, _signal_handler) while True: command, params = broadcast_queue.get() if not broadcaster.is_running or command is None: break broadcaster.handle_command(command, params) while not broadcast_queue.empty(): broadcast_queue.get() logging.info(f"BroadcastScheduler process({channel}) end")
class _BroadcastSchedulerMp(BroadcastScheduler): def __init__(self, channel: str, self_target: str = None): super().__init__() self.__channel = channel self.__self_target = self_target self.__process = ModuleProcess() self.__broadcast_queue = self.__process.Queue() self.__broadcast_queue.cancel_join_thread() @staticmethod def _main(broadcast_queue: mp.Queue, channel: str, self_target: str, properties: ModuleProcessProperties = None): if properties is not None: ModuleProcess.load_properties(properties, f"{channel}_broadcast") logging.info(f"BroadcastScheduler process({channel}) start") broadcast_queue.cancel_join_thread() broadcaster = _Broadcaster(channel, self_target) broadcaster.start() original_sigterm_handler = signal.getsignal(signal.SIGTERM) original_sigint_handler = signal.getsignal(signal.SIGINT) def _signal_handler(signal_num, frame): signal.signal(signal.SIGTERM, original_sigterm_handler) signal.signal(signal.SIGINT, original_sigint_handler) logging.error( f"BroadcastScheduler process({channel}) has been received signal({signal_num})" ) broadcast_queue.put((None, None)) broadcaster.stop() signal.signal(signal.SIGTERM, _signal_handler) signal.signal(signal.SIGINT, _signal_handler) while True: command, params = broadcast_queue.get() if not broadcaster.is_running or command is None: break broadcaster.handle_command(command, params) while not broadcast_queue.empty(): broadcast_queue.get() logging.info(f"BroadcastScheduler process({channel}) end") def start(self): def crash_callback_in_join_thread(process: ModuleProcess): os.kill(os.getpid(), signal.SIGTERM) args = (self.__broadcast_queue, self.__channel, self.__self_target) self.__process.start( target=_BroadcastSchedulerMp._main, args=args, crash_callback_in_join_thread=crash_callback_in_join_thread) def stop(self): logging.info(f"Terminate BroadcastScheduler process({self})") self.__process.terminate() def wait(self): self.__process.join() def _put_command(self, command, params, block=False, block_timeout=None): self.__broadcast_queue.put((command, params))