web有哪些方式可以实时更新数据

在Web开发中,有几种方式可以实现数据的实时更新,以确保用户界面能够及时反映后端数据的变化。

以下是一些常用的实现实时数据更新的技术:

一. AJAX轮询(Polling)

轮询是一种通过定时发送HTTP请求到服务器来检查数据更新的方法。客户端每隔一定时间(如每5秒)发送一个请求到服务器,服务器响应当前的数据状态,客户端根据响应更新界面。这是最简单的实现实时更新的方法,但可能会导致服务器负载增加,因为请求是在固定间隔发送,无论数据是否真的发生变化。

二. 长轮询(Long Polling)

长轮询是轮询的一个变种,客户端发送请求到服务器后,服务器会保持连接打开,直到有数据更新时才响应请求。响应后,客户端立即再次发起请求,等待下一次更新。这减少了请求的次数,比传统轮询更有效率,但仍然会占用服务器资源。

三. Server-Sent Events(SSE)

Server-Sent Events是一种允许服务器主动向客户端发送新数据的技术。客户端创建一个到服务器的单向连接,服务器通过这个连接可以发送更新的数据。SSE适用于需要从服务器到客户端的单向数据流,如推送通知。SSE在客户端使用JavaScript的EventSource接口实现。

四. WebSocket

WebSocket提供了一个全双工的通信通道,允许数据在客户端和服务器之间双向实时传输。一旦WebSocket连接建立,服务器和客户端都可以随时发送数据,这使得WebSocket非常适合需要高频实时交互的应用,如在线游戏、聊天应用等。WebSocket协议比HTTP轻量,减少了开销和延迟。

五. GraphQL订阅

GraphQL是一种为API提供更灵活、高效数据查询的语言和运行时。GraphQL订阅支持通过WebSocket实现实时数据更新。客户端订阅特定的数据更新,当这些数据发生变化时,服务器会通过建立的WebSocket连接推送更新。

六. 使用第三方服务

还有一些第三方服务和库,如Firebase Realtime Database、Pusher、Socket.IO等,它们提供了构建实时Web应用的框架和API。这些服务通常封装了WebSocket或其他技术,简化了实时数据通信的实现。

选择合适的技术

选择哪种技术取决于应用的需求、预期的用户规模、服务器资源以及开发时间等因素。例如,对于需要高频更新和双向通信的应用,WebSocket可能是最佳选择;而对于更新频率较低的情况,SSE或长轮询可能更合适。

WebSocket与SSE具体区别: 高频更新使用sse好还是WebSocket

代码实现,使用 javascript,python

一. AJAX轮询(Polling)

javascript

<!DOCTYPE html>
<html lang="en">
<head><meta charset="UTF-8"><meta name="viewport" content="width=device-width, initial-scale=1.0"><title>AJAX Polling Example</title>
</head>
<body><h1>Current Time:</h1><p id="time"></p><script>function fetchCurrentTime() {fetch('/time').then(response => response.json()).then(data => {document.getElementById('time').innerText = data.time;}).catch(error => console.error('Error:', error));}// 轮询间隔设置为1000毫秒(1秒)setInterval(fetchCurrentTime, 1000);</script>
</body>
</html>

python

from flask import Flask, jsonify
import datetimeapp = Flask(__name__)@app.route('/time')
def get_current_time():return jsonify({'time': datetime.datetime.now().isoformat()})if __name__ == '__main__':app.run(debug=True)

二. 长轮询(Long Polling)

javascript

