mirror of
https://github.com/DarkflameUniverse/DarkflameServer.git
synced 2024-11-21 21:17:25 +00:00
Bug fixes and cleanup
Fix co-pilot induced column bugs Fix insert/update statements Added saving functionality Added update clause for column
This commit is contained in:
parent
820b375c50
commit
bc518be654
@ -273,23 +273,34 @@ void LeaderboardManager::SaveScore(const LWOOBJID& playerID, GameID gameID, Lead
|
|||||||
va_end(args);
|
va_end(args);
|
||||||
}
|
}
|
||||||
|
|
||||||
std::string FormatInsert(const std::string& columns, const std::string& format, va_list args, bool update) {
|
std::string FormatInsert(const std::string& columns, const std::string& format, va_list args, bool useUpdate) {
|
||||||
const char* insert = "INSERT";
|
const char* insert = "INSERT";
|
||||||
const char* update = "UPDATE";
|
const char* update = "UPDATE";
|
||||||
auto queryBase = "%s leaderboard SET %s WHERE id = ?;";
|
const char* queryType = useUpdate ? update : insert;
|
||||||
|
|
||||||
|
const char* scoreFilter = "character_id = ? AND game_id = ?";
|
||||||
|
const char* usedFilter = useUpdate ? scoreFilter : "";
|
||||||
|
|
||||||
constexpr uint16_t STRING_LENGTH = 400;
|
constexpr uint16_t STRING_LENGTH = 400;
|
||||||
char formattedInsert[STRING_LENGTH];
|
char formattedInsert[STRING_LENGTH];
|
||||||
|
auto queryBase = "%s leaderboard SET %s, character_id = ?, game_id = ? %s;";
|
||||||
|
snprintf(formattedInsert, STRING_LENGTH, queryBase, queryType, format.c_str(), usedFilter);
|
||||||
|
|
||||||
char finishedQuery[STRING_LENGTH];
|
char finishedQuery[STRING_LENGTH];
|
||||||
snprintf(formattedInsert, STRING_LENGTH, queryBase, columns.c_str(), format.c_str());
|
|
||||||
vsnprintf(finishedQuery, STRING_LENGTH, formattedInsert, args);
|
vsnprintf(finishedQuery, STRING_LENGTH, formattedInsert, args);
|
||||||
return finishedQuery;
|
return finishedQuery;
|
||||||
}
|
}
|
||||||
|
|
||||||
void LeaderboardManager::SaveScore(const LWOOBJID& playerID, GameID gameID, Leaderboard::Type leaderboardType, va_list args) {
|
void LeaderboardManager::SaveScore(const LWOOBJID& playerID, GameID gameID, Leaderboard::Type leaderboardType, va_list args) {
|
||||||
|
// Increment the numTimes this player has played this game.
|
||||||
|
std::unique_ptr<sql::PreparedStatement> incrementStatement(Database::CreatePreppedStmt("UPDATE leaderboard SET timesPlayed = timesPlayed + 1 WHERE character_id = ? AND game_id = ?;"));
|
||||||
|
incrementStatement->setInt(1, playerID);
|
||||||
|
incrementStatement->setInt(2, gameID);
|
||||||
|
incrementStatement->executeUpdate();
|
||||||
|
|
||||||
std::string insertStatement;
|
std::string insertStatement;
|
||||||
std::string selectedColumns;
|
std::string selectedColumns;
|
||||||
std::string insertFormat;
|
std::string insertFormat;
|
||||||
// If ResultSet is empty, just insert our score.
|
|
||||||
std::va_list argsCopy;
|
std::va_list argsCopy;
|
||||||
va_copy(argsCopy, args);
|
va_copy(argsCopy, args);
|
||||||
|
|
||||||
@ -300,8 +311,8 @@ void LeaderboardManager::SaveScore(const LWOOBJID& playerID, GameID gameID, Lead
|
|||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case Leaderboard::Type::Racing: {
|
case Leaderboard::Type::Racing: {
|
||||||
selectedColumns = "bestLapTime, bestTime";
|
selectedColumns = "bestLapTime, bestTime, numWins";
|
||||||
insertFormat = "bestLapTime=%f, bestTime=%f";
|
insertFormat = "bestLapTime=%f, bestTime=%f, numWins=%i";
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case Leaderboard::Type::UnusedLeaderboard4: {
|
case Leaderboard::Type::UnusedLeaderboard4: {
|
||||||
@ -311,18 +322,18 @@ void LeaderboardManager::SaveScore(const LWOOBJID& playerID, GameID gameID, Lead
|
|||||||
}
|
}
|
||||||
case Leaderboard::Type::MonumentRace:
|
case Leaderboard::Type::MonumentRace:
|
||||||
case Leaderboard::Type::FootRace: {
|
case Leaderboard::Type::FootRace: {
|
||||||
selectedColumns = "time";
|
selectedColumns = "bestTime";
|
||||||
insertFormat = "time=%i";
|
insertFormat = "bestTime=%i";
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case Leaderboard::Type::Survival: {
|
case Leaderboard::Type::Survival: {
|
||||||
selectedColumns = "points, time";
|
selectedColumns = "score, bestTime";
|
||||||
insertFormat = "points=%i, time=%i";
|
insertFormat = "score=%i, bestTime=%i";
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case Leaderboard::Type::SurvivalNS: {
|
case Leaderboard::Type::SurvivalNS: {
|
||||||
selectedColumns = "time, wave";
|
selectedColumns = "bestTime, score";
|
||||||
insertFormat = "time=%i, wave=%i";
|
insertFormat = "bestTime=%i, score=%i";
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case Leaderboard::Type::Donations: {
|
case Leaderboard::Type::Donations: {
|
||||||
@ -340,112 +351,126 @@ void LeaderboardManager::SaveScore(const LWOOBJID& playerID, GameID gameID, Lead
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
const char* lookup = "SELECT %s FROM leaderboard WHERE character_id = ? AND game_id = ?;";
|
const char* lookup = "SELECT %s FROM leaderboard WHERE character_id = ? AND game_id = ?;";
|
||||||
|
|
||||||
constexpr uint16_t STRING_LENGTH = 400;
|
constexpr uint16_t STRING_LENGTH = 400;
|
||||||
char lookupBuffer[STRING_LENGTH];
|
char lookupBuffer[STRING_LENGTH];
|
||||||
snprintf(lookupBuffer, STRING_LENGTH, lookup, selectedColumns.c_str());
|
snprintf(lookupBuffer, STRING_LENGTH, lookup, selectedColumns.c_str());
|
||||||
|
|
||||||
std::unique_ptr<sql::PreparedStatement> query(Database::CreatePreppedStmt(lookupBuffer));
|
std::unique_ptr<sql::PreparedStatement> query(Database::CreatePreppedStmt(lookupBuffer));
|
||||||
query->setInt(1, playerID);
|
query->setInt(1, playerID);
|
||||||
query->setInt(2, gameID);
|
query->setInt(2, gameID);
|
||||||
std::unique_ptr<sql::ResultSet> myScoreResult(query->executeQuery());
|
std::unique_ptr<sql::ResultSet> myScoreResult(query->executeQuery());
|
||||||
|
|
||||||
switch (leaderboardType) {
|
std::string saveQuery;
|
||||||
case Leaderboard::Type::ShootingGallery: {
|
if (myScoreResult->next()) {
|
||||||
int32_t oldScore = myScoreResult->getInt("score");
|
switch (leaderboardType) {
|
||||||
int32_t score;
|
case Leaderboard::Type::ShootingGallery: {
|
||||||
score = va_arg(argsCopy, int32_t);
|
int32_t oldScore = myScoreResult->getInt("score");
|
||||||
|
int32_t score;
|
||||||
|
score = va_arg(argsCopy, int32_t);
|
||||||
|
|
||||||
float oldHitPercentage = myScoreResult->getFloat("hitPercentage");
|
float oldHitPercentage = myScoreResult->getFloat("hitPercentage");
|
||||||
float hitPercentage;
|
float hitPercentage;
|
||||||
hitPercentage = va_arg(argsCopy, double);
|
hitPercentage = va_arg(argsCopy, double);
|
||||||
|
|
||||||
int32_t oldStreak = myScoreResult->getInt("streak");
|
int32_t oldStreak = myScoreResult->getInt("streak");
|
||||||
int32_t streak;
|
int32_t streak;
|
||||||
streak = va_arg(argsCopy, int32_t);
|
streak = va_arg(argsCopy, int32_t);
|
||||||
|
|
||||||
if (
|
if (
|
||||||
score > oldScore || // If score is better
|
score > oldScore || // If score is better
|
||||||
(score == oldScore && hitPercentage > oldHitPercentage) || // or if the score is tied and the hitPercentage is better
|
(score == oldScore && hitPercentage > oldHitPercentage) || // or if the score is tied and the hitPercentage is better
|
||||||
(score == oldScore && hitPercentage == oldHitPercentage && streak > oldStreak)) { // or if the score and hitPercentage are tied and the streak is better
|
(score == oldScore && hitPercentage == oldHitPercentage && streak > oldStreak)) { // or if the score and hitPercentage are tied and the streak is better
|
||||||
// Save
|
saveQuery = FormatInsert(selectedColumns, insertFormat, args, true);
|
||||||
|
}
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
break;
|
case Leaderboard::Type::Racing: {
|
||||||
}
|
float oldLapTime = myScoreResult->getFloat("bestLapTime");
|
||||||
case Leaderboard::Type::Racing: {
|
float lapTime;
|
||||||
float oldLapTime = myScoreResult->getFloat("bestLapTime");
|
lapTime = va_arg(argsCopy, double);
|
||||||
float lapTime;
|
|
||||||
lapTime = va_arg(argsCopy, double);
|
|
||||||
|
|
||||||
float oldTime = myScoreResult->getFloat("bestTime");
|
float oldTime = myScoreResult->getFloat("bestTime");
|
||||||
float oldTime;
|
float newTime;
|
||||||
oldTime = va_arg(argsCopy, double);
|
newTime = va_arg(argsCopy, double);
|
||||||
|
|
||||||
int32_t oldNumWins = myScoreResult->getInt("numWins");
|
int32_t oldNumWins = myScoreResult->getInt("numWins");
|
||||||
bool won;
|
bool won;
|
||||||
won = va_arg(argsCopy, int32_t);
|
won = va_arg(argsCopy, int32_t);
|
||||||
// Compare bestTime, if LOWER save
|
// Compare bestTime, if LOWER save
|
||||||
// Compare bestLapTime, if LOWER save
|
// Compare bestLapTime, if LOWER save
|
||||||
// Increment numWins if player won
|
// Increment numWins if player won
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case Leaderboard::Type::UnusedLeaderboard4: {
|
case Leaderboard::Type::UnusedLeaderboard4: {
|
||||||
int32_t oldScore = myScoreResult->getInt("score");
|
int32_t oldScore = myScoreResult->getInt("score");
|
||||||
int32_t points;
|
int32_t points;
|
||||||
points = va_arg(argsCopy, int32_t);
|
points = va_arg(argsCopy, int32_t);
|
||||||
// Compare score, if HIGHER save
|
// Compare score, if HIGHER save
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case Leaderboard::Type::MonumentRace: {
|
case Leaderboard::Type::MonumentRace: {
|
||||||
int32_t oldTime = myScoreResult->getInt("time");
|
int32_t oldTime = myScoreResult->getInt("bestTime");
|
||||||
int32_t time;
|
int32_t time;
|
||||||
time = va_arg(argsCopy, int32_t);
|
time = va_arg(argsCopy, int32_t);
|
||||||
// Compare time, if LOWER save
|
// Compare time, if LOWER save
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case Leaderboard::Type::FootRace: {
|
case Leaderboard::Type::FootRace: {
|
||||||
int32_t oldTime = myScoreResult->getInt("time");
|
int32_t oldTime = myScoreResult->getInt("bestTime");
|
||||||
int32_t time;
|
int32_t time;
|
||||||
time = va_arg(argsCopy, int32_t);
|
time = va_arg(argsCopy, int32_t);
|
||||||
// Compare time, if HIGHER save
|
// Compare time, if HIGHER save
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case Leaderboard::Type::Survival: {
|
case Leaderboard::Type::Survival: {
|
||||||
int32_t oldPoints = myScoreResult->getInt("points");
|
int32_t oldPoints = myScoreResult->getInt("score");
|
||||||
int32_t points;
|
int32_t points;
|
||||||
points = va_arg(argsCopy, int32_t);
|
points = va_arg(argsCopy, int32_t);
|
||||||
|
|
||||||
int32_t oldTime = myScoreResult->getInt("time");
|
int32_t oldTime = myScoreResult->getInt("bestTime");
|
||||||
int32_t time;
|
int32_t time;
|
||||||
time = va_arg(argsCopy, int32_t);
|
time = va_arg(argsCopy, int32_t);
|
||||||
// Compare points, if HIGHER save, if TIED compare time, if LOWER save
|
// Compare points, if HIGHER save, if TIED compare time, if LOWER save
|
||||||
// If classic_survival_scoring is 1, reverse the order of the points and time columns
|
// If classic_survival_scoring is 1, reverse the order of the points and time columns
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case Leaderboard::Type::SurvivalNS: {
|
case Leaderboard::Type::SurvivalNS: {
|
||||||
int32_t oldTime = myScoreResult->getInt("time");
|
int32_t oldTime = myScoreResult->getInt("bestTime");
|
||||||
int32_t time;
|
int32_t time;
|
||||||
time = va_arg(argsCopy, int32_t);
|
time = va_arg(argsCopy, int32_t);
|
||||||
|
|
||||||
int32_t oldWave = myScoreResult->getInt("wave");
|
int32_t oldWave = myScoreResult->getInt("score");
|
||||||
int32_t wave;
|
int32_t wave;
|
||||||
wave = va_arg(argsCopy, int32_t);
|
wave = va_arg(argsCopy, int32_t);
|
||||||
// Compare wave, if HIGHER save, if TIED compare time, if LOWER save
|
// Compare wave, if HIGHER save, if TIED compare time, if LOWER save
|
||||||
break;
|
break;
|
||||||
|
}
|
||||||
|
case Leaderboard::Type::Donations: {
|
||||||
|
int32_t oldScore = myScoreResult->getInt("score");
|
||||||
|
int32_t score;
|
||||||
|
score = va_arg(argsCopy, int32_t);
|
||||||
|
// Compare score, if HIGHER save
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
case Leaderboard::Type::None: {
|
||||||
|
// This type is included here simply to resolve a compiler warning on mac about unused enum types
|
||||||
|
Game::logger->Log("LeaderboardManager", "Warning: Saving score for leaderboard of type None. Are you sure this is intended?");
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
default:
|
||||||
|
Game::logger->Log("LeaderboardManager", "Unknown leaderboard type %i. Cannot save score!", leaderboardType);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
saveQuery = FormatInsert(selectedColumns, insertFormat, argsCopy, false);
|
||||||
}
|
}
|
||||||
case Leaderboard::Type::Donations: {
|
Game::logger->Log("LeaderboardManager", "%s", saveQuery.c_str());
|
||||||
int32_t oldScore = myScoreResult->getInt("score");
|
if (!saveQuery.empty()) {
|
||||||
int32_t score;
|
std::unique_ptr<sql::PreparedStatement> insertQuery(Database::CreatePreppedStmt(saveQuery));
|
||||||
score = va_arg(argsCopy, int32_t);
|
insertQuery->setInt(1, playerID);
|
||||||
// Compare score, if HIGHER save
|
insertQuery->setInt(2, gameID);
|
||||||
break;
|
insertQuery->execute();
|
||||||
}
|
|
||||||
case Leaderboard::Type::None: {
|
|
||||||
// This type is included here simply to resolve a compiler warning on mac about unused enum types
|
|
||||||
Game::logger->Log("LeaderboardManager", "Warning: Saving score for leaderboard of type None. Are you sure this is intended?");
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
default:
|
|
||||||
Game::logger->Log("LeaderboardManager", "Unknown leaderboard type %i. Cannot save score!", leaderboardType);
|
|
||||||
break;
|
|
||||||
}
|
}
|
||||||
va_end(argsCopy);
|
va_end(argsCopy);
|
||||||
}
|
}
|
||||||
|
@ -7,5 +7,6 @@ ALTER TABLE leaderboard
|
|||||||
MODIFY time FLOAT NOT NULL DEFAULT 0;
|
MODIFY time FLOAT NOT NULL DEFAULT 0;
|
||||||
|
|
||||||
ALTER TABLE leaderboard CHANGE time bestTime float;
|
ALTER TABLE leaderboard CHANGE time bestTime float;
|
||||||
|
ALTER TABLE leaderboard CHANGE last_played TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP() ON UPDATE CURRENT_TIMESTAMP();
|
||||||
|
|
||||||
UPDATE leaderboard SET streak = bestTime where game_id = 1864;
|
UPDATE leaderboard SET streak = bestTime where game_id = 1864;
|
||||||
|
@ -30,10 +30,10 @@ protected:
|
|||||||
Leaderboard leaderboard(gameID, infoType, false, 14231, type);
|
Leaderboard leaderboard(gameID, infoType, false, 14231, type);
|
||||||
leaderboard.SetupLeaderboard();
|
leaderboard.SetupLeaderboard();
|
||||||
leaderboard.Serialize(&bitStream);
|
leaderboard.Serialize(&bitStream);
|
||||||
TestLeaderboard(leaderboard, 1);
|
// TestLeaderboard(leaderboard, 1);
|
||||||
TestLeaderboard(leaderboard, 10);
|
// TestLeaderboard(leaderboard, 10);
|
||||||
TestLeaderboard(leaderboard, 100);
|
// TestLeaderboard(leaderboard, 100);
|
||||||
TestLeaderboard(leaderboard, 1000);
|
// TestLeaderboard(leaderboard, 1000);
|
||||||
}
|
}
|
||||||
|
|
||||||
CBITSTREAM;
|
CBITSTREAM;
|
||||||
@ -73,9 +73,9 @@ protected:
|
|||||||
|
|
||||||
TEST_F(LeaderboardTests, LeaderboardSpeedTest) {
|
TEST_F(LeaderboardTests, LeaderboardSpeedTest) {
|
||||||
RunTests(1864, Leaderboard::Type::ShootingGallery , Leaderboard::InfoType::Top);
|
RunTests(1864, Leaderboard::Type::ShootingGallery , Leaderboard::InfoType::Top);
|
||||||
RunTests(1864, Leaderboard::Type::ShootingGallery, Leaderboard::InfoType::MyStanding);
|
// RunTests(1864, Leaderboard::Type::ShootingGallery, Leaderboard::InfoType::MyStanding);
|
||||||
RunTests(1864, Leaderboard::Type::ShootingGallery, Leaderboard::InfoType::Friends);
|
// RunTests(1864, Leaderboard::Type::ShootingGallery, Leaderboard::InfoType::Friends);
|
||||||
LeaderboardManager::Instance().SaveScore(14231, 0, Leaderboard::Type::ShootingGallery, 3, 3000, 15.0f, 100);
|
LeaderboardManager::Instance().SaveScore(14231, 1864, Leaderboard::Type::ShootingGallery, 3, 53001, 15.0f, 100);
|
||||||
// RunTests(0, Leaderboard::Type::Racing);
|
// RunTests(0, Leaderboard::Type::Racing);
|
||||||
LeaderboardManager::Instance().SaveScore(14231, 0, Leaderboard::Type::Racing, 3, 260.0f, 250.0f, true);
|
LeaderboardManager::Instance().SaveScore(14231, 0, Leaderboard::Type::Racing, 3, 260.0f, 250.0f, true);
|
||||||
// RunTests(0, Leaderboard::Type::MonumentRace);
|
// RunTests(0, Leaderboard::Type::MonumentRace);
|
||||||
|
Loading…
Reference in New Issue
Block a user