Skip to content

Commit a538d58

Browse files
fixed global shutdown
1 parent d02a192 commit a538d58

8 files changed

Lines changed: 259 additions & 59 deletions

File tree

include/game/GameLogic.hpp

Lines changed: 8 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -100,22 +100,29 @@ class GameLogic : public LogicCore
100100
void OnPlayerDisconnected(uint64_t sessionId);
101101

102102
// Broadcasting
103+
void BroadcastPlayerUpdates();
103104
void BroadcastToNearbyPlayers(const glm::vec3& position, uint16_t messageType,
104105
const std::vector<uint8_t>& data, float radius = 50.0f);
105106
void BroadcastToNearbyOnlinePlayers(const glm::vec3& position, uint16_t messageType,
106107
const std::vector<uint8_t>& data, float radius = 50.0f);
107108
void SyncNearbyEntitiesToPlayer(uint64_t sessionId, const glm::vec3& position);
108109

109110
// Helper broadcast methods
111+
void BroadcastToNearbyPlayersJson(const glm::vec3& position, const nlohmann::json& message, float radius);
110112
void BroadcastToAllPlayers(const nlohmann::json& message);
111113
void BroadcastToAllPlayersBinary(uint16_t messageType, const std::vector<uint8_t>& data);
112114
void BroadcastToPlayers(const std::vector<uint64_t>& sessionIds, const nlohmann::json& message);
115+
void BroadcastPlayerState(uint64_t playerId, const ServerState& state);
116+
void BroadcastPlayerSpawn(uint64_t playerId);
117+
void BroadcastPlayerDespawn(uint64_t playerId, const glm::vec3& lastPosition);
118+
void BroadcastPlayerSpawnJson(uint64_t playerId);
119+
void BroadcastPlayerDespawnJson(uint64_t playerId, const glm::vec3& lastPosition);
120+
void BroadcastPlayerUpdatesJson();
113121

114122
// Broadcast entity spawn to nearby players
115123
void BroadcastEntitySpawn(uint64_t entityId, EntityType type, const glm::vec3& position,
116124
float yaw, const std::string& name);
117125
void SendPositionCorrection(uint64_t sessionId, const glm::vec3& position, const glm::vec3& velocity);
118-
void BroadcastPlayerState(uint64_t playerId, const ServerState& state);
119126
void BroadcastEntityDespawn(uint64_t entityId, const glm::vec3& position);
120127

121128
void HandleAuthentication(uint64_t sessionId, const std::vector<uint8_t>& data);

