1 Star 0 Fork 93

高乐康/HasChatService

forked from howcode/HasChatService 
加入 Gitee
与超过 1200万 开发者一起发现、参与优秀开源项目,私有仓库也完全免费 :)
免费加入
该仓库未声明开源许可证文件(LICENSE),使用请关注具体项目描述及其代码上游依赖。
克隆/下载
app.js 22.55 KB
一键复制 编辑 原始数据 按行查看 历史
howcode 提交于 2023-10-11 17:10 . pref:优化验证码发送逻辑
123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830
const express = require("express");
const socket = require("socket.io");
const cors = require("cors");
const mysql = require("mysql");
const nodemailer = require("nodemailer");
const multer = require("multer");
const fs = require("fs");
const path = require("path");
const { emailConfig, nowTime } = require("./config");
const {
getUSerList,
getUserById,
getRandomUser,
getUserByEmail,
getUserByOutTradeNo,
getOnlineUserById,
insertUser,
updateUserOutTradeNoById,
updateUserOnlineStateById,
updateHistorySessionListById,
updateUserNoCodeById,
} = require("./query/user");
const {
getContentBySendId,
getUnReadContent,
insertContent,
updateContentReadFlagById,
} = require("./query/content");
const {
insertCommunity,
getCommunityList,
getCommunityLikeRecord,
insertCommunityLikeRecord,
deleteCommunityLikeRecord,
getCommunityLikeCount,
insertCommunityComment,
getCommunityCommentList,
deleteCommunityComment,
getUnreadCommunityList,
getCommunityMessageList,
updateCommunityContentStateById,
} = require("./query/community");
const {
insertHistorySession,
getHistorySession,
getOneHistorySession,
} = require("./query/historySession");
const sessionEmail = {};
const config = require("./config");
const app = express();
app.use(cors());
app.use(express.json());
app.use(express.urlencoded({ extended: true }));
const msg = {
sucess: function (data, message = "") {
return {
code: 200,
message,
data,
};
},
error: function (message = "") {
return {
code: 600,
message,
};
},
};
// 生成token
function newGuid() {
var guid = "";
for (var i = 1; i <= 32; i++) {
var n = Math.floor(Math.random() * 16.0).toString(16);
guid += n;
if (i == 8 || i == 12 || i == 16 || i == 20) guid += "-";
}
return guid;
}
// 随机生成验证码
function getCode(n) {
let all = "azxcvbnmsdfghjklqwertyuiopZXCVBNMASDFGHJKLQWERTYUIOP0123456789";
let result = "";
for (let i = 0; i < n; i++) {
let index = Math.floor(Math.random() * 62);
result += all.charAt(index);
}
return result;
}
// 随机获取数组
function getRandArray(arr) {
var result = {};
arr.sort(function () {
return 0.5 - Math.random();
});
result = arr[0];
return result;
}
/**
* 路径是否存在,不存在则创建
* @param {string} dir 路径
*/
async function dirExists(dir) {
let isExists = await getStat(dir);
// 如果该路径存在且不是文件,返回 true
if (isExists && isExists.isDirectory()) {
return true;
} else if (isExists) {
// 这个路径对应一个文件夹,无法再创建文件了
return false;
}
// 如果该路径不存在
let tempDir = path.parse(dir).dir; //拿到上级路径
// 递归判断,如果上级路径也不存在,则继续循环执行,直到存在
let status = await dirExists(tempDir);
let mkdirStatus;
if (status) {
mkdirStatus = await mkdir(dir);
}
return mkdirStatus;
}
/**
* 读取路径信息
* @param {string} filepath 路径
*/
function getStat(filePath) {
return new Promise((resolve, reject) => {
fs.stat(filePath, (err, stats) => {
if (err) {
resolve(false);
} else {
resolve(stats);
}
});
});
}
/**
* 创建路径
* @param {string} dir 路径
*/
function mkdir(dir) {
return new Promise((resolve, reject) => {
try {
fs.mkdir(dir, { recursive: true }, (err) => {
if (err) {
resolve(false);
} else {
resolve(true);
}
});
} catch (error) {
console.log("error", error);
}
});
}
// 根据Id获取用户信息
app.post("/api/getUserById", async function (req, res) {
try {
let { id } = req.body;
let queryResult = await getUserById(id);
if (queryResult.state) {
res.send(msg.sucess(queryResult.data, "成功"));
} else {
res.send(msg.error("获取数据失败"));
}
} catch (error) {
res.send(msg.error(error.message));
}
});
// 获取用户列表
app.post("/api/userList", async function (req, res) {
try {
let { id, pageIndex, pageSize } = req.body;
let queryResult = await getUSerList(id, pageIndex, pageSize);
if (queryResult.state) {
res.send(msg.sucess(queryResult.data, "成功"));
} else {
res.send(msg.error("获取数据失败"));
}
} catch (error) {
res.send(msg.error(error.message));
}
});
// 随机获取一条用户数据
app.post("/api/getRandomUser", async function (req, res) {
try {
let queryResult = await getRandomUser();
if (queryResult.state) {
res.send(msg.sucess(queryResult.data[0], "成功"));
} else {
res.send(msg.error("获取数据失败"));
}
} catch (error) {
res.send(msg.error(error.message));
}
});
// 登陆接口
app.post("/api/login", async function (req, res) {
try {
let { email, password } = req.body;
let queryResult = {
myInfo: null,
token: "",
};
let result = await getUserByEmail(email);
if (result.state) {
if (result.data.length > 0) {
queryResult.myInfo = result.data[0];
if (queryResult.myInfo.Password == password) {
queryResult.token = newGuid();
res.send(msg.sucess(queryResult, "成功"));
} else {
res.send(msg.error("密码错误"));
return;
}
} else {
res.send(msg.error("该用户不存在"));
return;
}
} else {
res.send(msg.error("查询数据失败"));
return;
}
} catch (err) {
res.send(msg.error(err.message));
}
});
// 发送邮箱验证码
app.post("/api/sendVerificationCode", async function (req, res) {
try {
let { email, timestamp } = req.body;
// 校验邮箱是否被注册
let result = await getUserByEmail(email);
if (result.state) {
if (result.data.length > 0) {
res.send(msg.error("该邮箱已被注册"));
return;
} else {
// 创建发送邮件的请求对象
let transporter = nodemailer.createTransport(emailConfig);
let verificationCode = getCode(6);
// 邮件信息
let mailObj = {
from: `来自<${emailConfig.auth.user}>`, // 发送方邮箱及标题
to: email, // 对方邮箱地址
subject: "【haschat】账号注册", //
html: `您正在注册haschat账号,本次请求的邮件验证码是:<b>${verificationCode}</b>(如非本人操作,请忽略该信息)`, // html格式
};
transporter.sendMail(mailObj, (err, info) => {
if (err) {
console.log("发邮件出错了", err);
res.send(msg.sucess(null, "发邮件出错了"));
} else {
sessionEmail[timestamp] = verificationCode;
res.send(msg.sucess(null, "发送验证码成功"));
console.log("邮件发送成功");
}
});
}
} else {
res.send(msg.error("获取数据失败"));
}
} catch (err) {
res.send(msg.error(err.message));
}
});
// 校验邮箱验证码
app.post("/api/checkVerificationCode", function (req, res) {
try {
let { verificationCode, timestamp } = req.body;
if (sessionEmail[timestamp] == verificationCode) {
delete sessionEmail[timestamp];
res.send(msg.sucess(null, "验证码校验通过"));
} else {
res.send(msg.error("验证码校验失败"));
}
} catch (err) {
res.send(msg.error(err.message));
}
});
// 注册接口
app.post("/api/register", async function (req, res) {
try {
let { email, name, password, surePassword, avatar } = req.body;
if (password !== surePassword) {
res.send(msg.error("两次密码不一致"));
}
// 校验邮箱是否被注册
let result = await getUserByEmail(email);
if (result.state) {
if (result.data.length > 0) {
res.send(msg.error("该邮箱已被注册"));
return;
}
// 新增用户
let obj = {
name: name,
nickName: name,
email: email,
password: password,
avatar: avatar || config.newUserConfig.Avatar,
};
let result2 = await insertUser(obj);
if (result2.state) {
res.send(msg.sucess(null, "注册成功"));
} else {
res.send(msg.error("注册失败"));
}
} else {
res.send(msg.error("获取数据失败"));
}
} catch (err) {
res.send(msg.error(err.message));
}
});
// 上传文件接口
app.post(
"/api/uploadFile",
multer({
dest: "upload",
}).array("file", 1),
(req, res) => {
const files = req.files;
const fileList = [];
for (let i in files) {
let file = files[i];
fs.renameSync(file.path, `upload/${file.filename}${file.originalname}`);
file.path = `upload/${file.filename}${file.originalname}`;
fileList.push(file);
}
res.send(fileList);
}
);
// 上传图片接口
app.post(
"/api/uploadImage",
multer({
dest: "upload",
}).array("file", 1),
async (req, res) => {
const files = req.files;
const fileList = [];
await dirExists("upload/img/");
for (let i in files) {
let file = files[i];
fs.renameSync(
file.path,
`upload/img/${file.filename}${file.originalname}`
);
file.path = `upload/img/${file.filename}${file.originalname}`;
fileList.push(file);
}
res.send(fileList);
}
);
// 获取资源文件
app.get("/api/getFile", (req, res) => {
req.query.url
? res.download(`upload/${req.query.url}`)
: res.send(msg.error("获取数据失败"));
});
// 获取图片资源文件
app.get("/api/getImage", (req, res) => {
req.query.url
? res.download(req.query.url)
: res.send(msg.error("获取数据失败"));
});
// 发布社区
app.post("/api/publishComunity", async function (req, res) {
try {
let model = req.body;
if (!(model.PublishId > 0)) {
res.send(msg.error("请登陆后再发布"));
return;
}
if (!model.Content) {
res.send(msg.error("内容不得为空"));
return;
}
model.CreateDateUtc = nowTime();
let result2 = await insertCommunity(model);
if (result2.state) {
res.send(msg.sucess(null, "发布成功"));
} else {
res.send(msg.error("发布失败"));
}
} catch (err) {
res.send(msg.error(err.message));
}
});
// 获取社区内容
app.post("/api/getCommunityList", async function (req, res) {
try {
let model = req.body;
if (!(model.pageIndex > 0 && model.pageSize > 0)) {
res.send(msg.error("参数必须大于零"));
return;
}
let result = await getCommunityList(model);
if (result.state) {
let queryData = result.data;
for (let i = 0, len = queryData.length; i < len; i++) {
queryData[i].ImgList = JSON.parse(queryData[i].ImgList);
let result2 = await getCommunityLikeRecord({
userId: model.userId,
communityId: queryData[i].Id,
});
if (result2.state) {
queryData[i].IsLike = result2.data?.length > 0 ? true : false;
}
let result3 = await getCommunityLikeCount({
communityId: queryData[i].Id,
});
queryData[i].LikeNum = result3.data.length;
let result4 = await getCommunityCommentList({
communityId: queryData[i].Id,
});
queryData[i].CommentList = result4.data;
}
res.send(msg.sucess(queryData, "查询成功"));
} else {
res.send(msg.error("查询失败"));
}
} catch (err) {
res.send(msg.error(err.message));
}
});
// 新增社区喜爱
app.post("/api/insertCommunityLikeRecord", async function (req, res) {
try {
let model = req.body;
if (!(model.userId > 0 && model.communityId > 0)) {
res.send(msg.error("缺乏必要参数"));
return;
}
let result = await getCommunityLikeRecord(model);
if (result.state) {
if (result.data.length == 0) {
let result2 = await insertCommunityLikeRecord(model);
if (result2.state) {
let result3 = await getCommunityLikeCount({
communityId: model.communityId,
});
let count = result3.state ? result3.data.length : -1;
res.send(msg.sucess(count, "点赞成功"));
} else {
res.send(msg.error("点赞异常"));
}
} else {
res.send(msg.sucess(null, "点赞成功"));
}
} else {
res.send(msg.error("点赞失败"));
}
} catch (err) {
res.send(msg.error(err.message));
}
});
// 删除社区喜爱
app.post("/api/deleteCommunityLikeRecord", async function (req, res) {
try {
let model = req.body;
if (!(model.userId > 0 && model.communityId > 0)) {
res.send(msg.error("缺乏必要参数"));
return;
}
let result = await deleteCommunityLikeRecord(model);
if (result.state) {
let result2 = await getCommunityLikeCount({
communityId: model.communityId,
});
let count = result2.state ? result2.data.length : -1;
res.send(msg.sucess(count, "取消成功"));
} else {
res.send(msg.error("取消失败"));
}
} catch (err) {
res.send(msg.error(err.message));
}
});
// 新增社区评论
app.post("/api/insertCommunityComment", async function (req, res) {
try {
let model = req.body;
if (!(model.sendId > 0)) {
res.send(msg.error("请登陆后再发布"));
return;
}
if (!(model.communityId > 0)) {
res.send(msg.error("社区Id不得为空"));
return;
}
if (!model.content) {
res.send(msg.error("内容不得为空"));
return;
}
model.createDateUtc = nowTime();
let result = await insertCommunityComment(model);
if (result.state) {
res.send(msg.sucess(null, "评论成功"));
} else {
res.send(msg.error("评论失败"));
}
} catch (err) {
res.send(msg.error(err.message));
}
});
// 获取社区评论
app.post("/api/getCommunityCommentList", async function (req, res) {
try {
let model = req.body;
if (!(model.communityId > 0)) {
res.send(msg.error("社区Id不得为空"));
return;
}
let result = await getCommunityCommentList(model);
if (result.state) {
res.send(msg.sucess(result.data, "查询成功"));
} else {
res.send(msg.error("查询失败"));
}
} catch (err) {
res.send(msg.error(err.message));
}
});
// 删除社区评论
app.post("/api/deleteCommunityComment", async function (req, res) {
try {
let model = req.body;
if (!(model.id > 0)) {
res.send(msg.error("缺乏必要参数"));
return;
}
let result = await deleteCommunityComment(model);
if (result.state) {
res.send(msg.sucess(null, "删除成功"));
} else {
res.send(msg.error("删除失败"));
}
} catch (err) {
res.send(msg.error(err.message));
}
});
// 获取用户未读信息
app.post("/api/getUnreadCommunityList", async function (req, res) {
try {
let model = req.body;
if (!(model.receiverId > 0)) {
res.send(msg.error("Id不得为空"));
return;
}
let result = await getUnreadCommunityList(model);
if (result.state) {
res.send(msg.sucess(result.data, "查询成功"));
} else {
res.send(msg.error("查询失败"));
}
} catch (err) {
res.send(msg.error(err.message));
}
});
// 获取用户评论消息
app.post("/api/getCommunityMessageList", async function (req, res) {
try {
let model = req.body;
if (!(model.receiverId > 0)) {
res.send(msg.error("Id不得为空"));
return;
}
let result = await getCommunityMessageList(model);
if (result.state) {
res.send(msg.sucess(result.data, "查询成功"));
} else {
res.send(msg.error("查询失败"));
}
} catch (err) {
res.send(msg.error(err.message));
}
});
// 更新用户的消息阅读状态
app.post("/api/updateCommunityContentStateById", async function (req, res) {
try {
let model = req.body;
if (!(model.receiverId > 0)) {
res.send(msg.error("Id不得为空"));
return;
}
let result = await updateCommunityContentStateById(model);
if (result.state) {
res.send(msg.sucess(result.data, "更新成功"));
} else {
res.send(msg.error("更新失败"));
}
} catch (err) {
res.send(msg.error(err.message));
}
});
// 迁移历史会话
// app.post('/api/changeHistorySession', async function (req, res) {
// try {
// let queryResult = await getUSerList(99999);
// if (queryResult.state) {
// if (queryResult.data.length > 0) {
// queryResult.data.forEach(x => {
// let historySessionList = [];
// if (x.HistorySessionList != null) {
// historySessionList = JSON.parse(x.HistorySessionList)
// }
// historySessionList.forEach(async obj => {
// let historySession = {
// FormId: obj.Id,
// Name: obj.Name,
// NickName: obj.NickName,
// PersonalitySign: obj.PersonalitySign,
// Mobile: obj.Mobile,
// Region: obj.Region,
// Avatar: obj.Avatar,
// Email: obj.Email,
// ById: x.Id,
// };
// let result2 = await insertHistorySession(historySession);
// })
// })
// }
// res.send(msg.sucess({}, '成功'))
// } else {
// res.send(msg.error("新增数据失败"))
// }
// } catch (err) {
// res.send(msg.error(err.message))
// }
// })
// 获取历史会话列表
app.post("/api/getHistorySessionById", async function (req, res) {
let { id, pageIndex, pageSize } = req.body;
let queryResult = await getHistorySession(id, pageIndex, pageSize);
if (queryResult.state) {
res.send(msg.sucess(queryResult.data, "成功"));
} else {
res.send(msg.error("获取数据失败"));
}
});
// 获取历史会话列表
app.post("/api/insertHistorySession", async function (req, res) {
try {
let params = req.body;
let queryResult = await getOneHistorySession(params.byId, params.formId);
if (queryResult.state && queryResult.data.length == 0) {
let historySession = {
FormId: params.formId,
Name: params.name,
NickName: params.nickName,
PersonalitySign: params.personalitySign || null,
Mobile: params.mobile || null,
Region: params.region || null,
Avatar: params.avatar,
Email: params.email,
ById: params.byId,
};
await insertHistorySession(historySession);
}
res.send(msg.sucess({}, "成功"));
} catch (error) {
res.send(msg.error(error.message));
}
});
// 获取会话内容
app.post("/api/getContentBySendId", async function (req, res) {
try {
let { id, pageIndex, pageSize } = req.body;
let queryResult = await getContentBySendId(id, pageIndex, pageSize);
if (queryResult.state) {
res.send(msg.sucess(queryResult.data, "成功"));
} else {
res.send(msg.error("获取数据失败"));
}
} catch (error) {
res.send(msg.error(error.message));
}
});
const server = app.listen(9527, function () {
console.log("server running on port 9527");
});
const io = socket(server, {
cors: {
origin: "*",
},
});
// 事件
io.on("connection", function (socket) {
// 加入聊天
socket.on("joinChat", async (data) => {
try {
//若该用户已登陆,将旧设备登陆的用户强制下线
let queryResult = await getUserById(data.SendId);
if (
queryResult.state &&
queryResult.data.length > 0 &&
queryResult.data[0].OnlineState
) {
socket.to(queryResult.data[0].OutTradeNo).emit("squeezeOut", {
noCode: queryResult.data[0].NoCode,
});
}
let queryResult2 = await updateUserOutTradeNoById(data.SendId, socket.id);
queryResult2 = await updateUserOnlineStateById(data.SendId, true);
queryResult2 = await updateUserNoCodeById(data.SendId, data.NoCode);
socket.emit("joinSuccess", {});
} catch (err) {
console.log(err.message);
}
});
//发送消息
socket.on("sendMsg", async (data) => {
try {
let queryResult = await getUserById(data.Conversition.ReciverId);
if (!queryResult.state) {
console.log("获取数据失败");
return;
}
let reciver = queryResult.data;
data.Conversition.State = 1; // 设置发送状态为成功
data.Conversition.CreateDateUtc = nowTime();
let result = await insertContent(data.Conversition); // 在数据库中先插入聊天内容
if (reciver.length > 0) {
socket.to(reciver[0].OutTradeNo).emit("reviceMsg", data.Conversition); // 推送
}
socket.emit("changMsgState", data.Conversition);
// 将发送者的会话存储到接收者的历史会话中
let queryResult2 = await getOneHistorySession(
data.ReciverId,
data.Sender.Id
);
if (queryResult2.state && queryResult2.data.length == 0) {
let historySession = {
FormId: data.Sender.Id,
Name: data.Sender.Name,
NickName: data.Sender.NickName,
PersonalitySign: data.Sender.PersonalitySign || null,
Mobile: data.Sender.Mobile || null,
Region: data.Sender.Region || null,
Avatar: data.Sender.Avatar,
Email: data.Sender.Email,
ById: data.ReciverId,
};
await insertHistorySession(historySession);
}
// if (reciver[0].HistorySessionList != null) {
// let historySessionList = JSON.parse(reciver[0].HistorySessionList);
// let len = historySessionList.filter((x) => x.Id == data.Sender.Id)?.length ?? 0;
// if (len === 0) {
// data.Sender.HistorySessionList = "";
// historySessionList.push(data.Sender);
// updateHistorySessionListById(JSON.stringify(historySessionList), reciver[0].Id);
// }
// } else {
// let historySessionList = [];
// data.Sender.HistorySessionList = "";
// historySessionList.push(data.Sender);
// updateHistorySessionListById(JSON.stringify(historySessionList), reciver[0].Id);
// }
} catch (err) {
console.log(err.message);
}
});
//修改信息阅读状态
socket.on("changeMsgRead", async (data) => {
try {
let queryResult = await getUnReadContent(data.SendId, data.ReciverId);
if (queryResult.state && queryResult.data.length > 0) {
queryResult.data.map((x) => {
updateContentReadFlagById(x.Id);
});
}
} catch (err) {
console.log(err.message);
}
});
socket.on("disconnect", async () => {
let queryResult = await getUserByOutTradeNo(socket.id);
if (queryResult.state && queryResult.data.length > 0) {
updateUserOnlineStateById(queryResult.data[0].Id, false);
}
});
});
马建仓 AI 助手
尝试更多
代码解读
代码找茬
代码优化
1
https://gitee.com/gao-lekang/has-chat-service.git
git@gitee.com:gao-lekang/has-chat-service.git
gao-lekang
has-chat-service
HasChatService
main

搜索帮助