基于Twisted的简单聊天室

本文介绍了一个使用Twisted框架实现的简单聊天服务器。该服务器支持私聊和公聊功能,并使用Redis存储用户名和密码。文中提供了完整的Python代码示例。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

实现了私聊,公聊。用户名密码存在redis。为了拓展,做了简单的模块。

#coding=utf8
from twisted.internet import reactor, defer
from twisted.protocols.basic import LineReceiver
from twisted.internet.protocol import Factory, Protocol, ServerFactory
import redis


class Server(ServerFactory):
        def __init__(self):
            self.users = {}
            self.last_messages = {}
            self.__db = dbServer
        #def start(self):

        #def stop(self):

        def do_login(self, pro, args):
            username, passwd = args
            if self.__db.get(username) is not None:
                if passwd != self.__db.get(username):
                    return "do_login", False, "login failed"
                else:
                    user = User(username, passwd, pro, 1)
                    self.users[username] = user
                    pro.user = user
                    return "do_login", True, "login success"
            else:
               self.__db.set(username, passwd)
               self.__db.save()
            user = User(username, passwd, pro, 1)
            self.users[username] = user
            pro.user = user
            return "do_login", True, "login success"

        def checklogin(self, user):
            return user.logined

        def do_privatemsg(self, pro, args):
            target, msg = args
            user = pro.user
            if self.checklogin(user):
                self.last_messages[user] = msg
                msg = '['+user.name+']' + msg
                return "do_privatemsg", self.users[target], msg

        def do_publicmsg(self, pro, args):
            msg = args
            user = pro.user
            print user.name
            if self.checklogin(user):
                self.last_messages[user] = msg
                msg = '['+user.name+']' + msg[0]
                return "do_publicmsg", self.users.values(), msg

class User(object):
        def __init__(self, name, passwd, pro, logined):
                self.name = name
                self.password = passwd
                self.nick_name = '&&' + name + '&&'
                self.proto = pro
                self.logined = logined

class ChatProtocol(LineReceiver):
        #line format: "func target_name *contents"
        #example: "privatemsg hs how are you....."
        #example: "publicmsg how are you....."
        #example: "login hs password"
        def __init__(self):
            self.user = 0
            self.pro = self

        def connectionMade(self):
            self.sendLine("please input: 'login,username,password'")

        def lineReceived(self, line):
            defer.maybeDeferred(self.parse, line).addCallback(self.processor).addCallback(self.ack)

        def parse(self, line):
            result = line.split(',')
            func = result[0]
            args = result[1:]
            return func, args

        def processor(self, args):
            func, arg = args
            _func = getattr(server, 'do_' + func)
            if _func:
                return _func(self.pro, arg)
            else:
                raise Exception("xxxxx")

        def ack(self, args):
            func, target, msg = args
            if func == 'do_login':
                if not target:
                   self.kickOut()
                self.sendLine(msg)
            elif func == 'do_privatemsg':
                target.proto.sendLine(msg)
            elif func == 'do_publicmsg':
                for user in target:
                    if user.proto != self:
                        user.proto.sendLine(msg)
            else:
                pass

        def kickOut(self):
            self.sendLine('passwd is wrong')
            self.transport.loseConnection()

class redisServer(object):
        def __init__(self):
            r = redis.Redis(host='localhost', port=6379, db=0)
            self.db = r
        def set(self, key, value):
            self.db.set(key, value)
        def save(self):
            self.db.save()
        def get(self, key):
            return self.db.get(key)


dbServer = redisServer()
server = Server()
server.protocol = ChatProtocol
reactor.listenTCP(8008,server)
print 'server start!'
reactor.run()

  

转载于:https://www.cnblogs.com/huangxiaohen/p/4236191.html

### 创建基于UDP协议的Python聊天室 为了实现一个简单的基于UDP协议的聊天室应用,可以利用Python中的`socket`库来处理网络通信。由于提到Twisted是一个事件驱动引擎,能够简化通过TCP、UDP等多种协议构建应用程序的过程[^3],这里提供一种不依赖于Twisted而直接使用标准库的方法。 下面展示了一个基本的例子,其中包括服务器端和客户端两部分代码: #### 服务端代码 ```python import socket def start_server(host='0.0.0.0', port=9999): udp_socket = socket.socket(socket.AF_INET, socket.SOCK_DGRAM) udp_socket.bind((host, port)) while True: data, addr = udp_socket.recvfrom(1024) # 缓冲区大小为1KB message = f"Received from {addr}: {data.decode('utf-8')}" print(message) if __name__ == '__main__': try: start_server() except KeyboardInterrupt: pass ``` 此段程序会监听指定地址与端口上的所有传入消息,并将其打印出来。注意这里的IP设置成了'0.0.0.0'意味着接受来自任何接口的消息;如果只想让本地计算机内的其他进程连接,则应改为'127.0.0.1'^[3]。 #### 客户端代码 ```python import socket def send_message(server_ip, server_port, msg): client_socket = socket.socket(socket.AF_INET, socket.SOCK_DGRAM) client_socket.sendto(msg.encode('utf-8'), (server_ip, server_port)) if __name__ == '__main__': import sys if len(sys.argv) != 4: print(f"Usage: python {sys.argv[0]} <server-ip> <server-port> '<message>'") exit(-1) _, ip, port_str, message = sys.argv port = int(port_str) send_message(ip, port, message) ``` 这段脚本允许用户向特定的服务端发送一条信息。运行时需提供三个参数:目标主机名/IP地址、端口号以及想要传输的内容字符串^[3]。 上述例子仅展示了最基础的功能框架,在实际开发过程中还需要考虑更多因素如错误处理机制、多线程支持以便同时接收多个用户的输入等特性。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值