include/network/BinaryProtocol.hpp

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -42,7 +42,10 @@ namespace BinaryProtocol {
4242
MESSAGE_TYPE_PLAYER_ROTATION = 302,
4343
MESSAGE_TYPE_PLAYER_STATE = 303,
4444
MESSAGE_TYPE_PLAYER_POSITION_CORRECTION = 304,
45-
45+
MESSAGE_TYPE_PLAYER_UPDATE = 305,
46+
MESSAGE_TYPE_PLAYER_SPAWN = 306,
47+
MESSAGE_TYPE_PLAYER_DESPAWN = 307,
48+
4649
// NPC messages
4750
MESSAGE_TYPE_NPC_SPAWN = 400,
4851
MESSAGE_TYPE_NPC_UPDATE = 401,

include/network/GameServer.hpp

Lines changed: 3 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -28,22 +28,20 @@ class GameServer {
2828
void Run();
2929
void Shutdown();
3030

31-
// For binary protocol
31+
asio::io_context& GetIoContext() { return ioContext_; }
32+
3233
using SessionFactory = std::function<std::shared_ptr<GameSession>(asio::ip::tcp::socket, std::shared_ptr<asio::ssl::context>)>;
3334
void SetSessionFactory(SessionFactory factory);
3435

35-
// For WebSocket protocol
3636
using WebSocketFactory = std::function<WebSocketProtocol::WebSocketConnection::Pointer(asio::ip::tcp::socket, std::shared_ptr<asio::ssl::context>)>;
3737
void SetWebSocketConnectionFactory(WebSocketFactory factory);
3838

3939
private:
4040
void DoAccept();
4141
void StartWorkerThreads();
42-
void SetupSignalHandlers();
4342

4443
asio::io_context ioContext_;
4544
asio::ip::tcp::acceptor acceptor_;
46-
asio::signal_set signals_;
4745

4846
WorkerGroupConfig groupConfig_;
4947
const ConfigManager& globalConfig_;
@@ -56,7 +54,7 @@ class GameServer {
5654
std::vector<std::thread> workerThreads_;
5755
std::atomic<bool> running_{false};
5856

59-
std::shared_ptr<asio::ssl::context> sslContext_; // optional, set if SSL is configured
57+
std::shared_ptr<asio::ssl::context> sslContext_;
6058

6159
SessionFactory sessionFactory_;
6260
WebSocketFactory webSocketFactory_;

src/database/SQLiteClient.cpp

Lines changed: 7 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -2,15 +2,13 @@
22

33
#include "database/SQLiteClient.hpp"
44

5-
// =============== Constructor and Destructor ===============
65
SQLiteClient::SQLiteClient(const nlohmann::json& config, const SQLProvider& sqlProvider)
76
: db_(nullptr),
87
sqlProvider_(sqlProvider),
98
config_(config),
109
lastInsertId_(0),
1110
affectedRows_(0)
1211
{
13-
// Determine database file path
1412
if (config.contains("file") && config["file"].is_string()) {
1513
dbPath_ = config["file"].get<std::string>();
1614
} else if (config.contains("name") && config["name"].is_string()) {
@@ -29,7 +27,6 @@ SQLiteClient::~SQLiteClient() {
2927
Logger::Debug("SQLiteClient destroyed");
3028
}
3129

32-
// =============== Connection Management ===============
3330
bool SQLiteClient::Connect() {
3431
std::lock_guard<std::mutex> lock(dbMutex_);
3532
if (db_) return true;
@@ -48,10 +45,16 @@ bool SQLiteClient::Connect() {
4845
return false;
4946
}
5047

51-
// --- New: Set busy timeout to 5 seconds ---
5248
sqlite3_busy_timeout(db_, 5000);
5349

5450
char* errMsg = nullptr;
51+
52+
rc = sqlite3_exec(db_, "PRAGMA synchronous = NORMAL;", nullptr, nullptr, &errMsg);
53+
if (rc != SQLITE_OK) {
54+
Logger::Warn("Failed to enable synchronous NORMAL: {}", errMsg ? errMsg : "unknown error");
55+
sqlite3_free(errMsg);
56+
}
57+
5558
rc = sqlite3_exec(db_, "PRAGMA journal_mode=WAL;", nullptr, nullptr, &errMsg);
5659
if (rc != SQLITE_OK) {
5760
Logger::Warn("Failed to enable WAL mode: {}", errMsg ? errMsg : "unknown error");
@@ -115,7 +118,6 @@ void SQLiteClient::ReconnectAll() {
115118
Reconnect();
116119
}
117120

118-
// =============== Connection Pool Management (dummy) ===============
119121
bool SQLiteClient::InitializeConnectionPool(size_t /*minConnections*/, size_t /*maxConnections*/) {
120122
Logger::Debug("SQLiteClient: connection pool not implemented");
121123
return true;
@@ -131,7 +133,6 @@ size_t SQLiteClient::GetIdleConnections() const {
131133
return 0;
132134
}
133135

134-
// =============== Helper Methods ===============
135136
bool SQLiteClient::ExecuteSql(const std::string& sql, std::vector<std::vector<std::string>>* results) {
136137
std::lock_guard<std::mutex> lock(dbMutex_);
137138
if (!db_) {
@@ -226,7 +227,6 @@ bool SQLiteClient::TableExists(const std::string& tableName) {
226227
return ExecuteSql(sql, &results) && !results.empty();
227228
}
228229

229-
// =============== Query Operations ===============
230230
nlohmann::json SQLiteClient::Query(const std::string& sql) {
231231
std::lock_guard<std::mutex> lock(dbMutex_);
232232
if (!db_) {
@@ -312,7 +312,6 @@ bool SQLiteClient::ExecuteWithParams(const std::string& sql, const std::vector<s
312312
return Execute(processedSql);
313313
}
314314

315-
// =============== Shard Operations ===============
316315
nlohmann::json SQLiteClient::QueryShard(int /*shardId*/, const std::string& sql) {
317316
return Query(sql);
318317
}
@@ -328,7 +327,6 @@ bool SQLiteClient::ExecuteShardWithParams(int /*shardId*/, const std::string& sq
328327
return ExecuteWithParams(sql, params);
329328
}
330329

331-
// =============== Utility Methods ===============
332330
int SQLiteClient::GetShardId(uint64_t entityId) const {
333331
return static_cast<int>(entityId % totalShards_);
334332
}
@@ -345,7 +343,6 @@ int SQLiteClient::GetAffectedRows() {
345343
return affectedRows_;
346344
}
347345

348-
// =============== Statistics ===============
349346
nlohmann::json SQLiteClient::GetDatabaseStats() {
350347
nlohmann::json stats;
351348
auto now = std::chrono::steady_clock::now();
@@ -377,7 +374,6 @@ void SQLiteClient::ResetStats() {
377374
Logger::Info("SQLite statistics reset");
378375
}
379376

380-
// =============== Transaction Operations ===============
381377
bool SQLiteClient::BeginTransaction() {
382378
std::string sql = sqlProvider_.GetQuery("begin_transaction");
383379
if (sql.empty()) sql = "BEGIN TRANSACTION;";
@@ -419,7 +415,6 @@ bool SQLiteClient::ExecuteTransaction(const std::function<bool()>& operation) {
419415
return success;
420416
}
421417

422-
// =============== Player Data Operations ===============
423418
bool SQLiteClient::SavePlayerData(uint64_t playerId, const nlohmann::json& data) {
424419
std::string sql = sqlProvider_.GetQuery("save_player_data");
425420
if (sql.empty()) {
@@ -506,7 +501,6 @@ nlohmann::json SQLiteClient::GetPlayer(uint64_t playerId) {
506501
return nlohmann::json();
507502
}
508503

509-
// =============== Game State Operations ===============
510504
bool SQLiteClient::SaveGameState(const std::string& key, const nlohmann::json& state) {
511505
std::string sql = sqlProvider_.GetQuery("save_game_state");
512506
if (sql.empty()) {
@@ -548,7 +542,6 @@ std::vector<std::string> SQLiteClient::ListGameStates() {
548542
return keys;
549543
}
550544

551-
// =============== World Data Operations ===============
552545
bool SQLiteClient::SaveChunkData(int chunkX, int chunkZ, const nlohmann::json& chunkData) {
553546
std::lock_guard<std::mutex> lock(dbMutex_);
554547
if (!db_) {
@@ -561,7 +554,6 @@ bool SQLiteClient::SaveChunkData(int chunkX, int chunkZ, const nlohmann::json& c
561554
sql = "INSERT OR REPLACE INTO world_chunks (chunk_x, chunk_z, biome, data, last_updated) VALUES (?, ?, ?, ?, datetime('now'));";
562555
}
563556

564-
// Begin immediate transaction
565557
char* errMsg = nullptr;
566558
int rc = sqlite3_exec(db_, "BEGIN IMMEDIATE;", nullptr, nullptr, &errMsg);
567559
if (rc != SQLITE_OK) {
@@ -570,7 +562,6 @@ bool SQLiteClient::SaveChunkData(int chunkX, int chunkZ, const nlohmann::json& c
570562
return false;
571563
}
572564

573-
// Prepare and execute the INSERT statement
574565
sqlite3_stmt* stmt = nullptr;
575566
rc = sqlite3_prepare_v2(db_, sql.c_str(), -1, &stmt, nullptr);
576567
if (rc != SQLITE_OK) {
@@ -596,7 +587,6 @@ bool SQLiteClient::SaveChunkData(int chunkX, int chunkZ, const nlohmann::json& c
596587

597588
sqlite3_finalize(stmt);
598589

599-
// Commit or rollback
600590
if (success) {
601591
rc = sqlite3_exec(db_, "COMMIT;", nullptr, nullptr, &errMsg);
602592
if (rc != SQLITE_OK) {
@@ -667,7 +657,6 @@ std::vector<std::pair<int, int>> SQLiteClient::ListChunksInRange(int centerX, in
667657
return chunks;
668658
}
669659

670-
// =============== Inventory Operations ===============
671660
bool SQLiteClient::SaveInventory(uint64_t playerId, const nlohmann::json& inventory) {
672661
std::string sql = sqlProvider_.GetQuery("save_inventory");
673662
if (sql.empty()) {
@@ -688,7 +677,6 @@ nlohmann::json SQLiteClient::LoadInventory(uint64_t playerId) {
688677
return nlohmann::json();
689678
}
690679

691-
// =============== Quest Operations ===============
692680
bool SQLiteClient::SaveQuestProgress(uint64_t playerId, const std::string& questId, const nlohmann::json& progress) {
693681
std::string sql = sqlProvider_.GetQuery("save_quest_progress");
694682
if (sql.empty()) {

0 commit comments

Comments
 (0)