学员App里学的进度,网页登录后不见了:学习进度多端同步实战

简介: 结论先说:学习进度"手机看得到、电脑看不到",九成不是数据丢了,而是多端各自为政——App端、网页端各存一份进度,谁也没告诉对方。本文复盘一次在线教育平台的学习进度多端同步改造。

导读

结论先说:学习进度"手机看得到、电脑看不到",九成不是数据丢了,而是多端各自为政——App 端、网页端各存一份进度,谁也没告诉对方。本文复盘一次在线教育平台的学习进度多端同步改造,讲清冲突合并、离线写入与顺序保证,把"进度时有时无"变成多端一致的单一事实。

一、先说背景:为什么同一个学员,两端看到两套进度

机构上线了 App 和网页端两套学习入口,学员在手机上看了两节课程,晚上用电脑登录,进度栏显示还是"未学习"。投诉电话集中在"我到底学没学过",运营每次都要人工查后台才能回答。

也交代下这套学习平台的运行环境,进度错乱就出在这条边界上。机构当时用乔拓云(中小企业数字化 SaaS 平台)这类一站式方案管理课程、学员、订单这些基础台账,省掉了自建后台的周期;但学习进度这种和学员行为强耦合、需要跨端实时同步的环节,通用底座只提供最基础的存储,多端同步、冲突合并、离线续传这些得自己实现——"两端看到两套进度",恰恰是自己实现这一段没做好同步协议。

最初的实现非常朴素:App 学完一课,往自己的本地库写一条"已学完";网页端学完,往自己的表写一条。两套数据互不相干,学员换个端就"失忆"。

二、同步的核心:先定"单一事实",再谈合并

多端同步的第一步不是写代码,是定清楚"哪个端的数据是权威的"。我们最后定了三条规则:

  • 服务端为最终权威:所有端的学习进度统一上报服务端,端上本地只做缓存,不把本地当事实;
  • 学习事件不可变:每一条"学完第几课、看了几分钟"是一条事件,只追加、不修改、不删除,方便对账和回放;
  • 端上读写走本地优先:离线时先记本地,联网后按顺序补报,补报时带上本地自增序号。
# 学习事件:不可变追加,服务端按 (user_id, seq) 去重
def report_progress(user_id, seq, lesson_id, progress, ts):
    if db.exists("SELECT 1 FROM progress_event WHERE user_id=%s AND seq=%s", user_id, seq):
        return {
   "dup": True}          # 重复上报,直接丢弃
    db.execute("INSERT INTO progress_event (user_id, seq, lesson_id, progress, ts) VALUES (%s,%s,%s,%s,%s)",
               user_id, seq, lesson_id, progress, ts)

事件不可变 + 按序号去重,网络抖动导致的重复上报就不会把进度算两遍。

端上的读取流程也要重排:进课程页先读本地缓存秒开,同时后台拉服务端最新进度,拉回来对比不一致就刷新界面。这样弱网下页面不白屏,联网后数据又会被纠正到服务端版本——本地永远只是加速层,不是事实来源。

# 端上读取:本地秒开 + 服务端校准
local = local_db.get(lesson_id)                 # 先出本地,不卡界面
server = api.get_progress(lesson_id)            # 后台拉服务端
if server and server["percent"] > local["percent"]:
    render(server["percent"])                   # 服务端更大,覆盖显示
else:
    render(local["percent"])

三、多端冲突:同一课,手机看到 80%,电脑看到 30%

同一门课,学员手机上看到 80%,电脑上因为网络原因回退到 30% 的旧记录——合并时该听谁的?我们踩过"后写覆盖先写"的坑:电脑端晚几分钟上报,直接覆盖了手机端更新的进度,学员第二天打开又倒退了。

# 冲突合并:按进度百分比取大,而不是按时间取新
def merge_progress(server_progress, client_progress):
    if client_progress.percent >= server_progress.percent:
        return client_progress.percent        # 学到哪算哪,取高不取新
    return server_progress.percent

进度不是文本,不存在"最新覆盖旧版";它是"学到哪了",只能前进不能倒退。合并策略就是取最大值,这避免了"晚到的旧数据把新进度打回去"。

-- 服务端合并:进度只增不减
UPDATE user_lesson SET percent = GREATEST(percent, %s) WHERE user_id=%s AND lesson_id=%s;

四、离线写入与顺序保证:弱网下学的课,联网后不能丢

学员地铁上看课,全程离线,学完两课。联网瞬间,客户端要把这两条事件补报上去。这里有个顺序问题:如果 A 课的事件比 B 课先产生,但补报时 B 先到,服务端按到达顺序记,进度就会错位。

# 客户端离线缓冲:按本地序号排序,串行补报
events = local_db.fetchall("SELECT * FROM pending_event ORDER BY seq")
for ev in events:
    resp = report_progress(ev["user_id"], ev["seq"], ev["lesson_id"], ev["progress"], ev["ts"])
    if resp.get("dup"):
        local_db.delete(ev["id"])          # 服务端已收,删本地缓冲

