diff --git a/lib/nntp/tiny/server.py b/lib/nntp/tiny/server.py index 0b6a525..90d9e53 100644 --- a/lib/nntp/tiny/server.py +++ b/lib/nntp/tiny/server.py @@ -1,8 +1,11 @@ import enum +import socket +import threading from typing import Callable from nntp.tiny.newsgroup import Newsgroup +from nntp.tiny.session import Session class ServerCapability(enum.Flag): NONE = 0 @@ -22,3 +25,17 @@ class Server(): for newsgroup in db.query(Newsgroup).each(): self.newsgroups[newsgroup.name.casefold()] = newsgroup + + def run(self): + listener = socket.socket(socket.AF_INET, socket.SOCK_STREAM) + listener.bind(('localhost', 1190)) + listener.listen() + + while True: + sock, addr = listener.accept() + + session = Session(self, sock) + thread = threading.Thread(target=session.handle) + thread.start() + + listener.close() diff --git a/lib/nntp/tiny/session.py b/lib/nntp/tiny/session.py index 08bff91..3c40ea5 100644 --- a/lib/nntp/tiny/session.py +++ b/lib/nntp/tiny/session.py @@ -9,7 +9,6 @@ from typing import Optional from nntp.tiny.buffer import LineBuffer, BufferOverflow from nntp.tiny.db import Database -from nntp.tiny.server import Server, ServerCapability from nntp.tiny.response import Response, ResponseCode from nntp.tiny.newsgroup import Newsgroup from nntp.tiny.message import Message @@ -104,8 +103,8 @@ class Session(): RE_SPLIT = re.compile(r'\s+') - def __init__(self, server: Server, sock: socket.socket): - self.server: Server = server + def __init__(self, server, sock: socket.socket): + self.server = server self.db: Database = server.connect_to_db() self.sock: socket.socket = sock self.buf: LineBuffer = LineBuffer() @@ -739,7 +738,7 @@ class Session(): def greet(self): return self.respond(ResponseCode.NNTP_SERVICE_READY_POST_PROHIBITED) - def handle(self): + def handle_command(self): line = self.readline() if line == '': @@ -761,3 +760,11 @@ class Session(): except Exception as e: traceback.print_exception(e) return self.respond(ResponseCode.NNTP_COMMAND_UNAVAILABLE) + + def handle(self): + self.greet() + + while self.state & SessionState.ACTIVE: + self.handle_command() + + self.sock.close()