使用Python的Tornado框架实现一个一对一聊天的程序


Posted in Python onApril 25, 2015

按思路来聊:

类似微信,点击用户可以进入一对一聊天页面;另有聊天框列表包含所有存在聊天记录的一对一聊天框,点击进入聊天页面。
【数据结构】

因为双方都有聊天记录,所以每一个聊天实际上得储存两份,设计的数据结构如下:

A :

user_a = {“id”:1,”name”:”A”}

B :

user_b = {“id”:2,”name”:”B”}

A的聊天记录:

chat_a = { “id”:1, “user”:1, “who”:2, “name”:”B”, “new”:0, msg:[]}

B的聊天记录:

chat_b = { “id”:2, “user”:2, “who”:1, “name”:”A”, “new”:0, msg:[]}

msg实际上是个list,结构如下:msg = { “user”:发送者id, “name”:发送者name, “date”:发送时间, “content”:消息内容 }
【业务逻辑】

当A点击好友列表中B的名字?>进入聊天框(根据双方id通过字段user、who找到对应chat_a,chat = coll.find_one({“user”:user_a[‘id'], “who”:user_b[‘id']});如果该chat不存在,则利用双方id创建chat_a)

发送消息(更新chat_a和chat_b,如果chat_b不存在则创建chat_b;如果chat_b不在线则更新chat_b[‘new'] = 1)

A删除聊天框(删除chat_a)
【记录客户端连接】

由于是多个一对一聊天,所以不能直接用教程里的set来记录连接。

最后的决定是用一个 dict,用双方用户id拼接的字符串作为key,用list存客户端连接。

...SocketHandler(...):

chats = dict()
...
def on_open(self):
  ...
  #通过双方id来生成一个独一无二的字符串
  min = user_a['id']
  max = user_b['id']
  if min >max:
    max = user_a['id']
    min = user_b['id']
  key = str(user_a['id'])+"_"+str(user_b['id'])
  #判断当前会话是否存在,存在则添加当前用户
  if key in chats:
    SocketHandler.chats[key].append(self)
  #不存在则创建会话,并将当前用户添加进去
  else
    SocketHandler.chats[key] = [self]

【发送消息】

从客户端调用send函数,在服务端on_message函数中接受参数后更新双方聊天记录。之后调用send_to_all(key, message)来更新聊天窗口。
【发通知/更新聊天窗口】

更新数据库里的聊天记录后还要在聊天窗口更新html,所以需要通知该会话的连接者。

根据我们记录连接者的方式,对应的通知函数如下:

def send_to_all(key,message):
  for user in SocketHandler.chats[key]:
    user.write_message(json.dumps(message))

【关闭连接】

根据我们记录连接者的方式,对应的关闭函数如下:

def on_close(self):
  ...
  #用on_open函数中的方法构造key
  if key in SocketHandler.chats:
    SocketHandler.chats[key].remove(self)#删除当前连接
    if len(SocketHandler.chats[key]) == 0:
      del SocketHandler.chats[key]#当会话无连接者则删除会话

经过上面的改造,就实现多个一对一聊天功能

Python 相关文章推荐
python自动安装pip
Apr 24 Python
Python selenium 三种等待方式详解(必会)
Sep 15 Python
python版学生管理系统
Jan 10 Python
Python实现的井字棋(Tic Tac Toe)游戏示例
Jan 31 Python
Django中Model的使用方法教程
Mar 07 Python
Python查找数组中数值和下标相等的元素示例【二分查找】
Feb 13 Python
Python使用线程来接收串口数据的示例
Jul 02 Python
python里运用私有属性和方法总结
Jul 08 Python
使用python socket分发大文件的实现方法
Jul 08 Python
django最快程序开发流程详解
Jul 19 Python
Python开发之基于模板匹配的信用卡数字识别功能
Jan 13 Python
Django项目uwsgi+Nginx保姆级部署教程实现
Apr 19 Python
使用Python发送邮件附件以定时备份MySQL的教程
Apr 25 #Python
安装Python的web.py框架并从hello world开始编程
Apr 25 #Python
用Python编写一个基于终端的实现翻译的脚本
Apr 24 #Python
Python的Bottle框架中获取制定cookie的教程
Apr 24 #Python
利用Python的装饰器解决Bottle框架中用户验证问题
Apr 24 #Python
在Python中使用mongoengine操作MongoDB教程
Apr 24 #Python
python使用arp欺骗伪造网关的方法
Apr 24 #Python
You might like
php db类库进行数据库操作
2009/03/19 PHP
PHP 图像尺寸调整代码
2010/05/26 PHP
浅析memcache启动以及telnet命令详解
2013/06/28 PHP
PHP中使用SimpleXML检查XML文件结构实例
2015/01/07 PHP
使用 laravel sms 构建短信验证码发送校验功能
2017/11/06 PHP
PHP基于DateTime类解决Unix时间戳与日期互转问题【针对1970年前及2038年后时间戳】
2018/06/13 PHP
理解JavaScript变量作用域更轻松
2009/10/25 Javascript
html向js方法传递参数具体实现
2013/08/08 Javascript
jQuery Validate 验证,校验规则写在控件中的具体实例
2014/02/27 Javascript
客户端验证用户名和密码的方法详解
2016/06/16 Javascript
jQuery获取this当前对象子元素对象的方法
2016/11/29 Javascript
对称加密与非对称加密优缺点详解
2017/02/06 Javascript
JS中解决谷歌浏览器记住密码输入框颜色改变功能
2017/02/13 Javascript
JS实现图片放大缩小的方法
2017/02/15 Javascript
Vuejs仿网易云音乐实现听歌及搜索功能
2017/03/30 Javascript
微信小程序实现缓存根据不同的id来进行设置和读取缓存
2017/06/12 Javascript
微信小程序使用Promise简化回调
2018/02/06 Javascript
JS实现DOM删除节点操作示例
2018/04/04 Javascript
vue 自定义指令自动获取文本框焦点的方法
2018/08/25 Javascript
Vue+Spring Boot简单用户登录(附Demo)
2020/11/12 Javascript
vue祖孙组件之间的数据传递案例
2020/12/07 Vue.js
[05:34]2014DOTA2国际邀请赛中国区预选赛精彩TOPPLAY第二弹
2014/06/25 DOTA
[01:35]2018完美盛典章节片——共竞
2018/12/17 DOTA
Python中使用logging模块代替print(logging简明指南)
2014/07/09 Python
python开发之基于thread线程搜索本地文件的方法
2015/11/11 Python
django框架中间件原理与用法详解
2019/12/10 Python
在tensorflow下利用plt画论文中loss,acc等曲线图实例
2020/06/15 Python
浅析Python中字符串的intern机制
2020/10/03 Python
Sephora丝芙兰马来西亚官方网站:国际化妆品购物
2018/03/15 全球购物
教育科学研究生自荐信
2013/10/09 职场文书
学生检讨书怎么写
2014/10/09 职场文书
毕业赠语大全
2015/06/23 职场文书
教你使用一行Python代码玩遍童年的小游戏
2021/08/23 Python
为Centos安装指定版本的Docker
2022/04/01 Servers
Python内置类型集合set和frozenset的使用详解
2022/04/26 Python
Nginx的gzip相关介绍
2022/05/11 Servers