enum _:ServerData { IP[24] }
enum _:SqlData { ServerInfo[32], Prefix[10] }
new const CONFIG_NAME[] = "csbans_tools.ini";
g_szServerData[ServerData],
g_MenuStatus[33][menuStatus];
register_plugin(PLUGIN, VERSION, AUTHOR);
register_clcmd("csbans_menu","CreateMenuPlayer",ACCESS_FLAG,"- open CSBANS menu");
register_dictionary("csbans_tools.txt");
g_aUsers = ArrayCreate(UserInfo);
new filedir[MAX_RESOURCE_PATH_LENGTH];
get_localinfo("amxx_configsdir", filedir, charsmax(filedir));
format(filedir, charsmax(filedir), "%s/%s", filedir, CONFIG_NAME);
if(!file_exists(filedir)) {
set_fail_state("File '%s' not found!", filedir);
if(!parseConfigINI(filedir)) {
set_fail_state("Fatal parse error!");
public fbans_sql_connected(const Handle: db){
new ip[16]; get_cvar_string("fb_server_ip", ip, charsmax(ip));
new port[8]; get_cvar_string("fb_server_port", port, charsmax(port));
formatex(g_szServerData[IP], charsmax(g_szServerData[IP]), "%s:%s", ip, port);
get_cvar_string("fb_servers_table", g_szSqlData[ServerInfo], charsmax(g_szSqlData[ServerInfo]));
strtok(g_szSqlData[ServerInfo], g_szSqlData[Prefix], charsmax(g_szSqlData[Prefix]), "", 0, '_');
g_Data[0] = SQL_GET_SERVER_ID;
formatex(g_szQuery, charsmax(g_szQuery), "SELECT `id` FROM `%s` WHERE `address` = '%s'",
g_szSqlData[ServerInfo], g_szServerData[IP]
SQL_ThreadQuery(g_hSqlTuple, "SQL_Handler", g_szQuery, g_Data, sizeof(g_Data));
public LoadAdminSQL(openMenu,id,player){
g_Data[0] = SQL_GET_PLAYERS;
formatex(g_szQuery, charsmax(g_szQuery), "SELECT \
FROM `%s_amxadmins` AS `a`, `%s_admins_servers` AS `b` \
WHERE `b`.`admin_id` = `a`.`id` \
AND `b`.`server_id` = %d \
g_szSqlData[Prefix], g_szSqlData[Prefix], g_idServer);
SQL_ThreadQuery(g_hSqlTuple, "SQL_Handler", g_szQuery, g_Data, sizeof(g_Data));
public SQL_Handler(failstate, Handle:query, err[], errcode, dt[], datasize){
case TQUERY_CONNECT_FAILED, TQUERY_QUERY_FAILED:{
log_amx("[Проблемы с БД. Код ошибки: #%d] Ошибка: %s", errcode, err);
case SQL_GET_SERVER_ID: {
g_idServer = SQL_ReadResult(query, 0);
if(!SQL_NumResults(query)){
log_amx("Администраторы для сервера %s не найдены в БД!", g_szServerData[IP]);
while(SQL_MoreResults(query)){
g_sUser[id_db] = SQL_ReadResult(query, 0);
SQL_ReadResult(query, 1, g_sUser[Auth], charsmax(g_sUser[Auth]));
SQL_ReadResult(query, 4, g_sUser[Access], charsmax(g_sUser[Access]));
g_sUser[Expired] = SQL_ReadResult(query, 6);
ArrayPushArray(g_aUsers, g_sUser);
if(get_user_flags(dt[2]) & ACCESS_FLAG){
CreateMenuInfo(dt[2],dt[3]);
server_cmd("amx_reloadadmins");
get_user_name(dt[2],adminName,charsmax(adminName));
switch((g_Days[dt[4]][Day] % 10)){
client_print_color(dt[1],print_team_default,"%L %L %L",dt[1],"CSBANS_TAG_CHAT",dt[1],"CSBANS_CHAT_SET_APPOINTED", adminName, g_Groups[dt[3]][Name],g_Days[dt[4]][Day],dt[1],"CSBANS_DAY_CHAT");
client_print_color(dt[1],print_team_default,"%L %L %L",dt[1],"CSBANS_TAG_CHAT",dt[1],"CSBANS_CHAT_SET_APPOINTED", adminName, g_Groups[dt[3]][Name],g_Days[dt[4]][Day],dt[1],"CSBANS_DAY_234_CHAT");
client_print_color(dt[1],print_team_default,"%L %L %L",dt[1],"CSBANS_TAG_CHAT",dt[1],"CSBANS_CHAT_SET_APPOINTED", adminName, g_Groups[dt[3]][Name],g_Days[dt[4]][Day],dt[1],"CSBANS_DAY_N_CHAT");
LoadAdminSQL(1,dt[2],dt[1]);
case SQL_UPDATE_PLAYER: {
get_user_name(dt[2],adminName,charsmax(adminName));
switch((g_Days[dt[3]][Day] % 10)){
client_print_color(dt[1],print_team_default,"%L %L %L",dt[1],"CSBANS_TAG_CHAT",dt[1],"CSBANS_CHAT_UPDATE_APPOINTED", adminName, g_Days[dt[3]][Day],dt[1],"CSBANS_DAY_CHAT");
client_print_color(dt[1],print_team_default,"%L %L %L",dt[1],"CSBANS_TAG_CHAT",dt[1],"CSBANS_CHAT_UPDATE_APPOINTED", adminName, g_Days[dt[3]][Day],dt[1],"CSBANS_DAY_234_CHAT");
client_print_color(dt[1],print_team_default,"%L %L %L",dt[1],"CSBANS_TAG_CHAT",dt[1],"CSBANS_CHAT_UPDATE_APPOINTED", adminName, g_Days[dt[3]][Day],dt[1],"CSBANS_DAY_N_CHAT");
LoadAdminSQL(1,dt[2],dt[1]);
case SQL_REMOVE_PLAYER: {
get_user_name(dt[2],adminName,charsmax(adminName));
client_print_color(dt[1],print_team_default,"%L %L",dt[1],"CSBANS_TAG_CHAT",dt[1],"CSBANS_CHAT_REMOVE",adminName);
LoadAdminSQL(1,dt[2],dt[1]);
public CreateMenuPlayer(id){
if(!(get_user_flags(id) & ACCESS_FLAG)){
client_print_color(id,print_team_default,"%L %L",id,"CSBANS_TAG_CHAT",id,"CSBANS_NOT_ACCESS");
client_print(id,print_console,"[CSBANS] %L",id,"CSBANS_NOT_ACCESS");
g_MenuStatus[id][MENU_CURRENT] = MID_LIST;
formatex(langStr,charsmax(langStr),"%L",id,"CSBANS_TITLE_PLAYERS");
new menu = menu_create(langStr,"HandlerMenu");
new players[MAX_PLAYERS],pCount;
new name[MAX_NAME_LENGTH],lKey[10];
get_players(players,pCount);
for(new i ; i < pCount ; ++i){
if(is_user_hltv(id) || is_user_bot(id) || !is_user_connected(id)){
get_user_name(players[i],name,charsmax(name));
formatex(langStr,charsmax(langStr),"%s",name);
formatex(lKey,charsmax(lKey),"f%d",players[i]);
menu_additem(menu,langStr,lKey);
public CreateMenuInfo(id,player){
if(!is_user_connected(player)){
if(!(get_user_flags(id) & ACCESS_FLAG)){
client_print_color(id,print_team_default,"%L %L",id,"CSBANS_TAG_CHAT",id,"CSBANS_NOT_ACCESS");
client_print(id,print_console,"[CSBANS] %L",id,"CSBANS_NOT_ACCESS");
g_MenuStatus[id][MENU_CURRENT] = MID_INFO;
g_MenuStatus[id][MENU_EDITID] = player;
new langStr[128],name[32],lKey[10];
get_user_name(player,name,charsmax(name));
formatex(langStr,charsmax(langStr),"%L",id,"CSBANS_TITLE_INFO",name);
new menu = menu_create(langStr,"HandlerMenu")
if(getUserArray(player,arr_lUser)){
if(arr_lUser[Expired] != 0){
formatex(lKey,charsmax(lKey),"u%d",player);
formatex(langStr,charsmax(langStr),"%L",id,"CSBANS_UPDATE");
menu_additem(menu,langStr,lKey);
formatex(lKey,charsmax(lKey),"d%d",player);
formatex(langStr,charsmax(langStr),"%L",id,"CSBANS_DROP");
menu_additem(menu,langStr,lKey);
if(arr_lUser[id_groups] == -1){
formatex(langStr,charsmax(langStr),"%L",id,"CSBANS_TITLE_INFO_YES","Не известно");
menu_addtext(menu,langStr)
formatex(langStr,charsmax(langStr),"%L",id,"CSBANS_TITLE_INFO_YES",arr_lUser[NameGroups]);
menu_addtext(menu,langStr)
if(arr_lUser[Expired] == 0){
formatex(langStr,charsmax(langStr),"%L",id,"CSBANS_TITLE_INFO_YES_DATE","Никогда");
menu_addtext(menu,langStr)
format_time(Date,charsmax(Date), "%d.%m.%Y",arr_lUser[Expired])
formatex(langStr,charsmax(langStr),"%L",id,"CSBANS_TITLE_INFO_YES_DATE",Date);
menu_addtext(menu,langStr)
new day = (arr_lUser[Expired]-get_systime())/86400;
formatex(langStr,charsmax(langStr),"%L",id,"CSBANS_TITLE_INFO_YES_EXPIRE_DAYS",day);
menu_addtext(menu,langStr)
formatex(lKey,charsmax(lKey),"a%d",player);
formatex(langStr,charsmax(langStr),"%L",id,"CSBANS_ADD");
menu_additem(menu,langStr,lKey);
formatex(langStr,charsmax(langStr),"%L",id,"CSBANS_TITLE_INFO_NO");
menu_addtext(menu,langStr)
public CreateMenuGroups(id,player,id_day){
if(!is_user_connected(player)){
if(!(get_user_flags(id) & ACCESS_FLAG)){
client_print_color(id,print_team_default,"%L %L",id,"CSBANS_TAG_CHAT",id,"CSBANS_NOT_ACCESS");
client_print(id,print_console,"[CSBANS] %L",id,"CSBANS_NOT_ACCESS");
g_MenuStatus[id][MENU_CURRENT] = MID_GROUPS;
g_MenuStatus[id][MENU_EDITID] = player;
new langStr[128],name[32],lKey[10];
get_user_name(player,name,charsmax(name));
formatex(langStr,charsmax(langStr),"%L",id,"CSBANS_TITLE_GROUPS",name);
new menu = menu_create(langStr,"HandlerMenu");
formatex(langStr,charsmax(langStr),"%L%L",id,"CSBANS_TITLE_GROUPS_DAY",g_Days[id_day][Day],id,"CSBANS_TITLE_GROUPS_SUB");
formatex(lKey,charsmax(lKey),"D%d:%d",player,id_day);
menu_additem(menu,langStr,lKey);
for(new i; i < i_groups; i++){
formatex(langStr,charsmax(langStr),"%s",g_Groups[i][Name]);
formatex(lKey,charsmax(lKey),"s%d|%d:%d",i,player,id_day);
menu_additem(menu,langStr,lKey);
public CreateMenuDays(id,player){
if(!is_user_connected(player)){
if(!(get_user_flags(id) & ACCESS_FLAG)){
client_print_color(id,print_team_default,"%L %L",id,"CSBANS_TAG_CHAT",id,"CSBANS_NOT_ACCESS");
client_print(id,print_console,"[CSBANS] %L",id,"CSBANS_NOT_ACCESS");
g_MenuStatus[id][MENU_CURRENT] = MID_DAYS;
g_MenuStatus[id][MENU_EDITID] = player;
new langStr[128],name[32],lKey[10];
get_user_name(player,name,charsmax(name));
formatex(langStr,charsmax(langStr),"%L",id,"CSBANS_TITLE_DAYS",name);
new menu = menu_create(langStr,"HandlerMenu");
for(new i; i < i_days; i++){
switch((g_Days[i][Day] % 10)){
formatex(langStr,charsmax(langStr),"%L",id,"CSBANS_DAY",g_Days[i][Day]);
formatex(lKey,charsmax(lKey),"U%d:%d",player,i);
formatex(langStr,charsmax(langStr),"%L",id,"CSBANS_DAY_234",g_Days[i][Day]);
formatex(lKey,charsmax(lKey),"U%d:%d",player,i);
formatex(langStr,charsmax(langStr),"%L",id,"CSBANS_DAY_N",g_Days[i][Day]);
formatex(lKey,charsmax(lKey),"U%d:%d",player,i);
menu_additem(menu,langStr,lKey);
public HandlerMenu(id,menu,item){
switch(g_MenuStatus[id][MENU_CURRENT]){
case MID_INFO: CreateMenuPlayer(id);
case MID_GROUPS,MID_DAYS: CreateMenuInfo(id,g_MenuStatus[id][MENU_EDITID]);
menu_item_getinfo(menu,item,a,itemData,19,n,1,a);
CreateMenuInfo(id,str_to_num(itemData[1]));
if(!is_user_connected(str_to_num(itemData[1]))){
CreateMenuGroups(id,str_to_num(itemData[1]),0);
new tmp1[32],tmp2[32],tmp3[32],player,id_day;
strtok(itemData, tmp1, charsmax(tmp1), tmp2, charsmax(tmp2), 'D');strtok(tmp2, tmp2, charsmax(tmp2), tmp3, charsmax(tmp3), ':');
player = str_to_num(tmp2);
id_day = str_to_num(tmp3);
if(!is_user_connected(player)){
CreateMenuGroups(id,player,id_day);
new tmp1[32],tmp2[32],tmp3[32],tmp4[32],id_group,player,id_day,name[32],authid[64];
strtok(itemData, tmp1, charsmax(tmp1), tmp2, charsmax(tmp2), 's');strtok(tmp2, tmp2, charsmax(tmp2), tmp3, charsmax(tmp3), '|');strtok(tmp3, tmp3, charsmax(tmp3), tmp4, charsmax(tmp4), ':');
id_group = str_to_num(tmp2);
player = str_to_num(tmp3);
id_day = str_to_num(tmp4);
if(!is_user_connected(player)){
get_user_name(player,name,charsmax(name));
mysql_escape_string_tk(name,charsmax(name));
get_user_authid(player,authid,charsmax(authid));
g_Data[0] = SQL_SET_PLAYER;
formatex(g_szQuery, charsmax(g_szQuery), "INSERT INTO `%s_amxadmins` (`id`, `username`, `password`, `access`, `flags`, `steamid`, `nickname`, `icq`, `ashow`, `created`, `expired`, `days`) VALUES (NULL, '%s', NULL, '%s', 'ce', '%s', '%s', NULL, '0', '%d', '%d', '%d');INSERT INTO `%s_admins_servers` (`admin_id`, `server_id`, `custom_flags`, `use_static_bantime`) VALUES ((SELECT MAX(id) FROM `%s_amxadmins`), '%d', '', 'no');",
g_szSqlData[Prefix], authid,g_Groups[id_group][Access],authid,name,get_systime(),get_systime()+(g_Days[id_day][Day]*86400),g_Days[id_day][Day],g_szSqlData[Prefix],g_szSqlData[Prefix],g_idServer);
SQL_ThreadQuery(g_hSqlTuple, "SQL_Handler", g_szQuery, g_Data, sizeof(g_Data));
if(!is_user_connected(str_to_num(itemData[1]))){
CreateMenuDays(id,str_to_num(itemData[1]));
new tmp1[32],tmp2[32],tmp3[32],player,id_day;
strtok(itemData, tmp1, charsmax(tmp1), tmp2, charsmax(tmp2), 'U');strtok(tmp2, tmp2, charsmax(tmp2), tmp3, charsmax(tmp3), ':');
player = str_to_num(tmp2);
id_day = str_to_num(tmp3);
if(!is_user_connected(player)){
getUserArray(player,arr_lUser);
if(arr_lUser[Expired] < get_systime()){
formatex(g_szQuery, charsmax(g_szQuery), "UPDATE `%s_amxadmins` SET `expired` = '%d', `days` = '%d' WHERE `id` = %d;",
g_szSqlData[Prefix], get_systime()+(g_Days[id_day][Day]*86400),g_Days[id_day][Day],arr_lUser[id_db]);
formatex(g_szQuery, charsmax(g_szQuery), "UPDATE `%s_amxadmins` SET `expired` = `expired` + %d, `days` = `days` + %d WHERE `id` = %d;",
g_szSqlData[Prefix], (g_Days[id_day][Day]*86400),g_Days[id_day][Day],arr_lUser[id_db]);
g_Data[0] = SQL_UPDATE_PLAYER;
SQL_ThreadQuery(g_hSqlTuple, "SQL_Handler", g_szQuery, g_Data, sizeof(g_Data));
if(!is_user_connected(str_to_num(itemData[1]))){
getUserArray(str_to_num(itemData[1]),arr_lUser);
g_Data[0] = SQL_REMOVE_PLAYER;
g_Data[1] = str_to_num(itemData[1]);
formatex(g_szQuery, charsmax(g_szQuery), "DELETE FROM `%s_amxadmins` WHERE `id` = %d; DELETE FROM `%s_admins_servers` WHERE `admin_id` = %d AND `server_id` = %d",
g_szSqlData[Prefix], arr_lUser[id_db], g_szSqlData[Prefix], arr_lUser[id_db], g_idServer);
SQL_ThreadQuery(g_hSqlTuple, "SQL_Handler", g_szQuery, g_Data, sizeof(g_Data));
public NavButtons(id,menu){
formatex(tmpLang,charsmax(tmpLang),"%L",id,"BACK");
menu_setprop(menu,MPROP_BACKNAME,tmpLang);
formatex(tmpLang,charsmax(tmpLang),"%L",id,"EXIT");
menu_setprop(menu,MPROP_EXITNAME,tmpLang);
formatex(tmpLang,charsmax(tmpLang),"%L",id,"MORE");
menu_setprop(menu,MPROP_NEXTNAME,tmpLang);
bool:parseConfigINI(const configFile[]) {
new INIParser:parser = INI_CreateParser();
if(parser != Invalid_INIParser) {
INI_SetReaders(parser, "ReadCFGKeyValue", "ReadCFGNewSection");
INI_ParseFile(parser, configFile);
INI_DestroyParser(parser);
public bool:ReadCFGNewSection(INIParser:handle, const section[], bool:invalid_tokens, bool:close_bracket) {
log_amx("Closing bracket was not detected! Current section name '%s'.", section);
if(equal(section, "days")) {
if(equal(section, "groups")) {
public bool:ReadCFGKeyValue(INIParser:handle, const key[], const value[]) {
g_Days[i_days][Day] = str_to_num(key);
if(!key[0] || !value[0]) {
log_amx("Emty key or value!");
formatex(g_Groups[i_groups][Name],charsmax(g_Groups[][Name]),"%s",key);
formatex(g_Groups[i_groups][Access],charsmax(g_Groups[][Access]),"%s",value);
stock mysql_escape_string_tk(dest[],len){
replace_all(dest,len,"\\","\\\\");
replace_all(dest,len,"\0","\\0");
replace_all(dest,len,"\n","\\n");
replace_all(dest,len,"\r","\\r");
replace_all(dest,len,"\x1a","\Z");
replace_all(dest,len,"'","''");
replace_all(dest,len,"^"","^"^"");
stock getUserArray(id, array[UserInfo]){
if(!is_user_connected(id)){
get_user_authid(id,authid,charsmax(authid))
for(new i, aSize = ArraySize(g_aUsers); i < aSize; i++){
ArrayGetArray(g_aUsers, i, g_sUser);
if(equal(g_sUser[Auth],authid)){
for(new k; k < i_groups; k++){
if(equal(g_Groups[k][Access],g_sUser[Access])){
formatex(array[NameGroups],charsmax(array[NameGroups]),"%s",g_Groups[k][Name]);
formatex(array[Access],charsmax(array[Access]),"%s",g_sUser[Access]);
formatex(array[Auth],charsmax(array[Auth]),"%s",g_sUser[Auth]);
array[Expired] = g_sUser[Expired];
array[id_db] = g_sUser[id_db]