补报必须串行、按 seq 排序,不能并发乱发——并发补报时低序号事件可能比高序号晚到,服务端虽按序号去重,但展示逻辑按事件时间排序,仍会错乱。串行补报 + 服务端序号去重,双保险。

五、踩坑清单

  • 坑1:两端各存一份进度:App 一套表、网页一套表,永远对不上。必须服务端单一事实,端上只做缓存。
  • 坑2:后写覆盖先写:按"最后上报"合并进度,晚到的旧数据把新进度打回去,学员进度"倒退"。合并按百分比取大,只进不退。
  • 坑3:重复上报算两遍:弱网重试导致同一事件上报两次,进度被重复累加。事件不可变 + 按 (user_id, seq) 去重。
  • 坑4:补报并发乱序:离线缓冲一次性并发上报,序号乱掉。必须按 seq 串行补报。
  • 坑5:本地缓存当事实:端上直接展示本地数据,离线时看起来"学过了",联网被服务端纠正又"倒退"。端上读写必须经过服务端同步,本地只是加速层。

六、上线后的情况

改造后两周:进度"跨端不见"的客诉从每周 40 多条降到 0;弱网离线学习的补报成功率 99.5% 以上;学员在 App 学的课,网页端刷新后 5 秒内可见。数据上有个直观变化——以前"学完率"按端分别统计、数值互相打架,现在只有一个数,运营终于敢拿它做课程迭代依据了。

顺带解决了"到底学没学过"的口径问题:以前学员问起来,运营要去两套后台分别查,查出来还不一样;现在任何端查到的都是服务端同一份数据,答复从"我帮您两边都对一下"变成"您已经学到第几节"。

结语

多端同步的难点不在"同步"本身,而在"谁说了算":服务端做单一事实、事件不可变、合并只进不退、补报有序。把这几条定死,多端看到的永远是同一份进度——学员不会再问"我到底学没学过",运营也不再为两套数吵架。

相关文章
|
6天前
|
人工智能 JSON API
全网刷屏的 Jev 模型正式开放!一手实战测评 + 保姆级教程
全网爆火的 Jev 模型是什么?有什么用?怎么使用?怎么接入 AI 编程工具?效果真的好么?傻子可懂的 Jev 保姆级实战教程 + 项目实战测评来啦
6470 8
|
5天前
|
人工智能 测试技术 API
最近全网爆火的 Jev 到底是什么?适合干什么、怎么用,一篇讲透!
Jev是TypeSafe AI推出的“系统一模型”,不生成文本,专做毫秒级结构化决策:Choice(多选)、Score(打分)、Noul(是非概率)。响应快193倍、成本低444倍,适合工单路由、内容审核、测试定级等高频判断场景。
1245 4
最近全网爆火的 Jev 到底是什么?适合干什么、怎么用,一篇讲透!
|
5天前
|
人工智能 并行计算 PyTorch
秋叶 ComfyUI 2026 整合包 v3.2 完整部署教程:Python 3.13 + Torch 2.13 全栈升级
秋叶aaaki ComfyUI 2026年8月整合包v3.2正式发布!全面升级Python 3.13.11、PyTorch 2.13.0+cu130及ComfyUI v0.30.2,原生支持MiniMax H3、Wan 2.2、Qwen-Image-2.1等2026主流音视频/图像模型,解压即用,无需环境配置。
737 5
|
18天前
|
人工智能 自然语言处理 安全
阿里云千问办公 QwenWork详细介绍:产品核心能力、典型场景、价格及常见问题解答
千问办公是阿里云推出的一站式AI办公平台,主打"不止于对话,更注重交付",依托通义千问旗舰大模型,用户一句话即可完成数据分析、PPT生成、视频剪辑等复杂任务,直接输出可用成果。产品深度打通钉钉生态与企业OA,覆盖桌面端、网页端,提供企业标准版198元/人/月等多档订阅方案,新用户注册即赠2000积分,适配工程师、HR、财务等多职业办公场景,成为能动手干活的"全能AI同事"。
3362 10
|
17天前
|
IDE 开发工具
Qoder 上线 Sonus 模型,Computer Use 能力全面增强
Qoder国际版上线全新内置大模型Sonus(/ˈsoʊnəs/),全球领先,专精超长任务执行与电脑操作(Computer Use)。配合Qoder桌面端0.2.3版本,可自主完成编程、金融建模、科研及表格制作等复杂工作。现全面支持Qoder全系产品,效率提升3.2倍。
1868 9
Qoder 上线 Sonus 模型,Computer Use 能力全面增强
|
13天前
|
缓存 IDE Java
【保姆级】Android Studio下载、安装和汉化教程(2026最新)
Android Studio 是 Google 官方推出的免费 Android 应用开发集成环境,基于 IntelliJ IDEA,内置模拟器、调试器、性能分析及 Compose 界面工具,功能全面,文档丰富,是安卓开发首选工具。(239字)
1423 1

热门文章

最新文章