X-Git-Url: https://git.stg.codes/stg.git/blobdiff_plain/90e389f6ec12e60a62c362296ffcf314feb5b03d..ebd170a764ab9660adee464588cda1801c7986b4:/projects/stargazer/plugins/store/postgresql/postgresql_store_users.cpp diff --git a/projects/stargazer/plugins/store/postgresql/postgresql_store_users.cpp b/projects/stargazer/plugins/store/postgresql/postgresql_store_users.cpp index 11c757f2..3e564337 100644 --- a/projects/stargazer/plugins/store/postgresql/postgresql_store_users.cpp +++ b/projects/stargazer/plugins/store/postgresql/postgresql_store_users.cpp @@ -26,6 +26,16 @@ * */ +#include "postgresql_store.h" + +#include "stg/user_conf.h" +#include "stg/user_stat.h" +#include "stg/user_ips.h" +#include "stg/user_traff.h" +#include "stg/common.h" +#include "stg/const.h" +#include "../../../stg_timer.h" + #include #include #include @@ -33,15 +43,10 @@ #include -#include "stg/const.h" -#include "stg/locker.h" -#include "../../../stg_timer.h" -#include "postgresql_store.h" - //----------------------------------------------------------------------------- -int POSTGRESQL_STORE::GetUsersList(vector * usersList) const +int POSTGRESQL_STORE::GetUsersList(std::vector * usersList) const { -STG_LOCKER lock(&mutex, __FILE__, __LINE__); +std::lock_guard lock(m_mutex); if (PQstatus(connection) != CONNECTION_OK) { @@ -70,9 +75,9 @@ if (PQresultStatus(result) != PGRES_TUPLES_OK) PQclear(result); printfd(__FILE__, "POSTGRESQL_STORE::GetUsersList(): '%s'\n", strError.c_str()); if (RollbackTransaction()) - { - printfd(__FILE__, "POSTGRESQL_STORE::GetUsersList(): 'Failed to rollback transaction'\n"); - } + { + printfd(__FILE__, "POSTGRESQL_STORE::GetUsersList(): 'Failed to rollback transaction'\n"); + } return -1; } @@ -95,9 +100,9 @@ return 0; } //----------------------------------------------------------------------------- -int POSTGRESQL_STORE::AddUser(const string & name) const +int POSTGRESQL_STORE::AddUser(const std::string & name) const { -STG_LOCKER lock(&mutex, __FILE__, __LINE__); +std::lock_guard lock(m_mutex); if (PQstatus(connection) != CONNECTION_OK) { @@ -124,13 +129,13 @@ if (EscapeString(elogin)) { printfd(__FILE__, "POSTGRESQL_STORE::AddUser(): 'Failed to escape login'\n"); if (RollbackTransaction()) - { - printfd(__FILE__, "POSTGRESQL_STORE::AddUser(): 'Failed to rollback transaction'\n"); - } + { + printfd(__FILE__, "POSTGRESQL_STORE::AddUser(): 'Failed to rollback transaction'\n"); + } return -1; } -std::stringstream query; +std::ostringstream query; query << "SELECT sp_add_user('" << elogin << "')"; result = PQexec(connection, query.str().c_str()); @@ -141,9 +146,9 @@ if (PQresultStatus(result) != PGRES_TUPLES_OK) PQclear(result); printfd(__FILE__, "POSTGRESQL_STORE::AddUser(): '%s'\n", strError.c_str()); if (RollbackTransaction()) - { - printfd(__FILE__, "POSTGRESQL_STORE::AddUser(): 'Failed to rollback transaction'\n"); - } + { + printfd(__FILE__, "POSTGRESQL_STORE::AddUser(): 'Failed to rollback transaction'\n"); + } return -1; } @@ -159,9 +164,9 @@ return 0; } //----------------------------------------------------------------------------- -int POSTGRESQL_STORE::DelUser(const string & login) const +int POSTGRESQL_STORE::DelUser(const std::string & login) const { -STG_LOCKER lock(&mutex, __FILE__, __LINE__); +std::lock_guard lock(m_mutex); if (PQstatus(connection) != CONNECTION_OK) { @@ -188,13 +193,13 @@ if (EscapeString(elogin)) { printfd(__FILE__, "POSTGRESQL_STORE::DelUser(): 'Failed to escape login'\n"); if (RollbackTransaction()) - { - printfd(__FILE__, "POSTGRESQL_STORE::DelUser(): 'Failed to rollback transaction'\n"); - } + { + printfd(__FILE__, "POSTGRESQL_STORE::DelUser(): 'Failed to rollback transaction'\n"); + } return -1; } -std::stringstream query; +std::ostringstream query; query << "DELETE FROM tb_users WHERE name = '" << elogin << "'"; result = PQexec(connection, query.str().c_str()); @@ -205,9 +210,9 @@ if (PQresultStatus(result) != PGRES_COMMAND_OK) PQclear(result); printfd(__FILE__, "POSTGRESQL_STORE::DelUser(): '%s'\n", strError.c_str()); if (RollbackTransaction()) - { - printfd(__FILE__, "POSTGRESQL_STORE::DelUser(): 'Failed to rollback transaction'\n"); - } + { + printfd(__FILE__, "POSTGRESQL_STORE::DelUser(): 'Failed to rollback transaction'\n"); + } return -1; } @@ -222,16 +227,16 @@ if (CommitTransaction()) return 0; } //----------------------------------------------------------------------------- -int POSTGRESQL_STORE::SaveUserStat(const USER_STAT & stat, - const string & login) const +int POSTGRESQL_STORE::SaveUserStat(const STG::UserStat & stat, + const std::string & login) const { -STG_LOCKER lock(&mutex, __FILE__, __LINE__); +std::lock_guard lock(m_mutex); return SaveStat(stat, login); } //----------------------------------------------------------------------------- -int POSTGRESQL_STORE::SaveStat(const USER_STAT & stat, - const string & login, +int POSTGRESQL_STORE::SaveStat(const STG::UserStat & stat, + const std::string & login, int year, int month) const { @@ -260,19 +265,19 @@ if (EscapeString(elogin)) { printfd(__FILE__, "POSTGRESQL_STORE::SaveStat(): 'Failed to escape login'\n"); if (RollbackTransaction()) - { - printfd(__FILE__, "POSTGRESQL_STORE::SaveStat(): 'Failed to rollback transaction'\n"); - } + { + printfd(__FILE__, "POSTGRESQL_STORE::SaveStat(): 'Failed to rollback transaction'\n"); + } return -1; } -std::stringstream query; +std::ostringstream query; query << "UPDATE tb_users SET " "cash = " << stat.cash << ", " "free_mb = " << stat.freeMb << ", " - "last_activity_time = CAST('" << Int2TS(stat.lastActivityTime) << "' AS TIMESTAMP), " + "last_activity_time = CAST('" << formatTime(stat.lastActivityTime) << "' AS TIMESTAMP), " "last_cash_add = " << stat.lastCashAdd << ", " - "last_cash_add_time = CAST('" << Int2TS(stat.lastCashAddTime) << "' AS TIMESTAMP), " + "last_cash_add_time = CAST('" << formatTime(stat.lastCashAddTime) << "' AS TIMESTAMP), " "passive_time = " << stat.passiveTime << " " "WHERE name = '" << elogin << "'"; @@ -284,9 +289,9 @@ if (PQresultStatus(result) != PGRES_COMMAND_OK) PQclear(result); printfd(__FILE__, "POSTGRESQL_STORE::SaveStat(): '%s'\n", strError.c_str()); if (RollbackTransaction()) - { - printfd(__FILE__, "POSTGRESQL_STORE::SaveStat(): 'Failed to rollback transaction'\n"); - } + { + printfd(__FILE__, "POSTGRESQL_STORE::SaveStat(): 'Failed to rollback transaction'\n"); + } return -1; } @@ -303,8 +308,8 @@ for (int dir = 0; dir < DIR_NUM; ++dir) "'" << elogin << "', " "CAST('" << date << "' AS DATE), " "CAST(" << dir << " AS SMALLINT), " - "CAST(" << stat.up[dir] << " AS BIGINT), " - "CAST(" << stat.down[dir] << " AS BIGINT))"; + "CAST(" << stat.monthUp[dir] << " AS BIGINT), " + "CAST(" << stat.monthDown[dir] << " AS BIGINT))"; result = PQexec(connection, query.str().c_str()); @@ -333,10 +338,10 @@ return 0; } //----------------------------------------------------------------------------- -int POSTGRESQL_STORE::SaveUserConf(const USER_CONF & conf, - const string & login) const +int POSTGRESQL_STORE::SaveUserConf(const STG::UserConf & conf, + const std::string & login) const { -STG_LOCKER lock(&mutex, __FILE__, __LINE__); +std::lock_guard lock(m_mutex); if (PQstatus(connection) != CONNECTION_OK) { @@ -363,13 +368,13 @@ if (EscapeString(elogin)) { printfd(__FILE__, "POSTGRESQL_STORE::SaveUserConf(): 'Failed to escape login'\n"); if (RollbackTransaction()) - { - printfd(__FILE__, "POSTGRESQL_STORE::SaveUserConf(): 'Failed to rollback transaction'\n"); - } + { + printfd(__FILE__, "POSTGRESQL_STORE::SaveUserConf(): 'Failed to rollback transaction'\n"); + } return -1; } -std::stringstream query; +std::ostringstream query; query << "SELECT pk_user FROM tb_users WHERE name = '" << elogin << "'"; result = PQexec(connection, query.str().c_str()); @@ -380,9 +385,9 @@ if (PQresultStatus(result) != PGRES_TUPLES_OK) PQclear(result); printfd(__FILE__, "POSTGRESQL_STORE::SaveUserConf(): '%s'\n", strError.c_str()); if (RollbackTransaction()) - { - printfd(__FILE__, "POSTGRESQL_STORE::SaveUserConf(): 'Failed to rollback transaction'\n"); - } + { + printfd(__FILE__, "POSTGRESQL_STORE::SaveUserConf(): 'Failed to rollback transaction'\n"); + } return -1; } @@ -394,20 +399,22 @@ if (tuples != 1) printfd(__FILE__, "POSTGRESQL_STORE::SaveUserConf(): 'Invalid number of tuples. Wanted 1, actulally %d'\n", tuples); PQclear(result); if (RollbackTransaction()) - { - printfd(__FILE__, "POSTGRESQL_STORE::SaveUserConf(): 'Failed to rollback transaction'\n"); - } + { + printfd(__FILE__, "POSTGRESQL_STORE::SaveUserConf(): 'Failed to rollback transaction'\n"); + } return -1; } -std::stringstream tuple; -tuple << PQgetvalue(result, 0, 0); +uint32_t uid; -PQclear(result); + { + std::stringstream tuple; + tuple << PQgetvalue(result, 0, 0); -uint32_t uid; + PQclear(result); -tuple >> uid; + tuple >> uid; + } std::string eaddress = conf.address; std::string eemail = conf.email; @@ -424,9 +431,9 @@ if (EscapeString(eaddress)) { printfd(__FILE__, "POSTGRESQL_STORE::SaveUserConf(): 'Failed to escape address'\n"); if (RollbackTransaction()) - { - printfd(__FILE__, "POSTGRESQL_STORE::SaveUserConf(): 'Failed to rollback transaction'\n"); - } + { + printfd(__FILE__, "POSTGRESQL_STORE::SaveUserConf(): 'Failed to rollback transaction'\n"); + } return -1; } @@ -434,9 +441,9 @@ if (EscapeString(eemail)) { printfd(__FILE__, "POSTGRESQL_STORE::SaveUserConf(): 'Failed to escape email'\n"); if (RollbackTransaction()) - { - printfd(__FILE__, "POSTGRESQL_STORE::SaveUserConf(): 'Failed to rollback transaction'\n"); - } + { + printfd(__FILE__, "POSTGRESQL_STORE::SaveUserConf(): 'Failed to rollback transaction'\n"); + } return -1; } @@ -444,9 +451,9 @@ if (EscapeString(egroup)) { printfd(__FILE__, "POSTGRESQL_STORE::SaveUserConf(): 'Failed to escape group'\n"); if (RollbackTransaction()) - { - printfd(__FILE__, "POSTGRESQL_STORE::SaveUserConf(): 'Failed to rollback transaction'\n"); - } + { + printfd(__FILE__, "POSTGRESQL_STORE::SaveUserConf(): 'Failed to rollback transaction'\n"); + } return -1; } @@ -454,9 +461,9 @@ if (EscapeString(enote)) { printfd(__FILE__, "POSTGRESQL_STORE::SaveUserConf(): 'Failed to escape note'\n"); if (RollbackTransaction()) - { - printfd(__FILE__, "POSTGRESQL_STORE::SaveUserConf(): 'Failed to rollback transaction'\n"); - } + { + printfd(__FILE__, "POSTGRESQL_STORE::SaveUserConf(): 'Failed to rollback transaction'\n"); + } return -1; } @@ -464,9 +471,9 @@ if (EscapeString(epassword)) { printfd(__FILE__, "POSTGRESQL_STORE::SaveUserConf(): 'Failed to escape password'\n"); if (RollbackTransaction()) - { - printfd(__FILE__, "POSTGRESQL_STORE::SaveUserConf(): 'Failed to rollback transaction'\n"); - } + { + printfd(__FILE__, "POSTGRESQL_STORE::SaveUserConf(): 'Failed to rollback transaction'\n"); + } return -1; } @@ -474,9 +481,9 @@ if (EscapeString(ephone)) { printfd(__FILE__, "POSTGRESQL_STORE::SaveUserConf(): 'Failed to escape phone'\n"); if (RollbackTransaction()) - { - printfd(__FILE__, "POSTGRESQL_STORE::SaveUserConf(): 'Failed to rollback transaction'\n"); - } + { + printfd(__FILE__, "POSTGRESQL_STORE::SaveUserConf(): 'Failed to rollback transaction'\n"); + } return -1; } @@ -484,9 +491,9 @@ if (EscapeString(erealname)) { printfd(__FILE__, "POSTGRESQL_STORE::SaveUserConf(): 'Failed to escape real name'\n"); if (RollbackTransaction()) - { - printfd(__FILE__, "POSTGRESQL_STORE::SaveUserConf(): 'Failed to rollback transaction'\n"); - } + { + printfd(__FILE__, "POSTGRESQL_STORE::SaveUserConf(): 'Failed to rollback transaction'\n"); + } return -1; } @@ -494,9 +501,9 @@ if (EscapeString(etariffname)) { printfd(__FILE__, "POSTGRESQL_STORE::SaveUserConf(): 'Failed to escape tariff name'\n"); if (RollbackTransaction()) - { - printfd(__FILE__, "POSTGRESQL_STORE::SaveUserConf(): 'Failed to rollback transaction'\n"); - } + { + printfd(__FILE__, "POSTGRESQL_STORE::SaveUserConf(): 'Failed to rollback transaction'\n"); + } return -1; } @@ -504,9 +511,9 @@ if (EscapeString(enexttariff)) { printfd(__FILE__, "POSTGRESQL_STORE::SaveUserConf(): 'Failed to escape next tariff name'\n"); if (RollbackTransaction()) - { - printfd(__FILE__, "POSTGRESQL_STORE::SaveUserConf(): 'Failed to rollback transaction'\n"); - } + { + printfd(__FILE__, "POSTGRESQL_STORE::SaveUserConf(): 'Failed to rollback transaction'\n"); + } return -1; } @@ -514,9 +521,9 @@ if (EscapeString(ecorporation)) { printfd(__FILE__, "POSTGRESQL_STORE::SaveUserConf(): 'Failed to escape corporation name'\n"); if (RollbackTransaction()) - { - printfd(__FILE__, "POSTGRESQL_STORE::SaveUserConf(): 'Failed to rollback transaction'\n"); - } + { + printfd(__FILE__, "POSTGRESQL_STORE::SaveUserConf(): 'Failed to rollback transaction'\n"); + } return -1; } @@ -525,7 +532,7 @@ query << "UPDATE tb_users SET " "address = '" << eaddress << "', " "always_online = " << (conf.alwaysOnline ? "'t'" : "'f'") << ", " "credit = " << conf.credit << ", " - "credit_expire = CAST('" << Int2TS(conf.creditExpire) << "' AS TIMESTAMP), " + "credit_expire = CAST('" << formatTime(conf.creditExpire) << "' AS TIMESTAMP), " "disabled = " << (conf.disabled ? "'t'" : "'f'") << ", " "disabled_detail_stat = " << (conf.disabledDetailStat ? "'t'" : "'f'") << ", " "email = '" << eemail << "', " @@ -554,15 +561,15 @@ if (PQresultStatus(result) != PGRES_COMMAND_OK) PQclear(result); printfd(__FILE__, "POSTGRESQL_STORE::SaveUserConf(): '%s'\n", strError.c_str()); if (RollbackTransaction()) - { - printfd(__FILE__, "POSTGRESQL_STORE::SaveUserConf(): 'Failed to rollback transaction'\n"); - } + { + printfd(__FILE__, "POSTGRESQL_STORE::SaveUserConf(): 'Failed to rollback transaction'\n"); + } return -1; } PQclear(result); -if (SaveUserServices(uid, conf.service)) +if (SaveUserServices(uid, conf.services)) { printfd(__FILE__, "POSTGRESQL_STORE::SaveUserConf(): 'Failed to save user's services'\n"); if (RollbackTransaction()) @@ -602,10 +609,10 @@ return 0; } //----------------------------------------------------------------------------- -int POSTGRESQL_STORE::RestoreUserStat(USER_STAT * stat, - const string & login) const +int POSTGRESQL_STORE::RestoreUserStat(STG::UserStat * stat, + const std::string & login) const { -STG_LOCKER lock(&mutex, __FILE__, __LINE__); +std::lock_guard lock(m_mutex); if (PQstatus(connection) != CONNECTION_OK) { @@ -632,20 +639,22 @@ if (EscapeString(elogin)) { printfd(__FILE__, "POSTGRESQL_STORE::RestoreUserStat(): 'Failed to escape login'\n"); if (RollbackTransaction()) - { - printfd(__FILE__, "POSTGRESQL_STORE::RestoreUserStat(): 'Failed to rollback transaction'\n"); - } + { + printfd(__FILE__, "POSTGRESQL_STORE::RestoreUserStat(): 'Failed to rollback transaction'\n"); + } return -1; } -std::stringstream query; -query << "SELECT cash, free_mb, " - "last_activity_time, last_cash_add, " - "last_cash_add_time, passive_time " - "FROM tb_users " - "WHERE name = '" << elogin << "'"; + { + std::ostringstream query; + query << "SELECT cash, free_mb, " + "last_activity_time, last_cash_add, " + "last_cash_add_time, passive_time " + "FROM tb_users " + "WHERE name = '" << elogin << "'"; -result = PQexec(connection, query.str().c_str()); + result = PQexec(connection, query.str().c_str()); + } if (PQresultStatus(result) != PGRES_TUPLES_OK) { @@ -653,9 +662,9 @@ if (PQresultStatus(result) != PGRES_TUPLES_OK) printfd(__FILE__, "POSTGRESQL_STORE::RestoreUserStat(): '%s'\n", strError.c_str()); PQclear(result); if (RollbackTransaction()) - { - printfd(__FILE__, "POSTGRESQL_STORE::RestoreUserStat(): 'Failed to rollback transaction'\n"); - } + { + printfd(__FILE__, "POSTGRESQL_STORE::RestoreUserStat(): 'Failed to rollback transaction'\n"); + } return -1; } @@ -667,35 +676,38 @@ if (tuples != 1) printfd(__FILE__, "POSTGRESQL_STORE::RestoreUserStat(): 'Invalid number of tuples. Wanted 1, actulally %d'\n", tuples); PQclear(result); if (RollbackTransaction()) - { - printfd(__FILE__, "POSTGRESQL_STORE::RestoreUserStat(): 'Failed to rollback transaction'\n"); - } + { + printfd(__FILE__, "POSTGRESQL_STORE::RestoreUserStat(): 'Failed to rollback transaction'\n"); + } return -1; } -std::stringstream tuple; -tuple << PQgetvalue(result, 0, 0) << " "; -tuple << PQgetvalue(result, 0, 1) << " "; -stat->lastActivityTime = TS2Int(PQgetvalue(result, 0, 2)); -tuple << PQgetvalue(result, 0, 3) << " "; -stat->lastCashAddTime = TS2Int(PQgetvalue(result, 0, 4)); -tuple << PQgetvalue(result, 0, 5) << " "; - -PQclear(result); + { + std::stringstream tuple; + tuple << PQgetvalue(result, 0, 0) << " "; + tuple << PQgetvalue(result, 0, 1) << " "; + stat->lastActivityTime = readTime(PQgetvalue(result, 0, 2)); + tuple << PQgetvalue(result, 0, 3) << " "; + stat->lastCashAddTime = readTime(PQgetvalue(result, 0, 4)); + tuple << PQgetvalue(result, 0, 5) << " "; -tuple >> stat->cash - >> stat->freeMb - >> stat->lastCashAdd - >> stat->passiveTime; + PQclear(result); -query.str(""); + tuple >> stat->cash + >> stat->freeMb + >> stat->lastCashAdd + >> stat->passiveTime; + } -query << "SELECT dir_num, upload, download " - "FROM tb_stats_traffic " - "WHERE fk_user IN (SELECT pk_user FROM tb_users WHERE name = '" << elogin << "') AND " - "DATE_TRUNC('month', stats_date) = DATE_TRUNC('month', CAST('" << Int2TS(stgTime) << "' AS TIMESTAMP))"; + { + std::ostringstream query; + query << "SELECT dir_num, upload, download " + "FROM tb_stats_traffic " + "WHERE fk_user IN (SELECT pk_user FROM tb_users WHERE name = '" << elogin << "') AND " + "DATE_TRUNC('month', stats_date) = DATE_TRUNC('month', CAST('" << formatTime(stgTime) << "' AS TIMESTAMP))"; -result = PQexec(connection, query.str().c_str()); + result = PQexec(connection, query.str().c_str()); + } if (PQresultStatus(result) != PGRES_TUPLES_OK) { @@ -703,9 +715,9 @@ if (PQresultStatus(result) != PGRES_TUPLES_OK) printfd(__FILE__, "POSTGRESQL_STORE::RestoreUserStat(): '%s'\n", strError.c_str()); PQclear(result); if (RollbackTransaction()) - { - printfd(__FILE__, "POSTGRESQL_STORE::RestoreUserStat(): 'Failed to rollback transaction'\n"); - } + { + printfd(__FILE__, "POSTGRESQL_STORE::RestoreUserStat(): 'Failed to rollback transaction'\n"); + } return -1; } @@ -721,8 +733,8 @@ for (int i = 0; i < tuples; ++i) int dir; tuple >> dir; - tuple >> stat->up[dir]; - tuple >> stat->down[dir]; + tuple >> stat->monthUp[dir]; + tuple >> stat->monthDown[dir]; } PQclear(result); @@ -737,10 +749,10 @@ return 0; } //----------------------------------------------------------------------------- -int POSTGRESQL_STORE::RestoreUserConf(USER_CONF * conf, - const string & login) const +int POSTGRESQL_STORE::RestoreUserConf(STG::UserConf * conf, + const std::string & login) const { -STG_LOCKER lock(&mutex, __FILE__, __LINE__); +std::lock_guard lock(m_mutex); if (PQstatus(connection) != CONNECTION_OK) { @@ -767,27 +779,29 @@ if (EscapeString(elogin)) { printfd(__FILE__, "POSTGRESQL_STORE::RestoreUserStat(): 'Failed to escape login'\n"); if (RollbackTransaction()) - { - printfd(__FILE__, "POSTGRESQL_STORE::RestoreUserStat(): 'Failed to rollback transaction'\n"); - } - return -1; - } - -std::stringstream query; -query << "SELECT tb_users.pk_user, tb_users.address, tb_users.always_online, " - "tb_users.credit, tb_users.credit_expire, tb_users.disabled, " - "tb_users.disabled_detail_stat, tb_users.email, tb_users.grp, " - "tb_users.note, tb_users.passive, tb_users.passwd, tb_users.phone, " - "tb_users.real_name, tf1.name, tf2.name, tb_corporations.name " - "FROM tb_users LEFT JOIN tb_tariffs AS tf1 " - "ON tf1.pk_tariff = tb_users.fk_tariff " - "LEFT JOIN tb_tariffs AS tf2 " - "ON tf2.pk_tariff = tb_users.fk_tariff_change " - "LEFT JOIN tb_corporations " - "ON tb_corporations.pk_corporation = tb_users.fk_corporation " - "WHERE tb_users.name = '" << elogin << "'"; + { + printfd(__FILE__, "POSTGRESQL_STORE::RestoreUserStat(): 'Failed to rollback transaction'\n"); + } + return -1; + } -result = PQexec(connection, query.str().c_str()); + { + std::ostringstream query; + query << "SELECT tb_users.pk_user, tb_users.address, tb_users.always_online, " + "tb_users.credit, tb_users.credit_expire, tb_users.disabled, " + "tb_users.disabled_detail_stat, tb_users.email, tb_users.grp, " + "tb_users.note, tb_users.passive, tb_users.passwd, tb_users.phone, " + "tb_users.real_name, tf1.name, tf2.name, tb_corporations.name " + "FROM tb_users LEFT JOIN tb_tariffs AS tf1 " + "ON tf1.pk_tariff = tb_users.fk_tariff " + "LEFT JOIN tb_tariffs AS tf2 " + "ON tf2.pk_tariff = tb_users.fk_tariff_change " + "LEFT JOIN tb_corporations " + "ON tb_corporations.pk_corporation = tb_users.fk_corporation " + "WHERE tb_users.name = '" << elogin << "'"; + + result = PQexec(connection, query.str().c_str()); + } if (PQresultStatus(result) != PGRES_TUPLES_OK) { @@ -795,9 +809,9 @@ if (PQresultStatus(result) != PGRES_TUPLES_OK) printfd(__FILE__, "POSTGRESQL_STORE::RestoreUserConf(): '%s'\n", strError.c_str()); PQclear(result); if (RollbackTransaction()) - { - printfd(__FILE__, "POSTGRESQL_STORE::RestoreUserConf(): 'Failed to rollback transaction'\n"); - } + { + printfd(__FILE__, "POSTGRESQL_STORE::RestoreUserConf(): 'Failed to rollback transaction'\n"); + } return -1; } @@ -809,51 +823,54 @@ if (tuples != 1) printfd(__FILE__, "POSTGRESQL_STORE::RestoreUserConf(): 'Invalid number of tuples. Wanted 1, actulally %d'\n", tuples); PQclear(result); if (RollbackTransaction()) - { - printfd(__FILE__, "POSTGRESQL_STORE::RestoreUserConf(): 'Failed to rollback transaction'\n"); - } + { + printfd(__FILE__, "POSTGRESQL_STORE::RestoreUserConf(): 'Failed to rollback transaction'\n"); + } return -1; } uint32_t uid; -std::stringstream tuple; - -tuple << PQgetvalue(result, 0, 0) << " "; // uid -conf->address = PQgetvalue(result, 0, 1); // address -conf->alwaysOnline = !strncmp(PQgetvalue(result, 0, 2), "t", 1); -tuple << PQgetvalue(result, 0, 3) << " "; // credit -conf->creditExpire = TS2Int(PQgetvalue(result, 0, 4)); // creditExpire -conf->disabled = !strncmp(PQgetvalue(result, 0, 5), "t", 1); -conf->disabledDetailStat = !strncmp(PQgetvalue(result, 0, 6), "t", 1); -conf->email = PQgetvalue(result, 0, 7); // email -conf->group = PQgetvalue(result, 0, 8); // group -conf->note = PQgetvalue(result, 0, 9); // note -conf->passive = !strncmp(PQgetvalue(result, 0, 10), "t", 1); -conf->password = PQgetvalue(result, 0, 11); // password -conf->phone = PQgetvalue(result, 0, 12); // phone -conf->realName = PQgetvalue(result, 0, 13); // realName -conf->tariffName = PQgetvalue(result, 0, 14); // tariffName -conf->nextTariff = PQgetvalue(result, 0, 15); // nextTariff -conf->corp = PQgetvalue(result, 0, 16); // corp + { + std::stringstream tuple; + tuple << PQgetvalue(result, 0, 0) << " "; // uid + conf->address = PQgetvalue(result, 0, 1); // address + conf->alwaysOnline = !strncmp(PQgetvalue(result, 0, 2), "t", 1); + tuple << PQgetvalue(result, 0, 3) << " "; // credit + conf->creditExpire = readTime(PQgetvalue(result, 0, 4)); // creditExpire + conf->disabled = !strncmp(PQgetvalue(result, 0, 5), "t", 1); + conf->disabledDetailStat = !strncmp(PQgetvalue(result, 0, 6), "t", 1); + conf->email = PQgetvalue(result, 0, 7); // email + conf->group = PQgetvalue(result, 0, 8); // group + conf->note = PQgetvalue(result, 0, 9); // note + conf->passive = !strncmp(PQgetvalue(result, 0, 10), "t", 1); + conf->password = PQgetvalue(result, 0, 11); // password + conf->phone = PQgetvalue(result, 0, 12); // phone + conf->realName = PQgetvalue(result, 0, 13); // realName + conf->tariffName = PQgetvalue(result, 0, 14); // tariffName + conf->nextTariff = PQgetvalue(result, 0, 15); // nextTariff + conf->corp = PQgetvalue(result, 0, 16); // corp -PQclear(result); + PQclear(result); -if (conf->tariffName == "") - conf->tariffName = NO_TARIFF_NAME; -if (conf->corp == "") - conf->corp = NO_CORP_NAME; + if (conf->tariffName == "") + conf->tariffName = NO_TARIFF_NAME; + if (conf->corp == "") + conf->corp = NO_CORP_NAME; -tuple >> uid - >> conf->credit; + tuple >> uid + >> conf->credit; + } -query.str(""); -query << "SELECT name FROM tb_services " - "WHERE pk_service IN (SELECT fk_service " - "FROM tb_users_services " - "WHERE fk_user = " << uid << ")"; + { + std::ostringstream query; + query << "SELECT name FROM tb_services " + "WHERE pk_service IN (SELECT fk_service " + "FROM tb_users_services " + "WHERE fk_user = " << uid << ")"; -result = PQexec(connection, query.str().c_str()); + result = PQexec(connection, query.str().c_str()); + } if (PQresultStatus(result) != PGRES_TUPLES_OK) { @@ -861,9 +878,9 @@ if (PQresultStatus(result) != PGRES_TUPLES_OK) printfd(__FILE__, "POSTGRESQL_STORE::RestoreUserConf(): '%s'\n", strError.c_str()); PQclear(result); if (RollbackTransaction()) - { - printfd(__FILE__, "POSTGRESQL_STORE::RestoreUserConf(): 'Failed to rollback transaction'\n"); - } + { + printfd(__FILE__, "POSTGRESQL_STORE::RestoreUserConf(): 'Failed to rollback transaction'\n"); + } return -1; } @@ -871,17 +888,19 @@ tuples = PQntuples(result); for (int i = 0; i < tuples; ++i) { - conf->service.push_back(PQgetvalue(result, i, 0)); + conf->services.push_back(PQgetvalue(result, i, 0)); } PQclear(result); -query.str(""); -query << "SELECT num, data " - "FROM tb_users_data " - "WHERE fk_user = " << uid; + { + std::ostringstream query; + query << "SELECT num, data " + "FROM tb_users_data " + "WHERE fk_user = " << uid; -result = PQexec(connection, query.str().c_str()); + result = PQexec(connection, query.str().c_str()); + } if (PQresultStatus(result) != PGRES_TUPLES_OK) { @@ -889,9 +908,9 @@ if (PQresultStatus(result) != PGRES_TUPLES_OK) printfd(__FILE__, "POSTGRESQL_STORE::RestoreUserConf(): '%s'\n", strError.c_str()); PQclear(result); if (RollbackTransaction()) - { - printfd(__FILE__, "POSTGRESQL_STORE::RestoreUserConf(): 'Failed to rollback transaction'\n"); - } + { + printfd(__FILE__, "POSTGRESQL_STORE::RestoreUserConf(): 'Failed to rollback transaction'\n"); + } return -1; } @@ -916,12 +935,14 @@ for (int i = 0; i < tuples; ++i) PQclear(result); -query.str(""); -query << "SELECT host(ip), masklen(ip) " - "FROM tb_allowed_ip " - "WHERE fk_user = " << uid; + { + std::ostringstream query; + query << "SELECT host(ip), masklen(ip) " + "FROM tb_allowed_ip " + "WHERE fk_user = " << uid; -result = PQexec(connection, query.str().c_str()); + result = PQexec(connection, query.str().c_str()); + } if (PQresultStatus(result) != PGRES_TUPLES_OK) { @@ -929,34 +950,30 @@ if (PQresultStatus(result) != PGRES_TUPLES_OK) printfd(__FILE__, "POSTGRESQL_STORE::RestoreUserConf(): '%s'\n", strError.c_str()); PQclear(result); if (RollbackTransaction()) - { - printfd(__FILE__, "POSTGRESQL_STORE::RestoreUserConf(): 'Failed to rollback transaction'\n"); - } + { + printfd(__FILE__, "POSTGRESQL_STORE::RestoreUserConf(): 'Failed to rollback transaction'\n"); + } return -1; } tuples = PQntuples(result); -conf->ips.Erase(); +STG::UserIPs ips; for (int i = 0; i < tuples; ++i) { - IP_MASK ipm; - - int ip, mask; + STG::IPMask im; - ip = inet_strington(PQgetvalue(result, i, 0)); + im.ip = inet_strington(PQgetvalue(result, i, 0)); - if (str2x(PQgetvalue(result, i, 1), mask)) + if (str2x(PQgetvalue(result, i, 1), im.mask)) { printfd(__FILE__, "POSTGRESQL_STORE::RestoreUserConf(): 'Failed to fetch mask'\n"); continue; } - ipm.ip = ip; - ipm.mask = mask; - - conf->ips.Add(ipm); + ips.add(im); } +conf->ips = ips; PQclear(result); @@ -970,15 +987,15 @@ return 0; } //----------------------------------------------------------------------------- -int POSTGRESQL_STORE::WriteUserChgLog(const string & login, - const string & admLogin, +int POSTGRESQL_STORE::WriteUserChgLog(const std::string & login, + const std::string & admLogin, uint32_t admIP, - const string & paramName, - const string & oldValue, - const string & newValue, - const string & message = "") const + const std::string & paramName, + const std::string & oldValue, + const std::string & newValue, + const std::string & message = "") const { -STG_LOCKER lock(&mutex, __FILE__, __LINE__); +std::lock_guard lock(m_mutex); if (PQstatus(connection) != CONNECTION_OK) { @@ -1010,9 +1027,9 @@ if (EscapeString(elogin)) { printfd(__FILE__, "POSTGRESQL_STORE::WriteUserChgLog(): 'Failed to escape login'\n"); if (RollbackTransaction()) - { - printfd(__FILE__, "POSTGRESQL_STORE::WriteUserChgLog(): 'Failed to rollback transaction'\n"); - } + { + printfd(__FILE__, "POSTGRESQL_STORE::WriteUserChgLog(): 'Failed to rollback transaction'\n"); + } return -1; } @@ -1020,9 +1037,9 @@ if (EscapeString(eadminLogin)) { printfd(__FILE__, "POSTGRESQL_STORE::WriteUserChgLog(): 'Failed to escape admin's login'\n"); if (RollbackTransaction()) - { - printfd(__FILE__, "POSTGRESQL_STORE::WriteUserChgLog(): 'Failed to rollback transaction'\n"); - } + { + printfd(__FILE__, "POSTGRESQL_STORE::WriteUserChgLog(): 'Failed to rollback transaction'\n"); + } return -1; } @@ -1030,9 +1047,9 @@ if (EscapeString(eparam)) { printfd(__FILE__, "POSTGRESQL_STORE::WriteUserChgLog(): 'Failed to escape param's name'\n"); if (RollbackTransaction()) - { - printfd(__FILE__, "POSTGRESQL_STORE::WriteUserChgLog(): 'Failed to rollback transaction'\n"); - } + { + printfd(__FILE__, "POSTGRESQL_STORE::WriteUserChgLog(): 'Failed to rollback transaction'\n"); + } return -1; } @@ -1040,9 +1057,9 @@ if (EscapeString(eold)) { printfd(__FILE__, "POSTGRESQL_STORE::WriteUserChgLog(): 'Failed to escape old value'\n"); if (RollbackTransaction()) - { - printfd(__FILE__, "POSTGRESQL_STORE::WriteUserChgLog(): 'Failed to rollback transaction'\n"); - } + { + printfd(__FILE__, "POSTGRESQL_STORE::WriteUserChgLog(): 'Failed to rollback transaction'\n"); + } return -1; } @@ -1050,19 +1067,19 @@ if (EscapeString(enew)) { printfd(__FILE__, "POSTGRESQL_STORE::WriteUserChgLog(): 'Failed to escape new value'\n"); if (RollbackTransaction()) - { - printfd(__FILE__, "POSTGRESQL_STORE::WriteUserChgLog(): 'Failed to rollback transaction'\n"); - } + { + printfd(__FILE__, "POSTGRESQL_STORE::WriteUserChgLog(): 'Failed to rollback transaction'\n"); + } return -1; } -std::stringstream query; +std::ostringstream query; query << "SELECT sp_add_param_log_entry(" "'" << elogin << "', " "'" << eadminLogin << "', CAST('" << inet_ntostring(admIP) << "/32' AS INET), " "'" << eparam << "', " - "CAST('" << Int2TS(stgTime) << "' AS TIMESTAMP), " + "CAST('" << formatTime(stgTime) << "' AS TIMESTAMP), " "'" << eold << "', " "'" << enew << "', " "'" << emessage << "')"; @@ -1093,9 +1110,9 @@ return 0; } //----------------------------------------------------------------------------- -int POSTGRESQL_STORE::WriteUserConnect(const string & login, uint32_t ip) const +int POSTGRESQL_STORE::WriteUserConnect(const std::string & login, uint32_t ip) const { -STG_LOCKER lock(&mutex, __FILE__, __LINE__); +std::lock_guard lock(m_mutex); if (PQstatus(connection) != CONNECTION_OK) { @@ -1122,18 +1139,18 @@ if (EscapeString(elogin)) { printfd(__FILE__, "POSTGRESQL_STORE::WriteUserConnect(): 'Failed to escape login'\n"); if (RollbackTransaction()) - { - printfd(__FILE__, "POSTGRESQL_STORE::WriteUserConnect(): 'Failed to rollback transaction'\n"); - } + { + printfd(__FILE__, "POSTGRESQL_STORE::WriteUserConnect(): 'Failed to rollback transaction'\n"); + } return -1; } -std::stringstream query; +std::ostringstream query; if (version < 6) { query << "SELECT sp_add_session_log_entry(" "'" << elogin << "', " - "CAST('" << Int2TS(stgTime) << "' AS TIMESTAMP), " + "CAST('" << formatTime(stgTime) << "' AS TIMESTAMP), " "'c', CAST('" << inet_ntostring(ip) << "/32' AS INET), 0)"; } @@ -1141,7 +1158,7 @@ else { query << "SELECT sp_add_session_log_entry(" "'" << elogin << "', " - "CAST('" << Int2TS(stgTime) << "' AS TIMESTAMP), " + "CAST('" << formatTime(stgTime) << "' AS TIMESTAMP), " "'c', CAST('" << inet_ntostring(ip) << "/32' AS INET), 0, 0, '')"; } @@ -1172,16 +1189,16 @@ return 0; } //----------------------------------------------------------------------------- -int POSTGRESQL_STORE::WriteUserDisconnect(const string & login, - const DIR_TRAFF & up, - const DIR_TRAFF & down, - const DIR_TRAFF & sessionUp, - const DIR_TRAFF & sessionDown, +int POSTGRESQL_STORE::WriteUserDisconnect(const std::string & login, + const STG::DirTraff & monthUp, + const STG::DirTraff & monthDown, + const STG::DirTraff & sessionUp, + const STG::DirTraff & sessionDown, double cash, double freeMb, const std::string & reason) const { -STG_LOCKER lock(&mutex, __FILE__, __LINE__); +std::lock_guard lock(m_mutex); if (PQstatus(connection) != CONNECTION_OK) { @@ -1208,9 +1225,9 @@ if (EscapeString(elogin)) { printfd(__FILE__, "POSTGRESQL_STORE::WriteUserDisconnect(): 'Failed to escape login'\n"); if (RollbackTransaction()) - { - printfd(__FILE__, "POSTGRESQL_STORE::WriteUserDisconnect(): 'Failed to rollback transaction'\n"); - } + { + printfd(__FILE__, "POSTGRESQL_STORE::WriteUserDisconnect(): 'Failed to rollback transaction'\n"); + } return -1; } @@ -1220,32 +1237,34 @@ if (EscapeString(ereason)) { printfd(__FILE__, "POSTGRESQL_STORE::WriteUserDisconnect(): 'Failed to escape reason'\n"); if (RollbackTransaction()) - { - printfd(__FILE__, "POSTGRESQL_STORE::WriteUserDisconnect(): 'Failed to rollback transaction'\n"); - } + { + printfd(__FILE__, "POSTGRESQL_STORE::WriteUserDisconnect(): 'Failed to rollback transaction'\n"); + } return -1; } -std::stringstream query; -if (version < 6) { - // Old database version - no freeMb logging support - query << "SELECT sp_add_session_log_entry(" - "'" << elogin << "', " - "CAST('" << Int2TS(stgTime) << "' AS TIMESTAMP), " - "'d', CAST('0.0.0.0/0' AS INET), " - << cash << ")"; - } -else - { - query << "SELECT sp_add_session_log_entry(" - "'" << elogin << "', " - "CAST('" << Int2TS(stgTime) << "' AS TIMESTAMP), " - "'d', CAST('0.0.0.0/0' AS INET), " - << cash << ", " << freeMb << ", '" << ereason << "')"; - } + std::ostringstream query; + if (version < 6) + { + // Old database version - no freeMb logging support + query << "SELECT sp_add_session_log_entry(" + "'" << elogin << "', " + "CAST('" << formatTime(stgTime) << "' AS TIMESTAMP), " + "'d', CAST('0.0.0.0/0' AS INET), " + << cash << ")"; + } + else + { + query << "SELECT sp_add_session_log_entry(" + "'" << elogin << "', " + "CAST('" << formatTime(stgTime) << "' AS TIMESTAMP), " + "'d', CAST('0.0.0.0/0' AS INET), " + << cash << ", " << freeMb << ", '" << ereason << "')"; + } -result = PQexec(connection, query.str().c_str()); + result = PQexec(connection, query.str().c_str()); + } if (PQresultStatus(result) != PGRES_TUPLES_OK) { @@ -1267,9 +1286,9 @@ if (tuples != 1) printfd(__FILE__, "POSTGRESQL_STORE::WriteUserDisconnect(): 'Invalid number of tuples. Wanted 1, actulally %d'\n", tuples); PQclear(result); if (RollbackTransaction()) - { - printfd(__FILE__, "POSTGRESQL_STORE::WriteUserDisconnect(): 'Failed to rollback transaction'\n"); - } + { + printfd(__FILE__, "POSTGRESQL_STORE::WriteUserDisconnect(): 'Failed to rollback transaction'\n"); + } return -1; } @@ -1281,9 +1300,9 @@ if (str2x(PQgetvalue(result, 0, 0), lid)) printfd(__FILE__, "POSTGRESQL_STORE::WriteUserDisconnect(): '%s'\n", strError.c_str()); PQclear(result); if (RollbackTransaction()) - { - printfd(__FILE__, "POSTGRESQL_STORE::WriteUserDisconnect(): 'Failed to rollback transaction'\n"); - } + { + printfd(__FILE__, "POSTGRESQL_STORE::WriteUserDisconnect(): 'Failed to rollback transaction'\n"); + } return -1; } @@ -1291,7 +1310,7 @@ PQclear(result); for (int i = 0; i < DIR_NUM; ++i) { - std::stringstream query; + std::ostringstream query; query << "INSERT INTO tb_sessions_data " "(fk_session_log, " "dir_num, " @@ -1304,8 +1323,8 @@ for (int i = 0; i < DIR_NUM; ++i) << i << ", " << sessionUp[i] << ", " << sessionDown[i] << ", " - << up[i] << ", " - << down[i] << ")"; + << monthUp[i] << ", " + << monthDown[i] << ")"; result = PQexec(connection, query.str().c_str()); @@ -1334,11 +1353,11 @@ return 0; } //----------------------------------------------------------------------------- -int POSTGRESQL_STORE::WriteDetailedStat(const map & statTree, +int POSTGRESQL_STORE::WriteDetailedStat(const STG::TraffStat & statTree, time_t lastStat, - const string & login) const + const std::string & login) const { -STG_LOCKER lock(&mutex, __FILE__, __LINE__); +std::lock_guard lock(m_mutex); if (PQstatus(connection) != CONNECTION_OK) { @@ -1351,8 +1370,6 @@ if (PQstatus(connection) != CONNECTION_OK) } } -PGresult * result; - if (StartTransaction()) { printfd(__FILE__, "POSTGRESQL_STORE::WriteDetailedStat(): 'Failed to start transaction'\n"); @@ -1365,24 +1382,24 @@ if (EscapeString(elogin)) { printfd(__FILE__, "POSTGRESQL_STORE::WriteDetailedStat(): 'Failed to escape login'\n"); if (RollbackTransaction()) - { - printfd(__FILE__, "POSTGRESQL_STORE::WriteDetailedStat(): 'Failed to rollback transaction'\n"); - } + { + printfd(__FILE__, "POSTGRESQL_STORE::WriteDetailedStat(): 'Failed to rollback transaction'\n"); + } return -1; } -map::const_iterator it; +STG::TraffStat::const_iterator it; time_t currTime = time(NULL); for (it = statTree.begin(); it != statTree.end(); ++it) { - std::stringstream query; + std::ostringstream query; query << "INSERT INTO tb_detail_stats " "(till_time, from_time, fk_user, " "dir_num, ip, download, upload, cost) " "VALUES (" - "CAST('" << Int2TS(currTime) << "' AS TIMESTAMP), " - "CAST('" << Int2TS(lastStat) << "' AS TIMESTAMP), " + "CAST('" << formatTime(currTime) << "' AS TIMESTAMP), " + "CAST('" << formatTime(lastStat) << "' AS TIMESTAMP), " "(SELECT pk_user FROM tb_users WHERE name = '" << elogin << "'), " << it->first.dir << ", " << "CAST('" << inet_ntostring(it->first.ip) << "' AS INET), " @@ -1390,7 +1407,7 @@ for (it = statTree.begin(); it != statTree.end(); ++it) << it->second.up << ", " << it->second.cash << ")"; - result = PQexec(connection, query.str().c_str()); + PGresult * result = PQexec(connection, query.str().c_str()); if (PQresultStatus(result) != PGRES_COMMAND_OK) { @@ -1417,9 +1434,9 @@ return 0; } //----------------------------------------------------------------------------- -int POSTGRESQL_STORE::SaveMonthStat(const USER_STAT & stat, int month, int year, const string & login) const +int POSTGRESQL_STORE::SaveMonthStat(const STG::UserStat & stat, int month, int year, const std::string & login) const { -STG_LOCKER lock(&mutex, __FILE__, __LINE__); +std::lock_guard lock(m_mutex); return SaveStat(stat, login, year, month); } @@ -1430,21 +1447,23 @@ int POSTGRESQL_STORE::SaveUserServices(uint32_t uid, { PGresult * result; -std::stringstream query; -query << "DELETE FROM tb_users_services WHERE fk_user = " << uid; + { + std::ostringstream query; + query << "DELETE FROM tb_users_services WHERE fk_user = " << uid; -result = PQexec(connection, query.str().c_str()); + result = PQexec(connection, query.str().c_str()); + + if (PQresultStatus(result) != PGRES_COMMAND_OK) + { + strError = PQresultErrorMessage(result); + PQclear(result); + printfd(__FILE__, "POSTGRESQL_STORE::SaveUserServices(): '%s'\n", strError.c_str()); + return -1; + } -if (PQresultStatus(result) != PGRES_COMMAND_OK) - { - strError = PQresultErrorMessage(result); PQclear(result); - printfd(__FILE__, "POSTGRESQL_STORE::SaveUserServices(): '%s'\n", strError.c_str()); - return -1; } -PQclear(result); - std::vector::const_iterator it; for (it = services.begin(); it != services.end(); ++it) @@ -1457,7 +1476,7 @@ for (it = services.begin(); it != services.end(); ++it) return -1; } - std::stringstream query; + std::ostringstream query; query << "INSERT INTO tb_users_services " "(fk_user, fk_service) " "VALUES " @@ -1484,14 +1503,16 @@ return 0; //----------------------------------------------------------------------------- int POSTGRESQL_STORE::SaveUserIPs(uint32_t uid, - const USER_IPS & ips) const + const STG::UserIPs & ips) const { PGresult * result; -std::stringstream query; -query << "DELETE FROM tb_allowed_ip WHERE fk_user = " << uid; + { + std::ostringstream query; + query << "DELETE FROM tb_allowed_ip WHERE fk_user = " << uid; -result = PQexec(connection, query.str().c_str()); + result = PQexec(connection, query.str().c_str()); + } if (PQresultStatus(result) != PGRES_COMMAND_OK) { @@ -1503,9 +1524,9 @@ if (PQresultStatus(result) != PGRES_COMMAND_OK) PQclear(result); -for (int i = 0; i < ips.Count(); ++i) +for (size_t i = 0; i < ips.count(); ++i) { - std::stringstream query; + std::ostringstream query; query << "INSERT INTO tb_allowed_ip " "(fk_user, ip) " "VALUES " @@ -1545,7 +1566,7 @@ for (unsigned i = 0; i < data.size(); ++i) PGresult * result; - std::stringstream query; + std::ostringstream query; query << "SELECT sp_set_user_data(" << uid << ", " << "CAST(" << i << " AS SMALLINT), "