周末帮朋友抢了两次音乐节门票,一次成功一次失败。失败的教训挺深刻的,小程序从“抢票中”变“已售罄”只用了三秒钟。回过头来反思,倒不是手速问题,是这个小程序本身缺少一套能扛住瞬时流量的系统设计,而且前端交互也有明显的延迟感。后来我自己从头写了一个基于Python和微信小程序的票务票据抢票系统,把核心链路认真梳理了一遍,这才搞清楚这类项目真正难的地方在哪。
这篇文章就把这套系统的完整设计思路、后端抢票核心逻辑、小程序端交互流程、以及我在实际开发和压测中踩过的坑做个详细拆解。项目本身麻雀虽小五脏俱全,涵盖了Python Web后端、Redis高并发处理、微信小程序前端、支付接口对接、异步任务处理等知识点,很适合用来做毕业设计、个人项目积累,或者直接改造成真实场景下的演出票务系统。
1. 整体架构与需求拆解:抢票系统的本质是处理“瞬时高并发”
1.1 票务系统的核心业务闭环
先搞清楚这个系统到底要做什么。票务票据抢票系统的核心业务链路其实非常清晰:用户浏览活动 → 选择票档 → 提交抢票请求 → 后端锁定库存 → 创建订单 → 支付 → 出票。听起来不复杂,但一旦参与的并发量上来,每一个环节都有可能变成瓶颈。
在需求分析阶段,我把它拆成了三个核心模块:活动与票档管理(维护演出场次、票价、库存)、用户与登录模块(微信授权登录、基本信息维护)、订单与支付模块(创建订单、超时关闭、支付回调、票据生成)。这三个模块各自独立,又通过订单表串联起来,一起支撑起整套票务系统的正常运转。
很多人拿到这类题目容易一上来就写代码,其实最该做的是先把数据模型设计清楚。我在动手写第一行代码之前,花了三个晚上把订单状态流转图在纸上画了好几遍,确认了待支付、已支付、已取消、已退款、已过期这五个状态。这一步看起来基础,实际上决定了后续所有接口设计和并发控制方案的选择。
1.2 技术选型:为什么是Python后端加原生小程序前端
后端选型上,我选择了Python的Flask框架。理由很简单:Flask足够轻量,一个项目文件就能跑通核心逻辑,特别适合快速迭代和个人项目管理。相比Django,Flask省去了很多自动化的数据库管理和后台配置,让你能更清楚地看到每一步请求处理发生了什么。对于学Python的人来说,调试和维护成本都低得多,代码量也能压缩在比较可控的范围。
如果项目要接真实支付并且有复杂的后台管理需求,换成Django确实更省事,自带的Admin后台能省掉很多CRUD代码。但就抢票这个场景而言,Flask加Redis的组合在性能和开发效率上更有优势。Flask的异步支持虽然没有FastAPI那么原生,但配合Celery或者简单的线程池,处理抢票这种短任务绰绰有余。
小程序端我用的是微信原生开发。有人说用uni-app能一套代码多端复用,但原生开发在调试工具链成熟度、组件稳定性、以及像微信支付这种深度耦合功能的兼容性上是最稳的。而且原生小程序的wxml代码更接近前端基本功,对理解整个请求链路更有帮助。如果你想把这个项目作为毕设,面试时候聊原生开发的底层原理,也会比聊跨端框架更显得扎实。
1.3 高并发场景下必须提前设计的三道防线
抢票系统区别于普通电商系统的核心在于瞬间请求量远大于库存量。同一场演唱会的热门票档,一千张票可能面对几十万用户的抢购。这时候如果每次请求都直接操作MySQL扣库存,数据库很快就会被读写锁拖垮。
我在系统设计阶段就确定了三道防线:接入层限流(拦截明显的恶意刷票和重复请求)、Redis缓存层(承担大部分库存预扣减和排队逻辑)、数据库最终一致性(只在库存预扣成功后写入订单数据)。这三层各司其职,把并发压力分散在系统的不同层面,而不是全部压在数据库这一根柱子上。
具体来说,抢票请求到达后端后,先经过一个简单的令牌桶限流器,控制每秒最大放行请求数;通过限流后进入Redis的原子扣减操作,这一步直接决定用户是“抢到了”还是“已售罄”;只有扣减成功才会进入数据库创建订单。这个链路的好处是,数据库的写入压力被严格控制在“确实有票”这个前提下,而不是让每次无效请求都穿透到MySQL。
需要模型API调用? 免费领10W Token,多模型网关一键接入 Claude、DeepSeek 等主流模型。
2. 核心数据库设计与后端API实现:订单状态机是灵魂
2.1 数据表结构:从活动到订单的四张核心表
数据库我用的是MySQL,这是最常见也最稳妥的搭配。项目主要维护了四张核心表,分别对应活动信息、票档库存、订单数据和用户数据。活动表存的是场地、时间、海报、介绍这些基础信息;票档表关联活动ID,字段包括票档名称、价格、总库存和初始库存;订单表是整个系统的核心,存了订单号、用户ID、票档ID、订单金额、状态以及创建和更新时间;用户表则比较简单,主要关联微信的openid和用户的昵称头像等展示信息。
用户表结构
sql复制CREATE TABLE user (
id INT AUTO_INCREMENT PRIMARY KEY,
openid VARCHAR(64) NOT NULL UNIQUE,
nickname VARCHAR(64),
avatar_url VARCHAR(255),
phone VARCHAR(20),
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP
);
订单表这里特别注意要把状态字段加上索引,因为整个系统对订单的查询主要是按用户和状态两个维度来操作的。订单号我采用的是时间戳加随机数的方案,格式是年月日时分秒加六位随机数,这样即使同一秒内有大量请求也不会撞号。为什么不用数据库自增ID做订单号?因为订单号不可避免会在微信支付回调、客服查询这些场景中直接暴露给用户,自增ID很容易被遍历,存在信息泄露的隐患。
2.2 后端API设计:六个核心接口串起完整链路
后端接口我按业务逻辑拆成了六个:活动列表接口(首页展示所有可抢活动)、活动详情接口(展示指定活动的票档和库存)、小程序登录接口(微信授权换openid)、抢票接口(核心高并发入口)、订单查询接口(查看用户自己订单状态)、支付回调接口(微信支付结果通知)。
活动列表和详情接口就是基础CRUD,没有太多技术含量,直接把数据库里的数据查出来转JSON返回给前端,注意加个Redis缓存避免频繁查库。用户登录接口是每次小程序启动时都会调用的,前端拿到用户授权码后传给后端,后端请求微信接口获取openid,然后去用户表查找或创建记录,最后签发一个自定义登录凭证返回给小程序端,后续所有业务请求都带上这个凭证,后端在请求处理时先校验凭证再执行业务逻辑。
抢票接口是整套系统的核心,下面单独开一节详细讲。订单查询接口需要注意区分用户权限,只能查到自己的订单,这里不用刻意做权限校验,因为查询条件本身就绑定了当前登录用户ID,别人伪造请求也没办法查询到你的订单数据。
2.3 登录态的维护:从wx.login到自定义凭证
微信小程序的登录机制和传统Web登录不同,它最大的特点是没有密码输入这个过程,而是依赖微信的授权体系。前端调用wx.login拿到一个临时code,这个code的有效期只有五分钟,而且只能用一次。前端把这个code传给后端,后端再拿着code去微信的接口换取openid和session_key。
出于安全考虑,openid是绝对不能下发到小程序端的。一旦别人拿到你的openid,虽然没有session_key也做不了太出格的事,但毕竟涉及用户隐私数据。所以我让后端在拿到openid后自己生成一个随机token,把token和用户ID的映射关系存在Redis里,设置合理的过期时间,客户端后续所有请求都带着这个token访问即可。这个方案实现简单,也支持用户在多个设备上登录,比传统的session方案更适合小程序这种场景。
3. 抢票核心逻辑详解:Redis Lua脚本与库存扣减的并发控制
3.1 为什么不能直接操作数据库库存
很多新手做抢票功能,第一版代码往往是这样写的:查询库存 → 判断库存大于零 → 库存减一 → 创建订单。这个逻辑在低并发下完全够用,数据库ACID里有行级锁保护,不会出现两个请求同时读到库存为1然后都扣减成功的问题。真正的问题在高并发时暴露出来:数据库连接池会被打满,大量请求排队等待行级锁释放,响应时间直线飙升,5000个并发请求能拖垮一台数据库实例。
解决思路是把“库存扣减”这个操作挪到Redis里面完成。Redis是单线程模型,所有指令都是原子执行的,不存在并发竞争的问题。更重要的是Redis是纯内存操作,单机轻松扛每秒十万级QPS,作为抢票的核心闸门再合适不过。数据库只在抢票成功后才落盘订单数据,写入压力骤然减小。
3.2 Lua脚本实现原子性扣减
不过Redis的decr命令虽然能保证原子性,但抢票的逻辑不止是库存减一这么简单。我们需要同时完成三件事:判断票档是否在活动开抢时间窗口内、检查库存是否大于零、库存扣减并返回扣减结果。这三个动作必须在一个原子操作内完成,否则就会在并发请求交替执行时产生超卖。
Redis官方推荐的做法是使用Lua脚本。Lua脚本在Redis里也是原子执行的,因为Redis服务器会阻塞其他客户端请求直到脚本执行完毕。我设计的Lua脚本逻辑如下:
lua复制local stock_key = KEYS[1]
local sold_key = KEYS[2]
local stock = tonumber(redis.call('get', stock_key) or '0')
local sold = tonumber(redis.call('get', sold_key) or '0')
if stock <= 0 then
return 0
end
if sold >= stock then
return 0
end
redis.call('decr', stock_key)
redis.call('incr', sold_key)
return 1
这个脚本里我用一個键记录剩余库存,另一个键记录已售数量,两个值加起来等于总库存。这个设计的巧妙之处在于,即使某些极端情况下异步任务需要手动修正库存,已售数量的存在也能让你知道卖出了多少张,方便对账。脚本返回1表示抢票成功,返回0表示库存不足或活动已结束。
3.3 抢票接口的完整请求链路
有了Redis Lua脚本做底层支撑,抢票接口的完整流程就清晰了。用户点击小程序端“立即抢票”按钮后,前端携带活动ID、票档ID和登录凭证发起请求。后端先做参数校验和登录态校验,然后检查当前时间是否在活动开抢时间到活动结束时间这个窗口内,接着调用Lua脚本执行库存扣减。
如果扣减失败,直接返回“非常抱歉,票已售罄”。如果扣减成功,说明用户获取了购买资格,但此时还没真正生成订单。接下来后端会向数据库插入一条状态为“待支付”的订单记录,订单号按前文说的时间戳加随机数生成。插入订单成功后,再把这个订单号放入一个延迟队列。延迟队列的作用是处理超时未支付的订单,我设置了十五分钟的支付时限,超过这个时间订单自动取消,同时回补库存。
成功走到这一步后后端会返回一个包含订单号的JSON给前端,前端再拿着这个订单号拉起微信支付组件完成付款。也就是说,我们的抢票逻辑只锁定了库存资格,真正的资金流转留到支付环节才发生。
3.4 定时任务回补库存防止“锁单不付款”
延迟队列的实现,我选择的是直接用MySQL加一个后台定时任务扫描。做法是给订单表加一个expire_time字段,创建订单时设置为当前时间加十五分钟,每隔一分钟执行一次定时任务,找出所有状态为“待支付”且expire_time小于当前时间的订单,把它们批量改成“已取消”状态,同时把对应的票数加回库存。
订单超时回补库存时存在一个并发风险:如果用户卡在支付页面迟迟不下单,刚好到了十五分钟,定时任务把订单取消了,但用户这时又发起支付,实际支付成功但订单状态是“已取消”。这种情况在支付回调处理时我会做特殊判断,如果支付回调时发现订单已经超时取消,就执行自动退款流程。这个边缘场景在真实的票务系统中并不少见,提前在代码里做好兜底非常必要。
4. 微信小程序端交互实现:从页面搭建到支付对接
4.1 小程序端的四个核心页面
小程序端我规划了四个核心页面:首页(活动列表)、活动详情页(含票档选择和立即抢票按钮)、订单列表页、订单详情页。微信小程序原生开发的基础是类似的页面结构,一个页面由四个文件组成:wxml负责页面结构,wxss负责样式,js负责逻辑和数据交互,json负责页面配置。
首页用wx.request向后端请求活动列表数据,用setData渲染到wxml的循环列表中。每个活动卡片展示活动海报、标题、时间以及票价范围内购票状态。活动详情页是整条链路上最关键的一页,上半部分展示活动信息,中间部分用单选组件的样式展示票档列表,包括票价和当前库存余量。
wx:key这个属性一定要绑定列表数据的唯一标识,比如活动ID。很多新手写循环列表时不设置wx:key,页面渲染时就会出现告警提示,在开发工具里不明显,但在真机上数据更新时可能出现渲染错乱。我建议所有列表渲染都养成绑定wx:key的习惯,这是一个特别基础但特别容易忽略的体验问题。
4.2 立即抢票按钮的交互状态管理
抢票按钮的交互是整个小程序端最容易做出“廉价感”的地方。很多不好的实现是用户点击按钮后就发起请求,请求过程中按钮不做任何状态变化,用户以为没点上去就又点了几次,结果产生重复请求,白白增加了后端压力。
我的方案是给按钮绑定一个抢票状态值:初始状态是“立即抢票”,点击后变为“抢票中…”并且禁用按钮。后端返回成功就跳转订单详情页做支付;返回售罄就弹窗提示并且把按钮文字改为“已售罄”;网络异常则恢复按钮文字为“立即抢票”。这个状态切换用一个小型的状态机来控制,避免了用户快速连点时产生多个抢票请求的情况。
另外按钮的倒计时逻辑也要处理好。活动没开始前,按钮应该显示“距开始:XX:XX”,每秒用setInterval递减,时间到后自动切换为“立即抢票”并开放点击。如果用户打开页面时活动已经开抢,直接显示“立即抢票”按钮。这个倒计时逻辑看似简单,真正做的时候要注意清理定时器,防止页面退出后定时器还在跑,这一点在分享或者跳转页面时很容易踩坑。
4.3 微信支付V3的对接要点
小程序端的支付交互分为两段:后端负责生成预支付交易单并返回支付参数,前端负责调用微信支付组件拉起收银台。这里涉及微信支付商户号、小程序AppID、APIv3密钥、证书序列号等一大堆配置,任何一个不一致都会导致支付流程中断。
后端生成预支付交易单需要调用微信支付的统一下单接口,签名方式是商户私钥对请求参数的SHA256-RSA2048签名。这个签名算法对新手来说比较难调试,建议项目初期先用官方SDK,跑通流程后再尝试自己实现签名。我自己最终也没有自己写完整的签名逻辑,而是直接用了wechatpayv3这个Python库,它能正确完成签名和验签,省下了很多调试时间。
小程序前端拉起支付用的是wx.requestPayment接口,需要传入后端返回的timeStamp、nonceStr、package、signType和paySign五个参数。这五个参数中paySign是后端用商户私钥二次签名的结果,所以小程序端不能自己生成支付参数,必须严格依赖后端返回的数据。前端在收到支付成功回调后就跳转订单详情页展示票据信息,同时向后端轮询一次订单状态,确认订单已经从“待支付”变成“已支付”状态。
4.4 订单查询与票据信息的展示
订单列表页面通过用户的登录凭证查询订单数据,按时间倒序排列,每条订单显示活动名称、票档名称、购买数量、订单状态按钮。不同状态下按钮文字不一样,“待支付”显示去支付,“已支付”显示查看票据,“已取消”显示灰色文案。支付成功后的票据信息我采用的展示方式是动态生成一个含订单号、活动信息、入场二维码的页面。
二维码部分没有调用后端服务生成图片,而是直接用了微信小程序自带的canvas组件绘制。wx.createCanvasContext在小程序里处理起来有些繁琐,特别是二维码内容比较长时需要自动调节二维码大小。实际项目中,如果想省事可以直接将二维码内容生成图片返回给前端,但考虑到生成图片本身就有额外的服务器开销,我最终在小程序端用weapp-qrcode这个封装好的库来生成。注意二维码内容需要包含一个明细编码而不是明文订单号,这样即使用户截图分享给朋友,朋友也没办法直接扫出真实订单数据。
5. 部署环境配置与常见问题排查
5.1 Python环境安装与项目依赖管理
项目开发第一步是搭建Python环境。官网下载Python安装包时一定要勾选Add Python to PATH,这一步漏掉的话命令行里输python会提示不是内部或外部命令。安装完成后建议顺手更新一下pip镜像源,国内环境直接拉取官方源经常超时,换成清华的镜像源速度会快很多。
虚拟环境是Python项目管理的标配,我用venv创建独立环境,然后通过pip install把Flask、redis、pymysql、requests这些依赖装进去。等到所有依赖都确定没问题后,再用pip freeze生成requirements.txt文件,这样整个项目在任何一台机器上都能用pip install -r requirements.txt一键恢复环境。这个习惯在项目迭代中节省了大量时间,特别是换电脑或者和同学协作时特别有用。
5.2 Redis与MySQL的前置准备
Redis在Windows和Linux上的安装方式差别比较大。Windows上没有官方版本,通常使用tporadowski维护的Windows移植版,或者用WSL跑Linux版。如果只是本地开发调试,Redis不再需要太多配置,默认端口6379启动即可。生产环境就建议设置密码并用systemd管理启动,同时配置maxmemory限制和持久化策略,防止内存溢出,数据也不会因为重启就全部丢光。
MySQL方面,建库时注意字符集选utf8mb4而不是utf8,因为utf8在MySQL里最多只能存三字节的字符,而用户昵称里如果包含emoji表情字符会直接报错。数据库连接池的配置也要合理一些,连接数上限和等待超时时间都要考虑到抢票峰值时数据库的承受能力。我之前默认配置过小的连接池,压测时出现了大量连接拒绝的错误,排查了半天才定位到是连接池不够用。
5.3 微信开发者工具与真机调试注意事项
小程序开发过程中,微信开发者工具和真机表现存在不少差异。最典型的是域名校验问题。开发工具里可以勾选“不校验合法域名”,但目前版本的这个选项已经调整到“详情-本地设置”里,很多新手找不到。真机调试时不配置合法域名会直接无法请求后端接口,所以如果你的后端只跑在本地,需要借助内网穿透工具把局域网服务映射成一个可以公网访问的HTTPS域名,然后在小程序后台配置到request合法域名列表里。
开发过程中还有一个高频问题是顶部导航栏高度不一致。不同iPhone机型的刘海屏会导致导航栏高度不同,小程序提供了胶囊按钮的位置查询接口,可以通过wx.getMenuButtonBoundingClientRect获取胶囊按钮位置,再结合系统信息动态计算导航栏高度。我的做法是封装了一个工具函数来处理导航栏高度差异,在所有页面统一设置自定义导航栏,避免在不同机型上出现错位。
5.4 插曲:支付功能因商户号违规暂时无法使用的处理
项目做到支付环节时有个插曲。我申请好的微信支付商户号还没等我跑通一个完整支付流程,就因为资质审核的问题被暂时限制使用了,小程序端一直提示“由于违规,支付功能暂时无法使用”。这个情况不是个例,在做学生项目和毕设时经常遇到微信支付申请不通过或者被限制的情况。
我的处理方案是把支付流程拆成两个版本。正式版本对接微信支付,代码写好并验证了签名逻辑。演示版本则使用模拟支付,后端在测试环境直接调用一个mock接口模拟支付成功回调,跳过预支付和签名环节,这样既不影响核心流程演示,也能在答辩或者展示时流畅走完从抢票到出票的完整链路。等到真实商户号申请通过后,只需要把后端配置信息换成正式的商户参数,就能无缝切换到真实支付。
这个插曲提醒大家,如果项目里依赖微信支付的完整流程,一定要提前检查商户号的审核状态,不要把支付环节作为项目最后几天的里程碑任务。最好在项目早期就提交申请,资质审核的周期有时会远超预期。
5.5 常见问题速查表
| 现象 | 可能原因 | 解决方式 |
|---|---|---|
| 小程序请求后端一直报404 | 后端未启动或路径匹配错误 | 先检查后端日志确认是否收到请求再关注路由匹配 |
| 前端返回“库存不足”但数据库还有票 | Redis库存键未初始化或因过期被清除 | 活动上架时同步初始化Redis库存,并给库存键设置合理TTL |
| 用户支付成功但订单还是待支付 | 支付回调请求被拦截或验签失败 | 检查微信支付回调在代码中的处理逻辑,确认回调地址是否公网可达 |
| 抢票接口响应时间超过1秒 | Redis连接复用不够或服务器性能瓶颈 | 使用连接池降低连接建立开销,考虑把Redis部署和应用同机减少网络消耗 |
| 定时任务回补库存后仍有余票显示错误 | 定时任务遗漏了部分订单 | 检查过期时间字段是否为空,确保创建订单时始终写入expire_time |
6. 性能优化与真实抢票场景的压测实录
6.1 使用Locust做并发压测
项目基本完工后,我用Locust做了一次完整的抢票压测。测试场景是模拟一千个用户同时对一个一千张票的活动发起抢购请求,观察成功率和响应时间。压测结果出乎意料地流畅,一千个并发请求中九百六十二个成功抢到票,平均响应时间在一百八十毫秒左右。这说明Redis衔接库存加数据库落库的方案,在千级并发场景下完全够用。
真正把系统打垮的场景是测试五千个并发请求的时候,Flask自带的werkzeug开发服务器扛不住了,请求堆积严重,部分请求超时甚至连接被拒绝。这个瓶颈其实不在Redis和MySQL,而在应用服务器本身。Werkzeug是开发用服务器,每个请求分配一个线程,并发一高线程切换开销就变得极其可观。生产环境换用gevent协程方式运行Flask应用,或者在Flask前面再加一层uWSGI或者Gunicorn做反向代理,性能会有质的提升。
6.2 数据库连接池的参数调优
压测中还暴露出一个数据库连接池配置问题。默认的pymysql是每次请求单独创建连接,没有连接池概念。面对大规模并发请求时,后端每收到一个请求就去建立一个新的MySQL连接,数据库端的连接线程被大量创建和销毁,CPU占用率飙升,直接拖垮了数据库性能。
我的解决方案是通过SQLAlchemy的连接池做统一管理。核心配置是pool_size(连接池大小)设为20,max_overflow(连接池耗尽后最大额外创建连接数)设为30,pool_timeout(等待连接的最长秒数)设为10。配置完成后,即使请求量级大幅上升,数据库连接总数也始终被控制在合理范围内,后端的连接建立开销趋于稳定,压测性能明显改善。
6.3 高并发下还有哪些可以继续深挖的优化点
当前系统的千级并发表现已经能完成课题需求,但如果想要支撑真实商用的超大型抢票活动,还有几个可以继续深挖的方向:一是把库存的Redis操作进一步升级为纯异步队列,让请求进来后直接写入消息队列(比如RabbitMQ或Kafka),然后由消费端做库存扣减和订单创建,库存扣减结果通过WebSocket或者小程序订阅消息异步推送给用户。
二是把数据库连接从MySQL换成分散式的架构,比如对订单表做分库分表,或者引入TDSQL这类分布式数据库产品。不过这个改动幅度比较大,如果不是业务量确实大到单库扛不住,不建议在早期引入分库分表带来的复杂度。
三是网关层的接口防刷策略,除了限流还可以针对用户维度的频控加设备指纹识别,有效阻止脚本刷票。这部分其实在真实场景中才是重点,因为票务黄牛的自动化脚本攻击才是真实票务系统面临的最大技术挑战。
7. 项目总结与拓展方向
7.1 从项目中收获的技术成长路径
整套从零到一的票务抢票系统做完后,回头看收获最大的三个知识板块:一是高并发场景下的库存控制方法,从数据库锁到Redis原子操作再到Lua脚本这个演进过程,让我真正理解了数据一致性在不同存储层之间的权衡;二是微信生态的对接流程,包括登录、支付、订阅消息这些能力从申请到联调,每个环节都对应着真实的业务约束;三是项目代码的组织方式和排查问题的方法论,从一个入口文件写几百行到按照蓝图拆分功能模块,代码可维护性有了质的提升。
7.2 功能扩展方向:从抢票系统到更多场景
这个系统的核心模块本质上是一套通用的“抢购”解决方案,不只是用于演出门票,商品抢购、优惠券秒杀、课程报名、新冠疫苗接种预约这类有库存限制且短时间内有集中流量需求的场景都能复用。需要做的配置调整主要是活动类型字段和票档属性,核心的库存控制、防超卖、订单超时回收逻辑可以直接迁移。
另外如果想增加后台管理能力,可以在现有Flask后端基础上加一份管理端接口,实现活动的创建编辑、票档的上下架、订单的查询与退款操作。管理端前端可以使用Vue或者React做一个简单的Web界面,就能成为一套完整的前后端分离项目,功能完整度和项目体量都会有大大的提升,作为毕业设计绝对够看。
最后分享一个实用的小细节:用Flask开发时一定记得开启DEBUG模式的自动重载,每次修改代码保存后服务器会自动重启,省去频繁手动重启的步骤。部署到生产环境时再关闭DEBUG模式。还有小程序端的联调过程中经常会出现收到的数据结构里对象变成了undefined、数组长度遍历报错这类问题,建议前端写一个通用接口请求封装,统一处理异常提示和登录失效跳转逻辑,开发联调时会省很多事。