<script>function fetchCurrentTime() {fetch('/time').then(response => response.json()).then(data => {document.getElementById('time').innerText = data.time;fetchCurrentTime();  // 请求成功后,立即发起新的请求}).catch(error => {console.error('Error:', error);fetchCurrentTime();  // 请求失败后,立即发起新的请求});}// 初始化长轮询fetchCurrentTime();
</script>

python
在长轮询中,服务器端需要在有数据可发送时才响应请求。为了模拟这个过程,我们可以简单地使用time.sleep()来延迟响应,但请注意,这只是为了演示目的。在生产环境中,你应该使用更高级的方法(如使用消息队列)来处理长轮询。

from flask import Flask, jsonify
import datetime
import timeapp = Flask(__name__)@app.route('/time')
def get_current_time():# 模拟服务器等待数据的过程time.sleep(10)  # 假设等待10秒钟return jsonify({'time': datetime.datetime.now().isoformat()})if __name__ == '__main__':app.run(debug=True)

三. Server-Sent Events(SSE)

javascript
前端页面使用EventSource连接到/events路由。每当服务器发送新的时间数据时,onmessage回调函数就会更新页面上显示的时间。如果连接遇到错误,onerror回调会被触发。

<!DOCTYPE html>
<html lang="en">
<head><meta charset="UTF-8"><meta name="viewport" content="width=device-width, initial-scale=1.0"><title>SSE Example</title>
</head>
<body><h1>Current Time:</h1><p id="time"></p><script>if (!!window.EventSource) {var source = new EventSource('/events');source.onmessage = function(event) {document.getElementById('time').innerText = event.data;};source.onerror = function(error) {console.error("EventSource failed:", error);source.close(); // Depending on the needs, you might want to close the connection upon error.};} else {// 如果浏览器不支持EventSourceconsole.log("Your browser does not support EventSource.");}</script>
</body>
</html>

python
Flask需要发送一个特定格式的响应,以便浏览器可以将其识别为SSE。这通常通过响应头Content-Type: text/event-stream来实现。
这段代码创建了一个/events路由,当客户端请求这个路由时,服务器会无限期地每秒发送当前时间。generate_events函数是一个生成器,它产生SSE格式的数据。

from flask import Flask, Response
import datetime
import timeapp = Flask(__name__)def generate_events():while True:# 每秒生成一次时间数据time.sleep(1)yield f"data: {datetime.datetime.now().isoformat()}\n\n"@app.route('/events')
def sse_request():return Response(generate_events(), content_type='text/event-stream')if __name__ == '__main__':app.run(debug=True, threaded=True)

注意事项
浏览器兼容性:虽然现代浏览器普遍支持SSE,但在一些旧浏览器或特定环境下可能不可用。需要根据目标用户群体的浏览器使用情况做适当兼容性处理。
性能和资源:虽然SSE比轮询和长轮询更高效,但在高并发场景下仍可能对服务器资源造成压力。合理配置服务器和使用负载均衡等技术可以帮助缓解这些问题。
HTTP/2:在HTTP/2上使用SSE时,由于HTTP/2的多路复用特性,与HTTP/1.x相比,可以更高效地处理多个SSE连接。

四. WebSocket

使用WebSocket技术实现实时更新相较于SSE,可以提供全双工通信能力,这意味着服务器和客户端可以在同一连接上同时发送和接收消息。这对于需要高频更新或实时交互的应用非常有用。
javascript

<!DOCTYPE html>
<html lang="en">
<head><meta charset="UTF-8"><title>WebSocket Example</title><script src="https://cdn.socket.io/4.7.4/socket.io.js"></script><script type="text/javascript">document.addEventListener('DOMContentLoaded', function () {var socket = io('http://127.0.0.1/test', {path: '/a/socket.io'}); // 确保path与Nginx配置一致socket.on('connect', function() {console.log('Websocket connected!');});socket.on('message', function(data) {document.getElementById('time').textContent = data.time;});});</script>
</head>
<body><h1>Current Time:</h1><p id="time"></p>
</body>
</html>

当页面加载完成后,通过io.connect连接到WebSocket服务器。服务器发送的消息通过socket.on(‘message’, callback)来接收,并在页面上更新时间显示。
python
python默认监听socket.io路径下

from flask import Flask, render_template
from flask_socketio import SocketIO
from flask_socketio import Namespace, emit
import datetime
import time
from threading import Threadclass TestNamespace(Namespace):def on_connect(self):print('Client connected to /test')def on_disconnect(self):print('Client disconnected from /test')def on_my_event(self, data):print('received my_event: ' + str(data))emit('message', {'data': 'This is a message from the /test namespace'})app = Flask(__name__)
socketio = SocketIO(app)
# 在创建SocketIO实例之后注册这个命名空间
socketio.on_namespace(TestNamespace('/test'))def background_thread():"""Example of how to send server generated events to clients."""while True:time.sleep(1)timestamp = datetime.datetime.now().isoformat()socketio.emit('message', {'time': timestamp}, namespace='/test')#namespace='/' 发送默认路径 socket.io#socketio.emit('message', {'time': timestamp}, namespace='/')@app.route('/')
def index():return render_template('index.html')  # 假设你的HTML文件名为index.htmlif __name__ == '__main__':thread = Thread(target=background_thread)thread.daemon = Truethread.start()socketio.run(app, debug=True)

可能会存在跨域问题
配置python或者服务器nginx
python

socketio = SocketIO(App, cors_allowed_origins="*")

nginx

        location  /a {proxy_pass   http://127.0.0.1:xxxxx/;proxy_http_version 1.1;proxy_set_header Upgrade $http_upgrade; # 这些header是WebSocket协议所必需的proxy_set_header Connection "upgrade";proxy_set_header Host $host;proxy_set_header X-Real-IP $remote_addr; # 这些header对于记录真实客户端IP很有用proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;proxy_set_header X-Forwarded-Proto $scheme;proxy_redirect off;}

注意事项
WebSocket与HTTP/2:WebSocket协议与HTTP/2相比,提供了更复杂的控制和更低的延迟。它特别适用于需要快速、双向通信的应用。
安全性:在生产环境中使用WebSocket时,考虑使用WSS(WebSocket Secure)来保证数据传输的安全。
兼容性:虽然现代浏览器广泛支持WebSocket,但在某些网络环境下可能会受到限制。确保你的应用能够优雅地处理WebSocket不可用的情况。
使用WebSocket,你可以为用户创建一个高度交互式和响应式的Web应用,提供实时数据更新和通信。

五. GraphQL订阅

GraphQL订阅与WebSocket区别
GraphQL订阅和WebSocket都是用于实现实时通信的技术,但它们在概念上、使用场景和实现方式上有明显的区别。

WebSocket
WebSocket是一种网络通信协议,提供了建立持久连接的能力,使得客户端和服务器可以在任何时刻互相发送消息,这种连接是全双工的。WebSocket本身是传输层的协议,它不关心传输的内容是什么。因此,WebSocket非常灵活,可以用于各种各样的应用场景,从简单的消息推送到复杂的实时游戏。

全双工通信:客户端和服务器都可以随时发送数据。
持久连接:一旦WebSocket连接建立,它会保持开放状态直到客户端或服务器显式地关闭它。
内容无关:WebSocket不关心通过它传输的数据的内容,数据的格式和结构完全由应用层来定义。

GraphQL订阅
GraphQL订阅是GraphQL语言的一部分,用于实现客户端与服务器之间的实时通信。它允许客户端订阅特定事件,当这些事件发生时,服务器会将更新的数据推送给客户端。GraphQL订阅通常建立在WebSocket之上,使用WebSocket作为传输层来支持持续的结果集推送。

基于事件的通信:客户端订阅服务器上的特定事件,仅当这些事件发生时,服务器才会推送数据。
集成于GraphQL查询语言:订阅请求遵循GraphQL的查询语法,允许客户端指定它希望接收的数据的结构。
使用WebSocket作为传输层:虽然GraphQL订阅通常建立在WebSocket之上,但它专注于如何通过这个持久连接传输结构化的数据更新。

区别总结
使用场景:WebSocket更通用,适用于任何需要实时双向通信的应用。GraphQL订阅专注于数据订阅模型,适用于当数据发生变化时需要通知客户端的场景。
数据结构和格式:WebSocket不关心数据格式,而GraphQL订阅使用GraphQL查询语言来精确定义客户端期望接收的数据的形状和类型。
实现细节:WebSocket是一种底层的通信协议,而GraphQL订阅是一种在WebSocket(或其他传输层协议)之上实现的高级抽象。

javascript
此js需要vue框架

<!DOCTYPE html>
<html>
<head><title>GraphQL Subscription Example</title><script src="https://unpkg.com/@apollo/client"></script><script>document.addEventListener('DOMContentLoaded', function() {const client = new Apollo.ApolloClient({uri: 'YOUR_SERVER_URL/graphql',cache: new Apollo.InMemoryCache(),link: new Apollo.HttpLink({uri: 'YOUR_SERVER_URL/graphql',options: { reconnect: true }}),});client.subscribe({query: gql`subscription {currentTime}`,variables: {},}).subscribe({next(data) {console.log(data);document.getElementById('time').textContent = data.data.currentTime;},error(err) { console.error('Subscription error:', err); },});});</script>
</head>
<body><h1>Current Time:</h1><p id="time"></p>
</body>
</html>

python

from ariadne import gql, make_executable_schema, SubscriptionType, graphql
from ariadne.asgi import GraphQL
import asyncio
import datetime
import uvicorntype_defs = gql("""type Query {_: Boolean}type Subscription {currentTime: String!}
""")subscription = SubscriptionType()@subscription.source("currentTime")
async def generate_current_time(obj, info):while True:await asyncio.sleep(1)  # 每秒更新一次yield datetime.datetime.now().isoformat()@subscription.field("currentTime")
def resolve_current_time(time, info):return timeschema = make_executable_schema(type_defs, subscription)asgi_app = GraphQL(schema, debug=True)
if __name__ == '__main__':uvicorn.run(asgi_app, host="0.0.0.0", port=52020)

六. 使用第三方服务

javascript
python

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/788157.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

【2024最新】vue3的基本使用(超详细)

一、Vue 3 概述 1. 为什么要学习Vue 3 Vue 3是Vue.js的最新主要版本&#xff0c;它带来了许多改进和新特性&#xff0c;包括但不限于&#xff1a; 性能提升&#xff1a;Vue 3提供了更快的渲染速度和更低的内存使用率。Composition API&#xff1a;引入了一个新的API&#xf…

英伟达智算先锋训练,冲刺智算时代实战

随着数字经济的深入发展&#xff0c;智能算力作为关键生产力&#xff0c;其规模在2022年已达到268.0 EFLOPS&#xff0c;并预计到2028年将增长至2769 EFLOPS&#xff0c;显示出强劲的发展势头。在2024年政府工作报告中&#xff0c;也首次提出了“人工智能”行动&#xff0c;强调…

baseDao增删改查.

这里写目录标题 1、baseDao增删改查介绍2、basDao类3、BasDao类的作用 1、baseDao增删改查介绍 (1)、增加Create&#xff09;操作&#xff1a; 通过BaseDao的insert方法可以向数据库中插入一条新的记录。 该方法接受一个实体对象作参数&#xff0c;将该对象的属性映射到表的字…

Python轻量级框架Flask开发web应用(附源码自取)

目录 介绍 安装 简单初使用 新建项目目录 视图映射 无参映射 带参映射 ? 传参映射 连接mysql orm对象视图映射建表 ​编辑 crud操作 新增操作 查询操作 普通查询 查询返回json数据 前端传递json体数据查询 更新操作 删除操作 orm表关系映射 flask-migrate迁…

【Vue】vue3简介与环境配置

文章目录 项目编码规范什么是 Vue&#xff1f;安装node环境nvm针对node版本惊醒管理的工具 项目编码规范 组合式API Typescript setup(语法糖) 什么是 Vue&#xff1f; Vue 是一款用于构建用户界面的 JavaScript 框架。它基于标准 HTML、CSS 和 JavaScript 构建&#xff0c;…

JavaBean是什么?

Bean的本意为豌豆、子实&#xff0c;在这里引申为一种实体。JavaBean 是一种JAVA语言写成的可重用组件。为写成JavaBean&#xff0c;类必须是具体的和公共的&#xff0c;并且具有无参数的构造器。JavaBean 通过提供符合一致性设计模式的公共方法将内部域暴露成员属性&#xff0…

951. 翻转等价二叉树

跳转题目 判断两棵树是否为反转关系。 /*** Definition for a binary tree node.* struct TreeNode {* int val;* TreeNode *left;* TreeNode *right;* TreeNode() : val(0), left(nullptr), right(nullptr) {}* TreeNode(int x) : val(x), left(nullptr)…

操作系统高频面试知识总结 part1

操作系统 1.什么是操作系统&#xff1f;2.并发与并行&#xff1f;3.同步与异步&#xff1f;4.阻塞和非阻塞&#xff1f;5.什么是进程&#xff1f;6.什么是线程&#xff1f;7.进程与线程的区别&#xff1f;8.进程地址空间&#xff1f;9.进程常见状态&#xff1f;10.进程间通信&a…

Google人才选拔的独特视角

Google人才选拔的独特视角 独特的人才选拔标准 Google作为全球最大的搜索引擎公司&#xff0c;拥有无数优秀的人才。他们的选拔标准与众不同&#xff0c;有着自己独特的人才观。 重视多元化的背景 Google相信人才的多元化背景能够给公司带来不同的思考角度和创新思维。他们…

【总结】在嵌入式设备上可以离线运行的LLM--Llama

文章目录 Llama 简介运用另一种&#xff1a;MLC-LLM 一个令人沮丧的结论在资源受限的嵌入式设备上无法运行LLM&#xff08;大语言模型&#xff09;。 一丝曙光&#xff1a;tinyLlama-1.1b&#xff08;10亿参数&#xff0c;需要至少2.98GB的RAM&#xff09; Llama 简介 LLaMA…

Java language programming:作品评分系统

题目&#xff1a; 全国中小学生Scratch作品大赛拉开了序幕。每个参赛选手可以通过网络直接上传作品。本次比赛人人可做评委。每个网络评委可以通过网络对每一件作品进行打分。其自动去掉一个最高分和一个最低分&#xff0c;求出平均分。 输入格式: 输入数据包括两行: 第一行为…

电商技术揭秘四:电商平台的物流管理系统

文章目录 引言一、物流管理系统的功能与架构1.1 物流管理系统在电商平台中的作用概述保障订单的及时配送优化库存管理控制运营成本提升客户服务水平支持数据驱动的决策应对市场变化 1.2 订单处理功能分析自动化处理流程订单分配与履行错误检测与处理机制实时订单状态更新订单数…

ZKP价值链路的垂直整合

1. ZKP proof生命周期 从ZKP&#xff08;zero-knowledge proof&#xff09;生命周期&#xff0c;先看围绕ZKP的价值链路形成&#xff1a; 1&#xff09;User intent用户意图&#xff1a;以某用户意图为起点&#xff0c;如想要在某zk-rollup上swap某token、证明其身份、执行某…

【从零开始】自建高质量免费ip代理池(截止2024.4.1最新版)

文章目录 前言基础常识代理服务器状态码端口号 常见免费ip代理池网站实现思路代码实现main.pyutils.pydemo.py 结果如下 前言 为了防止ip被封后还能爬取网页&#xff0c;最常见的方法就是自己构建一个ip代理池。 本来用的是下面这个开源项目ip代理池&#xff0c; github开源项…

二维数字滤波器设计

Rafael C. Gonzalez “Digital Image Processing”的错误 按理说这本书的第三作者Steven是数字信号处理出身&#xff0c;他本人又对信号处理非常熟悉&#xff0c;不能理解为什么这本书的频域滤波器一章几乎没有对的地方。 对于巴特沃斯等模拟滤波器&#xff0c;利用全通带减去…

关于Qt的安装与版本更换

VS 2022 Qt 5.14.2配置记录_vs2022安装什么版本qt-CSDN博客

GPT 模型解析:ChatGPT 如何在语言处理领域引领潮流?

人工智能时代来临 我们正处于AI的iPhone时刻。——黄仁勋&#xff08;英伟达CEO&#xff09; ChatGPT 好得有点可怕了&#xff0c;我们距离危险的强人工智能不远了。——马斯克&#xff08;Tesla/SpaceX/Twitter CEO&#xff09; 以上的内容说明我们现在正处于一个技术大翻牌的…

就业班 第二阶段 2401--3.29 day9 shell之正则+数组

九、shell 编程-数组 普通数组:只能用整数作为数组的索引 关联数组:可以使用字符串作为数组的索引 数组定义 普通数组定义: [rootnewrain shell]# books( linux shell awk sed ) 引用: [rootnewrain shell]# echo ${books[0]} linux [rootnewrain shell]# echo ${books[1]…

大唐杯历届省赛押题训练(6)

考试-呼叫建立流程 一、单选题 1下面关于T-ADS被叫域选择下面说法正确的是( )1分/1分 A、被叫域选择是由MME发起的信令过程 B、T-ADS,过程是AS向3合1融合数据库查询T-ADS信息的过程 C、被叫域选择由主叫UE发起的域选择过程 D、主要是解决主叫驻留在那个网络的问题 提…

Avalonia笔记5-数据绑定

学习笔记&#xff1a; 1. 使用{Binding}标记拓展在XAML中进行绑定。通过绑定&#xff0c;所有数据上下文的变化都将自动更新到控件上。 <TextBlock Text"{Binding Name}"/> 2. 绑定模式 可以通过指定{Binding}的Mode来修改绑定的行为: OneWay 源的变化自动…