PHP+NodeJS实现实时推送通知的简易方案咨询
实现PHP + Node.js + Socket.IO实时推送通知方案
我帮你梳理下具体的实现步骤,核心就是让PHP在发布内容后通知Node.js服务,再由Socket.IO推送给所有在线用户——咱们一步步来:
1. 搭建Node.js + Socket.IO服务
首先得先跑起Socket.IO的服务,它会监听你指定的端口(比如3000,和你的PHP服务端口区分开)。
步骤1.1 初始化Node项目
先新建一个文件夹,比如node-notification-server,然后执行:
npm init -y npm install socket.io express cors
步骤1.2 编写服务端代码(server.js)
这里我们用Express搭个简单的HTTP服务,同时集成Socket.IO,还要加一个接口让PHP能发送通知请求:
const express = require('express'); const http = require('http'); const { Server } = require('socket.io'); const cors = require('cors'); const app = express(); app.use(cors()); // 解决跨域问题 app.use(express.json()); // 解析JSON请求体 const server = http.createServer(app); const io = new Server(server, { cors: { origin: "*", // 生产环境建议改成你的PHP域名,比如http://your-php-site.com methods: ["GET", "POST"] } }); // 监听客户端连接 io.on('connection', (socket) => { console.log('用户已连接:', socket.id); socket.on('disconnect', () => { console.log('用户已断开连接:', socket.id); }); }); // 接收PHP发来的通知请求 app.post('/send-notification', (req, res) => { const { content, username } = req.body; // 推送给所有在线客户端 io.emit('new-post', { message: `${username}发布了新内容: ${content}`, time: new Date().toLocaleString() }); res.status(200).json({ success: true, message: '通知已推送' }); }); // 启动服务,监听3000端口 server.listen(3000, () => { console.log('Socket.IO服务运行在http://localhost:3000'); });
启动服务:node server.js
2. 修改PHP的post.php,触发通知
当用户发布内容并成功插入数据库后,你需要给Node服务的/send-notification接口发请求,把通知内容传过去。这里用CURL来实现:
<?php // 你的PDO插入数据库代码 $pdo = new PDO('mysql:host=localhost;dbname=your_db', 'username', 'password'); $content = $_POST['content']; $username = $_SESSION['username']; // 假设你有用户登录态 // 插入数据库 $stmt = $pdo->prepare("INSERT INTO posts (content, username) VALUES (:content, :username)"); $stmt->bindParam(':content', $content); $stmt->bindParam(':username', $username); if ($stmt->execute()) { // 插入成功,发送通知到Node服务 $notificationData = [ 'content' => $content, 'username' => $username ]; $ch = curl_init('http://localhost:3000/send-notification'); curl_setopt($ch, CURLOPT_RETURNTRANSFER, true); curl_setopt($ch, CURLOPT_POST, true); curl_setopt($ch, CURLOPT_POSTFIELDS, json_encode($notificationData)); curl_setopt($ch, CURLOPT_HTTPHEADER, [ 'Content-Type: application/json' ]); $response = curl_exec($ch); curl_close($ch); // 可以根据response判断是否推送成功,这里简化处理 header('Location: /'); // 发布成功后跳转首页 } else { echo '发布失败'; } ?>
3. 前端页面集成Socket.IO客户端,显示通知
在你有导航栏的页面(比如header.php或者首页),引入Socket.IO客户端脚本,然后监听new-post事件,更新导航栏的通知:
<!-- 在页面头部引入Socket.IO客户端,注意版本要和服务端一致 --> <script src="https://cdn.socket.io/4.7.2/socket.io.min.js"></script> <script> // 连接Node的Socket.IO服务 const socket = io('http://localhost:3000'); // 监听新通知 socket.on('new-post', (data) => { // 这里可以自定义通知显示方式,比如在导航栏加小红点,或者弹出消息 const notificationBell = document.getElementById('notification-bell'); // 比如更新通知数 let currentCount = parseInt(notificationBell.dataset.count) || 0; notificationBell.dataset.count = currentCount + 1; notificationBell.innerHTML = `<span class="badge">${currentCount + 1}</span>`; // 也可以弹出提示框 alert(data.message); }); </script> <!-- 导航栏的通知图标示例 --> <nav> <div id="notification-bell" data-count="0"> 🔔 <span class="badge">0</span> </div> </nav>
一些注意事项
- 跨域问题:生产环境中,Node服务的
cors配置要指定你的PHP域名,不要用*,更安全。 - Socket.IO版本:客户端和服务端的版本要兼容,比如服务端用4.x,客户端也要用4.x的CDN链接。
- 错误处理:PHP的CURL请求要加错误处理,比如判断请求是否成功;Node服务也要处理异常情况。
- 持久化通知:如果需要用户离线后也能看到通知,还要把通知存在数据库里,用户登录后再拉取历史通知,这个可以在上面的基础上扩展。
内容的提问来源于stack exchange,提问作者pileup
相关产品推荐
相关产品推荐

