Skip to content

Instantly share code, notes, and snippets.

@TheEagleByte
Created April 27, 2019 16:13
Show Gist options
  • Save TheEagleByte/80b3eaddd69b9d28b9a6223eaced9f2f to your computer and use it in GitHub Desktop.
Save TheEagleByte/80b3eaddd69b9d28b9a6223eaced9f2f to your computer and use it in GitHub Desktop.
Rcon Module for Discord.NET using an implementation of Battle.NET
using System;
using System.Collections.Generic;
using System.Linq;
using System.Net;
using System.Text;
using System.Threading.Tasks;
using ALRP.BattleNET;
using ALRP.DiscordBot.Models;
using Discord;
using Discord.Commands;
using Microsoft.Extensions.Configuration;
namespace ALRP.DiscordBot.Modules
{
[Name("RCon")]
[Summary("RCon Commands")]
public class RConModule : ModuleBase<SocketCommandContext>
{
private readonly IConfigurationRoot _config;
private readonly BattlEyeLoginCredentials _credentials;
private int _playerListId = -1;
private string _playerList;
public RConModule(IConfigurationRoot config)
{
_config = config;
_credentials = new BattlEyeLoginCredentials
{
Host = Dns.GetHostAddresses(_config["RConConnection:Host"])[0],
Port = Convert.ToInt32(_config["RConConnection:Port"]),
Password = _config["RConConnection:Password"]
};
}
[Command("rconmessage", RunMode = RunMode.Async)]
[Summary("Sends a message in global chat")]
[RequireUserPermission(GuildPermission.Administrator)]
public async Task RconMessage(string message, int playerId = -1)
{
var client = new BattlEyeClient(_credentials);
client.Connect();
client.SendCommand(BattlEyeCommand.Say, $"{playerId} {message}");
while (client.CommandQueue > 0) { }
client.Disconnect();
await ReplyAsync("Message Sent To Server");
}
[Command("rconplayers", RunMode = RunMode.Async)]
[Summary("Gets all the current players in game at the moment")]
[RequireUserPermission(GuildPermission.Administrator)]
public async Task RconPlayers()
{
var client = new BattlEyeClient(_credentials);
client.BattlEyeMessageReceived += BattlEyeMessageReceived;
client.Connect();
_playerList = null;
_playerListId = client.SendCommand(BattlEyeCommand.Players);
while (_playerList == null) { }
var playerList = ParsePlayerList(_playerList).OrderBy(x => x.Id).ToList();
var sb = new StringBuilder($"*Player List ({playerList.Count} total):*\n```");
foreach (var player in playerList)
{
sb.Append($"\n{player.Id} {player.Name}");
}
sb.Append("```");
await ReplyAsync(sb.ToString());
}
[Command("playercount", RunMode = RunMode.Async)]
[Summary("Gets the current player count from the server")]
public async Task RconPlayerCount()
{
var client = new BattlEyeClient(_credentials);
client.BattlEyeMessageReceived += BattlEyeMessageReceived;
client.Connect();
_playerList = null;
_playerListId = client.SendCommand(BattlEyeCommand.Players);
while (_playerList == null) { }
await ReplyAsync($"There are currently `{ParsePlayerList(_playerList).ToList().Count}` players in-game.");
}
[Command("trollcount", RunMode = RunMode.Async)]
[Summary("Gets the current player count from the server")]
[RequireUserPermission(GuildPermission.Administrator)]
public async Task RconTrollCount()
{
await ReplyAsync("https://imgflip.com/i/2z6t5k");
}
private void BattlEyeMessageReceived(BattlEyeMessageEventArgs args)
{
if (args.Id == _playerListId)
{
_playerList = args.Message;
}
}
private static IEnumerable<RConPlayer> ParsePlayerList(string playerList)
{
// Get to the start of the list
playerList = playerList.Substring(playerList.IndexOf("-\n", StringComparison.Ordinal) + 3);
playerList = playerList.Substring(0, playerList.IndexOf("\n(", StringComparison.Ordinal));
var lines = playerList.Split("\n".ToCharArray());
return lines.Select(ParseRconPlayerLine);
}
private static RConPlayer ParseRconPlayerLine(string playerLine)
{
var splitLine = playerLine.Split(new [] {' ', '\t'}, StringSplitOptions.RemoveEmptyEntries);
return new RConPlayer
{
Id = Convert.ToInt32(splitLine[0]),
IpAddress = splitLine[1].Substring(0, splitLine[1].IndexOf(':')),
Port = Convert.ToInt32(splitLine[1].Substring(splitLine[1].IndexOf(':') + 1)),
Ping = Convert.ToInt32(splitLine[2]),
Guid = splitLine[3].Substring(0, splitLine[3].Length - 4),
Name = string.Join(" ", splitLine.Skip(4))
};
}
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment