Начал работу над новым ботом с возможностью взаимодействия с проконом. Как всегда не обошлось без проблем. Для того чтобы с плагина можно было напрямую взаимодействовать с ботом, находящемся в windows-сервисе, пришлось допиливать прокон. Создал на гитхабе форк YugoAmr/Procon-1 от последней активной на данный момент ветки AdKats, там можно проследить все вносимые изменения в разделе commits.
Если кому будет интересно, то на сегодняшний день внесены следующие изменения:
- в механизм компиляции и запуска плагинов добавлены сборки .net необходимые для использования WCF;
- обновлен файл geoip.dat (используется для определения страны игрока по ip);
- добавлена опция автоматического включения в причину бана отметки длительности в виде "[1d] <reason>" , по анологии с добавлением имени администратора;
- кнопка очистки строки поиска на вкладке банлиста;
- добавлено отслеживание события "PlayerSpawned" на соответствующей закладке и в лог файл (для попытки выявления крашеров серверов использующих баг спавна в технику).
Схема работы с дискордом следующая - в прокон добавляется плагин который устанавливает связь с ботом, win-сервис может быть запущен на любой машине в сети, главное условие это доступность компа из интернета (белый ip, проброс порта за nat).
Если прокон и бот находятся на разных компах, то для работы плагина требуется указать логин и пароль от любой учетной записи винды где крутится сервис бота, тип учетной записи обычный пользователь.
На текущий момент бот умеет:
- спам в указанный чат сервера дискорда сообщений о банах, киках, входах игроков на сервере, последнее разумно использовать только для проверки работоспособности взаимодействия прокона и бота ибо засрет сервер на раз, темболее если стоит раскачка;
- спам оффлайн банов по имени, а также EA_Guid с использованием базы от плагина PRoCon Chat, GUID, Stats and Map Logger;
- присутствует возможность отфильтровывать и не передавать бан/кик по тексту причины (допускается частичное совпадение с шаблоном), позволяет отсекать автоматические действия панкбастера и других плагинов типа bf4db, battlefield agency и др.;
- вывод в статус бота "Играет в" текущего количества игроков на сервере, счет команд и текущей карты (обновление каждые 10 секунд), если статус пуст значит нет связи с проконом или сервер упал;
- запрос текущего списка игроков;
- кил игроков;
- кик игроков;
- бан игроков.
Что планирую добавить в бота:
- поиск в банлисте прокона;
- разбан игроков по имени/гуиду;
- запрос админа из игры (аналогично плагину "Notify Me!", только сообщение в дискорд).
Если будут реальные желающие опробовать мою поделку, пишите в эту ветку или мне в дискорд (Yugo_Amaryl), расскажу что и как делать. Имейте в виду, что необходимо будет обновить прокон на вашем сервере на мою версию, а также где-то разместить windows-сервис с ботом.
Discord Bot работает с базой данных MySQL, информация берется от плагина прокона "CChatGUIDStatsLogger", соответственно настройки коннекта берем там.
На данном этапе бот запускается в виде консольного приложения, далее планируется переделка в службу Windows. Минимальные требования для запуска - наличие в системе установленного .Net Framework 4.7.2. Бот предоставляется "как есть". Если кого преследует тётя паранойя берем VisualStudio не ниже 2017 изучаем исходники и пересобираем самостоятельно.
Перед началом работы необходимо отредактировать файл конфигурации bot.json.
m_strHost - адрес сервера, m_strDBPort - порт БД MySQL, m_strDatabase - имя БД, m_strUserName,m_strPassword - логин и пароль для соединения, tableSuffix - суффикс, если используется, botToken - токен берем здесь Discord Developer Portal — API Docs for Bots and Developers, RolesHasPermission_SoldierInfo - перечисление дискорд-ролей вашего сервера через '|' имеющих право вызывать команды серии "SoldierInfo", RolesHasPermission_SoldierStats - см. выше, то же, только "SoldierStats", serverIndex - ServerID из tbl_server для которого будут работать команды.
(префикс '!')
"ping","test","hello" - проверка бота, параметры не требуются;
"fName","findName","searchName" - поиск игрока по имени, если нужно искать по частичному совпадению используем '*', при этом в результате будет выведен список совпадений без подробной информации о каждом игроке;
"fGuid","findGuid","searchGuid" - тоже что и выше, но уже по EA_GUID, поиск только по точному совпадению параметра.
"top10","top","topt" - Топ лист игроков, построенный на основе счета("Очки сетевой игры").
"stats" - статистика отдельного игрока.
Для работы этих команд необходимо внести изменения в структуру БД, описанных ниже.
"IpHistory" - просмотр истории изменений ip адресов игрока.
"NameHistory" - история изменений имени.
Для большинства команд надо указывать параметр, например:
"!fName Yugo_Amaryl", "!searchName yugo*", "!ipHistory Yugo_Amaryl", "!fGuid EA_D7DDBF43623E8E55C071EBCFABD094B2"
при этом регистр символов не учитывается.
Команда "stats" может вызываться в двух вариантах - без параметров, в этом случае поиск в базе производится по имени в дискорде; а также с указанием имени игрока в качестве параметра, в этом случае в конфигурации в RolesHasPermission_SoldierStats перечисляются дискорд-роли вашего сервера, которым будет доступен такой вызов, если ограничивать не требуется, то пишем туда "@everyone".
Теперь о доработке базы данных для сохранения статистики о смене ip и имен:
1. Необходимо создать таблицу "ip_history" и "soldiername_history":
SQL:
CREATE TABLE `ip_history` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`PlayerID` int(11) NOT NULL,
`IP_Address` varchar(15) NOT NULL,
`IPv6_Address` varchar(16) DEFAULT NULL,
`RecStamp` datetime NOT NULL,
UNIQUE KEY `id_UNIQUE` (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=1 DEFAULT CHARSET=utf8;
CREATE TABLE `soldiername_history` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`PlayerID` int(11) NOT NULL,
`Old_SoldierName` varchar(45) DEFAULT NULL,
`New_SoldierName` varchar(45) NOT NULL,
`RecStamp` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP,
PRIMARY KEY (`id`),
KEY `old_sldr` (`PlayerID`,`Old_SoldierName`),
KEY `new_sldr` (`PlayerID`,`New_SoldierName`)
) ENGINE=InnoDB AUTO_INCREMENT=1 DEFAULT CHARSET=utf8;
2. И добавить триггеры на таблицу "tbl_playerdata":
SQL:
CREATE DEFINER = CURRENT_USER TRIGGER `Имя_вашей_БД`.`tbl_playerdata_AFTER_UPDATE` AFTER UPDATE ON `tbl_playerdata` FOR EACH ROW
BEGIN
IF (NEW.IP_Address <> Old.IP_Address)
THEN
INSERT INTO `Имя_вашей_БД`.ip_history (PlayerID, IP_Address, IPv6_Address, RecStamp) VALUES (NEW.PlayerID, NEW.IP_Address, NEW.IPv6_Address, NOW());
END IF;
IF (NEW.SoldierName <> Old.SoldierName)
THEN
INSERT INTO `Имя_вашей_БД`.soldiername_history (PlayerID, New_SoldierName, Old_SoldierName) VALUES (NEW.PlayerID, NEW.SoldierName, OLD.SoldierName);
END IF;
END
Второй триггер не обязателен, добавляйте по желанию. Он блокирует замену значений полей "IP_Address", "PBGUID", "EAGUID", "SoldierName" на пустые.
SQL:
CREATE DEFINER = CURRENT_USER TRIGGER `Имя_вашей_БД`.`tbl_playerdata_BEFORE_UPDATE` BEFORE UPDATE ON `tbl_playerdata` FOR EACH ROW
BEGIN
IF ((NEW.IP_Address = '') or (length(NEW.IP_Address) = 0)) and (OLD.IP_Address <> '') and (length(OLD.IP_Address) <> 0) THEN
SET NEW.IP_Address = OLD.IP_Address;
END IF;
IF ((NEW.PBGUID = '') or (length(NEW.PBGUID) = 0)) and (OLD.PBGUID <> '') and (length(OLD.PBGUID) <> 0) THEN
SET NEW.PBGUID = OLD.PBGUID;
END IF;
IF ((NEW.EAGUID = '') or (length(NEW.EAGUID) = 0)) and (OLD.EAGUID <> '') and (length(OLD.EAGUID) <> 0) THEN
SET NEW.EAGUID = OLD.EAGUID;
END IF;
IF ((NEW.SoldierName = '') or (length(NEW.SoldierName) = 0)) and (OLD.SoldierName <> '') and (length(OLD.SoldierName) <> 0) THEN
SET NEW.SoldierName = OLD.SoldierName;
END IF;
END
Обратите внимание, что после ключевого слова "TRIGGER" в коде должно быть указанно имя вашей БД.
Если история вам не интересна, то вносить изменения не нужно, бот должен работать без особых проблем, но при вызове соответствующих команд в консоль программы будут выводиться сообщения об ошибках выполнения запроса MySQL.
Перед внесением изменений в структуру вашей базы данных настоятельно рекомендую сделать бэкап!
Для сборки проекта в него необходимо установить следующий набор пакетов используя для этого панель управления NuGet:
MySql.Data
Discord.Net
Discord.Net.Commands
Discord.Net.Providers.WS4Net
Microsoft.Extensions.DependencyInjection версии не ниже 2.0.0
и еще ряд других, которые подтянутся автоматом, как зависимости к тем что вверху.
Для запуска бота в качестве службы windows необходимо выполнить его установку, одним из 2 способов: с помощью утилиты "installutil.exe", которая идет вместе с .Net или командой windows "sc create"
Опишу только первый вариант, т.к. он наиболее простой. Предположим, что бот находится в каталоге C:\Bot, в этом случае в консоли запущенной с правами администратора выполняем следующую команду "c:\Windows\Microsoft.NET\Framework\v4.0.30319\InstallUtil.exe C:\Bot\StatBotService.exe".
Если не возникнет каких-либо ошибок в процессе инсталляции службы, то в диспетчере служб ("services.msc") вы обнаружите "Discord bot service".
Если такое имя вас не устраивает или если необходимо установить несколько ботов в одной системе, то используем второй вариант.
Как устанавливать службу с помощью "sc" можно найти в интернете или прочитать во встроенной справке вызвав команду без параметров.
upd 10.03.19: - изменена версия платформы .Net на 4.7.2
- привел в порядок исходники и набор пакетов в проекте, что привело к уменьшению количества файлов идущих в нагрузку к программе;
- добавил более корректное завершение сеанса клиента дискорда, для этого в консоли нажимаем кнопку "Esc" на клавиатуре, вместо красного крестика самого окна, после завершения сеанса программа закрывается автоматически.
Здравствуйте, а есть ли возможность сделать Cloud версию бота. Что бы ее можно было запускать из облачных ресурсов или со своих роутеров поддерживающих такие технологии.
Здравствуйте, а есть ли возможность сделать Cloud версию бота. Что бы ее можно было запускать из облачных ресурсов или со своих роутеров поддерживающих такие технологии.
На данном сайте используются файлы cookie, чтобы персонализировать контент и сохранить Ваш вход в систему, если Вы зарегистрируетесь.
Продолжая использовать этот сайт, Вы соглашаетесь на использование наших файлов cookie.