Commit cbb03722 authored by Emma's avatar Emma
Browse files

💡 cordy async.io

parent fe2dc3c4
from cordy import Cordy
from cordy import get_application
import config
from urls import url_map
from urls import url_map, ws_map
application = Cordy(config, url_map)
application = get_application(config, url_map, ws_map)
......@@ -3,24 +3,27 @@ from functools import reduce
from peewee import DatabaseProxy
from playhouse.postgres_ext import PostgresqlExtDatabase
from routes import Mapper
import socketio
from cordy.http import Request
from cordy.http.exceptions import HTTPException
from cordy.utils import import_string
class Cordy:
db = DatabaseProxy()
sio = socketio.Server(async_mode='gevent_uwsgi')
def __init__(self, config, mapper):
def __init__(self, config, mapper, ws_map=None):
self.config = config
self.mapper = Mapper()
self.mapper.extend(mapper)
if hasattr(self.config, 'DATABASE'):
self.db.initialize(PostgresqlExtDatabase(config.DATABASE['NAME']))
self.ws_map = ws_map if ws_map is not None else {}
def __call__(self, enviro, start):
from .utils import import_string
def _handle(enviro, start):
from .utils import import_string
......@@ -50,5 +53,29 @@ class Cordy:
resolved_middlewares = [import_string(m) for m in reversed(self.config.MIDDLEWARES)]
chained = reduce(lambda h, m: m(h), resolved_middlewares, _handle)
for path, controller in self.ws_map.items():
namespace = import_string(controller)
print(namespace, path)
self.sio.register_namespace(namespace(path))
chained = reduce(lambda h, m: m(h), resolved_middlewares, socketio.WSGIApp(self.sio, _handle, static_files={
'/public': './public',
}))
return chained(enviro, start)
def get_application(config, urls, ws_map={}):
cordy = Cordy(config, urls, ws_map)
return cordy
sio = socketio.Server(async_mode='gevent_uwsgi')
for path, controller in ws_map.items():
namespace = import_string(controller)
print(namespace, path)
sio.register_namespace(namespace(path))
return socketio.WSGIApp(sio, cordy, static_files={
'/public': './public',
})
import traceback
from geventwebsocket.protocols.base import BaseProtocol
from geventwebsocket.exceptions import WebSocketError
class Controller:
def __init__(self, request):
self.request = request
class WSController(Controller):
protocol_class = BaseProtocol
def set_ws(self, ws):
self.protocol = self.protocol_class(self)
self.ws = ws
def index(self, *args, **kwargs):
pass
def handle(self, **kwargs):
print('handling')
self.protocol.on_open()
while True:
try:
message = self.ws.receive()
except WebSocketError:
traceback.print_exc()
self.protocol.on_close()
break
except TypeError:
continue
self.protocol.on_message(message)
def on_open(self, *args, **kwargs):
print('Socket open', args, kwargs)
def on_close(self, *args, **kwargs):
print('Socket closed', args, kwargs)
def on_message(self, message, *args, **kwargs):
print(f'Received: {message}', args, kwargs)
@classmethod
def protocol_name(cls):
return cls.protocol_class.PROTOCOL_NAME
from socketio import Namespace
from cordy.base import Controller as CordyController
from cordy.crud.controllers import CRUDViewSet
from cordy.http.responses import HTMLResponse
......@@ -14,3 +16,16 @@ class Controller(CordyController):
class ToDoViewSet(CRUDViewSet):
Model = ToDo
class WSController(Namespace):
def on_connect(self, sid, environ):
print('Socket connected', sid, environ)
def on_disconnect(self, sid):
print('Disconnected', sid)
def on_brol(self, sid, data):
print('brol', sid, data)
self.emit('reply', {'much': 'machin'}) #, namespace='/ws/')
<html>
<head>
<script src="https://cdnjs.cloudflare.com/ajax/libs/socket.io/1.3.5/socket.io.min.js"></script>
</head>
<body>
<form id="the_form">
<input type="input" name="msg" id="msg"></input>
<input type="submit" value="➤"></input>
</form>
<script>
var socket = io('http://127.0.0.1:9090/ws/');
socket.on('connect', function(){console.log('connect!')});
socket.on('message', function(msg){console.log('message!', msg)});
socket.on('disconnect', function(){console.log('disconnect!')});
socket.on('reply', function(msg){console.log('reply!', msg)});
document.getElementById('the_form').onsubmit = function(e) {
let msg = document.getElementById('msg').value;
document.getElementById('msg').value = '';
// send it to the server
socket.emit('brol', msg);
return false
};
</script>
</body>
</html>
......@@ -11,3 +11,7 @@ url_map = [
Route('logout', '/auth/logout/', controller='cordy.auth.controllers.AuthController', action='logout',
conditions={'method': ['POST']}),
]
ws_map = {
'/ws/': 'myapp.WSController'
}
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment