mirror of
https://github.com/mangosfour/server.git
synced 2025-12-12 01:37:00 +00:00
Fix pdump write command and add check to pdump load (#106)
This commit is contained in:
parent
e3feea3a41
commit
5e1e9ae18a
2 changed files with 64 additions and 34 deletions
|
|
@ -242,7 +242,7 @@ bool changetokGuid(std::string& str, int n, std::map<uint32, uint32>& guidMap, u
|
|||
return changetoknth(str, n, chritem, false, nonzero);
|
||||
}
|
||||
|
||||
std::string CreateDumpString(char const* tableName, QueryResult* result)
|
||||
std::string CreateDumpString(char const* tableName, char const* tableColumnNamesAsChars, QueryResult* result)
|
||||
{
|
||||
if (!tableName || !result)
|
||||
{
|
||||
|
|
@ -250,7 +250,7 @@ std::string CreateDumpString(char const* tableName, QueryResult* result)
|
|||
}
|
||||
|
||||
std::ostringstream ss;
|
||||
ss << "INSERT INTO `" << tableName << "` VALUES (";
|
||||
ss << "INSERT INTO `" << tableName << "` ("<< tableColumnNamesAsChars <<") VALUES (";
|
||||
Field* fields = result->Fetch();
|
||||
for (uint32 i = 0; i < result->GetFieldCount(); ++i)
|
||||
{
|
||||
|
|
@ -370,7 +370,26 @@ void PlayerDumpWriter::DumpTableContent(std::string& dump, uint32 guid, char con
|
|||
wherestr = GenerateWhereStr(fieldname, guid);
|
||||
}
|
||||
|
||||
QueryResult* result = CharacterDatabase.PQuery("SELECT * FROM `%s` WHERE `%s`", tableFrom, wherestr.c_str());
|
||||
//fetch table columns
|
||||
std::string tableColumnNamesStr = "";
|
||||
QueryNamedResult* resNames = CharacterDatabase.PQueryNamed("SELECT * FROM `%s` LIMIT 1", tableFrom);
|
||||
if (!resNames)
|
||||
{
|
||||
return;
|
||||
}
|
||||
// There will be a result since if not teh code does not hit lines before... so no check needed
|
||||
QueryFieldNames const& namesMap = resNames->GetFieldNames();
|
||||
|
||||
for (QueryFieldNames::const_iterator itr = namesMap.begin(); itr != namesMap.end(); ++itr)
|
||||
{
|
||||
tableColumnNamesStr += "`" + *itr +"`,";
|
||||
}
|
||||
// remove last character of tableColumnNamesStr = ","
|
||||
tableColumnNamesStr.pop_back();
|
||||
namesMap.empty();
|
||||
|
||||
// fetch results of the table
|
||||
QueryResult* result = CharacterDatabase.PQuery("SELECT %s FROM `%s` WHERE %s", tableColumnNamesStr.c_str(), tableFrom, wherestr.c_str());
|
||||
if (!result)
|
||||
{
|
||||
return;
|
||||
|
|
@ -392,7 +411,7 @@ void PlayerDumpWriter::DumpTableContent(std::string& dump, uint32 guid, char con
|
|||
default: break;
|
||||
}
|
||||
|
||||
dump += CreateDumpString(tableTo, result);
|
||||
dump += CreateDumpString(tableTo, tableColumnNamesStr.c_str(), result);
|
||||
dump += "\n";
|
||||
}
|
||||
while (result->NextRow());
|
||||
|
|
@ -407,38 +426,29 @@ std::string PlayerDumpWriter::GetDump(uint32 guid)
|
|||
std::string dump;
|
||||
|
||||
dump += "IMPORTANT NOTE: This sql queries not created for apply directly, use '.pdump load' command in console or client chat instead.\n";
|
||||
dump += "IMPORTANT NOTE: NOT APPLY ITS DIRECTLY to character DB or you will DAMAGE and CORRUPT character DB\n\n";
|
||||
dump += "IMPORTANT NOTE: NOT APPLY ITS DIRECTLY to character DB or you will DAMAGE and CORRUPT character DB\n";
|
||||
|
||||
// revision check guard
|
||||
QueryNamedResult* result = CharacterDatabase.QueryNamed("SELECT * FROM `db_version` LIMIT 1");
|
||||
// Check the revision of character DB which will be the first line of the whole version/structure set
|
||||
QueryResult* result = CharacterDatabase.Query("SELECT `version`, `structure`, `description`, `comment` FROM `db_version` ORDER BY `version` DESC, `structure` DESC, `content` ASC LIMIT 1");
|
||||
|
||||
if (result)
|
||||
{
|
||||
QueryFieldNames const& namesMap = result->GetFieldNames();
|
||||
std::string reqName;
|
||||
for (QueryFieldNames::const_iterator itr = namesMap.begin(); itr != namesMap.end(); ++itr)
|
||||
{
|
||||
if (itr->substr(0, 9) == "required_")
|
||||
{
|
||||
reqName = *itr;
|
||||
break;
|
||||
}
|
||||
}
|
||||
Field* fields = result->Fetch();
|
||||
|
||||
if (!reqName.empty())
|
||||
{
|
||||
// this will fail at wrong character DB version
|
||||
dump += "UPDATE `version` SET `" + reqName + "` = 1 WHERE FALSE;\n\n";
|
||||
}
|
||||
else
|
||||
{
|
||||
sLog.outError("Character DB Table 'db_version' does not have revision guard field, revision guard query not added to pdump.");
|
||||
}
|
||||
dump += "DUMPED_WITH:"+std::to_string(fields[0].GetInt16())
|
||||
+ "." + std::to_string(fields[1].GetInt16()) + ".X "
|
||||
+" CHAR. DB VERSION ( "
|
||||
+ fields[2].GetCppString() + " / "
|
||||
+ fields[3].GetCppString() +
|
||||
")\n\n"
|
||||
;
|
||||
|
||||
delete result;
|
||||
}
|
||||
else
|
||||
{
|
||||
sLog.outError("Character DB not have 'db_version' table, revision guard query not added to pdump.");
|
||||
sLog.outError("Character DB not have 'db_version' table");
|
||||
}
|
||||
|
||||
for (DumpTable* itr = &dumpTables[0]; itr->isValid(); ++itr)
|
||||
|
|
@ -570,16 +580,35 @@ DumpReturn PlayerDumpReader::LoadDump(const std::string& file, uint32 account, s
|
|||
continue;
|
||||
}
|
||||
|
||||
// add required_ check
|
||||
if (line.substr(nw_pos, 41) == "UPDATE `db_version` SET `required_`")
|
||||
{
|
||||
if (!CharacterDatabase.Execute(line.c_str()))
|
||||
{
|
||||
ROLLBACK(DUMP_FILE_BROKEN);
|
||||
}
|
||||
// Check db version corresp.
|
||||
std::string dbVersionLinePrefix = line.substr(nw_pos, 12);
|
||||
|
||||
if (dbVersionLinePrefix =="DUMPED_WITH:")
|
||||
{
|
||||
QueryResult* result = CharacterDatabase.Query("SELECT `version`, `structure`, `description`, `comment` FROM `db_version` ORDER BY `version` DESC, `structure` DESC, `content` ASC LIMIT 1");
|
||||
|
||||
if (result)
|
||||
{
|
||||
Field* fields = result->Fetch();
|
||||
// Only version / structure is needed
|
||||
std::string dbversion = std::to_string(fields[0].GetInt16()) + "." + std::to_string(fields[1].GetInt16())+".X";
|
||||
size_t dbversionLen = dbversion.size();
|
||||
|
||||
std::string dbversionInDumpFile = line.substr(nw_pos+12, dbversionLen);
|
||||
|
||||
delete result;
|
||||
|
||||
if (dbversionInDumpFile != dbversion)
|
||||
{
|
||||
sLog.outError("LoadPlayerDump: Cannot load player dump - file version is %s, DB needs %s", dbversionInDumpFile.c_str(), dbversion.c_str());
|
||||
ROLLBACK(DUMP_DB_VERSION_MISMATCH);
|
||||
}
|
||||
else
|
||||
{
|
||||
continue;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// determine table name and load type
|
||||
std::string tn = gettablename(line);
|
||||
|
|
|
|||
|
|
@ -70,6 +70,7 @@ enum DumpReturn
|
|||
DUMP_TOO_MANY_CHARS,
|
||||
DUMP_UNEXPECTED_END,
|
||||
DUMP_FILE_BROKEN,
|
||||
DUMP_DB_VERSION_MISMATCH
|
||||
};
|
||||
|
||||
class PlayerDump
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue