在昨天基础上新增好友申请的功能:
ChatServer服务端:
1.在dbcmd.h中添加处理好友申请的函数声明:
/**
* @brief 获取用户的id
* @param username 用户名
* @param id 获取到的id
* @return 获取的结果
*/
bool getUserId(QString username, int &id);
/**
* @brief 查找用户
* @param username 自己的用户名,防止把自己找出来
* @param name
* @param list
* @return
*/
bool findUser(QString username, QString name, QJsonArray &list);
// 检查用户是否存在
bool checkUserExists(const QString &username);
// 添加好友申请
bool addFriendRequest(const QString &fromUser,
const QString &toUser, const QString &msg);
2.在dbcmd.cpp中实现:
bool DBCmd::getUserId(QString username, int &id)
{
QSqlQuery query(*db);
QString cmd;
cmd = QString("SELECT id FROM `chat_user` "
"WHERE username = '%1';")
.arg(username);
bool ok = query.exec(cmd);
if(!ok) return false;
if(!query.next()) return false;
id = query.value("id").toInt();
return true;
}
bool DBCmd::findUser(QString username, QString name, QJsonArray &list)
{
QSqlQuery query(*db);
QString cmd;
cmd = QString("SELECT cu.username, cu_info.name "
"FROM `chat_user` AS cu "
"JOIN `chat_user_info` AS cu_info "
"ON cu.id = cu_info.user_id "
"WHERE (cu_info.name LIKE '%%1%' "
"OR cu.username LIKE '%%1%') "
"AND cu.username != '%2';")
.arg(name)
.arg(username);
bool ok = query.exec(cmd);
if(!ok) return false;
while(query.next()){
QJsonObject obj;
obj.insert("username", query.value("username").toString());
obj.insert("name", query.value("name").toString());
list.append(obj);
}
return true;
}
bool DBCmd::checkUserExists(const QString &username)
{
QSqlQuery query(*db);
QString cmd = QString("SELECT id FROM `chat_user` WHERE username = '%1';")
.arg(username);
if (!query.exec(cmd)) {
return false;
}
return query.next(); // 如果有结果,返回true
}
bool DBCmd::addFriendRequest(const QString &fromUser, const QString &toUser, const QString &msg)
{
QSqlQuery query(*db);
QString date = QDateTime::currentDateTime().toString("yyyy-MM-dd hh:mm:ss.zzz");
// 获取用户ID
int fromUserId = -1;
int toUserId = -1;
// 查询发送者ID
QString cmd = QString("SELECT id FROM `chat_user` WHERE username = '%1';").arg(fromUser);
if (!query.exec(cmd) || !query.next()) {
return false;
}
fromUserId = query.value("id").toInt();
// 查询接收者ID
cmd = QString("SELECT id FROM `chat_user` WHERE username = '%1';").arg(toUser);
if (!query.exec(cmd) || !query.next()) {
return false;
}
toUserId = query.value("id").toInt();
// 插入好友申请
cmd = QString("INSERT INTO `friend_request` "
"(from_user_id, to_user_id, request_msg, create_time, status) "
"VALUES(%1, %2, '%3', '%4', 0);")
.arg(fromUserId)
.arg(toUserId)
.arg(msg)
.arg(date);
db->transaction();
bool ok = query.exec(cmd);
if (!ok || query.numRowsAffected() <= 0) {
db->rollback();
return false;
}
db->commit();
return true;
}
3.在mytcpsocket.h中添加处理好友申请的函数声明:
// 在class MyTcpSocket的protected部分添加
void handleFindUser(const QJsonObject &obj);
void handleAddFriend(const QJsonObject &obj);
4.在mytcpsocket.cpp中实现:
// 在handleFrame函数的switch语句中添加
case 2101:
handleFindUser(obj);
break;
case 2102:
handleAddFriend(obj);
break;
void MyTcpSocket::handleFindUser(const QJsonObject &obj)
{
QString name = obj.value("name").toString();
QJsonArray list;
DBCmd *cmd = DBExec::getObject()->getCmd();
bool ok = cmd->findUser(
username, name, list);
DBExec::getObject()->releaseCmd(cmd);
QJsonObject reObj;
reObj.insert("type", 2101);
reObj.insert("list", list);
write(QJsonDocument(reObj).toJson());
}
void MyTcpSocket::handleAddFriend(const QJsonObject &obj)
{
QString targetUsername = obj.value("username").toString();
QString requestMsg = obj.value("request_msg").toString();
// 验证目标用户是否存在
DBCmd *cmd = DBExec::getObject()->getCmd();
bool userExists = cmd->checkUserExists(targetUsername);
bool ok = false;
if (userExists) {
// 发送好友申请(保存到数据库)
ok = cmd->addFriendRequest(username, targetUsername, requestMsg);
}
DBExec::getObject()->releaseCmd(cmd);
// 构建反馈消息
QJsonObject reObj;
reObj.insert("type", 2102);
reObj.insert("re", ok);
write(QJsonDocument(reObj).toJson());
}
二、ChatClient客户端
1.在netexec.h中添加发送好友申请的函数声明和反馈信号:
// 在Net/netexec.h的public部分添加
/**
* @brief findUser 查找用户
* @param name
*/
void findUser(QString name);
/**
* @brief 发送好友申请
* @param username 目标用户名
* @param requestMsg 申请信息
*/
void sendFriendRequest(QString username, QString requestMsg);
// 在signals部分添加
void findUserReveived(QJsonArray list);
// 好友申请反馈信号
void friendRequestStatus(bool re);
//在protected部分添加
void handleFindUserRe(const QJsonObject &obj);
void handleFriendRequestRe(const QJsonObject &obj);
2.在netexec.cpp中实现查找好友,发送好友申请的函数和处理反馈的逻辑:
void NetExec::findUser(QString name)
{
QJsonObject obj;
obj.insert("type", 2101);
obj.insert("key", key);
obj.insert("name", name);
m_client->write(QJsonDocument(obj).toJson());
}
void NetExec::sendFriendRequest(QString username, QString requestMsg)
{
QJsonObject obj;
obj.insert("type", 2102); // 协议规定的类型
obj.insert("key", key); // 当前用户的密钥
obj.insert("username", username); // 目标好友用户名
obj.insert("request_msg", requestMsg); // 申请信息
m_client->write(QJsonDocument(obj).toJson());
}
// 在handleFrame函数的switch-case中添加对2102类型反馈的处理
case 2101:
handleFindUserRe(obj);
break;
case 2102:
handleFriendRequestRe(obj);
break;
void NetExec::handleFindUserRe(const QJsonObject &obj)
{
QJsonArray list = obj.value("list").toArray();
emit findUserReveived(list);
}
void NetExec::handleFriendRequestRe(const QJsonObject &obj)
{
bool re = obj.value("re").toBool();
emit friendRequestStatus(re);
}
3.在addfriendpage.h中添加处理好友申请反馈的槽函数声明:
// 在private slots部分添加
void onFriendRequestStatus(bool re);
4.在addfriendpage.cpp中完善双击列表项发送好友申请的功能:
// 包含QInputDialog头文件
#include <QInputDialog>
#include <QMessageBox>
// 在构造函数中添加信号连接
AddFriendPage::AddFriendPage(QWidget *parent)
: QWidget(parent)
, ui(new Ui::AddFriendPage)
{
ui->setupUi(this);
connect(NetExec::getObject(), &NetExec::findUserReveived,
this, &AddFriendPage::findUserReveivedSlot);
// 连接好友申请反馈信号
connect(NetExec::getObject(), &NetExec::friendRequestStatus,
this, &AddFriendPage::onFriendRequestStatus);
}
void AddFriendPage::onFriendRequestStatus(bool re)
{
if (re) {
QMessageBox::information(this, tr("提示"), tr("好友申请已发送!"));
} else {
QMessageBox::warning(this, tr("提示"), tr("好友申请发送失败!"));
}
}
void AddFriendPage::on_listWidget_itemDoubleClicked(QListWidgetItem *item)
{
QString text = item->text();
QString username = text.split('-').at(0);
//QInputDialog 输入申请信息
bool ok;
QString requestMsg = QInputDialog::getText(
this,
tr("添加好友"),
tr("请输入申请信息:"),
QLineEdit::Normal,
tr("我想加你为好友"),
&ok
);
if (ok && !requestMsg.isEmpty()) {
// 发送好友申请
NetExec::getObject()->sendFriendRequest(username, requestMsg);
}
}
8319

被折叠的 条评论
为什么被折叠?



