ARTICLE DETAIL

资讯详情

深耕网站视觉设计与运营推广的一线实战洞察。

PHP+Node.js+Vue三件套:数据库原理课程平台开发实战

PHP+Node.js+Vue三件套:数据库原理课程平台开发实战 明知是个课程平台我接手时还是被标题里的三件套组合震了一下Node.js、PHP、Vue外加数据库原理这门课。第一反应是“是不是过度设计了”等项目真正拆完才发现这种组合恰恰是高校和培训机构里数据库原理课程平台的典型形态——课程视频要人看、实验要人跑、题库要人刷还得管学生、管教师、管授权一套系统里塞了内容管理、在线编程、视频流、用户体系四类需求谁都不可能用单一一门语言优雅地收场。这篇文章我就从实际开发角度把这个平台的拆解思路、技术选型、环境搭建、核心模块实现以及我在联调和上线过程中踩过的坑一条条讲清楚。如果你也在搭类似的课程平台、实验管理系统或者单纯想搞明白“Vue Node.js PHP”这三条技术线怎么在一个项目里各司其职这篇文章应该能让你少走不少弯路。1. 项目整体设计与技术选型拆解1.1 为什么是“PHP Node.js Vue”三件套先回答那个最直接的问题为什么不用一套技术栈干完原因是这类课程平台的需求本身就不是单一技术栈能舒服吃下的。课程视频、实验报告、在线测试、用户管理、卡密兑换这些功能分别对应不同的最佳实践。历史代码和团队技能栈是第一个约束很多高校和培训机构的旧教务系统、学生管理系统本来就是PHP写的PHP在传统Web CRUD、用户会话管理、后台管理页面积累了大量现成方案ThinkPHP、Laravel这类框架对快速搭建业务后端太友好了。硬要全部迁移到Node.js成本高、收益小团队还容易在排错时犯怵。Node.js在这个系统里的定位不是替代PHP而是补位负责处理高并发的轻量接口、WebSocket实时课堂交互、Excel实验数据的批量预处理以及在开发阶段给Vue提供代理转发能力。热词里频繁出现的“nodejs安装及环境配置”“npm.ps1无法加载脚本”说明大量开发者确实在Node.js环境上栽过跟头这部分我后面单独开一节细讲。Vue则扛起整个前端。课程列表、视频播放页、实验操作台、教师后台这些页面交互密度高、状态多Vue的组件化开发方式能让多个开发者并行作业不互相踩脚。我见过有人在这个项目里用jQuery硬撸结果一个视频播放组件就写了800行回调地狱后来还是老老实实换成了Vue。三者的分工可以用一张简单的表总结技术栈承担职责典型模块Vue前端交互、路由控制、状态管理、视频播放课程页、实验台、个人中心、管理后台PHP业务后端、用户体系、授权管理、CRUD接口登录注册、卡密兑换、题库管理、成绩记录Node.js中间层服务、数据处理、实时通信、开发代理实验SQL校验、Excel导入、WebSocket课堂MySQL存储核心业务数据同时是数据库原理课程的教学载体用户表、课程表、卡密表、实验记录表1.2 核心功能模块怎么拆标题里的“数据库原理”四个字决定了这平台不只是个视频网站它必须具备“可运行实验”的能力。数据库原理这门课讲的是事务、锁、索引、范式、恢复机制学生光看PPT根本理解不了必须亲手执行SQL、观察锁等待、尝试制造死锁。所以平台的第一个硬需求是在线实验模块给学生一个网页版SQL执行窗口后端执行语句并返回结果集同时把执行时间、影响行数、是否触发锁都展示出来。第二个硬需求是视频与课件管理课程视频以m3u8切片形式存储支持拖动进度、清晰度切换课件PPT转成网页版预览。热词里“vue播放m3u8”“vue播放欢乐谷m.3u8”这类搜索量极高说明大量开发者都在踩HLS播放器的坑我在第4章会专门讲这个。第三个是题库与考试系统单选题、判断题、填空题以及数据库实验特有的“写出SQL并执行验证”题型。PHP负责题库维护和判分规则Node.js负责调用MySQL执行学生的SQL并与标准答案比对。第四个是用户与授权管理学生、教师、管理员三种角色免费试用、卡密兑换、管理员手动开通三种开通方式。热词里“php充值卡密代码”“php用户管理机制”“php域名授权系统网站源码”高频出现说明这类平台普遍不走复杂的支付流程而是用卡密解决收费问题。模块拆分的原则是边界清晰、单点可替换。视频服务将来可以换成云点播实验执行器可以独立升级为容器化沙箱卡密系统抽出来就是一个独立的PHP微服务。我见过有人把视频播放和实验执行耦合在同一个控制器里后来视频服务商出事整个系统跟着瘫了半天这就是拆分没做好的反面教材。2. 环境搭建三大技术栈的安装与联调准备2.1 Node.js安装与环境变量配置的坑Node.js的安装本身没什么难度去官网下LTS版本一路Next就行。真正麻烦的是安装完之后的环境变量配置。很多人在cmd里敲node -v提示“不是内部或外部命令”就是因为安装时没有勾选“Add to PATH”或者安装到了自定义目录但没把目录加进系统环境变量。检查方法很简单右键“此电脑” → 属性 → 高级系统设置 → 环境变量在Path里确认是否有Node.js的安装目录。如果装的是默认路径通常是C:\Program Files\nodejs\。手动添加时建议新增一个NODE_HOME变量指向安装目录再在Path里写%NODE_HOME%这样以后升级Node版本时只需要改一个变量不用翻找一长串Path。还有一个实操细节Node.js默认的全局包目录在C:\Users\你的用户名\AppData\Roaming\npm如果你用npm install -g装了全局工具比如vue/cli后命令无法识别十有八九是那个目录也不在Path里。配置npm的全局目录和国内镜像也是这个阶段顺手要做的事npm config set prefix D:\nodejs\npm-global npm config set registry https://registry.npmmirror.com国内镜像不是“加速器”之类的概念单纯是因为默认官方源在国外下载依赖动不动超时。把registry切到国内镜像后npm install的速度会从几百KB/s直接跳到几MB/s实测下来非常稳定。之后再装依赖踩坑的几率会小一半以上。2.2 “npm.ps1无法加载脚本”的完整解法这是我在热词里看到出现频率最高的错误也是所有Windows上搞Vue开发的新手第一道坎。报错长这样npm : 无法加载文件 C:\Program Files\nodejs\npm.ps1因为在此系统上禁止运行脚本。原因是npm在Windows上其实有两个入口一个是npm.cmd一个是npm.ps1。VS Code和PowerShell默认调用的PowerShell会优先执行.ps1脚本而Windows默认的执行策略是Restricted禁止运行任何.ps1脚本文件于是就直接报错拦住了。解法不复杂但需要注意细节。以管理员身份打开PowerShell执行Set-ExecutionPolicy -Scope CurrentUser RemoteSignedRemoteSigned的意思是本机创建的脚本可以运行从网上下载的脚本必须经过签名验证。这样既解决了npm的启动问题又不会把系统安全策略彻底关掉。很多人图省事直接设成Unrestricted结果所有脚本都能跑安全风险太大我不推荐这么做。如果暂时不想改执行策略还有一个临时方案在VS Code的终端里把默认Shell从PowerShell切到Command PromptCtrlShiftP→ “默认配置文件” → 选择cmd然后重新打开终端。cmd不会走.ps1直接用npm.cmd启动也能绕开这个限制。但我个人还是建议把执行策略改了因为后续很多工具比如Vue CLI的图形化界面还是会调用PowerShell版脚本绕来绕去不如一次解决。2.3 PHP环境与Vue开发联调的最小可行配置PHP环境我推荐用集成面板phpstudy、宝塔这类把Apache/Nginx、PHP、MySQL一次装齐。版本选择上PHP 7.4是兼容性和性能都比较稳的选择PHP 8.x也够用但一些老项目代码比如老版ThinkPHP在8.x下容易报Deprecated警告迁移成本高。如果是新写的PHP后端直接用PHP 8.1以上版本没毛病。这个项目里PHP和Vue分离部署联调阶段需要解决跨域问题。开发时最简单的方案是让Vue的dev server做代理Vue跑在http://localhost:5173PHP接口跑在http://localhost:8080在vue.config.js里配置如下module.exports { devServer: { proxy: { /api: { target: http://localhost:8080, changeOrigin: true, pathRewrite: { ^/api: } } } } }这样前端代码里请求/api/xxx时dev server会把请求转发给PHP服务器浏览器端看到的始终是同源请求跨域问题直接消失而且不用改PHP的响应头。PHP接口返回数据时最常犯的错是中文被转成了\uXXXX形式这是json_encode的默认行为。解决方式是在编码时加上JSON_UNESCAPED_UNICODEecho json_encode($data, JSON_UNESCAPED_UNICODE);还有数组和对象的问题——PHP里json_encode一个键不是从0开始的数组时会自动变成对象前端拿到后如果当数组遍历就会报错。经验是在PHP里处理好数据结构要么用array_values()重置索引要么明确告诉前端这里返回的是对象。热词里“php接口数组对象”对应的就是这类联调体验。3. 数据库原理教学模块从锁机制讲到实验支撑3.1 乐观锁与悲观锁的实现原理和适用场景数据库原理这门课锁机制永远是考试重点也是学生最容易懵的地方。课程平台里专门做了一个“锁机制演示实验”让学生自己动手触发锁等待和死锁。这里正好把乐观锁和悲观锁的原理掰开讲一遍。悲观锁的逻辑是“我修改之前先把数据锁住别人不许动”对应SQL是-- 事务A BEGIN; SELECT * FROM course_seat WHERE id 123 FOR UPDATE; -- 检查座位状态然后更新 UPDATE course_seat SET student_id 101 WHERE id 123; COMMIT;FOR UPDATE会在事务结束前一直持有这把行锁其他事务对这个行的更新要么阻塞等待要么超时放弃。这种方式适合并发冲突激烈、更新失败率高的场景比如选课系统、抢座系统、库存扣减。缺点也明显持锁时间长一旦忘记提交或事务异常回滚其他事务会一直卡住数据库连接池很快被打满。乐观锁的逻辑则完全不同它默认冲突发生得少所以在更新时才检查“数据是不是还是我读到的那个版本”。最典型的实现是加版本号字段-- 事务A读取时 SELECT id, seat_no, version FROM course_seat WHERE id 123; -- 假设读到的version 5更新时带上版本条件 UPDATE course_seat SET student_id 101, version version 1 WHERE id 123 AND version 5;如果在这期间有人先改过version已经不是5这次UPDATE影响行数为0程序就知道冲突了可以选择重试或给用户提示。乐观锁适合读多写少、冲突概率低的场景比如文章点赞、笔记编辑、购物车商品信息更新。给学生的演示实验分三步第一步用悲观锁模拟抢座开两个MySQL连接让学生亲眼看到第二个连接卡在FOR UPDATE上第二步用乐观锁模拟同样的场景让学生看到版本号冲突导致更新失败第三步让他们对比两种方案在不同并发下的耗时和失败率。平台在Node.js端封装了一个简单的查询接口通过mysql2连接池执行SQL并把结果返回到前端展示。配套的PHP端实现也不复杂// 乐观锁更新返回影响行数 $stmt $pdo-prepare(UPDATE course_seat SET student_id :sid, version version 1 WHERE id :id AND version :ver); $stmt-execute([:sid 101, :id 123, :ver 5]); if ($stmt-rowCount() 0) { // 版本冲突告知用户重试 }我在课堂演示时发现一个常见问题学生执行SELECT ... FOR UPDATE后忘记COMMIT直接把连接关了结果这个锁要等MySQL检测到连接断开才能释放其他学生的事务在界面上卡了十几秒才开始报错。这个现象本身倒成了最好的教学素材——“事务没提交锁就不会释放”。3.2 数据库原理实验模块怎么落地“数据库原理实验”是很多高校计算机相关专业躲不开的必修环节搜索热词里“西工大数据库原理实验”这类词条被高频搜索说明大量学生需要做实验、写报告。平台把实验分成两类知识点验证型和综合设计型。知识点验证型实验预设好题目比如“验证事务的ACID特性”“验证不同隔离级别下的脏读、不可重复读、幻读”。平台后端在Node.js里写了一个执行器学生输入SQL脚本执行器在独立的连接里运行把执行结果、耗时和锁等待信息收集起来返回给前端。这里有个安全细节——执行器必须限制单条SQL的执行时间和影响行数避免学生一条DELETE FROM把整个实验库清空。我用的是mysql2连接配置里的timeout参数同时用只读账号连接实验库从源头掐掉危险操作。综合设计型实验则更自由学生自己设计表结构写存储过程、触发器提交后由教师评分。这个模块的难点在Excel批量导入——经常有老师把学生名单、实验数据整理成Excel表格发来需要平台能批量导入数据库。PHP这边用PhpSpreadsheet解析Excel文件Node.js这边用node-xlsx也可以做我一般让PHP负责这个功能因为它和后台管理界面耦合得更紧。导入的逻辑不复杂但有个细节很关键先上传、预览、再入库。第一次导入时先把Excel解析成JSON返回前端让老师确认“第一行是表头”“第3列会被识别为日期格式”确认无误后再提交入库。否则经常出现日期被当成字符串、手机号被科学计数法、学号前面的0被吞掉这种经典问题等数据入库再改就麻烦了。3.3 PHP侧数据库访问的安全底线课程平台有用户输入、有实验SQL、有后台管理安全防线一点不能松。PHP访问MySQL必须用PDO预处理语句不要让用户输入直接拼进SQL。举个例子查询学生成绩的接口如果写成这样就是妥妥的注入漏洞// 错误示范 $sql SELECT * FROM scores WHERE student_name . $_GET[name] . ;换成PDO预处理$stmt $pdo-prepare(SELECT * FROM scores WHERE student_name ?); $stmt-execute([$_GET[name]]);为什么预处理能防注入因为参数值在执行阶段被当成纯数据MySQL不会把它解析成SQL语法的一部分。这个道理我给学生在实验课上也讲等于把“代码安全”也渗透到了数据库原理教学里。另外提一句热词里反复出现的“php伪协议”。php://filter这类流包装器本身是PHP提供的能力但如果代码里存在文件包含漏洞攻击者可以利用伪协议读取源码文件。这门课的平台里涉及文件上传和课件读取我在上线前检查清单里专门加了一条禁用没必要的流包装器校验所有文件包含路径白名单。这个话题不适合展开讲太多攻击细节但作为平台开发者的防御意识必须到位。4. Vue前端路由、状态与视频播放4.1 课程路由设计与路由参数处理Vue前端的页面结构大致是首页课程列表 → 课程详情页 → 视频播放页 → 实验操作台 → 个人中心 → 后台管理。路由用vue-router这里最值得讲清楚的是路由传参。Vue Router传参有两种方式query和params。query就是URL里的?id123刷新页面参数还在适合共享链接params则是路径参数像/course/123这种需要在路由配置里声明占位符const router createRouter({ routes: [ { path: /course/:id, name: CourseDetail, component: CourseDetail } ] })跳转时用router.push({ name: CourseDetail, params: { id: courseId } })页面里通过route.params.id读取。这里有个特别容易踩的坑如果跳转时传的params和路由配置里的占位符名字对不上或者根本没有占位符params不会出现在URL里刷新页面参数直接丢失。热词里“vue路由参数”被反复搜索多半就是栽在这上面。解决方案很朴素——需要在刷新后保留的参数就用query或者把参数同步到Pinia/Vuex并配合持久化插件。视频播放页还有一个交互细节学生看完一节视频后要自动记录学习进度下次进来可以从上次位置继续。这个我用query传进度参数播放器每隔5秒上报一次当前时间戳到后端课程列表页根据进度显示“已学习80%”的进度条。4.2 m3u8视频流播放从“欢乐谷直播”说到课程视频课程视频用的是m3u8格式这其实是HLSHTTP Live Streaming协议下的播放列表文件里面存的是一个个.ts切片视频文件路径。为什么选它因为切片后支持分辨率切换、拖动进度加载快、对服务器压力小而且各大云厂商的点播服务普遍输出这种格式。热词里“vue播放欢乐谷m.3u8”“vue播放m3u8免安装”高频率出现说明很多不是做课程平台的人也遇到了m3u8播放需求比如景区直播流、视频监控回放。Vue里播放m3u8原生video标签在Safari和iOS上能直接播但Chrome和Firefox都不支持HLS原生播放必须借助hls.js来做解封装。最小可用的实现长这样template video refvideoRef controls autoplay/video /template script setup import Hls from hls.js import { ref, onMounted } from vue const videoRef ref(null) const src /api/course/video/lesson-1.m3u8 onMounted(() { const video videoRef.value if (Hls.isSupported()) { const hls new Hls({ maxBufferLength: 30, enableWorker: true }) hls.loadSource(src) hls.attachMedia(video) hls.on(Hls.Events.ERROR, (event, data) { if (data.fatal) { // 网络错误尝试恢复 if (data.type Hls.ErrorTypes.NETWORK_ERROR) { hls.startLoad() } } }) } else if (video.canPlayType(application/vnd.apple.mpegurl)) { // 原生支持HLS的浏览器直接赋值 video.src src } }) /script实践里几个关键参数maxBufferLength控制缓冲长度避免内存飙升enableWorker开启解码多线程播放4K切片时卡顿会明显减少。我用的是Nginx静态托管切片文件access.log里能看到播放器按顺序请求.ts分片每片2到6秒这个规律和数据断点续传的逻辑很像。另一个经验是课程视频的防盗链不能只靠前端。m3u8文件本身是明文别人拿到URL就能扒走视频。我给平台加了Nginx层的Referer校验和拉流签名带时间戳的token有效挡住了大部分盗链。但这属于部署优化开发阶段不需要管。4.3 Vue调试工具与常见面试考点Vue开发离不开的调试利器就是vue-devtools浏览器扩展商店直接下载安装。关键在于版本匹配Vue 2项目要装Vue 2版本对应插件Vue 3项目要装支持Vue 3的新版。装错版本最常见的表现是进了页面插件图标灰色不可点击。装好后可以在Components面板实时查看组件树和props/state在Vuex/Pinia面板直接改仓库数据排查状态问题效率翻倍。热词里“vue面试题”搜索量大说明很多人一边做项目一边准备面试。和这个平台相关的常见考点我列几个Vue响应式原理Proxy/defineProperty、生命周期执行顺序、路由守卫的应用场景。课程平台里的“登录后才能访问课程”就是典型的router.beforeEach守卫场景router.beforeEach((to, from, next) { const token localStorage.getItem(token) if (to.meta.requiresAuth !token) { next({ path: /login, query: { redirect: to.fullPath } }) } else { next() } })这个实现简单可靠面试时还能借此引出“token过期怎么办”“路由守卫里发请求的坑”这类延伸话题。5. 用户机制、卡密授权与线上运营5.1 PHP充值卡密代码的完整设计思路课程平台不接第三方支付而是走卡密兑换的老路。不是支付渠道不好接而是卡密这种模式在高校培训场景下太方便了——老师批量买卡学生兑换省去实名认证和退款处理。热词“php充值卡密代码”“php充值卡密代码视频”说明这是相当多课程类PHP项目的真实需求。卡密系统拆成三个核心环节生成卡密、存储卡密、兑换卡密。生成卡密的核心逻辑是“随机、不重复、可批量”function generateCard($len 12, $batch 100) { $chars ABCDEFGHJKLMNPQRSTUVWXYZ23456789; // 去掉易混淆字符 $cards []; for ($i 0; $i $batch; $i) { $card ; for ($j 0; $j $len; $j) { $card . $chars[random_int(0, strlen($chars) - 1)]; } $cards[] $card; } return $cards; }字符集去掉了0/O、1/I这类容易混淆的字母这个细节看起来小但实际打印出来让学生手动输入时能少一半客服工单。random_int比rand更安全生成卡密这种场景必须用前者。存储时给卡密表设计几个关键字段card_no唯一索引、batch_no批次号、status状态0-未使用、1-已使用、2-已禁用、expire_at过期时间、used_by使用者ID、used_at使用时间。数据库事务配合唯一索引保证同一张卡不会被兑换两次。兑换接口是防刷的重点。学生输入卡密后PHP接口里做的事是查卡密存在性 → 校验状态 → 更新用户余额 → 标记卡密已用。整个流程必须放到一个事务里否则会出现极端条件下“余额加了但卡没标记”的情况。还要加频率限制同一个IP、同一个用户每分钟最多兑换3次挡住暴力枚举。卡密兑换不能做幂等的事重复提交同一张卡第二次必须明确报“该卡已被使用”不能给用户账户重复加钱。5.2 用户管理机制与多场景案例热词里“php的用户管理机制”是PHP开发的高频需求课程平台也不例外。用户体系表结构大致是用户ID、用户名、密码哈希存储、角色学生/教师/管理员、状态、创建时间。密码存储必须用password_hash和password_verify这是PHP官方推荐的密码哈希方案// 注册 $hash password_hash($password, PASSWORD_DEFAULT); // 登录验证 if (password_verify($password, $hash)) { // 登录成功 }PHP传统的登录方案是SessionCookie课程平台我建议直接用Token。前端登录后拿到一个随机token存储在前端后续请求放到Authorization头里PHP端用内存缓存或数据库表存token和用户ID的映射设置7天有效期。为什么不用传统Session因为前端是Vue SPA接口完全跨域Session的Cookie跨域处理麻烦而且移动端App将来要复用接口时Session方案非常难受。平台必须区分学生、教师、管理员三种角色学生能看课、做实验、在线考试教师能维护题库、批改实验、查看成绩管理员管用户和卡密。我建议用PHP中间件的方式做权限控制而不是写死在每个控制器里——写死会导致权限逻辑到处都是改动一次要翻遍所有控制器太痛苦了。顺带说一句热词里的“模拟炒股php”“php图书管理系统”都是典型的PHP课程设计项目它们和课程平台在用户机制上高度相似登录注册、角色区分、数据CRUD。做过一遍课程平台回头再看这些课程设计题会发现核心套路都是同一套。5.3 域名授权与防盗用课程平台上线后源码部署给客户是常见玩法这就引申出“域名授权系统”的需求——一套PHP源码只能在一个域名下运行换域名就得重新激活。热词“php域名授权系统网站源码”反映的就是这个场景。实现思路不复杂安装时让用户填写授权域名系统把域名发送到你的授权服务器换取一个签名每次请求时PHP端校验当前HTTP_HOST是否和授权域名匹配如果换了域名业务接口直接返回“域名未授权”。这里有个关键点授权校验必须核心业务绑定不能只在前台静态页校验。比如课程列表可以缓存显示但实验执行、卡密兑换、后台管理的接口必须动态校验授权否则对方只要改几行代码把前台校验跳过去整套系统就白给了。实践中我用了一个简单的对称加密签名授权服务器返回的文件里包含域名信息和有效期PHP端用约定好的密钥解开校验防止随便复制。6. 常见问题排查与实操经验6.1 跨域、代理与多端适配整个项目开发期最头大的问题基本都出在多服务联调上。前端5173端口、后端PHP 8080端口、Node.js 3000端口三个服务来回跳。前面讲了vue.config.js的代理方案能解决开发期跨域但上线后Nginx反向代理才是正解把前端打包后的dist目录指到根路径/api下的请求转发给PHP-FPM/exp下的请求转发给Node.js服务。这样用户访问的始终是同一个域名浏览器不会产生跨域问题运维排查也简单。热词里“用在vue里的腾讯地图”“vscode vue怎么制作手机软件”都是课程平台衍生出来的常见需求。腾讯地图在Vue项目里通常直接引入JS API在onMounted里初始化地图实例用于实验数据的地理分布展示手机端的话Vue 3项目可以用Capacitor或者uni-app套壳打包成App但核心逻辑还是Web的那套只是多了原生壳的交互桥。边界处理上要留意的是移动端video播放hls的兼容性iOS原生支持但Android WebView不一定得在代码里判断一下。还有那个热词“electron 主渲染进程 ipc 通信 和vue有关系吗”——答案是Electron和Vue没有必然关系。Electron提供桌面壳和主进程能力文件系统、原生窗口、系统托盘Vue只管渲染进程里的界面。如果项目将来要打包成Windows桌面版比如教师端离线阅卷工具主进程和渲染进程的IPC通信走的还是Electron自身的ipcMain和ipcRendererVue只负责调用渲染进程侧封装好的API不要把它俩混为一谈。6.2 前端环境与Node脚本的日常坑npm install慢、报错、依赖树冲突是每个Vue项目开发者每天的必修课。我的经验是先用npm config get registry确认镜像源再确认package-lock.json存在且没有手改最后才考虑清缓存npm cache clean --force rm -rf node_modules package-lock.json npm installnode_modules删掉重装是解决大半疑难杂症的“大杀器”但不到万不得已不要用因为全量重装一次耗时好几分钟。如果只是某个包版本对不上优先用npm install 包名指定版本精准修复。热词里“pycharm配置nodejs”看起来奇怪但确实有很多人是拿PyCharm写Vue的——因为他们在同一个IDE里既写Python数据分析又写Vue前端。PyCharm里跑npm命令需要先在Settings → Tools → Terminal里把Shell路径指对或者直接在Settings → Languages Frameworks → Node.js里配置Node解释器路径。配置好后能识别npm命令语法和高亮不再满屏红色波浪线。6.3 一套从开发到上线的检查清单项目收尾阶段我习惯把所有检查项列成一张表逐项打钩。这张表是从几次事故教训里攒出来的贴出来给大家参考检查项具体操作事故教训来源环境版本确认Node、PHP、MySQL版本与生产一致本地PHP 8.2线上PHP 7.4接口直接500数据库开启慢查询日志检查核心表索引实验记录表无索引多人在线时查询超时安全关闭危险函数和伪协议、PDO预处理自查文件包含伪协议导致源码泄露授权域名授权、卡密兑换接口限流未限流时被脚本批量撞卡视频检查m3u8切片是否完整、防盗链签名是否过期切片缺失导致视频播放到后半段黑屏打包前端npm run build后检查静态资源路径资源路径用了绝对路径部署到子目录就404日志三套服务统一日志格式开启错误记录排错时三份日志各写各的没法关联这套清单里的每一行都是真金白银的教训。特别是日志格式那条项目初期Node.js、PHP、前端各写各的日志时间戳格式都不一样出问题时对着三份日志根本对不上号。后来统一成ISO8601时间 | 级别 | 服务名 | 请求ID | 消息的格式排查效率才真正提上去。最后说一个我在这类课程平台项目里感受最深的事三套技术栈并存的项目最怕的不是技术难点而是沟通成本的失控。前端说要字段后端说要格式Node.js说要接口约定如果没有一份所有人一起维护的接口文档联调阶段每天都能吵起来。我们后来在项目初期花了半天时间把接口文档模板定下来字段命名、错误码规范、分页格式全部统一成文档后续开发少吵了无数架。如果你也要做类似的多技术栈项目一定不要跳过这一步。
返回列表