10 #include "stg/user_ips.h"
11 #include "stg/user_conf.h"
12 #include "stg/user_stat.h"
13 #include "stg/blowfish.h"
14 #include "stg/plugin_creator.h"
15 #include "stg/logger.h"
16 #include "mysql_store.h"
18 #define adm_enc_passwd "cjeifY8m3"
24 const int pt_mega = 1024 * 1024;
25 const std::string badSyms = "'`";
26 const char repSym = '\"';
27 const int RepitTimes = 3;
30 int GetInt(const std::string & str, T * val, T defaultVal = T())
34 *val = static_cast<T>(strtoll(str.c_str(), &res, 10));
38 *val = defaultVal; //Error!
45 int GetDouble(const std::string & str, double * val, double defaultVal)
49 *val = strtod(str.c_str(), &res);
53 *val = defaultVal; //Error!
60 int GetTime(const std::string & str, time_t * val, time_t defaultVal)
64 *val = strtol(str.c_str(), &res, 10);
68 *val = defaultVal; //Error!
75 //-----------------------------------------------------------------------------
76 std::string ReplaceStr(std::string source, const std::string & symlist, const char chgsym)
78 std::string::size_type pos=0;
80 while( (pos = source.find_first_of(symlist,pos)) != std::string::npos)
81 source.replace(pos, 1,1, chgsym);
86 int GetULongLongInt(const std::string & str, uint64_t * val, uint64_t defaultVal)
90 *val = strtoull(str.c_str(), &res, 10);
94 *val = defaultVal; //Error!
101 PLUGIN_CREATOR<MYSQL_STORE> msc;
104 extern "C" STORE * GetStore();
105 //-----------------------------------------------------------------------------
106 //-----------------------------------------------------------------------------
107 //-----------------------------------------------------------------------------
110 return msc.GetPlugin();
112 //-----------------------------------------------------------------------------
113 MYSQL_STORE_SETTINGS::MYSQL_STORE_SETTINGS()
117 //-----------------------------------------------------------------------------
118 int MYSQL_STORE_SETTINGS::ParseParam(const std::vector<PARAM_VALUE> & moduleParams,
119 const std::string & name, std::string & result)
123 std::vector<PARAM_VALUE>::const_iterator pvi;
124 pvi = find(moduleParams.begin(), moduleParams.end(), pv);
125 if (pvi == moduleParams.end() || pvi->value.empty())
127 errorStr = "Parameter \'" + name + "\' not found.";
131 result = pvi->value[0];
135 //-----------------------------------------------------------------------------
136 int MYSQL_STORE_SETTINGS::ParseSettings(const MODULE_SETTINGS & s)
138 if (ParseParam(s.moduleParams, "user", dbUser) < 0 &&
139 ParseParam(s.moduleParams, "dbuser", dbUser) < 0)
141 if (ParseParam(s.moduleParams, "password", dbPass) < 0 &&
142 ParseParam(s.moduleParams, "rootdbpass", dbPass) < 0)
144 if (ParseParam(s.moduleParams, "database", dbName) < 0 &&
145 ParseParam(s.moduleParams, "dbname", dbName) < 0)
147 if (ParseParam(s.moduleParams, "server", dbHost) < 0 &&
148 ParseParam(s.moduleParams, "dbhost", dbHost) < 0)
153 //-----------------------------------------------------------------------------
154 //-----------------------------------------------------------------------------
155 //-----------------------------------------------------------------------------
156 MYSQL_STORE::MYSQL_STORE()
157 : version("mysql_store v.0.67"),
159 logger(GetPluginLogger(GetStgLogger(), "store_mysql"))
162 //-----------------------------------------------------------------------------
163 int MYSQL_STORE::MysqlQuery(const char* sQuery,MYSQL * sock) const
167 if( (ret = mysql_query(sock,sQuery)) )
169 for(int i=0; i<RepitTimes; i++)
171 if( (ret = mysql_query(sock,sQuery)) )
172 ;//need to send error result
180 //-----------------------------------------------------------------------------
182 //-----------------------------------------------------------------------------
183 int MYSQL_STORE::ParseSettings()
185 int ret = storeSettings.ParseSettings(settings);
189 errorStr = storeSettings.GetStrError();
192 if(storeSettings.GetDBPassword().length() == 0)
194 errorStr = "Database password must be not empty. Please read Manual.";
198 if (!(sock = mysql_real_connect(&mysql,storeSettings.GetDBHost().c_str(),
199 storeSettings.GetDBUser().c_str(),storeSettings.GetDBPassword().c_str(),
202 errorStr = "Couldn't connect to mysql engine! With error:\n";
203 errorStr += mysql_error(&mysql);
209 if(mysql_select_db(sock, storeSettings.GetDBName().c_str()))
211 std::string res = "CREATE DATABASE " + storeSettings.GetDBName();
213 if(MysqlQuery(res.c_str(),sock))
215 errorStr = "Couldn't create database! With error:\n";
216 errorStr += mysql_error(sock);
222 if(mysql_select_db(sock, storeSettings.GetDBName().c_str()))
224 errorStr = "Couldn't select database! With error:\n";
225 errorStr += mysql_error(sock);
229 ret = CheckAllTables(sock);
234 ret = CheckAllTables(sock);
238 logger("MYSQL_STORE: Current DB schema version: %d", schemaVersion);
246 //-----------------------------------------------------------------------------
247 bool MYSQL_STORE::IsTablePresent(const std::string & str,MYSQL * sock)
251 if (!(result=mysql_list_tables(sock,str.c_str() )))
253 errorStr = "Couldn't get tables list With error:\n";
254 errorStr += mysql_error(sock);
259 my_ulonglong num_rows = mysql_num_rows(result);
262 mysql_free_result(result);
264 return num_rows == 1;
266 //-----------------------------------------------------------------------------
267 int MYSQL_STORE::CheckAllTables(MYSQL * sock)
269 //info-------------------------------------------------------------------------
270 if(!IsTablePresent("info",sock))
272 sprintf(qbuf,"CREATE TABLE info (version INTEGER NOT NULL)");
274 if(MysqlQuery(qbuf,sock))
276 errorStr = "Couldn't create info table With error:\n";
277 errorStr += mysql_error(sock);
282 sprintf(qbuf,"INSERT INTO info SET version=0");
284 if(MysqlQuery(qbuf,sock))
286 errorStr = "Couldn't write default version. With error:\n";
287 errorStr += mysql_error(sock);
295 std::vector<std::string> info;
296 if (GetAllParams(&info, "info", "version"))
303 GetInt(info.front(), &schemaVersion, 0);
306 //admins-----------------------------------------------------------------------
307 if(!IsTablePresent("admins",sock))
309 sprintf(qbuf,"CREATE TABLE admins (login VARCHAR(40) DEFAULT '' PRIMARY KEY,"\
310 "password VARCHAR(150) DEFAULT '*',ChgConf TINYINT DEFAULT 0,"\
311 "ChgPassword TINYINT DEFAULT 0,ChgStat TINYINT DEFAULT 0,"\
312 "ChgCash TINYINT DEFAULT 0,UsrAddDel TINYINT DEFAULT 0,"\
313 "ChgTariff TINYINT DEFAULT 0,ChgAdmin TINYINT DEFAULT 0)");
315 if(MysqlQuery(qbuf,sock))
317 errorStr = "Couldn't create admin table list With error:\n";
318 errorStr += mysql_error(sock);
323 sprintf(qbuf,"INSERT INTO admins SET login='admin',"\
324 "password='geahonjehjfofnhammefahbbbfbmpkmkmmefahbbbfbmpkmkmmefahbbbfbmpkmkaa',"\
325 "ChgConf=1,ChgPassword=1,ChgStat=1,ChgCash=1,UsrAddDel=1,ChgTariff=1,ChgAdmin=1");
327 if(MysqlQuery(qbuf,sock))
329 errorStr = "Couldn't create default admin. With error:\n";
330 errorStr += mysql_error(sock);
336 //tariffs-----------------------------------------------------------------------
337 std::string param, res;
338 if(!IsTablePresent("tariffs",sock))
340 res = "CREATE TABLE tariffs (name VARCHAR(40) DEFAULT '' PRIMARY KEY,";
342 for (int i = 0; i < DIR_NUM; i++)
344 strprintf(¶m, " PriceDayA%d DOUBLE DEFAULT 0.0,", i);
347 strprintf(¶m, " PriceDayB%d DOUBLE DEFAULT 0.0,", i);
350 strprintf(¶m, " PriceNightA%d DOUBLE DEFAULT 0.0,", i);
353 strprintf(¶m, " PriceNightB%d DOUBLE DEFAULT 0.0,", i);
356 strprintf(¶m, " Threshold%d INT DEFAULT 0,", i);
359 strprintf(¶m, " Time%d VARCHAR(15) DEFAULT '0:0-0:0',", i);
362 strprintf(¶m, " NoDiscount%d INT DEFAULT 0,", i);
365 strprintf(¶m, " SinglePrice%d INT DEFAULT 0,", i);
369 res += "PassiveCost DOUBLE DEFAULT 0.0, Fee DOUBLE DEFAULT 0.0,"
370 "Free DOUBLE DEFAULT 0.0, TraffType VARCHAR(10) DEFAULT '',"
371 "period VARCHAR(32) NOT NULL DEFAULT 'month',"
372 "change_policy VARCHAR(32) NOT NULL DEFAULT 'allow',"
373 "change_policy_timeout TIMESTAMP NOT NULL DEFAULT '1970-01-01 00:00:00')";
375 if(MysqlQuery(res.c_str(),sock))
377 errorStr = "Couldn't create tariffs table list With error:\n";
378 errorStr += mysql_error(sock);
383 res = "INSERT INTO tariffs SET name='tariff',";
385 for (int i = 0; i < DIR_NUM; i++)
387 strprintf(¶m, " NoDiscount%d=1,", i);
390 strprintf(¶m, " Threshold%d=0,", i);
393 strprintf(¶m, " Time%d='0:0-0:0',", i);
398 strprintf(¶m, " SinglePrice%d=0,", i);
404 strprintf(¶m, " PriceDayA%d=0.0,", i);
409 strprintf(¶m, " PriceDayB%d=0.0,", i);
415 strprintf(¶m, " PriceNightA%d=0.0,", i);
420 strprintf(¶m, " PriceNightB%d=0.0,", i);
425 res += "PassiveCost=0.0, Fee=10.0, Free=0,"\
426 "SinglePrice0=1, SinglePrice1=1,PriceDayA1=0.75,PriceDayB1=0.75,"\
427 "PriceNightA0=1.0,PriceNightB0=1.0,TraffType='up+down',period='month',"\
428 "change_policy='allow', change_policy_timeout='1970-01-01 00:00:00'";
430 if(MysqlQuery(res.c_str(),sock))
432 errorStr = "Couldn't create default tariff. With error:\n";
433 errorStr += mysql_error(sock);
438 sprintf(qbuf,"UPDATE info SET version=1");
440 if(MysqlQuery(qbuf,sock))
442 errorStr = "Couldn't write default version. With error:\n";
443 errorStr += mysql_error(sock);
450 //users-----------------------------------------------------------------------
451 if(!IsTablePresent("users",sock))
453 res = "CREATE TABLE users (login VARCHAR(50) NOT NULL DEFAULT '' PRIMARY KEY, Password VARCHAR(150) NOT NULL DEFAULT '*',"\
454 "Passive INT(3) DEFAULT 0,Down INT(3) DEFAULT 0,DisabledDetailStat INT(3) DEFAULT 0,AlwaysOnline INT(3) DEFAULT 0,Tariff VARCHAR(40) NOT NULL DEFAULT '',"\
455 "Address VARCHAR(254) NOT NULL DEFAULT '',Phone VARCHAR(128) NOT NULL DEFAULT '',Email VARCHAR(50) NOT NULL DEFAULT '',"\
456 "Note TEXT NOT NULL,RealName VARCHAR(254) NOT NULL DEFAULT '',StgGroup VARCHAR(40) NOT NULL DEFAULT '',"\
457 "Credit DOUBLE DEFAULT 0, TariffChange VARCHAR(40) NOT NULL DEFAULT '',";
459 for (int i = 0; i < USERDATA_NUM; i++)
461 strprintf(¶m, " Userdata%d VARCHAR(254) NOT NULL,", i);
465 param = " CreditExpire INT(11) DEFAULT 0,";
468 strprintf(¶m, " IP VARCHAR(254) DEFAULT '*',");
471 for (int i = 0; i < DIR_NUM; i++)
473 strprintf(¶m, " D%d BIGINT(30) DEFAULT 0,", i);
476 strprintf(¶m, " U%d BIGINT(30) DEFAULT 0,", i);
480 strprintf(¶m, "Cash DOUBLE DEFAULT 0,FreeMb DOUBLE DEFAULT 0,LastCashAdd DOUBLE DEFAULT 0,"\
481 "LastCashAddTime INT(11) DEFAULT 0,PassiveTime INT(11) DEFAULT 0,LastActivityTime INT(11) DEFAULT 0,"\
482 "NAS VARCHAR(17) NOT NULL, INDEX (AlwaysOnline), INDEX (IP), INDEX (Address),"\
483 " INDEX (Tariff),INDEX (Phone),INDEX (Email),INDEX (RealName))");
486 if(MysqlQuery(res.c_str(),sock))
488 errorStr = "Couldn't create users table list With error:\n";
489 errorStr += mysql_error(sock);
490 errorStr += "\n\n" + res;
495 res = "INSERT INTO users SET login='test',Address='',AlwaysOnline=0,"\
496 "Credit=0.0,CreditExpire=0,Down=0,Email='',DisabledDetailStat=0,"\
497 "StgGroup='',IP='192.168.1.1',Note='',Passive=0,Password='123456',"\
498 "Phone='', RealName='',Tariff='tariff',TariffChange='',NAS='',";
500 for (int i = 0; i < USERDATA_NUM; i++)
502 strprintf(¶m, " Userdata%d='',", i);
506 for (int i = 0; i < DIR_NUM; i++)
508 strprintf(¶m, " D%d=0,", i);
511 strprintf(¶m, " U%d=0,", i);
515 res += "Cash=10.0,FreeMb=0.0,LastActivityTime=0,LastCashAdd=0,"\
516 "LastCashAddTime=0, PassiveTime=0";
518 if(MysqlQuery(res.c_str(),sock))
520 errorStr = "Couldn't create default user. With error:\n";
521 errorStr += mysql_error(sock);
527 //logs-----------------------------------------------------------------------
528 if(!IsTablePresent("logs"))
530 sprintf(qbuf,"CREATE TABLE logs (unid INT UNSIGNED NOT NULL AUTO_INCREMENT PRIMARY KEY, login VARCHAR(40),text TEXT)");
534 errorStr = "Couldn't create admin table list With error:\n";
535 errorStr += mysql_error(sock);
540 //messages---------------------------------------------------------------------
541 if(!IsTablePresent("messages",sock))
543 sprintf(qbuf,"CREATE TABLE messages (login VARCHAR(40) DEFAULT '', id BIGINT, "\
544 "type INT, lastSendTime INT, creationTime INT, showTime INT,"\
545 "stgRepeat INT, repeatPeriod INT, text TEXT)");
547 if(MysqlQuery(qbuf,sock))
549 errorStr = "Couldn't create messages table. With error:\n";
550 errorStr += mysql_error(sock);
556 //month_stat-------------------------------------------------------------------
557 if(!IsTablePresent("stat",sock))
559 res = "CREATE TABLE stat (login VARCHAR(50), month TINYINT, year SMALLINT,";
561 for (int i = 0; i < DIR_NUM; i++)
563 strprintf(¶m, " U%d BIGINT,", i);
566 strprintf(¶m, " D%d BIGINT,", i);
570 res += " cash DOUBLE, INDEX (login))";
572 if(MysqlQuery(res.c_str(),sock))
574 errorStr = "Couldn't create stat table. With error:\n";
575 errorStr += mysql_error(sock);
583 //-----------------------------------------------------------------------------
584 int MYSQL_STORE::MakeUpdates(MYSQL * sock)
586 if (schemaVersion < 1)
588 if (MysqlQuery("ALTER TABLE tariffs ADD period VARCHAR(32) NOT NULL DEFAULT 'month'", sock))
590 errorStr = "Couldn't update tariffs table to version 1. With error:\n";
591 errorStr += mysql_error(sock);
595 if (MysqlQuery("UPDATE info SET version = 1", sock))
597 errorStr = "Couldn't update DB schema version to 1. With error:\n";
598 errorStr += mysql_error(sock);
603 logger("MYSQL_STORE: Updated DB schema to version %d", schemaVersion);
606 if (schemaVersion < 2)
608 if (MysqlQuery("ALTER TABLE tariffs ADD change_policy VARCHAR(32) NOT NULL DEFAULT 'allow'", sock) ||
609 MysqlQuery("ALTER TABLE tariffs ADD change_policy_timeout TIMESTAMP NOT NULL DEFAULT '1970-01-01 00:00:00'", sock))
611 errorStr = "Couldn't update tariffs table to version 2. With error:\n";
612 errorStr += mysql_error(sock);
616 if (MysqlQuery("UPDATE info SET version = 2", sock))
618 errorStr = "Couldn't update DB schema version to 2. With error:\n";
619 errorStr += mysql_error(sock);
624 logger("MYSQL_STORE: Updated DB schema to version %d", schemaVersion);
628 //-----------------------------------------------------------------------------
630 int MYSQL_STORE::GetAllParams(std::vector<std::string> * ParamList,
631 const std::string & table, const std::string & name) const
640 sprintf(qbuf,"SELECT %s FROM %s", name.c_str(), table.c_str());
642 if(MysqlGetQuery(qbuf,sock))
644 errorStr = "Couldn't GetAllParams Query for: ";
645 errorStr += name + " - " + table + "\n";
646 errorStr += mysql_error(sock);
651 if (!(res=mysql_store_result(sock)))
653 errorStr = "Couldn't GetAllParams Results for: ";
654 errorStr += name + " - " + table + "\n";
655 errorStr += mysql_error(sock);
659 num = mysql_num_rows(res);
661 for(i = 0; i < num; i++)
663 row = mysql_fetch_row(res);
664 ParamList->push_back(row[0]);
667 mysql_free_result(res);
673 //-----------------------------------------------------------------------------
674 int MYSQL_STORE::GetUsersList(std::vector<std::string> * usersList) const
676 if(GetAllParams(usersList, "users", "login"))
681 //-----------------------------------------------------------------------------
682 int MYSQL_STORE::GetAdminsList(std::vector<std::string> * adminsList) const
684 if(GetAllParams(adminsList, "admins", "login"))
689 //-----------------------------------------------------------------------------
690 int MYSQL_STORE::GetTariffsList(std::vector<std::string> * tariffsList) const
692 if(GetAllParams(tariffsList, "tariffs", "name"))
697 //-----------------------------------------------------------------------------
698 int MYSQL_STORE::AddUser(const std::string & login) const
700 std::string query = "INSERT INTO users SET login='" + login + "',Note='',NAS=''";
702 for (int i = 0; i < USERDATA_NUM; i++)
703 query += ",Userdata" + x2str(i) + "=''";
705 if(MysqlSetQuery(query.c_str()))
707 errorStr = "Couldn't add user:\n";
708 //errorStr += mysql_error(sock);
714 //-----------------------------------------------------------------------------
715 int MYSQL_STORE::DelUser(const std::string & login) const
717 sprintf(qbuf,"DELETE FROM users WHERE login='%s' LIMIT 1", login.c_str());
719 if(MysqlSetQuery(qbuf))
721 errorStr = "Couldn't delete user:\n";
722 //errorStr += mysql_error(sock);
728 //-----------------------------------------------------------------------------
729 int MYSQL_STORE::RestoreUserConf(USER_CONF * conf, const std::string & login) const
736 query = "SELECT login, Password, Passive, Down, DisabledDetailStat, \
737 AlwaysOnline, Tariff, Address, Phone, Email, Note, \
738 RealName, StgGroup, Credit, TariffChange, ";
740 for (int i = 0; i < USERDATA_NUM; i++)
742 sprintf(qbuf, "Userdata%d, ", i);
746 query += "CreditExpire, IP FROM users WHERE login='";
747 query += login + "' LIMIT 1";
749 //sprintf(qbuf,"SELECT * FROM users WHERE login='%s' LIMIT 1", login.c_str());
751 if(MysqlGetQuery(query.c_str(),sock))
753 errorStr = "Couldn't restore Tariff(on query):\n";
754 errorStr += mysql_error(sock);
759 if (!(res=mysql_store_result(sock)))
761 errorStr = "Couldn't restore Tariff(on getting result):\n";
762 errorStr += mysql_error(sock);
767 if (mysql_num_rows(res) != 1)
769 errorStr = "User not found";
774 row = mysql_fetch_row(res);
776 conf->password = row[1];
778 if (conf->password.empty())
780 mysql_free_result(res);
781 errorStr = "User \'" + login + "\' password is blank.";
786 if (GetInt(row[2],&conf->passive) != 0)
788 mysql_free_result(res);
789 errorStr = "User \'" + login + "\' data not read. Parameter Passive.";
794 if (GetInt(row[3], &conf->disabled) != 0)
796 mysql_free_result(res);
797 errorStr = "User \'" + login + "\' data not read. Parameter Down.";
802 if (GetInt(row[4], &conf->disabledDetailStat) != 0)
804 mysql_free_result(res);
805 errorStr = "User \'" + login + "\' data not read. Parameter DisabledDetailStat.";
810 if (GetInt(row[5], &conf->alwaysOnline) != 0)
812 mysql_free_result(res);
813 errorStr = "User \'" + login + "\' data not read. Parameter AlwaysOnline.";
818 conf->tariffName = row[6];
820 if (conf->tariffName.empty())
822 mysql_free_result(res);
823 errorStr = "User \'" + login + "\' tariff is blank.";
828 conf->address = row[7];
829 conf->phone = row[8];
830 conf->email = row[9];
831 conf->note = row[10];
832 conf->realName = row[11];
833 conf->group = row[12];
835 if (GetDouble(row[13], &conf->credit, 0) != 0)
837 mysql_free_result(res);
838 errorStr = "User \'" + login + "\' data not read. Parameter Credit.";
843 conf->nextTariff = row[14];
845 for (int i = 0; i < USERDATA_NUM; i++)
847 conf->userdata[i] = row[15+i];
850 GetTime(row[15+USERDATA_NUM], &conf->creditExpire, 0);
852 std::string ipStr = row[16+USERDATA_NUM];
858 catch (const std::string & s)
860 mysql_free_result(res);
861 errorStr = "User \'" + login + "\' data not read. Parameter IP address. " + s;
867 mysql_free_result(res);
872 //-----------------------------------------------------------------------------
873 int MYSQL_STORE::RestoreUserStat(USER_STAT * stat, const std::string & login) const
883 for (int i = 0; i < DIR_NUM; i++)
885 sprintf(qbuf, "D%d, U%d, ", i, i);
889 query += "Cash, FreeMb, LastCashAdd, LastCashAddTime, PassiveTime, LastActivityTime \
890 FROM users WHERE login = '";
891 query += login + "'";
893 //sprintf(qbuf,"SELECT * FROM users WHERE login='%s' LIMIT 1", login.c_str());
895 if(MysqlGetQuery(query.c_str() ,sock))
897 errorStr = "Couldn't restore UserStat(on query):\n";
898 errorStr += mysql_error(sock);
903 if (!(res=mysql_store_result(sock)))
905 errorStr = "Couldn't restore UserStat(on getting result):\n";
906 errorStr += mysql_error(sock);
911 row = mysql_fetch_row(res);
913 unsigned int startPos=0;
917 for (int i = 0; i < DIR_NUM; i++)
920 sprintf(s, "D%d", i);
921 if (GetULongLongInt(row[startPos+i*2], &traff, 0) != 0)
923 mysql_free_result(res);
924 errorStr = "User \'" + login + "\' stat not read. Parameter " + std::string(s);
928 stat->monthDown[i] = traff;
930 sprintf(s, "U%d", i);
931 if (GetULongLongInt(row[startPos+i*2+1], &traff, 0) != 0)
933 mysql_free_result(res);
934 errorStr = "User \'" + login + "\' stat not read. Parameter " + std::string(s);
938 stat->monthUp[i] = traff;
941 startPos += (2*DIR_NUM);
943 if (GetDouble(row[startPos], &stat->cash, 0) != 0)
945 mysql_free_result(res);
946 errorStr = "User \'" + login + "\' stat not read. Parameter Cash";
951 if (GetDouble(row[startPos+1],&stat->freeMb, 0) != 0)
953 mysql_free_result(res);
954 errorStr = "User \'" + login + "\' stat not read. Parameter FreeMb";
959 if (GetDouble(row[startPos+2], &stat->lastCashAdd, 0) != 0)
961 mysql_free_result(res);
962 errorStr = "User \'" + login + "\' stat not read. Parameter LastCashAdd";
967 if (GetTime(row[startPos+3], &stat->lastCashAddTime, 0) != 0)
969 mysql_free_result(res);
970 errorStr = "User \'" + login + "\' stat not read. Parameter LastCashAddTime";
975 if (GetTime(row[startPos+4], &stat->passiveTime, 0) != 0)
977 mysql_free_result(res);
978 errorStr = "User \'" + login + "\' stat not read. Parameter PassiveTime";
983 if (GetTime(row[startPos+5], &stat->lastActivityTime, 0) != 0)
985 mysql_free_result(res);
986 errorStr = "User \'" + login + "\' stat not read. Parameter LastActivityTime";
991 mysql_free_result(res);
995 //-----------------------------------------------------------------------------
996 int MYSQL_STORE::SaveUserConf(const USER_CONF & conf, const std::string & login) const
1001 strprintf(&res,"UPDATE users SET Password='%s', Passive=%d, Down=%d, DisabledDetailStat = %d, "\
1002 "AlwaysOnline=%d, Tariff='%s', Address='%s', Phone='%s', Email='%s', "\
1003 "Note='%s', RealName='%s', StgGroup='%s', Credit=%f, TariffChange='%s', ",
1004 conf.password.c_str(),
1007 conf.disabledDetailStat,
1009 conf.tariffName.c_str(),
1010 (ReplaceStr(conf.address,badSyms,repSym)).c_str(),
1011 (ReplaceStr(conf.phone,badSyms,repSym)).c_str(),
1012 (ReplaceStr(conf.email,badSyms,repSym)).c_str(),
1013 (ReplaceStr(conf.note,badSyms,repSym)).c_str(),
1014 (ReplaceStr(conf.realName,badSyms,repSym)).c_str(),
1015 (ReplaceStr(conf.group,badSyms,repSym)).c_str(),
1017 conf.nextTariff.c_str()
1020 for (int i = 0; i < USERDATA_NUM; i++)
1022 strprintf(¶m, " Userdata%d='%s',", i,
1023 (ReplaceStr(conf.userdata[i],badSyms,repSym)).c_str());
1027 strprintf(¶m, " CreditExpire=%d,", conf.creditExpire);
1030 std::ostringstream ipStr;
1033 strprintf(¶m, " IP='%s'", ipStr.str().c_str());
1036 strprintf(¶m, " WHERE login='%s' LIMIT 1", login.c_str());
1039 if(MysqlSetQuery(res.c_str()))
1041 errorStr = "Couldn't save user conf:\n";
1042 //errorStr += mysql_error(sock);
1048 //-----------------------------------------------------------------------------
1049 int MYSQL_STORE::SaveUserStat(const USER_STAT & stat, const std::string & login) const
1054 res = "UPDATE users SET";
1056 for (int i = 0; i < DIR_NUM; i++)
1058 strprintf(¶m, " D%d=%lld,", i, stat.monthDown[i]);
1061 strprintf(¶m, " U%d=%lld,", i, stat.monthUp[i]);
1065 strprintf(¶m, " Cash=%f, FreeMb=%f, LastCashAdd=%f, LastCashAddTime=%d,"\
1066 " PassiveTime=%d, LastActivityTime=%d",
1070 stat.lastCashAddTime,
1072 stat.lastActivityTime
1076 strprintf(¶m, " WHERE login='%s' LIMIT 1", login.c_str());
1079 if(MysqlSetQuery(res.c_str()))
1081 errorStr = "Couldn't save user stat:\n";
1082 // errorStr += mysql_error(sock);
1088 //-----------------------------------------------------------------------------
1089 int MYSQL_STORE::WriteLogString(const std::string & str, const std::string & login) const
1091 std::string res, tempStr;
1100 strprintf(&tempStr, "logs_%02d_%4d", lt->tm_mon+1, lt->tm_year+1900);
1101 if (!(sock=MysqlConnect())){
1102 errorStr = "Couldn't connect to Server";
1105 if (!(result=mysql_list_tables(sock,tempStr.c_str() )))
1107 errorStr = "Couldn't get table " + tempStr + ":\n";
1108 errorStr += mysql_error(sock);
1113 my_ulonglong num_rows = mysql_num_rows(result);
1115 mysql_free_result(result);
1119 sprintf(qbuf,"CREATE TABLE logs_%02d_%4d (unid INT UNSIGNED NOT NULL AUTO_INCREMENT PRIMARY KEY, login VARCHAR(40),text TEXT)",
1120 lt->tm_mon+1, lt->tm_year+1900);
1122 if(MysqlQuery(qbuf,sock))
1124 errorStr = "Couldn't create WriteDetailedStat table:\n";
1125 errorStr += mysql_error(sock);
1131 strprintf(&res, "%s -- %s",LogDate(t), str.c_str());
1135 strprintf(&send,"INSERT INTO logs_%02d_%4d SET login='%s', text='%s'",
1136 lt->tm_mon+1, lt->tm_year+1900,
1137 login.c_str(), (ReplaceStr(res,badSyms,repSym)).c_str());
1139 if(MysqlQuery(send.c_str(),sock))
1141 errorStr = "Couldn't write log string:\n";
1142 errorStr += mysql_error(sock);
1150 //-----------------------------------------------------------------------------
1151 int MYSQL_STORE::WriteUserChgLog(const std::string & login,
1152 const std::string & admLogin,
1154 const std::string & paramName,
1155 const std::string & oldValue,
1156 const std::string & newValue,
1157 const std::string & message) const
1159 std::string userLogMsg = "Admin \'" + admLogin + "\', " + inet_ntostring(admIP) + ": \'"
1160 + paramName + "\' parameter changed from \'" + oldValue +
1161 "\' to \'" + newValue + "\'. " + message;
1163 return WriteLogString(userLogMsg, login);
1165 //-----------------------------------------------------------------------------
1166 int MYSQL_STORE::WriteUserConnect(const std::string & login, uint32_t ip) const
1168 std::string logStr = "Connect, " + inet_ntostring(ip);
1169 return WriteLogString(logStr, login);
1171 //-----------------------------------------------------------------------------
1172 int MYSQL_STORE::WriteUserDisconnect(const std::string & login,
1173 const DIR_TRAFF & up,
1174 const DIR_TRAFF & down,
1175 const DIR_TRAFF & sessionUp,
1176 const DIR_TRAFF & sessionDown,
1179 const std::string & /*reason*/) const
1181 std::string logStr = "Disconnect, ";
1182 std::ostringstream sssu;
1183 std::ostringstream sssd;
1184 std::ostringstream ssmu;
1185 std::ostringstream ssmd;
1186 std::ostringstream sscash;
1192 sssd << sessionDown;
1196 logStr += " session upload: \'";
1197 logStr += sssu.str();
1198 logStr += "\' session download: \'";
1199 logStr += sssd.str();
1200 logStr += "\' month upload: \'";
1201 logStr += ssmu.str();
1202 logStr += "\' month download: \'";
1203 logStr += ssmd.str();
1204 logStr += "\' cash: \'";
1205 logStr += sscash.str();
1208 return WriteLogString(logStr, login);
1210 //-----------------------------------------------------------------------------
1211 int MYSQL_STORE::SaveMonthStat(const USER_STAT & stat, int month, int year,
1212 const std::string & login) const
1214 std::string param, res;
1216 strprintf(&res, "INSERT INTO stat SET login='%s', month=%d, year=%d,",
1217 login.c_str(), month+1, year+1900);
1219 for (int i = 0; i < DIR_NUM; i++)
1221 strprintf(¶m, " U%d=%lld,", i, stat.monthUp[i]);
1224 strprintf(¶m, " D%d=%lld,", i, stat.monthDown[i]);
1228 strprintf(¶m, " cash=%f", stat.cash);
1231 if(MysqlSetQuery(res.c_str()))
1233 errorStr = "Couldn't SaveMonthStat:\n";
1234 //errorStr += mysql_error(sock);
1240 //-----------------------------------------------------------------------------*/
1241 int MYSQL_STORE::AddAdmin(const std::string & login) const
1243 sprintf(qbuf,"INSERT INTO admins SET login='%s'", login.c_str());
1245 if(MysqlSetQuery(qbuf))
1247 errorStr = "Couldn't add admin:\n";
1248 //errorStr += mysql_error(sock);
1254 //-----------------------------------------------------------------------------*/
1255 int MYSQL_STORE::DelAdmin(const std::string & login) const
1257 sprintf(qbuf,"DELETE FROM admins where login='%s' LIMIT 1", login.c_str());
1259 if(MysqlSetQuery(qbuf))
1261 errorStr = "Couldn't delete admin:\n";
1262 //errorStr += mysql_error(sock);
1268 //-----------------------------------------------------------------------------*/
1269 int MYSQL_STORE::SaveAdmin(const ADMIN_CONF & ac) const
1271 char passwordE[2 * ADM_PASSWD_LEN + 2];
1272 char pass[ADM_PASSWD_LEN + 1];
1273 char adminPass[ADM_PASSWD_LEN + 1];
1275 memset(pass, 0, sizeof(pass));
1276 memset(adminPass, 0, sizeof(adminPass));
1279 InitContext(adm_enc_passwd, strlen(adm_enc_passwd), &ctx);
1281 strncpy(adminPass, ac.password.c_str(), ADM_PASSWD_LEN);
1282 adminPass[ADM_PASSWD_LEN - 1] = 0;
1284 for (int i = 0; i < ADM_PASSWD_LEN/8; i++)
1286 EncryptBlock(pass + 8*i, adminPass + 8*i, &ctx);
1289 pass[ADM_PASSWD_LEN - 1] = 0;
1290 Encode12(passwordE, pass, ADM_PASSWD_LEN);
1292 sprintf(qbuf,"UPDATE admins SET password='%s', ChgConf=%d, ChgPassword=%d, "\
1293 "ChgStat=%d, ChgCash=%d, UsrAddDel=%d, ChgTariff=%d, ChgAdmin=%d "\
1294 "WHERE login='%s' LIMIT 1",
1306 if(MysqlSetQuery(qbuf))
1308 errorStr = "Couldn't save admin:\n";
1309 //errorStr += mysql_error(sock);
1315 //-----------------------------------------------------------------------------
1316 int MYSQL_STORE::RestoreAdmin(ADMIN_CONF * ac, const std::string & login) const
1318 char pass[ADM_PASSWD_LEN + 1];
1319 char password[ADM_PASSWD_LEN + 1];
1320 char passwordE[2*ADM_PASSWD_LEN + 2];
1323 memset(password, 0, sizeof(password));
1329 sprintf(qbuf,"SELECT * FROM admins WHERE login='%s' LIMIT 1", login.c_str());
1331 if(MysqlGetQuery(qbuf,sock))
1333 errorStr = "Couldn't restore admin:\n";
1334 errorStr += mysql_error(sock);
1339 if (!(res=mysql_store_result(sock)))
1341 errorStr = "Couldn't restore admin:\n";
1342 errorStr += mysql_error(sock);
1347 if ( mysql_num_rows(res) == 0)
1349 mysql_free_result(res);
1350 errorStr = "Couldn't restore admin as couldn't found him in table.\n";
1355 row = mysql_fetch_row(res);
1361 mysql_free_result(res);
1362 errorStr = "Error in parameter password";
1367 memset(passwordE, 0, sizeof(passwordE));
1368 strncpy(passwordE, p.c_str(), 2*ADM_PASSWD_LEN);
1370 memset(pass, 0, sizeof(pass));
1372 if (passwordE[0] != 0)
1374 Decode21(pass, passwordE);
1375 InitContext(adm_enc_passwd, strlen(adm_enc_passwd), &ctx);
1377 for (int i = 0; i < ADM_PASSWD_LEN/8; i++)
1379 DecryptBlock(password + 8*i, pass + 8*i, &ctx);
1387 ac->password = password;
1391 if (GetInt(row[2], &a) == 0)
1392 ac->priv.userConf = a;
1395 mysql_free_result(res);
1396 errorStr = "Error in parameter ChgConf";
1401 if (GetInt(row[3], &a) == 0)
1402 ac->priv.userPasswd = a;
1405 mysql_free_result(res);
1406 errorStr = "Error in parameter ChgPassword";
1411 if (GetInt(row[4], &a) == 0)
1412 ac->priv.userStat = a;
1415 mysql_free_result(res);
1416 errorStr = "Error in parameter ChgStat";
1421 if (GetInt(row[5], &a) == 0)
1422 ac->priv.userCash = a;
1425 mysql_free_result(res);
1426 errorStr = "Error in parameter ChgCash";
1431 if (GetInt(row[6], &a) == 0)
1432 ac->priv.userAddDel = a;
1435 mysql_free_result(res);
1436 errorStr = "Error in parameter UsrAddDel";
1441 if (GetInt(row[7], &a) == 0)
1442 ac->priv.tariffChg = a;
1445 mysql_free_result(res);
1446 errorStr = "Error in parameter ChgTariff";
1451 if (GetInt(row[8], &a) == 0)
1452 ac->priv.adminChg = a;
1455 mysql_free_result(res);
1456 errorStr = "Error in parameter ChgAdmin";
1461 mysql_free_result(res);
1465 //-----------------------------------------------------------------------------
1466 int MYSQL_STORE::AddTariff(const std::string & name) const
1468 sprintf(qbuf,"INSERT INTO tariffs SET name='%s'", name.c_str());
1470 if(MysqlSetQuery(qbuf))
1472 errorStr = "Couldn't add tariff:\n";
1473 // errorStr += mysql_error(sock);
1479 //-----------------------------------------------------------------------------
1480 int MYSQL_STORE::DelTariff(const std::string & name) const
1482 sprintf(qbuf,"DELETE FROM tariffs WHERE name='%s' LIMIT 1", name.c_str());
1484 if(MysqlSetQuery(qbuf))
1486 errorStr = "Couldn't delete tariff: ";
1487 // errorStr += mysql_error(sock);
1493 //-----------------------------------------------------------------------------
1494 int MYSQL_STORE::RestoreTariff(TARIFF_DATA * td, const std::string & tariffName) const
1499 sprintf(qbuf,"SELECT * FROM tariffs WHERE name='%s' LIMIT 1", tariffName.c_str());
1501 if(MysqlGetQuery(qbuf,sock))
1503 errorStr = "Couldn't restore Tariff:\n";
1504 errorStr += mysql_error(sock);
1509 if (!(res=mysql_store_result(sock)))
1511 errorStr = "Couldn't restore Tariff:\n";
1512 errorStr += mysql_error(sock);
1518 td->tariffConf.name = tariffName;
1520 row = mysql_fetch_row(res);
1523 for (int i = 0; i<DIR_NUM; i++)
1525 strprintf(¶m, "Time%d", i);
1527 if (str.length() == 0)
1529 mysql_free_result(res);
1530 errorStr = "Cannot read tariff " + tariffName + ". Parameter " + param;
1535 ParseTariffTimeStr(str.c_str(),
1536 td->dirPrice[i].hDay,
1537 td->dirPrice[i].mDay,
1538 td->dirPrice[i].hNight,
1539 td->dirPrice[i].mNight);
1541 strprintf(¶m, "PriceDayA%d", i);
1542 if (GetDouble(row[1+i*8], &td->dirPrice[i].priceDayA, 0.0) < 0)
1544 mysql_free_result(res);
1545 errorStr = "Cannot read tariff " + tariffName + ". Parameter " + param;
1549 td->dirPrice[i].priceDayA /= (1024*1024);
1551 strprintf(¶m, "PriceDayB%d", i);
1552 if (GetDouble(row[2+i*8], &td->dirPrice[i].priceDayB, 0.0) < 0)
1554 mysql_free_result(res);
1555 errorStr = "Cannot read tariff " + tariffName + ". Parameter " + param;
1559 td->dirPrice[i].priceDayB /= (1024*1024);
1561 strprintf(¶m, "PriceNightA%d", i);
1562 if (GetDouble(row[3+i*8], &td->dirPrice[i].priceNightA, 0.0) < 0)
1564 mysql_free_result(res);
1565 errorStr = "Cannot read tariff " + tariffName + ". Parameter " + param;
1569 td->dirPrice[i].priceNightA /= (1024*1024);
1571 strprintf(¶m, "PriceNightB%d", i);
1572 if (GetDouble(row[4+i*8], &td->dirPrice[i].priceNightB, 0.0) < 0)
1574 mysql_free_result(res);
1575 errorStr = "Cannot read tariff " + tariffName + ". Parameter " + param;
1579 td->dirPrice[i].priceNightB /= (1024*1024);
1581 strprintf(¶m, "Threshold%d", i);
1582 if (GetInt(row[5+i*8], &td->dirPrice[i].threshold) < 0)
1584 mysql_free_result(res);
1585 errorStr = "Cannot read tariff " + tariffName + ". Parameter " + param;
1590 strprintf(¶m, "SinglePrice%d", i);
1591 if (GetInt(row[8+i*8], &td->dirPrice[i].singlePrice) < 0)
1593 mysql_free_result(res);
1594 errorStr = "Cannot read tariff " + tariffName + ". Parameter " + param;
1599 strprintf(¶m, "NoDiscount%d", i);
1600 if (GetInt(row[7+i*8], &td->dirPrice[i].noDiscount) < 0)
1602 mysql_free_result(res);
1603 errorStr = "Cannot read tariff " + tariffName + ". Parameter " + param;
1609 if (GetDouble(row[2+8*DIR_NUM], &td->tariffConf.fee, 0.0) < 0)
1611 mysql_free_result(res);
1612 errorStr = "Cannot read tariff " + tariffName + ". Parameter Fee";
1617 if (GetDouble(row[3+8*DIR_NUM], &td->tariffConf.free, 0.0) < 0)
1619 mysql_free_result(res);
1620 errorStr = "Cannot read tariff " + tariffName + ". Parameter Free";
1625 if (GetDouble(row[1+8*DIR_NUM], &td->tariffConf.passiveCost, 0.0) < 0)
1627 mysql_free_result(res);
1628 errorStr = "Cannot read tariff " + tariffName + ". Parameter PassiveCost";
1633 str = row[4+8*DIR_NUM];
1634 param = "TraffType";
1636 if (str.length() == 0)
1638 mysql_free_result(res);
1639 errorStr = "Cannot read tariff " + tariffName + ". Parameter " + param;
1644 td->tariffConf.traffType = TARIFF::StringToTraffType(str);
1646 if (schemaVersion > 0)
1648 str = row[5+8*DIR_NUM];
1651 if (str.length() == 0)
1653 mysql_free_result(res);
1654 errorStr = "Cannot read tariff " + tariffName + ". Parameter " + param;
1659 td->tariffConf.period = TARIFF::StringToPeriod(str);
1663 td->tariffConf.period = TARIFF::MONTH;
1666 if (schemaVersion > 1)
1668 str = row[6+8*DIR_NUM];
1669 param = "ChangePolicy";
1671 if (str.length() == 0)
1673 mysql_free_result(res);
1674 errorStr = "Cannot read tariff " + tariffName + ". Parameter " + param;
1679 td->tariffConf.changePolicy = TARIFF::StringToChangePolicy(str);
1683 td->tariffConf.changePolicy = TARIFF::ALLOW;
1686 mysql_free_result(res);
1690 //-----------------------------------------------------------------------------
1691 int MYSQL_STORE::SaveTariff(const TARIFF_DATA & td, const std::string & tariffName) const
1695 std::string res="UPDATE tariffs SET";
1697 for (int i = 0; i < DIR_NUM; i++)
1699 strprintf(¶m, " PriceDayA%d=%f,", i,
1700 td.dirPrice[i].priceDayA * pt_mega);
1703 strprintf(¶m, " PriceDayB%d=%f,", i,
1704 td.dirPrice[i].priceDayB * pt_mega);
1707 strprintf(¶m, " PriceNightA%d=%f,", i,
1708 td.dirPrice[i].priceNightA * pt_mega);
1711 strprintf(¶m, " PriceNightB%d=%f,", i,
1712 td.dirPrice[i].priceNightB * pt_mega);
1715 strprintf(¶m, " Threshold%d=%d,", i,
1716 td.dirPrice[i].threshold);
1720 strprintf(¶m, " Time%d", i);
1722 strprintf(&s, "%0d:%0d-%0d:%0d",
1723 td.dirPrice[i].hDay,
1724 td.dirPrice[i].mDay,
1725 td.dirPrice[i].hNight,
1726 td.dirPrice[i].mNight);
1728 res += (param + "='" + s + "',");
1730 strprintf(¶m, " NoDiscount%d=%d,", i,
1731 td.dirPrice[i].noDiscount);
1734 strprintf(¶m, " SinglePrice%d=%d,", i,
1735 td.dirPrice[i].singlePrice);
1739 strprintf(¶m, " PassiveCost=%f,", td.tariffConf.passiveCost);
1742 strprintf(¶m, " Fee=%f,", td.tariffConf.fee);
1745 strprintf(¶m, " Free=%f,", td.tariffConf.free);
1748 res += " TraffType='" + TARIFF::TraffTypeToString(td.tariffConf.traffType) + "'";
1750 if (schemaVersion > 0)
1751 res += ", Period='" + TARIFF::PeriodToString(td.tariffConf.period) + "'";
1753 if (schemaVersion > 1)
1754 res += ", change_policy='" + TARIFF::ChangePolicyToString(td.tariffConf.changePolicy) + "'";
1756 strprintf(¶m, " WHERE name='%s' LIMIT 1", tariffName.c_str());
1759 if(MysqlSetQuery(res.c_str()))
1761 errorStr = "Couldn't save tariff:\n";
1762 //errorStr += mysql_error(sock);
1768 //-----------------------------------------------------------------------------
1769 int MYSQL_STORE::WriteDetailedStat(const std::map<IP_DIR_PAIR, STAT_NODE> & statTree,
1771 const std::string & login) const
1773 std::string res, stTime, endTime, tempStr;
1780 if (lt->tm_hour == 0 && lt->tm_min <= 5)
1788 strprintf(&tempStr, "detailstat_%02d_%4d", lt->tm_mon+1, lt->tm_year+1900);
1790 if (!(sock=MysqlConnect())){
1795 if (!(result=mysql_list_tables(sock,tempStr.c_str() )))
1797 errorStr = "Couldn't get table " + tempStr + ":\n";
1798 errorStr += mysql_error(sock);
1803 my_ulonglong num_rows = mysql_num_rows(result);
1805 mysql_free_result(result);
1809 sprintf(qbuf,"CREATE TABLE detailstat_%02d_%4d (login VARCHAR(40) DEFAULT '',"\
1810 "day TINYINT DEFAULT 0,startTime TIME,endTime TIME,"\
1811 "IP VARCHAR(17) DEFAULT '',dir INT DEFAULT 0,"\
1812 "down BIGINT DEFAULT 0,up BIGINT DEFAULT 0, cash DOUBLE DEFAULT 0.0, INDEX (login), INDEX(dir), INDEX(day), INDEX(IP))",
1813 lt->tm_mon+1, lt->tm_year+1900);
1815 if(MysqlQuery(qbuf,sock))
1817 errorStr = "Couldn't create WriteDetailedStat table:\n";
1818 errorStr += mysql_error(sock);
1827 lt1 = localtime(&lastStat);
1836 lt2 = localtime(&t);
1842 strprintf(&stTime, "%02d:%02d:%02d", h1, m1, s1);
1843 strprintf(&endTime, "%02d:%02d:%02d", h2, m2, s2);
1845 strprintf(&res,"INSERT INTO detailstat_%02d_%4d SET login='%s',"\
1846 "day=%d,startTime='%s',endTime='%s',",
1847 lt->tm_mon+1, lt->tm_year+1900,
1854 std::map<IP_DIR_PAIR, STAT_NODE>::const_iterator stIter;
1855 stIter = statTree.begin();
1857 while (stIter != statTree.end())
1859 strprintf(&tempStr,"IP='%s', dir=%d, down=%lld, up=%lld, cash=%f",
1860 inet_ntostring(stIter->first.ip).c_str(),
1862 stIter->second.down,
1867 if( MysqlQuery((res+tempStr).c_str(),sock) )
1869 errorStr = "Couldn't insert data in WriteDetailedStat:\n";
1870 errorStr += mysql_error(sock);
1875 result=mysql_store_result(sock);
1877 mysql_free_result(result);
1884 //-----------------------------------------------------------------------------
1885 int MYSQL_STORE::AddMessage(STG_MSG * msg, const std::string & login) const
1889 gettimeofday(&tv, NULL);
1891 msg->header.id = static_cast<uint64_t>(tv.tv_sec) * 1000000 + static_cast<uint64_t>(tv.tv_usec);
1893 sprintf(qbuf,"INSERT INTO messages SET login='%s', id=%lld",
1895 static_cast<long long>(msg->header.id)
1898 if(MysqlSetQuery(qbuf))
1900 errorStr = "Couldn't add message:\n";
1901 //errorStr += mysql_error(sock);
1905 return EditMessage(*msg, login);
1907 //-----------------------------------------------------------------------------
1908 int MYSQL_STORE::EditMessage(const STG_MSG & msg, const std::string & login) const
1912 strprintf(&res,"UPDATE messages SET type=%d, lastSendTime=%u, creationTime=%u, "\
1913 "showTime=%u, stgRepeat=%d, repeatPeriod=%u, text='%s' "\
1914 "WHERE login='%s' AND id=%lld LIMIT 1",
1916 msg.header.lastSendTime,
1917 msg.header.creationTime,
1918 msg.header.showTime,
1920 msg.header.repeatPeriod,
1921 (ReplaceStr(msg.text,badSyms,repSym)).c_str(),
1926 if(MysqlSetQuery(res.c_str()))
1928 errorStr = "Couldn't edit message:\n";
1929 //errorStr += mysql_error(sock);
1935 //-----------------------------------------------------------------------------
1936 int MYSQL_STORE::GetMessage(uint64_t id, STG_MSG * msg, const std::string & login) const
1942 sprintf(qbuf,"SELECT * FROM messages WHERE login='%s' AND id=%llu LIMIT 1",
1943 login.c_str(), static_cast<unsigned long long>(id));
1945 if(MysqlGetQuery(qbuf,sock))
1947 errorStr = "Couldn't GetMessage:\n";
1948 errorStr += mysql_error(sock);
1953 if (!(res=mysql_store_result(sock)))
1955 errorStr = "Couldn't GetMessage:\n";
1956 errorStr += mysql_error(sock);
1961 row = mysql_fetch_row(res);
1963 if(row[2]&&str2x(row[2], msg->header.type))
1965 mysql_free_result(res);
1966 errorStr = "Invalid value in message header for user: " + login;
1971 if(row[3] && str2x(row[3], msg->header.lastSendTime))
1973 mysql_free_result(res);
1974 errorStr = "Invalid value in message header for user: " + login;
1979 if(row[4] && str2x(row[4], msg->header.creationTime))
1981 mysql_free_result(res);
1982 errorStr = "Invalid value in message header for user: " + login;
1987 if(row[5] && str2x(row[5], msg->header.showTime))
1989 mysql_free_result(res);
1990 errorStr = "Invalid value in message header for user: " + login;
1995 if(row[6] && str2x(row[6], msg->header.repeat))
1997 mysql_free_result(res);
1998 errorStr = "Invalid value in message header for user: " + login;
2003 if(row[7] && str2x(row[7], msg->header.repeatPeriod))
2005 mysql_free_result(res);
2006 errorStr = "Invalid value in message header for user: " + login;
2011 msg->header.id = id;
2014 mysql_free_result(res);
2018 //-----------------------------------------------------------------------------
2019 int MYSQL_STORE::DelMessage(uint64_t id, const std::string & login) const
2021 sprintf(qbuf,"DELETE FROM messages WHERE login='%s' AND id=%lld LIMIT 1",
2022 login.c_str(), static_cast<long long>(id));
2024 if(MysqlSetQuery(qbuf))
2026 errorStr = "Couldn't delete Message:\n";
2027 //errorStr += mysql_error(sock);
2033 //-----------------------------------------------------------------------------
2034 int MYSQL_STORE::GetMessageHdrs(std::vector<STG_MSG_HDR> * hdrsList, const std::string & login) const
2039 sprintf(qbuf,"SELECT * FROM messages WHERE login='%s'", login.c_str());
2041 if(MysqlGetQuery(qbuf,sock))
2043 errorStr = "Couldn't GetMessageHdrs:\n";
2044 errorStr += mysql_error(sock);
2049 if (!(res=mysql_store_result(sock)))
2051 errorStr = "Couldn't GetMessageHdrs:\n";
2052 errorStr += mysql_error(sock);
2058 my_ulonglong num_rows = mysql_num_rows(res);
2061 for (i = 0; i < num_rows; i++)
2063 row = mysql_fetch_row(res);
2064 if (str2x(row[1], id))
2069 if(str2x(row[2], hdr.type))
2073 if(str2x(row[3], hdr.lastSendTime))
2077 if(str2x(row[4], hdr.creationTime))
2081 if(str2x(row[5], hdr.showTime))
2085 if(str2x(row[6], hdr.repeat))
2089 if(str2x(row[7], hdr.repeatPeriod))
2093 hdrsList->push_back(hdr);
2096 mysql_free_result(res);
2100 //-----------------------------------------------------------------------------
2102 int MYSQL_STORE::MysqlSetQuery(const char * Query) const {
2105 int ret=MysqlGetQuery(Query,sock);
2109 //-----------------------------------------------------------------------------
2110 int MYSQL_STORE::MysqlGetQuery(const char * Query,MYSQL * & sock) const {
2111 if (!(sock=MysqlConnect())) {
2114 return MysqlQuery(Query,sock);
2116 //-----------------------------------------------------------------------------
2117 MYSQL * MYSQL_STORE::MysqlConnect() const {
2119 if ( !(sock=mysql_init(NULL)) ){
2120 errorStr= "mysql init susck\n";
2123 if (!(sock = mysql_real_connect(sock,storeSettings.GetDBHost().c_str(),
2124 storeSettings.GetDBUser().c_str(),storeSettings.GetDBPassword().c_str(),
2127 errorStr = "Couldn't connect to mysql engine! With error:\n";
2128 errorStr += mysql_error(sock);
2132 if(mysql_select_db(sock, storeSettings.GetDBName().c_str())){
2133 errorStr = "Database lost !\n";
2139 //-----------------------------------------------------------------------------