如何在客户端不先使用 python 和 flask 请求的情况下通过 socket-io 发送数据
How can I send data though socket-io without the client requesting first with python and flask
我的目标是让我的 Flask 服务器每三秒或在调用函数时发送客户端数据。为此,我正在使用 SocketIO。但是,根据我正在使用的一些示例代码,似乎我只能在客户端请求后才能发送数据。我不希望客户端必须 'poll' 查找是否有新数据,所以我希望服务器在准备好时推送它。
这是我到目前为止尝试过的方法。 (一些代码是不必要的,因为它是基于一个例子)这应该使用 socketio 每隔几秒将时间推送到客户端。
HTML
<!DOCTYPE HTML>
<html>
<head>
<title>Socket-Test</title>
<script src="//code.jquery.com/jquery-1.12.4.min.js"></script>
<script src="//cdnjs.cloudflare.com/ajax/libs/socket.io/2.2.0/socket.io.js"></script>
<script type="text/javascript" charset="utf-8">
$(document).ready(function() {
namespace = '/test';
var socket = io(namespace);
socket.on('my_response', function(msg, cb) {
$('#log').text( $('<div/>').text(msg.data).html());
if (cb)
cb();
});
});
</script>
</head>
<body style="background-color:white;">
<h1 style="background-color:white;">Socket</h1>
<div id="time" ></div>
</body>
</html>
Python
import threading
from flask import Flask, render_template, session, copy_current_request_context,request
from flask_socketio import SocketIO, emit, disconnect
from threading import Lock
import time
async_mode = None
app = Flask(__name__)
app.config['SECRET_KEY'] = 'secret!'
socket_ = SocketIO(app, async_mode=async_mode)
thread = None
thread_lock = Lock()
clients = []
def update():
time.sleep(1)
emit('my_response',
{'data': time.time},
room=clients[0])
t=threading.Thread(target=update)
@socket_.on('connect')
def handle_connect():
print('Client connected')
clients.append(request.sid)
t.start()
@app.route('/')
def index():
return render_template('index.html', async_mode=socket_.async_mode)
@socket_.on('my_event', namespace='/test')
def test_message(message):
session['receive_count'] = session.get('receive_count', 0) + 1
emit('my_response',
{'data': message['data'], 'count': session['receive_count']})
@socket_.on('my_broadcast_event', namespace='/test')
def test_broadcast_message(message):
session['receive_count'] = session.get('receive_count', 0) + 1
emit('my_response',
{'data': time.time},
broadcast=True)
socket_.run(app,port=8050)
我尝试 运行 但它给我错误 RuntimeError: Working outside of request context.
我按照本教程修复了我的代码:https://www.shanelynn.ie/asynchronous-updates-to-a-webpage-with-flask-and-socket-io/
import threading
from flask import Flask, render_template, session, copy_current_request_context,request
from flask_socketio import SocketIO, emit, disconnect
from threading import Lock
import time
async_mode = None
app = Flask(__name__)
app.config['SECRET_KEY'] = 'secret!'
socket_ = SocketIO(app, async_mode=async_mode)
thread = None
thread_lock = Lock()
def update():
time.sleep(1)
socket_.emit('my_response',
{'data': time.time()},
namespace='/test')
print("emitted")
update()
t=threading.Thread(target=update)
@socket_.on('connect', namespace='/test')
def handle_connect():
print('Client connected')
if not t.isAlive():
t.start()
@app.route('/')
def index():
return render_template('index.html', async_mode=socket_.async_mode)
socket_.run(app,port=8070)
HTML
<!DOCTYPE HTML>
<html>
<head>
<title>Socket-Test</title>
<script src="//code.jquery.com/jquery-1.12.4.min.js"></script>
<script src="//cdnjs.cloudflare.com/ajax/libs/socket.io/2.2.0/socket.io.js"></script>
<script type="text/javascript" charset="utf-8">
$(document).ready(function() {
namespace = '/test';
var socket = io(namespace);
console.log(("test"));
socket.on('my_response', function(msg) {
$('#time').text( $('<div/>').text(msg.data).html());
console.log(msg);
});
});
</script>
</head>
<body style="background-color:white;">
<h1 style="background-color:white;">Socket</h1>
<div id="time" ></div>
</body>
</html>
我的目标是让我的 Flask 服务器每三秒或在调用函数时发送客户端数据。为此,我正在使用 SocketIO。但是,根据我正在使用的一些示例代码,似乎我只能在客户端请求后才能发送数据。我不希望客户端必须 'poll' 查找是否有新数据,所以我希望服务器在准备好时推送它。
这是我到目前为止尝试过的方法。 (一些代码是不必要的,因为它是基于一个例子)这应该使用 socketio 每隔几秒将时间推送到客户端。
HTML
<!DOCTYPE HTML>
<html>
<head>
<title>Socket-Test</title>
<script src="//code.jquery.com/jquery-1.12.4.min.js"></script>
<script src="//cdnjs.cloudflare.com/ajax/libs/socket.io/2.2.0/socket.io.js"></script>
<script type="text/javascript" charset="utf-8">
$(document).ready(function() {
namespace = '/test';
var socket = io(namespace);
socket.on('my_response', function(msg, cb) {
$('#log').text( $('<div/>').text(msg.data).html());
if (cb)
cb();
});
});
</script>
</head>
<body style="background-color:white;">
<h1 style="background-color:white;">Socket</h1>
<div id="time" ></div>
</body>
</html>
Python
import threading
from flask import Flask, render_template, session, copy_current_request_context,request
from flask_socketio import SocketIO, emit, disconnect
from threading import Lock
import time
async_mode = None
app = Flask(__name__)
app.config['SECRET_KEY'] = 'secret!'
socket_ = SocketIO(app, async_mode=async_mode)
thread = None
thread_lock = Lock()
clients = []
def update():
time.sleep(1)
emit('my_response',
{'data': time.time},
room=clients[0])
t=threading.Thread(target=update)
@socket_.on('connect')
def handle_connect():
print('Client connected')
clients.append(request.sid)
t.start()
@app.route('/')
def index():
return render_template('index.html', async_mode=socket_.async_mode)
@socket_.on('my_event', namespace='/test')
def test_message(message):
session['receive_count'] = session.get('receive_count', 0) + 1
emit('my_response',
{'data': message['data'], 'count': session['receive_count']})
@socket_.on('my_broadcast_event', namespace='/test')
def test_broadcast_message(message):
session['receive_count'] = session.get('receive_count', 0) + 1
emit('my_response',
{'data': time.time},
broadcast=True)
socket_.run(app,port=8050)
我尝试 运行 但它给我错误 RuntimeError: Working outside of request context.
我按照本教程修复了我的代码:https://www.shanelynn.ie/asynchronous-updates-to-a-webpage-with-flask-and-socket-io/
import threading
from flask import Flask, render_template, session, copy_current_request_context,request
from flask_socketio import SocketIO, emit, disconnect
from threading import Lock
import time
async_mode = None
app = Flask(__name__)
app.config['SECRET_KEY'] = 'secret!'
socket_ = SocketIO(app, async_mode=async_mode)
thread = None
thread_lock = Lock()
def update():
time.sleep(1)
socket_.emit('my_response',
{'data': time.time()},
namespace='/test')
print("emitted")
update()
t=threading.Thread(target=update)
@socket_.on('connect', namespace='/test')
def handle_connect():
print('Client connected')
if not t.isAlive():
t.start()
@app.route('/')
def index():
return render_template('index.html', async_mode=socket_.async_mode)
socket_.run(app,port=8070)
HTML
<!DOCTYPE HTML>
<html>
<head>
<title>Socket-Test</title>
<script src="//code.jquery.com/jquery-1.12.4.min.js"></script>
<script src="//cdnjs.cloudflare.com/ajax/libs/socket.io/2.2.0/socket.io.js"></script>
<script type="text/javascript" charset="utf-8">
$(document).ready(function() {
namespace = '/test';
var socket = io(namespace);
console.log(("test"));
socket.on('my_response', function(msg) {
$('#time').text( $('<div/>').text(msg.data).html());
console.log(msg);
});
});
</script>
</head>
<body style="background-color:white;">
<h1 style="background-color:white;">Socket</h1>
<div id="time" ></div>
</body>
</html>