From 7ce3253ea5ac155e69e0b67e5e8ae016939af617 Mon Sep 17 00:00:00 2001 From: chenshuzhiyi <15782136+chenshuzhiyi@user.noreply.gitee.com> Date: Thu, 25 Sep 2025 10:30:14 +0800 Subject: [PATCH 1/9] =?UTF-8?q?=E5=AD=98=E6=A1=A3?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/server/gamelogic/rpc-dispatchers.cpp | 81 ++++++++++++++++++++++++ src/server/server.cpp | 5 ++ src/server/server.h | 2 + src/server/user/player.cpp | 48 ++++++++++++++ src/server/user/player.h | 10 +++ 5 files changed, 146 insertions(+) diff --git a/src/server/gamelogic/rpc-dispatchers.cpp b/src/server/gamelogic/rpc-dispatchers.cpp index e3cbedb..a8136d8 100644 --- a/src/server/gamelogic/rpc-dispatchers.cpp +++ b/src/server/gamelogic/rpc-dispatchers.cpp @@ -379,6 +379,83 @@ static _rpcRet _rpc_Room_decreaseRefCount(const JsonRpcPacket &packet) { return { true, nullVal }; } +static _rpcRet _rpc_Player_saveState(const JsonRpcPacket &packet) { + if (!(packet.param_count == 2 && + std::holds_alternative(packet.param1) && + std::holds_alternative(packet.param2) + )) { + return { false, nullVal }; + } + + auto connId = std::get(packet.param1); + auto jsonData = std::get(packet.param2); + + auto player = Server::instance().user_manager().findPlayerByConnId(connId).lock(); + if (!player) { + return { false, nullVal }; + } + + player->saveState(jsonData); + return { true, nullVal }; +} + +static _rpcRet _rpc_Player_getSaveState(const JsonRpcPacket &packet) { + if (!(packet.param_count == 1 && + std::holds_alternative(packet.param1) + )) { + return { false, nullVal }; + } + + auto connId = std::get(packet.param1); + + auto player = Server::instance().user_manager().findPlayerByConnId(connId).lock(); + if (!player) { + return { false, nullVal }; + } + + std::string result = player->getSaveState(); + return { true, result }; +} + +static _rpcRet _rpc_Player_saveGlobalState(const JsonRpcPacket &packet) { + if (!(packet.param_count == 2 && + std::holds_alternative(packet.param1) && + std::holds_alternative(packet.param2) + )) { + return { false, nullVal }; + } + + auto connId = std::get(packet.param1); + auto jsonData = std::get(packet.param2); + + auto player = Server::instance().user_manager().findPlayerByConnId(connId).lock(); + if (!player) { + return { false, nullVal }; + } + + player->saveGlobalState(jsonData); + return { true, nullVal }; +} + +static _rpcRet _rpc_Player_getGlobalSaveState(const JsonRpcPacket &packet) { + if (!(packet.param_count == 1 && + std::holds_alternative(packet.param1) + )) { + return { false, nullVal }; + } + + auto connId = std::get(packet.param1); + + auto player = Server::instance().user_manager().findPlayerByConnId(connId).lock(); + if (!player) { + return { false, nullVal }; + } + + std::string result = player->getGlobalSaveState(); + return { true, result }; +} + + // 收官:getRoom std::string RpcDispatchers::getPlayerObject(Player &p) { @@ -499,6 +576,10 @@ const JsonRpc::RpcMethodMap RpcDispatchers::ServerRpcMethods { { "ServerPlayer_setThinking", _rpc_Player_setThinking }, { "ServerPlayer_setDied", _rpc_Player_setDied }, { "ServerPlayer_emitKick", _rpc_Player_emitKick }, + { "ServerPlayer_saveState", _rpc_Player_saveState }, + { "ServerPlayer_getSaveState", _rpc_Player_getSaveState }, + { "ServerPlayer_saveGlobalState", _rpc_Player_saveGlobalState }, + { "ServerPlayer_getGlobalSaveState", _rpc_Player_getGlobalSaveState }, { "Room_delay", _rpc_Room_delay }, { "Room_updatePlayerWinRate", _rpc_Room_updatePlayerWinRate }, diff --git a/src/server/server.cpp b/src/server/server.cpp index 145574b..a3cdeb1 100644 --- a/src/server/server.cpp +++ b/src/server/server.cpp @@ -36,6 +36,7 @@ Server::Server() : m_socket { nullptr } { main_thread_id = std::this_thread::get_id(); db = std::make_unique(); + gamedb = std::make_unique("./server/game.db", "./server/gamedb_init.sql"); // 初始化 reloadConfig(); refreshMd5(); @@ -116,6 +117,10 @@ Sqlite3 &Server::database() { return *db; } +Sqlite3 &Server::gameDatabase() { + return *gamedb; +} + Shell &Server::shell() { return *m_shell; } diff --git a/src/server/server.h b/src/server/server.h index 16abde0..ddbab8c 100644 --- a/src/server/server.h +++ b/src/server/server.h @@ -51,6 +51,7 @@ public: UserManager &user_manager(); RoomManager &room_manager(); Sqlite3 &database(); + Sqlite3 &gameDatabase(); // gamedb的getter Shell &shell(); void sendEarlyPacket(ClientSocket &client, const std::string_view &type, const std::string_view &msg); @@ -88,6 +89,7 @@ private: std::unique_ptr m_socket; std::unique_ptr db; + std::unique_ptr gamedb; // 存档变量 std::mutex transaction_mutex; std::unordered_map> m_threads; diff --git a/src/server/user/player.cpp b/src/server/user/player.cpp index 8557338..9da8df6 100644 --- a/src/server/user/player.cpp +++ b/src/server/user/player.cpp @@ -384,3 +384,51 @@ void Player::onReadyChanged() { room->doBroadcastNotify(room->getPlayers(), "ReadyChanged", Cbor::encodeArray({ id, ready })); } + +void Player::saveState(std::string_view jsonData) { + auto room = getRoom().lock(); + if (!room) return; + std::string mode = room->getGameMode(); + writeSaveState(mode, jsonData); +} + +std::string Player::getSaveState() { + auto room = getRoom().lock(); + if (!room) return "{}"; + std::string mode = room->getGameMode(); + return readSaveState(mode); +} + +void Player::saveGlobalState(std::string_view jsonData) { + writeSaveState("__global__", jsonData); +} + +std::string Player::getGlobalSaveState() { + return readSaveState("__global__"); +} + +void Player::writeSaveState(std::string mode, std::string_view jsonData) { + if (!Sqlite3::checkString(mode)) return; + if (!Sqlite3::checkString(jsonData)) return; + + std::string hexData = toHex(jsonData); + std::string sql = "REPLACE INTO game_saves (uid, mode, data) VALUES (" + + std::to_string(id) + ",'" + mode + "',X'" + hexData + "')"; + + Server::instance().gameDatabase().exec(sql); +} + +std::string Player::readSaveState(std::string mode) { + if (!Sqlite3::checkString(mode)) return "{}"; + + std::string sql = "SELECT data FROM game_saves WHERE uid = " + + std::to_string(id) + " AND mode = '" + mode + "'"; + + auto result = Server::instance().gameDatabase().select(sql); + if (result.empty() || result[0].count("data") == 0) { + return "{}"; + } + + // 注意这里认为data是JSON字符串 + return result[0]["data"]; +} \ No newline at end of file diff --git a/src/server/user/player.h b/src/server/user/player.h index 8c842fa..1b75195 100644 --- a/src/server/user/player.h +++ b/src/server/user/player.h @@ -96,6 +96,13 @@ public: void resumeGameTimer(); int getGameTime(); + // 模式存档 + void saveState(std::string_view jsonData); + std::string getSaveState(); + // 全局存档 + void saveGlobalState(std::string_view jsonData); + std::string getGlobalSaveState(); + private: int id = 0; std::string screenName; // screenName should not be same. @@ -125,4 +132,7 @@ private: int64_t gameTime = 0; // 在这个房间的有效游戏时长(秒) int64_t gameTimerStartTimestamp; + + void writeSaveState(std::string mode, std::string_view jsonData); + std::string readSaveState(std::string mode); }; -- Gitee From 970693d483aabb03f44dfe0a3b1a23713910b75d Mon Sep 17 00:00:00 2001 From: chenshuzhiyi <15782136+chenshuzhiyi@user.noreply.gitee.com> Date: Thu, 25 Sep 2025 10:52:41 +0800 Subject: [PATCH 2/9] fix --- src/server/user/player.cpp | 75 +++++++++++++++++++++++++++++--------- 1 file changed, 57 insertions(+), 18 deletions(-) diff --git a/src/server/user/player.cpp b/src/server/user/player.cpp index 9da8df6..8496096 100644 --- a/src/server/user/player.cpp +++ b/src/server/user/player.cpp @@ -386,14 +386,18 @@ void Player::onReadyChanged() { } void Player::saveState(std::string_view jsonData) { - auto room = getRoom().lock(); + auto room_base = getRoom().lock(); + if (!room_base) return; + auto room = dynamic_pointer_cast(room_base); if (!room) return; std::string mode = room->getGameMode(); writeSaveState(mode, jsonData); } std::string Player::getSaveState() { - auto room = getRoom().lock(); + auto room_base = getRoom().lock(); + if (!room_base) return "{}"; + auto room = dynamic_pointer_cast(room_base); if (!room) return "{}"; std::string mode = room->getGameMode(); return readSaveState(mode); @@ -408,27 +412,62 @@ std::string Player::getGlobalSaveState() { } void Player::writeSaveState(std::string mode, std::string_view jsonData) { - if (!Sqlite3::checkString(mode)) return; - if (!Sqlite3::checkString(jsonData)) return; - - std::string hexData = toHex(jsonData); - std::string sql = "REPLACE INTO game_saves (uid, mode, data) VALUES (" + - std::to_string(id) + ",'" + mode + "',X'" + hexData + "')"; + if (!Sqlite3::checkString(mode)) { + spdlog::error("Invalid mode string for saveState: {}", mode); + return; + } + if (!Sqlite3::checkString(jsonData)) { + spdlog::error("Invalid jsonData string for saveState"); + return; + } - Server::instance().gameDatabase().exec(sql); + try { + std::string hexData = toHex(jsonData); + // 确保数据一致 + Server::instance().gameDatabase().exec("BEGIN TRANSACTION;"); + + std::string sql = "REPLACE INTO game_saves (uid, mode, data) VALUES (" + + std::to_string(id) + ",'" + mode + "',X'" + hexData + "')"; + + // 检查 + if (!Server::instance().gameDatabase().exec(sql)) { + spdlog::error("Failed to execute saveState SQL: {}", sql); + Server::instance().gameDatabase().exec("ROLLBACK;"); + return; + } + + Server::instance().gameDatabase().exec("COMMIT;"); + } catch (const std::exception &e) { + spdlog::error("Exception in saveState: {}", e.what()); + Server::instance().gameDatabase().exec("ROLLBACK;"); + } } std::string Player::readSaveState(std::string mode) { - if (!Sqlite3::checkString(mode)) return "{}"; - - std::string sql = "SELECT data FROM game_saves WHERE uid = " + - std::to_string(id) + " AND mode = '" + mode + "'"; - - auto result = Server::instance().gameDatabase().select(sql); - if (result.empty() || result[0].count("data") == 0) { + if (!Sqlite3::checkString(mode)) { + spdlog::error("Invalid mode string for readSaveState: {}", mode); return "{}"; } - // 注意这里认为data是JSON字符串 - return result[0]["data"]; + try { + std::string sql = "SELECT data FROM game_saves WHERE uid = " + + std::to_string(id) + " AND mode = '" + mode + "'"; + + auto result = Server::instance().gameDatabase().select(sql); + if (result.empty() || result[0].count("data") == 0 || result[0]["data"] == "#null") { + return "{}"; + } + + // 简单验证 + const std::string& data = result[0]["data"]; + if (!data.empty() && (data[0] == '{' || data[0] == '[')) { + return data; + } + + spdlog::warn("Returned data is not valid JSON: {}", data.substr(0, 50)); + return "{}"; + } catch (const std::exception &e) { + spdlog::error("Exception in readSaveState: {}", e.what()); + return "{}"; + } } \ No newline at end of file -- Gitee From 57d191edf5daa597c0cbe950699b716eeabd8cb7 Mon Sep 17 00:00:00 2001 From: chenshuzhiyi <15782136+chenshuzhiyi@user.noreply.gitee.com> Date: Thu, 25 Sep 2025 10:59:06 +0800 Subject: [PATCH 3/9] 2 --- src/server/user/player.cpp | 21 +++++++++------------ 1 file changed, 9 insertions(+), 12 deletions(-) diff --git a/src/server/user/player.cpp b/src/server/user/player.cpp index 8496096..b0bc736 100644 --- a/src/server/user/player.cpp +++ b/src/server/user/player.cpp @@ -390,7 +390,7 @@ void Player::saveState(std::string_view jsonData) { if (!room_base) return; auto room = dynamic_pointer_cast(room_base); if (!room) return; - std::string mode = room->getGameMode(); + std::string mode(room->getGameMode()); writeSaveState(mode, jsonData); } @@ -399,7 +399,7 @@ std::string Player::getSaveState() { if (!room_base) return "{}"; auto room = dynamic_pointer_cast(room_base); if (!room) return "{}"; - std::string mode = room->getGameMode(); + std::string mode(room->getGameMode()); return readSaveState(mode); } @@ -425,21 +425,18 @@ void Player::writeSaveState(std::string mode, std::string_view jsonData) { std::string hexData = toHex(jsonData); // 确保数据一致 Server::instance().gameDatabase().exec("BEGIN TRANSACTION;"); - + std::string sql = "REPLACE INTO game_saves (uid, mode, data) VALUES (" + std::to_string(id) + ",'" + mode + "',X'" + hexData + "')"; - - // 检查 - if (!Server::instance().gameDatabase().exec(sql)) { - spdlog::error("Failed to execute saveState SQL: {}", sql); - Server::instance().gameDatabase().exec("ROLLBACK;"); - return; - } - + + Server::instance().gameDatabase().exec(sql); Server::instance().gameDatabase().exec("COMMIT;"); } catch (const std::exception &e) { spdlog::error("Exception in saveState: {}", e.what()); - Server::instance().gameDatabase().exec("ROLLBACK;"); + try { + Server::instance().gameDatabase().exec("ROLLBACK;"); + } catch (...) { + } } } -- Gitee From 02f7054b55a2fc7e63a5c54a18282ce4d4d40acc Mon Sep 17 00:00:00 2001 From: chenshuzhiyi <15782136+chenshuzhiyi@user.noreply.gitee.com> Date: Thu, 25 Sep 2025 11:42:19 +0800 Subject: [PATCH 4/9] =?UTF-8?q?=E7=96=91=E4=BC=BC=E6=88=90=E4=BA=8B?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .gitignore | 1 + server/gamedb_init.sql | 12 ++++++++++++ src/server/user/player.cpp | 8 ++++---- 3 files changed, 17 insertions(+), 4 deletions(-) create mode 100644 server/gamedb_init.sql diff --git a/.gitignore b/.gitignore index 22f9e8e..bc14de9 100644 --- a/.gitignore +++ b/.gitignore @@ -18,6 +18,7 @@ /freekill-asio /server/* !/server/init.sql +!/server/gamedb_init.sql /freekill.server.config.json /freekill.server.*log /freekill.*log diff --git a/server/gamedb_init.sql b/server/gamedb_init.sql new file mode 100644 index 0000000..2b56239 --- /dev/null +++ b/server/gamedb_init.sql @@ -0,0 +1,12 @@ +-- SPDX-License-Identifier: GPL-3.0-or-later + +CREATE TABLE IF NOT EXISTS game_saves ( + id INTEGER PRIMARY KEY AUTOINCREMENT, + uid INTEGER NOT NULL, + mode TEXT NOT NULL, + data BLOB NOT NULL, + UNIQUE(uid, mode) +); + +CREATE INDEX IF NOT EXISTS idx_game_saves_uid ON game_saves(uid); +CREATE INDEX IF NOT EXISTS idx_game_saves_mode ON game_saves(mode); \ No newline at end of file diff --git a/src/server/user/player.cpp b/src/server/user/player.cpp index b0bc736..3e51c54 100644 --- a/src/server/user/player.cpp +++ b/src/server/user/player.cpp @@ -416,10 +416,10 @@ void Player::writeSaveState(std::string mode, std::string_view jsonData) { spdlog::error("Invalid mode string for saveState: {}", mode); return; } - if (!Sqlite3::checkString(jsonData)) { - spdlog::error("Invalid jsonData string for saveState"); - return; - } + // if (!Sqlite3::checkString(jsonData)) { + // spdlog::error("Invalid jsonData string for saveState"); + // return; + // } try { std::string hexData = toHex(jsonData); -- Gitee From 2205a6181bd65b90633da0d3383546fb53cd495d Mon Sep 17 00:00:00 2001 From: chenshuzhiyi <15782136+chenshuzhiyi@user.noreply.gitee.com> Date: Thu, 25 Sep 2025 23:23:02 +0800 Subject: [PATCH 5/9] fix --- server/gamedb_init.sql | 6 ++-- src/server/user/player.cpp | 66 +++++++++++++------------------------- 2 files changed, 26 insertions(+), 46 deletions(-) diff --git a/server/gamedb_init.sql b/server/gamedb_init.sql index 2b56239..73fb98b 100644 --- a/server/gamedb_init.sql +++ b/server/gamedb_init.sql @@ -1,6 +1,6 @@ -- SPDX-License-Identifier: GPL-3.0-or-later -CREATE TABLE IF NOT EXISTS game_saves ( +CREATE TABLE IF NOT EXISTS gameSaves ( id INTEGER PRIMARY KEY AUTOINCREMENT, uid INTEGER NOT NULL, mode TEXT NOT NULL, @@ -8,5 +8,5 @@ CREATE TABLE IF NOT EXISTS game_saves ( UNIQUE(uid, mode) ); -CREATE INDEX IF NOT EXISTS idx_game_saves_uid ON game_saves(uid); -CREATE INDEX IF NOT EXISTS idx_game_saves_mode ON game_saves(mode); \ No newline at end of file +CREATE INDEX IF NOT EXISTS idx_gameSaves_uid ON gameSaves(uid); +CREATE INDEX IF NOT EXISTS idx_gameSaves_mode ON gameSaves(mode); \ No newline at end of file diff --git a/src/server/user/player.cpp b/src/server/user/player.cpp index 3e51c54..e335260 100644 --- a/src/server/user/player.cpp +++ b/src/server/user/player.cpp @@ -390,7 +390,7 @@ void Player::saveState(std::string_view jsonData) { if (!room_base) return; auto room = dynamic_pointer_cast(room_base); if (!room) return; - std::string mode(room->getGameMode()); + auto mode = room->getGameMode(); writeSaveState(mode, jsonData); } @@ -399,7 +399,7 @@ std::string Player::getSaveState() { if (!room_base) return "{}"; auto room = dynamic_pointer_cast(room_base); if (!room) return "{}"; - std::string mode(room->getGameMode()); + auto mode = room->getGameMode(); return readSaveState(mode); } @@ -416,28 +416,15 @@ void Player::writeSaveState(std::string mode, std::string_view jsonData) { spdlog::error("Invalid mode string for saveState: {}", mode); return; } - // if (!Sqlite3::checkString(jsonData)) { - // spdlog::error("Invalid jsonData string for saveState"); - // return; - // } - - try { - std::string hexData = toHex(jsonData); - // 确保数据一致 - Server::instance().gameDatabase().exec("BEGIN TRANSACTION;"); - - std::string sql = "REPLACE INTO game_saves (uid, mode, data) VALUES (" + - std::to_string(id) + ",'" + mode + "',X'" + hexData + "')"; - - Server::instance().gameDatabase().exec(sql); - Server::instance().gameDatabase().exec("COMMIT;"); - } catch (const std::exception &e) { - spdlog::error("Exception in saveState: {}", e.what()); - try { - Server::instance().gameDatabase().exec("ROLLBACK;"); - } catch (...) { - } - } + + auto hexData = toHex(jsonData); + auto &gamedb = Server::instance().gameDatabase(); + auto sql = fmt::format("REPLACE INTO gameSaves (uid, mode, data) VALUES ({},'{}',X'{}')", id, mode, hexData); + + gamedb.exec("BEGIN TRANSACTION;"); + + gamedb.exec(sql); + gamedb.exec("COMMIT;"); } std::string Player::readSaveState(std::string mode) { @@ -446,25 +433,18 @@ std::string Player::readSaveState(std::string mode) { return "{}"; } - try { - std::string sql = "SELECT data FROM game_saves WHERE uid = " + - std::to_string(id) + " AND mode = '" + mode + "'"; - - auto result = Server::instance().gameDatabase().select(sql); - if (result.empty() || result[0].count("data") == 0 || result[0]["data"] == "#null") { - return "{}"; - } - - // 简单验证 - const std::string& data = result[0]["data"]; - if (!data.empty() && (data[0] == '{' || data[0] == '[')) { - return data; - } - - spdlog::warn("Returned data is not valid JSON: {}", data.substr(0, 50)); - return "{}"; - } catch (const std::exception &e) { - spdlog::error("Exception in readSaveState: {}", e.what()); + auto sql = fmt::format("SELECT data FROM gameSaves WHERE uid = {} AND mode = '{}'", id, mode); + + auto result = Server::instance().gameDatabase().select(sql); + if (result.empty() || result[0].count("data") == 0 || result[0]["data"] == "#null") { return "{}"; } + + const auto& data = result[0]["data"]; + if (!data.empty() && (data[0] == '{' || data[0] == '[')) { + return data; + } + + spdlog::warn("Returned data is not valid JSON: {}", data.substr(0, 50)); + return "{}"; } \ No newline at end of file -- Gitee From 704b736c5fa956d5e1f5b377418c355907772737 Mon Sep 17 00:00:00 2001 From: chenshuzhiyi <15782136+chenshuzhiyi@user.noreply.gitee.com> Date: Fri, 26 Sep 2025 00:27:04 +0800 Subject: [PATCH 6/9] fix --- src/server/user/player.cpp | 4 ++-- src/server/user/player.h | 4 ++-- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/src/server/user/player.cpp b/src/server/user/player.cpp index e335260..42736c8 100644 --- a/src/server/user/player.cpp +++ b/src/server/user/player.cpp @@ -411,7 +411,7 @@ std::string Player::getGlobalSaveState() { return readSaveState("__global__"); } -void Player::writeSaveState(std::string mode, std::string_view jsonData) { +void Player::writeSaveState(std::string_view mode, std::string_view jsonData) { if (!Sqlite3::checkString(mode)) { spdlog::error("Invalid mode string for saveState: {}", mode); return; @@ -427,7 +427,7 @@ void Player::writeSaveState(std::string mode, std::string_view jsonData) { gamedb.exec("COMMIT;"); } -std::string Player::readSaveState(std::string mode) { +std::string Player::readSaveState(std::string_view mode) { if (!Sqlite3::checkString(mode)) { spdlog::error("Invalid mode string for readSaveState: {}", mode); return "{}"; diff --git a/src/server/user/player.h b/src/server/user/player.h index 1b75195..0860156 100644 --- a/src/server/user/player.h +++ b/src/server/user/player.h @@ -133,6 +133,6 @@ private: int64_t gameTime = 0; // 在这个房间的有效游戏时长(秒) int64_t gameTimerStartTimestamp; - void writeSaveState(std::string mode, std::string_view jsonData); - std::string readSaveState(std::string mode); + void writeSaveState(std::string_view mode, std::string_view jsonData); + std::string readSaveState(std::string_view mode); }; -- Gitee From aa84df3f55709c9f115c4371e848e78eec292794 Mon Sep 17 00:00:00 2001 From: chenshuzhiyi <15782136+chenshuzhiyi@user.noreply.gitee.com> Date: Fri, 26 Sep 2025 00:56:42 +0800 Subject: [PATCH 7/9] 1 --- src/server/user/player.cpp | 8 ++++---- src/server/user/player.h | 4 ++-- 2 files changed, 6 insertions(+), 6 deletions(-) diff --git a/src/server/user/player.cpp b/src/server/user/player.cpp index 42736c8..db7ee61 100644 --- a/src/server/user/player.cpp +++ b/src/server/user/player.cpp @@ -390,7 +390,7 @@ void Player::saveState(std::string_view jsonData) { if (!room_base) return; auto room = dynamic_pointer_cast(room_base); if (!room) return; - auto mode = room->getGameMode(); + std::string mode(room->getGameMode()); writeSaveState(mode, jsonData); } @@ -399,7 +399,7 @@ std::string Player::getSaveState() { if (!room_base) return "{}"; auto room = dynamic_pointer_cast(room_base); if (!room) return "{}"; - auto mode = room->getGameMode(); + std::string mode(room->getGameMode()); return readSaveState(mode); } @@ -411,7 +411,7 @@ std::string Player::getGlobalSaveState() { return readSaveState("__global__"); } -void Player::writeSaveState(std::string_view mode, std::string_view jsonData) { +void Player::writeSaveState(std::string mode, std::string_view jsonData) { if (!Sqlite3::checkString(mode)) { spdlog::error("Invalid mode string for saveState: {}", mode); return; @@ -427,7 +427,7 @@ void Player::writeSaveState(std::string_view mode, std::string_view jsonData) { gamedb.exec("COMMIT;"); } -std::string Player::readSaveState(std::string_view mode) { +std::string Player::readSaveState(std::string mode) { if (!Sqlite3::checkString(mode)) { spdlog::error("Invalid mode string for readSaveState: {}", mode); return "{}"; diff --git a/src/server/user/player.h b/src/server/user/player.h index 0860156..1b75195 100644 --- a/src/server/user/player.h +++ b/src/server/user/player.h @@ -133,6 +133,6 @@ private: int64_t gameTime = 0; // 在这个房间的有效游戏时长(秒) int64_t gameTimerStartTimestamp; - void writeSaveState(std::string_view mode, std::string_view jsonData); - std::string readSaveState(std::string_view mode); + void writeSaveState(std::string mode, std::string_view jsonData); + std::string readSaveState(std::string mode); }; -- Gitee From 3e9b45fecc504b5c52d20381fe5d4c25e7e300a2 Mon Sep 17 00:00:00 2001 From: chenshuzhiyi <15782136+chenshuzhiyi@user.noreply.gitee.com> Date: Fri, 26 Sep 2025 01:15:25 +0800 Subject: [PATCH 8/9] 2 --- src/server/user/player.cpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/server/user/player.cpp b/src/server/user/player.cpp index db7ee61..5a8b157 100644 --- a/src/server/user/player.cpp +++ b/src/server/user/player.cpp @@ -390,7 +390,7 @@ void Player::saveState(std::string_view jsonData) { if (!room_base) return; auto room = dynamic_pointer_cast(room_base); if (!room) return; - std::string mode(room->getGameMode()); + std::string mode { room->getGameMode() }; writeSaveState(mode, jsonData); } @@ -399,7 +399,7 @@ std::string Player::getSaveState() { if (!room_base) return "{}"; auto room = dynamic_pointer_cast(room_base); if (!room) return "{}"; - std::string mode(room->getGameMode()); + std::string mode { room->getGameMode() }; return readSaveState(mode); } -- Gitee From 405af53855fb3cee09150eba7b1a3cab0e520ba4 Mon Sep 17 00:00:00 2001 From: chenshuzhiyi <15782136+chenshuzhiyi@user.noreply.gitee.com> Date: Fri, 26 Sep 2025 01:42:11 +0800 Subject: [PATCH 9/9] =?UTF-8?q?=E6=94=B6=E5=B7=A5?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/server/user/player.cpp | 7 ++----- 1 file changed, 2 insertions(+), 5 deletions(-) diff --git a/src/server/user/player.cpp b/src/server/user/player.cpp index 5a8b157..8679e26 100644 --- a/src/server/user/player.cpp +++ b/src/server/user/player.cpp @@ -421,10 +421,7 @@ void Player::writeSaveState(std::string mode, std::string_view jsonData) { auto &gamedb = Server::instance().gameDatabase(); auto sql = fmt::format("REPLACE INTO gameSaves (uid, mode, data) VALUES ({},'{}',X'{}')", id, mode, hexData); - gamedb.exec("BEGIN TRANSACTION;"); - - gamedb.exec(sql); - gamedb.exec("COMMIT;"); + gamedb.exec(sql);; } std::string Player::readSaveState(std::string mode) { @@ -445,6 +442,6 @@ std::string Player::readSaveState(std::string mode) { return data; } - spdlog::warn("Returned data is not valid JSON: {}", data.substr(0, 50)); + spdlog::warn("Returned data is not valid JSON: {}", data); return "{}"; } \ No newline at end of file -- Gitee