aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMachiavelli <none@none>2010-06-28 16:09:06 +0200
committerMachiavelli <none@none>2010-06-28 16:09:06 +0200
commitb6e180c17c0626a665cd189075e9d9b7f4b48d0d (patch)
tree45455ad7f4f203befde1ebb11a4e365ccd1ae751
parent988467467cd743c03148b859936da8ce076b5aa5 (diff)
Add PreparedStatementHolder class that will be used for registering and calling prepared statements on the MySQL server.
Information about prepared statements can be found here: http://dev.mysql.com/tech-resources/articles/4.1/prepared-statements.html In short: better performance shall ensue. --HG-- branch : trunk
-rw-r--r--src/server/shared/CMakeLists.txt1
-rw-r--r--src/server/shared/Database/PreparedStatements.cpp93
-rw-r--r--src/server/shared/Database/PreparedStatements.h30
-rw-r--r--win/VC90/shared.vcproj8
4 files changed, 132 insertions, 0 deletions
diff --git a/src/server/shared/CMakeLists.txt b/src/server/shared/CMakeLists.txt
index 0fd58e63588..b3ededd8c62 100644
--- a/src/server/shared/CMakeLists.txt
+++ b/src/server/shared/CMakeLists.txt
@@ -94,6 +94,7 @@ set(trinitydatabase_STAT_SRCS
Database/SQLStorage.cpp
Database/SqlDelayThread.cpp
Database/SqlOperations.cpp
+ Database/PreparedStatements.cpp
)
include_directories(
diff --git a/src/server/shared/Database/PreparedStatements.cpp b/src/server/shared/Database/PreparedStatements.cpp
new file mode 100644
index 00000000000..40a910acf9e
--- /dev/null
+++ b/src/server/shared/Database/PreparedStatements.cpp
@@ -0,0 +1,93 @@
+#include "PreparedStatements.h"
+
+void PreparedStatementHolder::_prepareStatement(const char* name, const char* sql, Database *db, uint32 &count)
+{
+ const char prefix[] = "PREPARE ";
+ size_t querySize = 8 + strlen(name) + 6 + strlen(sql) + 2 + 1;
+ char* query = new char[querySize];
+ strcpy(query, prefix);
+ strcat(query, name);
+ strcat(query, " FROM ");
+ strcat(query, "'");
+ strcat(query, sql);
+ strcat(query, "'");
+
+ DEBUG_LOG("Preparing statement: %s", query);
+ db->Execute(query);
+
+ delete[] query;
+ ++count;
+}
+
+void PreparedStatementHolder::LoadAuthserver(Database *db, uint32 &count)
+{
+ _prepareStatement("auth_ping", "SELECT 1 FROM realmlist LIMIT 1", db, count);
+};
+
+void PreparedStatementHolder::Execute(Database *db, const char *name)
+{
+ const char prefix[] = "EXECUTE ";
+ size_t querySize = 8 + strlen(name) + 1;
+ char* query = new char[querySize];
+ strcpy(query, prefix);
+ strcat(query, name);
+
+ DEBUG_LOG("Prepared statement: %s", query);
+ db->Execute(query);
+ delete[] query;
+}
+
+void PreparedStatementHolder::PExecute(Database *db, const char *name, const char* args)
+{
+ // NOTE: if args == NULL, we're crashing here. No need to waste performance on checking;
+ // devs must make sure they use PExecute for args and Execute for no args.
+
+ const char prefix[] = "EXECUTE ";
+ size_t querySize = 8 + strlen(name) + 7 + strlen(args) + 1;
+ char* query = new char[querySize];
+ strcpy(query, prefix);
+ strcat(query, name);
+ strcat(query, " USING ");
+ strcat(query, args);
+
+ DEBUG_LOG("Prepared statement (parsed args): %s", query);
+ db->Execute(query);
+ delete[] query;
+}
+
+QueryResult_AutoPtr PreparedStatementHolder::Query(Database *db, const char *name)
+{
+ QueryResult_AutoPtr _return = QueryResult_AutoPtr(NULL);
+
+ const char prefix[] = "EXECUTE ";
+ size_t querySize = 8 + strlen(name) + 1;
+ char* query = new char[querySize];
+ strcpy(query, prefix);
+ strcat(query, name);
+
+ DEBUG_LOG("Prepared statement with resultset: %s", query);
+ _return = db->Query(query);
+ delete[] query;
+ return _return;
+}
+
+QueryResult_AutoPtr PreparedStatementHolder::PQuery(Database *db, const char *name, const char *args)
+{
+ // NOTE: if args == NULL, we're crashing here. No need to waste performance on checking;
+ // devs must make sure they use PQuery for args and Query for no args.
+
+ QueryResult_AutoPtr _return = QueryResult_AutoPtr(NULL);
+
+ const char prefix[] = "EXECUTE ";
+ size_t querySize = 8 + strlen(name) + 7 + strlen(args) + 1;
+ char* query = new char[querySize];
+ strcpy(query, prefix);
+ strcat(query, name);
+ strcat(query, " USING ");
+ strcat(query, args);
+
+ DEBUG_LOG("Prepared statement with resultset (parsed args): %s", query);
+ _return = db->Query(query);
+ delete[] query;
+ return _return;
+} \ No newline at end of file
diff --git a/src/server/shared/Database/PreparedStatements.h b/src/server/shared/Database/PreparedStatements.h
new file mode 100644
index 00000000000..c19119dcb3d
--- /dev/null
+++ b/src/server/shared/Database/PreparedStatements.h
@@ -0,0 +1,30 @@
+#ifndef sPreparedStatement
+
+#include "ace/Singleton.h"
+#include "Database/DatabaseEnv.h"
+
+class PreparedStatementHolder
+{
+ public:
+ ///- Load prepare statements on database $db and increase $count for every statement
+ void LoadCharacters(Database *db, uint32 &count);
+ void LoadAuthserver(Database *db, uint32 &count);
+ void LoadWorldserver(Database *db, uint32 &count);
+
+ ///- Executes prepared statement that doesn't require feedback with name $name on database $db
+ void Execute(Database *db, const char* name);
+ ///- Executes prepared statement that doesn't require feedback with name $name and args $args
+ ///- on database $db
+ void PExecute(Database *db, const char* name, const char* args);
+
+ ///- Executes a prepared statement without args on db $db with name $name and puts the result set in a pointer.
+ QueryResult_AutoPtr Query(Database* db, const char* name);
+ ///- Executes a prepared statement with args $args on db $db with name $name and put the result set in a pointer.
+ QueryResult_AutoPtr PQuery(Database* db, const char* name, const char* args);
+
+ private:
+ void _prepareStatement(const char* name, const char* sql, Database *db, uint32 &count);
+
+};
+#define sPreparedStatement (*ACE_Singleton<PreparedStatementHolder, ACE_Null_Mutex>::instance())
+#endif \ No newline at end of file
diff --git a/win/VC90/shared.vcproj b/win/VC90/shared.vcproj
index 536939f9d5a..f3908ec4596 100644
--- a/win/VC90/shared.vcproj
+++ b/win/VC90/shared.vcproj
@@ -473,6 +473,14 @@
>
</File>
<File
+ RelativePath="..\..\src\server\shared\Database\PreparedStatements.cpp"
+ >
+ </File>
+ <File
+ RelativePath="..\..\src\server\shared\Database\PreparedStatements.h"
+ >
+ </File>
+ <File
RelativePath="..\..\src\server\shared\Database\QueryResult.cpp"
>
</File>