diff --git a/NOTES b/NOTES new file mode 100644 index 0000000..5e1b484 --- /dev/null +++ b/NOTES @@ -0,0 +1,27 @@ +20190825 +======== + +# Redukti + +Components: +* State: Dictionary holding values of application state +* Action: A name and data pair that encode a change to the state +* Reducer: A function that takes a state and action to produce a new state +* Root reducer: Passes the state and action to all reducers + +# Derivide + +Components: +* Event: Destination, type of change occurring, old value, and new value +* Stream: A series of events +* Pool: Collection of resources for off main thread tasks +* Plugin: Takes events from stream, performs side effect, and returns result +* Schema: Set of rules describing the structure of data, used for validating +* Blob: Collection of data validated against schema(s) +* Database: The validated form of the blob from schema(s) + +# Taijitu + +Components: +* Dispatcher: Waits for new events and sends them to new reducers or listener +* Listener: Waits for new events and sends them to plugins or dispatcher diff --git a/event_loop.py b/event_loop.py new file mode 100644 index 0000000..823e71a --- /dev/null +++ b/event_loop.py @@ -0,0 +1,71 @@ +from gevent import Greenlet, spawn, sleep, joinall +from gevent.queue import Queue +from socket import socket, timeout as sock_timeout +from socket import AF_INET, SOCK_STREAM, SOL_SOCKET, SO_REUSEADDR +from ssl import wrap_socket + +queues = dict() +queues["hook"] = Queue() +queues["push"] = Queue() +queues["pull"] = Queue() + +def test(context, old_value, new_value): + status = old_value == new_value + return True, status + +def push(queues): + while all([queue for queue in queues]): + send = queues.get("push") + receive = queues.get("pull") + event = send.get() + assert isinstance(event, tuple), f"Expected tuple: {event}" + if len(event) == 2: + error, response = event + if error: + break + + elif len(event) == 4: + where, context, old_value, new_value = event + receive.put(event) + + return + +def pull(queues): + plugins = dict() + while all([queue for queue in queues]): + hook = queues.get("hook") + send = queues.get("push") + receive = queues.get("pull") + while not hook.empty(): + plugin = hook.get() + assert callable(plugin), f"Expected function: {plugin}" + plugins[plugin.__name__.lower()] = plugin + + event = receive.get() + assert isinstance(event, tuple), f"Expected tuple: {event}" + assert len(event) == 4, f"Invalid format: {event}" + where, context, old_value, new_value = event + + stop = False + for plugin_name, plugin in plugins.items(): + if plugin_name == where: + result = plugin(context, old_value, new_value) + assert isinstance(result, tuple), f"Expected tuple: {result}" + assert len(result) == 2, f"Invalid format: {result}" + send.put(result) + error, response = result + if error: + stop = True + break + + if stop: + break + + return + +queues["hook"].put(test) +queues["push"].put(("test", "change", None, True)) + +yin = spawn(push, queues) +yang = spawn(pull, queues) +start = lambda: joinall([yang, yin])