zoukankan      html  css  js  c++  java
  • 在flask中使用websocket-实时消息推送

    - flask默认使用wsgi支持http协议,如需使用websocket需要安装gevent-websocket模块,http,websocket协议都可以支持

      Django应用:channel
      Tornado应用:自己有

     pip3 install gevent-websocket

    app.py

    from flask import Flask,request,render_template,redirect,session
    import uuid
    from geventwebsocket.handler import WebSocketHandler
    from gevent.pywsgi import WSGIServer
    import json
    
    
    app = Flask(__name__)
    app.secret_key = ';lkjnfdidiclsjek'
    
    GENTIEMAN = {
        '1':{'name':'钢弹','count':0},
        '2':{'name':'铁锤','count':0},
        '3':{'name':'闫帅','count':0},
    }
    
    WEBSOCKET_DICT = {}
    
    @app.before_request
    def before_reuqest():
        if request.path == '/login':
            return None
        user_info = session.get('user_info')
        if user_info:
            return None
        return redirect('login')
    
    @app.route('/login',methods=['GET','POST'])
    def login():
        if request.method == 'GET':
            return render_template('login.html')
        else:
            uid = str(uuid.uuid4())
            session['user_info'] = {'id':uid,'name':request.form.get('user')}
            return redirect('/index')
    
    
    @app.route('/index')
    def index():
        return render_template('index.html',users=GENTIEMAN)
    
    @app.route('/message')
    def message():
        # 1. 判断是否为Websocket请求,http不包含wsgi.websocket
        ws = request.environ.get('wsgi.websocket')
        if not ws:
            return 'use websocket'
        # 此处连接成功
        current_user_id = session['user_info']['id']
        WEBSOCKET_DICT[current_user_id] = ws
        while True:
            # 2. 等待用户发送消息,并接受
            message = ws.receive()  # 投票对应的ID
    
            # 关闭 mesaage = None
            if not message:
                del WEBSOCKET_DICT[current_user_id]
                break
    
            # 3. 获取用户要投票的ID,并+1
            old = GENTIEMAN[message]['count']
            new = old + 1
            GENTIEMAN[message]['count'] = new
    
            data = {'user_id':message,'count':new,'type':'vote'}
            # 给所有客户端推送消息
            for conn in WEBSOCKET_DICT.values():
                conn.send(json.dumps(data))
        return '完毕'
    
    @app.route('/notify')
    def notify():
        data = {'data':'订单生成','type':'alert'}
        for conn in WEBSOCKET_DICT.values():
            conn.send(json.dumps(data))
        return '完毕'
    
    if __name__ == '__main__':
        # 如果是http请求走app使用原有的wsgi处理,如果是websocket请求走WebSocketHandler处理
        http_server = WSGIServer(('127.0.0.1', 5000), app, handler_class=WebSocketHandler)
        http_server.serve_forever()

    index.html

    <body>
        <h1>投票系统:参与投票的人</h1>
        <ul>
            {% for k,v in users.items() %}
                <li id="user_{{k}}" ondblclick="vote('{{k}}')">{{v.name}} <span>{{v.count}}</span> </li>
            {% endfor %}
    
        </ul>
        <script src="{{ url_for('static',filename='jquery-3.3.1.min.js')}}"></script>
        <script>
            var socket = new WebSocket("ws://127.0.0.1:5000/message");
    
            socket.onmessage = function (event) {
                /* 服务器端向客户端发送数据时,自动执行 */
                var response = JSON.parse(event.data); // {'user':1,'count':new}
                if(response.type == 'vote'){
                    var nid = '#user_' + response.user_id;
                    $(nid).find('span').text(response.count)
                }else{
                    alert(response.data);
                }
    
            };
    
            /*
            我要给某人投票
             */
             function vote(id) {
                socket.send(id);
            }
    
        </script>
    </body>

    login.html

    <body>
    <form method="post">
        <input type="text" name="user">
        <input type="submit" value="提交">
    </form>
    </body>
  • 相关阅读:
    window.open 子窗口关闭刷新父页面
    window.open打开新窗口报错ie 位指明错误,原因是window没有加引号!
    ORA-22922: 不存在的 LOB 值 可以使用外层嵌套wm_concat()解决
    子窗口打开父窗口
    页面加载时触发事件
    json
    orcale 函数wm_concat不存咋lob值使用zh_concat 替换
    mongo常见错误
    mongo中插入数据,出现id重复
    cpu占用率
  • 原文地址:https://www.cnblogs.com/sunlong88/p/9623707.html
Copyright © 2011-2022 走看看