Use new event handling model

This commit is contained in:
Kristóf Tóth 2019-07-12 23:26:57 +02:00
parent eb60c1e08e
commit d9e69a6327
5 changed files with 59 additions and 93 deletions

View File

@ -5,11 +5,12 @@ from tornado.ioloop import IOLoop
from tornado.web import RequestHandler, Application from tornado.web import RequestHandler, Application
from tfw.builtins import FSMAwareEventHandler from tfw.builtins import FSMAwareEventHandler
from tfw.main import EventHandlerFactory
class ControllerPostHandler(RequestHandler): class ControllerPostHandler(RequestHandler):
# pylint: disable=abstract-method # pylint: disable=abstract-method,attribute-defined-outside-init,unused-argument
def initialize(self, **kwargs): # pylint: disable=arguments-differ def initialize(self, **kwargs):
self.controller = kwargs['controller'] self.controller = kwargs['controller']
def post(self, *args, **kwargs): def post(self, *args, **kwargs):
@ -26,6 +27,8 @@ class ControllerEventHandler(FSMAwareEventHandler):
if __name__ == '__main__': if __name__ == '__main__':
controller = ControllerEventHandler('controller') controller = ControllerEventHandler('controller')
controller_eh = EventHandlerFactory().build(controller)
application = Application([( application = Application([(
f'/{os.environ["SECRET"]}', f'/{os.environ["SECRET"]}',
ControllerPostHandler, ControllerPostHandler,

View File

@ -2,25 +2,25 @@ import logging
from ast import literal_eval from ast import literal_eval
from tfw.components import MessageSender from tfw.components import MessageSender
from tfw.builtins import TFWServerUplinkConnector from tfw.builtins import TerminalCommandsEventHandler
from tfw.builtins import EventHandler, FSMAwareEventHandler, TerminalCommandsEventHandler from tfw.main import TFWUplinkConnector
LOG = logging.getLogger(__name__) LOG = logging.getLogger(__name__)
class CenatorEventHandler(EventHandler): class CenatorEventHandler:
keys = ['history.bash']
# pylint: disable=no-self-use
""" """
Logs commands executed in terminal to messages and invokes an Logs commands executed in terminal to messages and invokes an
additional callback function to handle special commands. additional callback function to handle special commands.
!! Please remove from production code. !! !! Please remove from production code. !!
""" """
def __init__(self, key): def handle_event(self, message, server_connector):
super().__init__(key)
def handle_event(self, message):
command = message['value'] command = message['value']
LOG.debug('User executed command: "%s"', command) LOG.debug('User executed command: "%s"', command)
MessageSender(self.server_connector).send('JOHN CENA', f'You\'ve executed "{command}"') MessageSender(server_connector).send('JOHN CENA', f'You\'ve executed "{command}"')
class TestCommandsEventHandler(TerminalCommandsEventHandler): class TestCommandsEventHandler(TerminalCommandsEventHandler):
@ -40,7 +40,7 @@ class TestCommandsEventHandler(TerminalCommandsEventHandler):
""" """
if not args: if not args:
message_template = """'{"key": "", "data": {"command": ""}}'""" message_template = """'{"key": "", "data": {"command": ""}}'"""
TFWServerUplinkConnector().send_message({ TFWUplinkConnector().send_message({
'key': 'shell', 'key': 'shell',
'data': { 'data': {
'command': 'write', 'command': 'write',
@ -48,24 +48,22 @@ class TestCommandsEventHandler(TerminalCommandsEventHandler):
} }
}) })
else: else:
TFWServerUplinkConnector().send_message(literal_eval(args[0])) TFWUplinkConnector().send_message(literal_eval(args[0]))
class MessageFSMStepsEventHandler(FSMAwareEventHandler): class MessageFSMStepsEventHandler:
# pylint: disable=no-self-use
""" """
This example EventHandler is capable of detecting FSM state. This example EventHandler is capable of detecting FSM state.
!! Please remove from production code !! !! Please remove from production code !!
""" """
def handle_event(self, message): def handle_event(self, message, server_connector):
pass
def handle_fsm_step(self, **kwargs):
""" """
When the FSM steps this method is invoked. When the FSM steps this method is invoked.
Receives a 'data' field from an fsm_update message as kwargs. Receives a 'data' field from an fsm_update message as kwargs.
""" """
MessageSender(self.server_connector).send( MessageSender(server_connector).send(
'FSM info', 'FSM info',
f'FSM has stepped from state "{kwargs["last_event"]["from_state"]}" ' f'FSM has stepped from state "{message["last_event"]["from_state"]}" '
f'to state "{kwargs["current_state"]}" in response to trigger "{kwargs["last_event"]["trigger"]}"' f'to state "{message["current_state"]}" in response to trigger "{message["last_event"]["trigger"]}"'
) )

View File

@ -5,73 +5,87 @@ from functools import partial
from tornado.ioloop import IOLoop from tornado.ioloop import IOLoop
from tfw.fsm import YamlFSM from tfw.fsm import YamlFSM
from tfw.event_handlers import FSMAwareEventHandler
from tfw.builtins import IdeEventHandler, TerminalEventHandler, FrontendEventHandler from tfw.builtins import IdeEventHandler, TerminalEventHandler, FrontendEventHandler
from tfw.builtins import LogMonitoringEventHandler, ProcessManagingEventHandler from tfw.builtins import LogMonitoringEventHandler, ProcessManagingEventHandler
from tfw.builtins import DirectorySnapshottingEventHandler, FSMManagingEventHandler from tfw.builtins import DirectorySnapshottingEventHandler, FSMManagingEventHandler
from tfw.config import TFWENV from tfw.main import EventHandlerFactory, setup_signal_handlers
from tfw.logging import Log, Logger, LogFormatter, VerboseLogFormatter from tfw.logging import Log, Logger, LogFormatter, VerboseLogFormatter
from tfw.config import TFWENV
from tao.config import TAOENV from tao.config import TAOENV
from custom_event_handlers import MessageFSMStepsEventHandler from custom_event_handlers import MessageFSMStepsEventHandler
from custom_event_handlers import CenatorEventHandler, TestCommandsEventHandler from custom_event_handlers import CenatorEventHandler, TestCommandsEventHandler
from signal_handling import setup_signal_handlers
LOG = logging.getLogger(__name__) LOG = logging.getLogger(__name__)
def main(): def main():
# pylint: disable=unused-variable # pylint: disable=unused-variable,too-many-locals
Logger([ Logger([
Log(stderr, LogFormatter(20)), Log(stderr, LogFormatter(20)),
Log(TFWENV.LOGFILE, VerboseLogFormatter()) Log(TFWENV.LOGFILE, VerboseLogFormatter())
]).start() ]).start()
eh_factory = EventHandlerFactory()
# TFW component EventHandlers (builtins, required for their respective functionalities) # TFW component EventHandlers (builtins, required for their respective functionalities)
fsm = FSMManagingEventHandler( # TFW FSM fsm = FSMManagingEventHandler( # TFW FSM
key='fsm',
fsm_type=partial( fsm_type=partial(
YamlFSM, YamlFSM,
'test_fsm.yml', 'test_fsm.yml',
{} # jinja2 variables, use empty dict to enable jinja2 parsing without any variables {} # jinja2 variables, use empty dict to enable jinja2 parsing without any variables
) )
) )
fsm_eh = eh_factory.build(fsm)
ide = IdeEventHandler( # Web IDE backend ide = IdeEventHandler( # Web IDE backend
key='ide',
allowed_directories=[TFWENV.IDE_WD, TFWENV.WEBSERVICE_DIR], allowed_directories=[TFWENV.IDE_WD, TFWENV.WEBSERVICE_DIR],
directory=TFWENV.IDE_WD, directory=TFWENV.IDE_WD,
exclude=['*.pyc'] exclude=['*.pyc']
) )
terminal = TerminalEventHandler( # Web shell backend ide_eh = eh_factory.build(ide)
key='shell'
) terminal = TerminalEventHandler() # Web shell backend
cenator = CenatorEventHandler('history.bash') # Reacts to terminal commands terminal_eh = eh_factory.build(terminal)
commands = TestCommandsEventHandler( # Catches special commands
key='history.bash',
bashrc=f'/home/{TAOENV.USER}/.bashrc'
)
processmanager = ProcessManagingEventHandler( # Handles 'deploy' button clicks processmanager = ProcessManagingEventHandler( # Handles 'deploy' button clicks
key='processmanager',
log_tail=2000 log_tail=2000
) )
processmanager_eh = eh_factory.build(processmanager)
logmonitor = LogMonitoringEventHandler( # Sends live logs of webservice process to frontend logmonitor = LogMonitoringEventHandler( # Sends live logs of webservice process to frontend
key='logmonitor',
process_name='webservice', process_name='webservice',
log_tail=2000 log_tail=2000
) )
logmonitor_eh = eh_factory.build(logmonitor)
snapshot = DirectorySnapshottingEventHandler( # Manages filesystem snapshots of directories snapshot = DirectorySnapshottingEventHandler( # Manages filesystem snapshots of directories
key='snapshot',
directories=[ directories=[
TFWENV.IDE_WD, TFWENV.IDE_WD,
TFWENV.WEBSERVICE_DIR TFWENV.WEBSERVICE_DIR
] ]
) )
snapshot_eh = eh_factory.build(snapshot)
frontend = FrontendEventHandler() # Proxies frontend API calls to frontend frontend = FrontendEventHandler() # Proxies frontend API calls to frontend
frontend_eh = eh_factory.build(frontend)
# Your custom event handlers # Your custom event handlers
message_fsm_steps_eh = MessageFSMStepsEventHandler( cenator = CenatorEventHandler()
key='test' cenator_eh = eh_factory.build(cenator)
message_fsm_steps = MessageFSMStepsEventHandler()
message_fsm_steps_eh = eh_factory.build(
message_fsm_steps,
event_handler_type=FSMAwareEventHandler
) )
commands = TestCommandsEventHandler( # Catches special commands
bashrc=f'/home/{TAOENV.USER}/.bashrc'
)
commands_eh = eh_factory.build(commands)
setup_signal_handlers() setup_signal_handlers()
IOLoop.instance().start() IOLoop.instance().start()

View File

@ -6,14 +6,8 @@ from tornado.ioloop import IOLoop
from tfw.builtins import PipeIOEventHandler from tfw.builtins import PipeIOEventHandler
from tfw.config import TFWENV from tfw.config import TFWENV
from tfw.logging import Log, Logger, LogFormatter, VerboseLogFormatter from tfw.logging import Log, Logger, LogFormatter, VerboseLogFormatter
from tfw.main import EventHandlerFactory, setup_signal_handlers
from pipe_io_auxlib import (
SignMessagePipeIOEventHandler, VerifyMessagePipeIOEventHandler,
BotPipeIOEventHandler,
DeployPipeIOEventHandler, IdePipeIOEventHandler,
FSMPipeIOEventHandler
)
from signal_handling import setup_signal_handlers
LOG = logging.getLogger(__name__) LOG = logging.getLogger(__name__)
@ -25,46 +19,14 @@ def main():
Log(TFWENV.LOGFILE, VerboseLogFormatter()) Log(TFWENV.LOGFILE, VerboseLogFormatter())
]).start() ]).start()
eh_factory = EventHandlerFactory()
json_pipe = PipeIOEventHandler( json_pipe = PipeIOEventHandler(
'', '/tmp/tfw_send',
'/tmp/tfw_json_send', '/tmp/tfw_recv'
'/tmp/tfw_json_recv'
) )
json_pipe_eh = eh_factory.build(json_pipe)
sign_pipe = SignMessagePipeIOEventHandler(
'/tmp/tfw_sign_send',
'/tmp/tfw_sign_recv',
forwarding=True
)
verify_pipe = VerifyMessagePipeIOEventHandler(
'/tmp/tfw_verify_send',
'/tmp/tfw_verify_recv'
)
bot_pipe = BotPipeIOEventHandler(
'/tmp/tfw_bot_send',
'/tmp/tfw_bot_recv',
permissions=0o666
)
deploy_pipe = DeployPipeIOEventHandler(
'/tmp/tfw_deploy_send',
'/tmp/tfw_deploy_recv',
'webservice'
)
ide_pipe = IdePipeIOEventHandler(
'/tmp/tfw_ide_send',
'/tmp/tfw_ide_recv',
'user_ops.py',
selected=True
)
fsm_pipe = FSMPipeIOEventHandler(
'/tmp/tfw_fsm_send',
'/tmp/tfw_fsm_recv'
)
setup_signal_handlers() setup_signal_handlers()
IOLoop.instance().start() IOLoop.instance().start()

View File

@ -1,11 +0,0 @@
from signal import signal, SIGTERM, SIGINT
from tfw.builtins import EventHandler
def setup_signal_handlers():
def stop(*_):
EventHandler.stop_all_instances()
exit(0)
signal(SIGTERM, stop)
signal(SIGINT, stop)