コード例 #1
0
        public static void Reload(CommandArguments command)
        {
            Reload();

            command.ReplyAsNotice = true;
            CommandHandler.ReplyToCommand(command, "Reloaded {0} token overrides", SecretTokens.Count);
        }
コード例 #2
0
        public override async void OnCommand(CommandArguments command)
        {
            if (command.Message.Length == 0)
            {
                CommandHandler.ReplyToCommand(command, "Usage:{0} ugc <ugcid>", Colors.OLIVE);

                return;
            }

            ulong ugcId;

            if (!ulong.TryParse(command.Message, out ugcId))
            {
                CommandHandler.ReplyToCommand(command, "Invalid UGC ID");

                return;
            }

            var callback = await Cloud.RequestUGCDetails(ugcId);

            if (callback.Result != EResult.OK)
            {
                CommandHandler.ReplyToCommand(command, "Unable to request UGC info: {0}{1}", Colors.RED, callback.Result);

                return;
            }

            CommandHandler.ReplyToCommand(command, "Creator: {0}{1}{2}, App: {3}{4}{5}, File: {6}{7}{8}, Size: {9}{10}{11} -{12} {13}",
                Colors.BLUE, callback.Creator.Render(true), Colors.NORMAL,
                Colors.BLUE, callback.AppID, Colors.NORMAL,
                Colors.BLUE, callback.FileName, Colors.NORMAL,
                Colors.BLUE, GetByteSizeString(callback.FileSize), Colors.NORMAL,
                Colors.DARKBLUE, callback.URL
            );
        }
コード例 #3
0
        public override void OnCommand(CommandArguments command)
        {
            BlogPost post;

            using (var db = Database.GetConnection())
            {
                if (command.Message.Length > 0)
                {
                    post = db.Query<BlogPost>("SELECT `ID`, `Slug`, `Title` FROM `Blog` WHERE `IsHidden` = 0 AND (`Slug` = @Slug OR `ID` = @Slug) LIMIT 1", new { Slug = command.Message }).SingleOrDefault();
                }
                else
                {
                    post = db.Query<BlogPost>("SELECT `ID`, `Slug`, `Title` FROM `Blog` WHERE `IsHidden` = 0 ORDER BY `Time` DESC LIMIT 1").SingleOrDefault();
                }
            }

            if (post.ID == 0)
            {
                CommandHandler.ReplyToCommand(command, "No blog post found.");

                return;
            }

            CommandHandler.ReplyToCommand(
                command,

                command.Message.Length > 0 ?
                    "Blog post:{0} {1}{2} -{3} {4}" :
                    "Latest blog post:{0} {1}{2} -{3} {4}",

                Colors.BLUE, post.Title, Colors.NORMAL,
                Colors.DARKBLUE, SteamDB.GetBlogURL(post.Slug.Length > 0 ? post.Slug : post.ID.ToString())
            );
        }
コード例 #4
0
ファイル: GID.cs プロジェクト: GoeGaming/SteamDatabaseBackend
        public override void OnCommand(CommandArguments command)
        {
            if (command.Message.Length == 0)
            {
                CommandHandler.ReplyToCommand(command, "Usage:{0} gid <globalid>", Colors.OLIVE);

                return;
            }

            ulong uGid;

            if (!ulong.TryParse(command.Message, out uGid))
            {
                CommandHandler.ReplyToCommand(command, "Invalid GlobalID.");

                return;
            }

            GlobalID gid = uGid;

            CommandHandler.ReplyToCommand(command, "{0} (SeqCount: {1}{2}{3}, StartTime: {4}{5}{6}, ProcessID: {7}{8}{9}, BoxID: {10}{11}{12})",
                (ulong)gid,
                Colors.LIGHTGRAY, gid.SequentialCount, Colors.NORMAL,
                Colors.LIGHTGRAY, gid.StartTime, Colors.NORMAL,
                Colors.LIGHTGRAY, gid.ProcessID, Colors.NORMAL,
                Colors.LIGHTGRAY, gid.BoxID, Colors.NORMAL
            );
        }
コード例 #5
0
        public static void ReplyToCommand(CommandArguments command, string message, params object[] args)
        {
            message = string.Format(message, args);

            switch (command.CommandType)
            {
                case ECommandType.IRC:
                {
                    var isChannelMessage = IRC.IsRecipientChannel(command.Recipient);

                    if (isChannelMessage)
                    {
                        message = string.Format("{0}{1}{2}: {3}", Colors.OLIVE, command.SenderIdentity.Nickname, Colors.NORMAL, message);
                    }

                    IRC.Instance.SendReply(isChannelMessage ? command.Recipient : command.SenderIdentity.Nickname.ToString(), message);

                    break;
                }

                case ECommandType.SteamChatRoom:
                {
                    Steam.Instance.Friends.SendChatRoomMessage(command.ChatRoomID, EChatEntryType.ChatMsg, string.Format(":dsham: {0}: {1}", Steam.Instance.Friends.GetFriendPersonaName(command.SenderID), Colors.StripColors(message)));
                    
                    break;
                }

                case ECommandType.SteamIndividual:
                {
                    Steam.Instance.Friends.SendChatMessage(command.SenderID, EChatEntryType.ChatMsg, Colors.StripColors(message));
                    
                    break;
                }
            }
        }
コード例 #6
0
        public override async Task OnCommand(CommandArguments command)
        {
            uint subID;

            if (command.Message.Length == 0 || !uint.TryParse(command.Message, out subID))
            {
                command.Reply("Usage:{0} sub <subid>", Colors.OLIVE);

                return;
            }

            var job = await Steam.Instance.Apps.PICSGetProductInfo(null, subID, false, false);
            var callback = job.Results.First(x => !x.ResponsePending);

            if (!callback.Packages.ContainsKey(subID))
            {
                command.Reply("Unknown SubID: {0}{1}{2}", Colors.BLUE, subID, LicenseList.OwnedSubs.ContainsKey(subID) ? SteamDB.StringCheckmark : string.Empty);

                return;
            }

            var info = callback.Packages[subID];

            info.KeyValues.SaveToFile(Path.Combine(Application.Path, "sub", string.Format("{0}.vdf", info.ID)), false);

            command.Reply("{0}{1}{2} -{3} {4}{5} - Dump:{6} {7}{8}{9}{10}",
                Colors.BLUE, Steam.GetPackageName(info.ID), Colors.NORMAL,
                Colors.DARKBLUE, SteamDB.GetPackageURL(info.ID), Colors.NORMAL,
                Colors.DARKBLUE, SteamDB.GetRawPackageURL(info.ID), Colors.NORMAL,
                info.MissingToken ? SteamDB.StringNeedToken : string.Empty,
                LicenseList.OwnedSubs.ContainsKey(info.ID) ? SteamDB.StringCheckmark : string.Empty
            );
        }
コード例 #7
0
ファイル: UGC.cs プロジェクト: GoeGaming/SteamDatabaseBackend
        public override void OnCommand(CommandArguments command)
        {
            if (command.Message.Length == 0)
            {
                CommandHandler.ReplyToCommand(command, "Usage:{0} ugc <ugcid>", Colors.OLIVE);

                return;
            }

            ulong ugcId;

            if (!ulong.TryParse(command.Message, out ugcId))
            {
                CommandHandler.ReplyToCommand(command, "Invalid UGC ID");

                return;
            }

            JobManager.AddJob(
                () => Cloud.RequestUGCDetails(ugcId),
                new JobManager.IRCRequest
                {
                    Command = command
                }
            );
        }
コード例 #8
0
        public override void OnCommand(CommandArguments command)
        {
            if (command.Message.Length == 0)
            {
                CommandHandler.ReplyToCommand(command, "Usage:{0} servers <filter> - See https://developer.valvesoftware.com/wiki/Master_Server_Query_Protocol", Colors.OLIVE);

                return;
            }

            if (command.Message.IndexOf('\\') == -1)
            {
                CommandHandler.ReplyToCommand(command, "That doesn't look like a filter.");

                return;
            }

            var request = new CGameServers_GetServerList_Request
            {
                filter = command.Message,
                limit = 5000,
            };

            JobManager.AddJob(
                () => GameServers.SendMessage(api => api.GetServerList(request)),
                new JobManager.IRCRequest
                {
                    Type = JobManager.IRCRequestType.TYPE_GAMESERVERS,
                    Command = command
                }
            );
        }
コード例 #9
0
ファイル: App.cs プロジェクト: Autositz/SteamDatabaseBackend
        public override void OnCommand(CommandArguments command)
        {
            if (command.Message.Length == 0)
            {
                CommandHandler.ReplyToCommand(command, "Usage:{0} app <appid or partial game name>", Colors.OLIVE);

                return;
            }

            var count = PICSProductInfo.ProcessedApps.Count;

            if (count > 100)
            {
                CommandHandler.ReplyToCommand(command, "There are currently {0} apps awaiting to be processed, try again later.", count);

                return;
            }

            uint appID;

            if (!uint.TryParse(command.Message, out appID))
            {
                string name = command.Message;

                if (!Utils.ConvertUserInputToSQLSearch(ref name))
                {
                    CommandHandler.ReplyToCommand(command, "Your request is invalid or too short.");

                    return;
                }

                using (var db = Database.GetConnection())
                {
                    appID = db.ExecuteScalar<uint>("SELECT `AppID` FROM `Apps` WHERE `Apps`.`StoreName` LIKE @Name OR `Apps`.`Name` LIKE @Name OR `Apps`.`LastKnownName` LIKE @Name ORDER BY `LastUpdated` DESC LIMIT 1", new { Name = name });
                }

                if (appID == 0)
                {
                    CommandHandler.ReplyToCommand(command, "Nothing was found matching your request.");

                    return;
                }
            }

            var apps = new List<uint>();

            apps.Add(appID);

            JobManager.AddJob(
                () => Steam.Instance.Apps.PICSGetAccessTokens(apps, Enumerable.Empty<uint>()),
                new JobManager.IRCRequest
                {
                    Target = appID,
                    Type = JobManager.IRCRequestType.TYPE_APP,
                    Command = command
                }
            );
        }
コード例 #10
0
        public static void OnChannelMessage(object sender, IrcEventArgs e)
        {
            if (e.Data.Message[0] != '!')
            {
                return;
            }

            if (e.Data.Message == "!relogin" && IRC.IsSenderOp(e.Data.Channel, e.Data.Nick))
            {
                if (Steam.Instance.Client.IsConnected)
                {
                    Steam.Instance.Client.Disconnect();
                }

                foreach (var idler in Program.GCIdlers)
                {
                    if (idler.Client.IsConnected)
                    {
                        idler.Client.Disconnect();
                    }
                }

                Log.WriteInfo("IRC", "Relogin forced by user {0} in channel {1}", e.Data.Nick, e.Data.Channel);

                IRC.Send(e.Data.Channel, "You're responsible for death of everything and everyone now.");
            }

            Action<CommandArguments> callbackFunction;

            if (Commands.TryGetValue(e.Data.MessageArray[0], out callbackFunction))
            {
                var command = new CommandArguments
                {
                    Channel = e.Data.Channel,
                    Nickname = e.Data.Nick,
                    MessageArray = e.Data.MessageArray
                };

                if (!Steam.Instance.Client.IsConnected)
                {
                    ReplyToCommand(command, "{0}{1}{2}: Not connected to Steam.", Colors.OLIVE, command.Nickname, Colors.NORMAL);

                    return;
                }

                if (SteamDB.IsBusy())
                {
                    ReplyToCommand(command, "{0}{1}{2}: The bot is currently busy.", Colors.OLIVE, command.Nickname, Colors.NORMAL);

                    return;
                }

                Log.WriteInfo("IRC", "Handling command {0} for user {1} in channel {2}", e.Data.MessageArray[0], e.Data.Nick, e.Data.Channel);

                callbackFunction(command);
            }
        }
コード例 #11
0
        public override void OnCommand(CommandArguments command)
        {
            if (command.Message.Length > 0)
            {
                return;
            }

            CommandHandler.ReplyToCommand(command, "Available commands: {0}{1}", Colors.OLIVE, Commands);
        }
コード例 #12
0
 public static void ReplyToCommand(CommandArguments command, string message, params object[] args)
 {
     if (command.IsChatRoomCommand)
     {
         Steam.Instance.Friends.SendChatRoomMessage(command.ChatRoomID, EChatEntryType.ChatMsg, Colors.StripColors(string.Format(message, args)));
     }
     else
     {
         IRC.Send(command.Channel, message, args);
     }
 }
コード例 #13
0
        private static void PrintBinary(CommandArguments command, KeyValue kv, string key)
        {
            if (kv[key].Children.Count == 0)
            {
                return;
            }

            kv = kv[key];

            CommandHandler.ReplyToCommand(command, "{0}{1} {2}({3} MB)", CDN, kv["file"].AsString(), Colors.DARKGRAY, (kv["size"].AsLong() / 1048576.0).ToString("0.###"));
        }
コード例 #14
0
        public override void OnCommand(CommandArguments command)
        {
            if (command.Message.Length == 0)
            {
                CommandHandler.ReplyToCommand(command, "Usage:{0} !app <appid or partial game name>", Colors.OLIVE);

                return;
            }

            uint appID;

            if (!uint.TryParse(command.Message, out appID))
            {
                string name = command.Message;

                if (!Utils.ConvertUserInputToSQLSearch(ref name))
                {
                    CommandHandler.ReplyToCommand(command, "Your request is too short.");

                    return;
                }

                using (MySqlDataReader Reader = DbWorker.ExecuteReader("SELECT `AppID` FROM `Apps` WHERE `Apps`.`StoreName` LIKE @Name OR `Apps`.`Name` LIKE @Name ORDER BY `LastUpdated` DESC LIMIT 1", new MySqlParameter("Name", name)))
                {
                    if (Reader.Read())
                    {
                        appID = Reader.GetUInt32("AppID");
                    }
                    else
                    {
                        CommandHandler.ReplyToCommand(command, "Nothing was found matching your request.");

                        return;
                    }
                }
            }

            var apps = new List<uint>();

            apps.Add(appID);

            JobManager.AddJob(
                () => Steam.Instance.Apps.PICSGetAccessTokens(apps, Enumerable.Empty<uint>()), 
                new JobManager.IRCRequest
                {
                    Target = appID,
                    Type = JobManager.IRCRequestType.TYPE_APP,
                    Command = command
                }
            );
        }
コード例 #15
0
        public override void OnCommand(CommandArguments command)
        {
            if (command.Message.Length > 0)
            {
                return;
            }

            // TODO: Correctly include commands for admins if an admin uses the command
            var commands = Commands
                            .Where(cmd => !cmd.IsAdminCommand && cmd != this)
                            .Select(cmd => cmd.Trigger);

            CommandHandler.ReplyToCommand(command, true, "Available commands: {0}{1}", Colors.OLIVE, string.Join(string.Format("{0}, {1}", Colors.NORMAL, Colors.OLIVE), commands));
        }
コード例 #16
0
        public static void AddJob(Func<JobID> action, CommandArguments command)
        {
            var jobID = action();

            var job = new JobAction
            {
                Action = action,
                Command = command
            };

            // Chat rooms don't have full message saved
            Log.WriteDebug("Job Manager", "New chat job: {0} ({1})", jobID, command.Message);

            Jobs.TryAdd(jobID, job);
        }
コード例 #17
0
        public override async Task OnCommand(CommandArguments command)
        {
            if (command.Message.Length == 0)
            {
                command.Reply("Usage:{0} servers <filter> - See https://developer.valvesoftware.com/wiki/Master_Server_Query_Protocol", Colors.OLIVE);

                return;
            }

            if (command.Message.IndexOf('\\') == -1)
            {
                command.Reply("That doesn't look like a filter.");

                return;
            }

            var request = new CGameServers_GetServerList_Request
            {
                filter = command.Message,
                limit = 5000,
            };

            var callback = await GameServers.SendMessage(api => api.GetServerList(request));
            var response = callback.GetDeserializedResponse<CGameServers_GetServerList_Response>();
            var servers = response.servers;

            if (!servers.Any())
            {
                command.Reply("No servers.");

                return;
            }

            if (servers.Count == 1)
            {
                var server = servers.First();

                command.Reply("{0} - {1} - {2}/{3} - Map: {4} - AppID: {5} - Version: {6} - Dir: {7} - Tags: {8} - Name: {9}",
                    server.addr, new SteamID(server.steamid).Render(true), server.players, server.max_players, server.map, server.appid, server.version, server.gamedir, server.gametype, server.name
                );

                return;
            }

            var serv = servers.Take(5).Select(x => string.Format("{0} ({1})", x.addr, x.players));

            command.Reply("{0}{1}", string.Join(", ", serv), servers.Count > 5 ? string.Format(", and {0}{1} more", servers.Count == 5000 ? ">" : "", servers.Count - 5) : "");
        }
コード例 #18
0
ファイル: Help.cs プロジェクト: qyh214/SteamDatabaseBackend
        public override async Task OnCommand(CommandArguments command)
        {
            await Task.Yield();

            if (command.Message.Length > 0)
            {
                return;
            }

            // TODO: Correctly include commands for admins if an admin uses the command
            var commands = Commands
                            .Where(cmd => !cmd.IsAdminCommand && cmd != this)
                            .Select(cmd => cmd.Trigger);

            command.Notice("Available commands: {0}{1}", Colors.OLIVE, string.Join(string.Format("{0}, {1}", Colors.NORMAL, Colors.OLIVE), commands));
        }
コード例 #19
0
        public override void OnCommand(CommandArguments command)
        {
            if (command.Message.Length == 0)
            {
                CommandHandler.ReplyToCommand(command, "Usage:{0} !players <appid or partial game name>", Colors.OLIVE);

                return;
            }

            uint appID;

            if (!uint.TryParse(command.Message, out appID))
            {
                string name = command.Message;

                if (!Utils.ConvertUserInputToSQLSearch(ref name))
                {
                    CommandHandler.ReplyToCommand(command, "Your request is too short.");

                    return;
                }

                using (MySqlDataReader Reader = DbWorker.ExecuteReader("SELECT `AppID` FROM `Apps` LEFT JOIN `AppsTypes` ON `Apps`.`AppType` = `AppsTypes`.`AppType` WHERE `AppsTypes`.`Name` IN ('game', 'application') AND (`Apps`.`StoreName` LIKE @Name OR `Apps`.`Name` LIKE @Name) ORDER BY `LastUpdated` DESC LIMIT 1", new MySqlParameter("Name", name)))
                {
                    if (Reader.Read())
                    {
                        appID = Reader.GetUInt32("AppID");
                    }
                    else
                    {
                        CommandHandler.ReplyToCommand(command, "Nothing was found matching your request.");

                        return;
                    }
                }
            }

            JobManager.AddJob(
                () => Steam.Instance.UserStats.GetNumberOfCurrentPlayers(appID),
                new JobManager.IRCRequest
                {
                    Target = appID,
                    Command = command
                }
            );
        }
コード例 #20
0
        public override void OnCommand(CommandArguments command)
        {
            if (command.Message.Length == 0)
            {
                CommandHandler.ReplyToCommand(command, "Usage:{0} players <appid or partial game name>", Colors.OLIVE);
                CommandHandler.ReplyToCommand(command, true, "Use {0}^{1} and {2}${3} just like in regex to narrow down your match, e.g:{4} !players Portal$", Colors.BLUE, Colors.NORMAL, Colors.BLUE, Colors.NORMAL, Colors.OLIVE);

                return;
            }

            uint appID;

            if (!uint.TryParse(command.Message, out appID))
            {
                string name = command.Message;

                if (!Utils.ConvertUserInputToSQLSearch(ref name))
                {
                    CommandHandler.ReplyToCommand(command, "Your request is invalid or too short.");

                    return;
                }

                using (var db = Database.GetConnection())
                {
                    appID = db.ExecuteScalar<uint>("SELECT `AppID` FROM `Apps` LEFT JOIN `AppsTypes` ON `Apps`.`AppType` = `AppsTypes`.`AppType` WHERE (`AppsTypes`.`Name` IN ('game', 'application') AND (`Apps`.`StoreName` LIKE @Name OR `Apps`.`Name` LIKE @Name)) OR (`AppsTypes`.`Name` = 'unknown' AND `Apps`.`LastKnownName` LIKE @Name) ORDER BY `LastUpdated` DESC LIMIT 1", new { Name = name });
                }

                if (appID == 0)
                {
                    CommandHandler.ReplyToCommand(command, "Nothing was found matching your request.");

                    return;
                }
            }

            JobManager.AddJob(
                () => Steam.Instance.UserStats.GetNumberOfCurrentPlayers(appID),
                new JobManager.IRCRequest
                {
                    Target = appID,
                    Command = command
                }
            );
        }
コード例 #21
0
        public override async void OnCommand(CommandArguments command)
        {
            if (command.Message.Length == 0)
            {
                CommandHandler.ReplyToCommand(command, "Usage:{0} bins <{1}> [stable (returns publicbeta by default)]", Colors.OLIVE, string.Join("/", Systems));

                return;
            }

            var args = command.Message.Split(' ');
            string os = args[0];

            if (os == "windows")
            {
                os = "win32";
            }
            else if (os == "linux")
            {
                os = "ubuntu12";
            }

            if (!Systems.Contains(os))
            {
                CommandHandler.ReplyToCommand(command, "Invalid OS. Valid ones are: {0}", string.Join(", ", Systems));

                return;
            }

            using (var webClient = new WebClient())
            {
                var isStable = args.Length > 1 && args[1].Equals("stable");
                string data = await webClient.DownloadStringTaskAsync(new Uri(string.Format("{0}steam_client_{1}{2}?_={3}", CDN, isStable ? "" : "publicbeta_", os, DateTime.UtcNow.Ticks)));

                var kv = KeyValue.LoadFromString(data);

                if (kv == null)
                {
                    throw new Exception("Failed to parse downloaded client manifest.");
                }

                PrintBinary(command, kv, string.Concat("bins_", os));
                PrintBinary(command, kv, string.Concat("bins_client_", os));
            }
        }
コード例 #22
0
        private static void OnCommandApp(CommandArguments command)
        {
            uint appID;

            if (command.MessageArray.Length == 2 && uint.TryParse(command.MessageArray[1], out appID))
            {
                var jobID = Steam.Instance.Apps.PICSGetProductInfo(appID, null, false, false);

                SteamProxy.Instance.IRCRequests.Add(new SteamProxy.IRCRequest
                {
                    JobID = jobID,
                    Target = appID,
                    Type = SteamProxy.IRCRequestType.TYPE_APP,
                    Command = command
                });
            }
            else
            {
                ReplyToCommand(command, "Usage:{0} !app <appid>", Colors.OLIVE);
            }
        }
コード例 #23
0
        public override void OnCommand(CommandArguments command)
        {
            using (MySqlDataReader Reader = DbWorker.ExecuteReader("SELECT `ID`, `Slug`, `Title` FROM `Blog` WHERE `IsHidden` = 0 ORDER BY `ID` DESC LIMIT 1"))
            {
                if (Reader.Read())
                {
                    var slug = Reader.GetString("Slug");

                    if (slug.Length == 0)
                    {
                        slug = Reader.GetString("ID");
                    }

                    CommandHandler.ReplyToCommand(
                        command,
                        "Latest blog post:{0} {1}{2} -{3} {4}",
                        Colors.GREEN, Reader.GetString("Title"), Colors.NORMAL,
                        Colors.DARKBLUE, SteamDB.GetBlogURL(slug)
                    );
                }
            }
        }
コード例 #24
0
        public override void OnCommand(CommandArguments command)
        {
            using (var webClient = new WebClient())
            {
                webClient.DownloadDataCompleted += delegate(object sender, DownloadDataCompletedEventArgs e)
                {
                    var kv = new KeyValue();

                    using (var ms = new MemoryStream(e.Result))
                    {
                        try
                        {
                            kv.ReadAsText(ms);
                        }
                        catch
                        {
                            CommandHandler.ReplyToCommand(command, "Something went horribly wrong and keyvalue parser died.");

                            return;
                        }
                    }

                    if (kv["bins_osx"].Children.Count == 0)
                    {
                        CommandHandler.ReplyToCommand(command, "Failed to find binaries in parsed response.");

                        return;
                    }

                    kv = kv["bins_osx"];

                    CommandHandler.ReplyToCommand(command, "You're on your own:{0} {1}{2} {3}({4} MB)", Colors.DARKBLUE, CDN, kv["file"].AsString(), Colors.DARKGRAY, (kv["size"].AsLong() / 1048576.0).ToString("0.###"));
                };

                webClient.DownloadDataAsync(new Uri(string.Format("{0}steam_client_publicbeta_osx?_={1}", CDN, DateTime.UtcNow.Ticks)));
            }
        }
コード例 #25
0
ファイル: Enum.cs プロジェクト: yaakov-h/SteamDatabaseBackend
        public override async Task OnCommand(CommandArguments command)
        {
            await Task.Yield();

            if (command.Message.Equals("list", StringComparison.CurrentCultureIgnoreCase))
            {
                command.Reply(string.Join(", ", SteamKitEnums.Select(@enum => @enum.Name)));

                return;
            }

            if (command.Message.Length == 0)
            {
                command.Reply("Usage:{0} enum <enumname> [value or substring [deprecated]]", Colors.OLIVE);

                return;
            }

            var args     = command.Message.Split(' ');
            var enumType = args[0].Replace("SteamKit2.", "");

            var matchingEnumType = SteamKitEnums
                                   .FirstOrDefault(x => x.Name.Equals(enumType, StringComparison.OrdinalIgnoreCase) || GetDottedTypeName(x).IndexOf(enumType, StringComparison.OrdinalIgnoreCase) != -1);

            if (matchingEnumType == null)
            {
                command.Reply("No such enum type.");

                return;
            }

            bool includeDeprecated = args.Length > 2 && args[2].Equals("deprecated", StringComparison.OrdinalIgnoreCase);

            GetType().GetMethod("RunForEnum", BindingFlags.Instance | BindingFlags.NonPublic)
            .MakeGenericMethod(matchingEnumType)
            .Invoke(this, new object[] { args.Length > 1 ? args[1] : string.Empty, command, includeDeprecated });
        }
コード例 #26
0
ファイル: UGC.cs プロジェクト: PawVamp/SteamDatabaseBackend
        public override async Task OnCommand(CommandArguments command)
        {
            if (command.Message.Length == 0)
            {
                command.Reply("Usage:{0} ugc <ugcid>", Colors.OLIVE);

                return;
            }

            if (!ulong.TryParse(command.Message, out var ugcId))
            {
                command.Reply("Invalid UGC ID");

                return;
            }

            var task = Cloud.RequestUGCDetails(ugcId);

            task.Timeout = TimeSpan.FromSeconds(10);
            var callback = await task;

            if (callback.Result != EResult.OK)
            {
                command.Reply("Unable to request UGC info: {0}{1}", Colors.RED, callback.Result);

                return;
            }

            command.Reply("Creator: {0}{1}{2}, App: {3}{4}{5}, File: {6}{7}{8}, Size: {9}{10}{11} -{12} {13}",
                          Colors.BLUE, callback.Creator.Render(), Colors.NORMAL,
                          Colors.BLUE, callback.AppID, Colors.NORMAL,
                          Colors.BLUE, callback.FileName, Colors.NORMAL,
                          Colors.BLUE, GetByteSizeString(callback.FileSize), Colors.NORMAL,
                          Colors.DARKBLUE, callback.URL
                          );
        }
コード例 #27
0
        private void HandleSteamMessage(CommandArguments commandData)
        {
            var message      = commandData.Message;
            var i            = message.IndexOf(' ');
            var inputCommand = i == -1 ? message.Substring(1) : message.Substring(1, i - 1);

            var command = RegisteredCommands.FirstOrDefault(cmd => cmd.Trigger.Equals(inputCommand));

            if (command == null)
            {
                return;
            }

            commandData.Message = i == -1 ? string.Empty : message.Substring(i).Trim();

            if (command.IsAdminCommand && !Settings.Current.SteamAdmins.Contains(commandData.SenderID.ConvertToUInt64()))
            {
                commandData.Reply("You're not an admin!");

                return;
            }

            TryCommand(command, commandData);
        }
コード例 #28
0
        public void OnSteamChatMessage(SteamFriends.ChatMsgCallback callback)
        {
            if (callback.ChatMsgType != EChatEntryType.ChatMsg || callback.ChatterID == Steam.Instance.Client.SteamID)
            {
                return;
            }

            var commandData = new CommandArguments
            {
                CommandType = ECommandType.SteamChatRoom,
                SenderID    = callback.ChatterID,
                ChatRoomID  = callback.ChatRoomID,
                Message     = callback.Message
            };

            if (callback.Message[0] != Settings.Current.IRC.CommandPrefix || callback.Message.Contains('\n'))
            {
                return;
            }

            Log.WriteInfo("CommandHandler", "Handling Steam command \"{0}\" for {1}", callback.Message, commandData);

            HandleSteamMessage(commandData);
        }
コード例 #29
0
        public void OnSteamChatMessage(SteamFriends.ChatMsgCallback callback)
        {
            if (callback.ChatMsgType != EChatEntryType.ChatMsg || callback.ChatterID == Steam.Instance.Client.SteamID)
            {
                return;
            }

            var commandData = new CommandArguments
            {
                CommandType = ECommandType.SteamChatRoom,
                SenderID = callback.ChatterID,
                ChatRoomID = callback.ChatRoomID,
                Message = callback.Message
            };

            PubFileHandler.OnMessage(commandData);
            LinkExpander.OnMessage(commandData);

            if (callback.Message[0] != Settings.Current.IRC.CommandPrefix || callback.Message.Contains('\n'))
            {
                return;
            }

            Log.WriteInfo("CommandHandler", "Handling Steam command \"{0}\" for {1}", callback.Message, commandData);

            HandleSteamMessage(commandData);
        }
コード例 #30
0
        public override void OnCommand(CommandArguments command)
        {
            if (command.Message.Length == 0)
            {
                CommandHandler.ReplyToCommand(command, "Usage:{0} steamid <steamid> [individual/group/gamegroup]", Colors.OLIVE);

                return;
            }

            var args    = command.Message.Split(' ');
            var urlType = EVanityURLType.Default;

            if (args.Length > 1)
            {
                switch (args[1])
                {
                case "individual":
                    urlType = EVanityURLType.Individual;
                    break;

                case "group":
                    urlType = EVanityURLType.Group;
                    break;

                case "game":
                case "gamegroup":
                    urlType = EVanityURLType.OfficialGameGroup;
                    break;

                default:
                    CommandHandler.ReplyToCommand(command, "Invalid vanity url type.");
                    return;
                }
            }

            SteamID steamID;

            if (urlType != EVanityURLType.Default || !TrySetSteamID(args[0], out steamID))
            {
                if (urlType == EVanityURLType.Default)
                {
                    urlType = EVanityURLType.Individual;
                }

                var eResult = ResolveVanityURL(args[0], urlType, out steamID);

                if (eResult != EResult.OK)
                {
                    CommandHandler.ReplyToCommand(command, "Failed to resolve vanity url: {0}{1}", Colors.RED, eResult.ToString());

                    return;
                }
            }

            CommandHandler.ReplyToCommand(command, ExpandSteamID(steamID));

            if (!steamID.IsValid || (!steamID.IsIndividualAccount && !steamID.IsClanAccount))
            {
                return;
            }

            JobAction job;

            if (JobManager.TryRemoveJob(new JobID(steamID), out job) && job.IsCommand)
            {
                CommandHandler.ReplyToCommand(job.CommandRequest.Command, true, "Your !steamid request was lost in space.");
            }

            JobManager.AddJob(
                () => FakePersonaStateJob(steamID),
                new JobManager.IRCRequest
            {
                Command = command
            }
                );
        }
コード例 #31
0
        public override async Task OnCommand(CommandArguments command)
        {
            if (command.Message.Length == 0)
            {
                command.Reply("Usage:{0} app <appid or partial game name>", Colors.OLIVE);

                return;
            }

            string name;

            if (!uint.TryParse(command.Message, out var appID))
            {
                name = command.Message;

                if (!Utils.ConvertUserInputToSQLSearch(ref name))
                {
                    command.Reply("Your request is invalid or too short.");

                    return;
                }

                using (var db = Database.GetConnection())
                {
                    appID = db.ExecuteScalar <uint>("SELECT `AppID` FROM `Apps` WHERE `Apps`.`StoreName` LIKE @Name OR `Apps`.`Name` LIKE @Name OR `Apps`.`LastKnownName` LIKE @Name ORDER BY `LastUpdated` DESC LIMIT 1", new { Name = name });
                }

                if (appID == 0)
                {
                    command.Reply("Nothing was found matching your request.");

                    return;
                }
            }

            var tokenCallback = await Steam.Instance.Apps.PICSGetAccessTokens(appID, null);

            SteamApps.PICSRequest request;

            if (tokenCallback.AppTokens.ContainsKey(appID))
            {
                request = Utils.NewPICSRequest(appID, tokenCallback.AppTokens[appID]);
            }
            else
            {
                request = Utils.NewPICSRequest(appID);
            }

            var job = await Steam.Instance.Apps.PICSGetProductInfo(new List <SteamApps.PICSRequest> {
                request
            }, Enumerable.Empty <SteamApps.PICSRequest>());

            var callback = job.Results.FirstOrDefault(x => x.Apps.ContainsKey(appID));

            if (callback == null)
            {
                command.Reply("Unknown AppID: {0}{1}{2}", Colors.BLUE, appID, LicenseList.OwnedApps.ContainsKey(appID) ? SteamDB.StringCheckmark : string.Empty);

                return;
            }

            var info = callback.Apps[appID];

            if (info.KeyValues["common"]["name"].Value != null)
            {
                name = Utils.RemoveControlCharacters(info.KeyValues["common"]["name"].AsString());
            }
            else
            {
                name = Steam.GetAppName(info.ID);
            }

            info.KeyValues.SaveToFile(Path.Combine(Application.Path, "app", string.Format("{0}.vdf", info.ID)), false);

            command.Reply("{0}{1}{2} -{3} {4}{5} - Dump:{6} {7}{8}{9}{10}",
                          Colors.BLUE, name, Colors.NORMAL,
                          Colors.DARKBLUE, SteamDB.GetAppURL(info.ID), Colors.NORMAL,
                          Colors.DARKBLUE, SteamDB.GetRawAppURL(info.ID), Colors.NORMAL,
                          info.MissingToken ? SteamDB.StringNeedToken : string.Empty,
                          LicenseList.OwnedApps.ContainsKey(info.ID) ? SteamDB.StringCheckmark : string.Empty
                          );

            if (command.IsUserAdmin && !LicenseList.OwnedApps.ContainsKey(info.ID))
            {
                JobManager.AddJob(() => Steam.Instance.Apps.RequestFreeLicense(info.ID));
            }
        }
コード例 #32
0
ファイル: App.cs プロジェクト: rgooler/SteamDatabaseBackend
        public static async Task <uint> TrySearchAppId(CommandArguments command)
        {
            uint appID = 0;
            var  name  = command.Message;
            Uri  uri;
            var  query = new Dictionary <string, string>
            {
                { "hitsPerPage", "1" },
                { "attributesToHighlight", "null" },
                { "attributesToSnippet", "null" },
                { "attributesToRetrieve", "[\"objectID\"]" },
                { "facetFilters", "[[\"appType:Game\",\"appType:Application\"]]" },
                { "advancedSyntax", "true" },
                { "query", name }
            };

            using (var content = new FormUrlEncodedContent(query))
            {
                uri = new UriBuilder("https://94he6yatei-dsn.algolia.net/1/indexes/steamdb/")
                {
                    Query = await content.ReadAsStringAsync()
                }.Uri;
            }

            using (var requestMessage = new HttpRequestMessage(HttpMethod.Get, uri))
            {
                requestMessage.Headers.Add("Referer", "https://github.com/SteamDatabase/SteamDatabaseBackend");
                requestMessage.Headers.Add("X-Algolia-Application-Id", "94HE6YATEI");
                requestMessage.Headers.Add("X-Algolia-API-Key", "2414d3366df67739fe6e73dad3f51a43");

                try
                {
                    var response = await Utils.HttpClient.SendAsync(requestMessage);

                    var data = await response.Content.ReadAsStringAsync();

                    var json = JsonConvert.DeserializeObject <AlgoliaSearchAppHits>(data);

                    if (json.Hits.Length > 0)
                    {
                        appID = json.Hits[0].AppID;
                    }
                }
                catch (Exception e)
                {
                    ErrorReporter.Notify("Algolia search", e);
                }
            }

            if (appID > 0)
            {
                return(appID);
            }

            await using (var db = await Database.GetConnectionAsync())
            {
                appID = await db.ExecuteScalarAsync <uint>("SELECT `AppID` FROM `Apps` LEFT JOIN `AppsTypes` ON `Apps`.`AppType` = `AppsTypes`.`AppType` WHERE (`AppsTypes`.`Name` IN ('game', 'application', 'video', 'hardware') AND (`Apps`.`StoreName` LIKE @Name OR `Apps`.`Name` LIKE @Name)) OR (`AppsTypes`.`Name` = 'unknown' AND `Apps`.`LastKnownName` LIKE @Name) ORDER BY `LastUpdated` DESC LIMIT 1", new { Name = name });
            }

            if (appID == 0)
            {
                command.Reply("Nothing was found matching your request.");
            }

            return(appID);
        }
コード例 #33
0
        public static void Reload(CommandArguments command)
        {
            Reload();

            command.Notice($"Reloaded {AppTokens.Count} app tokens and {PackageTokens.Count} package tokens");
        }
コード例 #34
0
        public override async Task OnCommand(CommandArguments command)
        {
            if (command.CommandType != ECommandType.IRC || !IRC.IsRecipientChannel(command.Recipient))
            {
                command.Reply("This command is only available in channels.");

                return;
            }

            var channel = command.Recipient;

            var s     = command.Message.Split(' ');
            var count = s.Length;

            if (count > 0)
            {
                uint id;
                switch (s[0])
                {
                case "reload":
                    await Application.ReloadImportant(command);

                    PICSTokens.Reload(command);

                    return;

                case "add":
                    if (count < 3)
                    {
                        break;
                    }

                    if (!uint.TryParse(s[2], out id))
                    {
                        break;
                    }

                    switch (s[1])
                    {
                    case "app":
                        var exists = Application.ImportantApps.TryGetValue(id, out var channels);

                        if (exists && channels.Contains(channel))
                        {
                            command.Reply($"App {Colors.BLUE}{id}{Colors.NORMAL} ({Steam.GetAppName(id)}) is already important in {Colors.BLUE}{channel}{Colors.NORMAL}.");
                        }
                        else
                        {
                            if (exists)
                            {
                                Application.ImportantApps[id].Add(channel);
                            }
                            else
                            {
                                Application.ImportantApps.Add(id, new List <string> {
                                    channel
                                });
                            }

                            await using (var db = await Database.GetConnectionAsync())
                            {
                                await db.ExecuteAsync("INSERT INTO `ImportantApps` (`AppID`, `Channel`) VALUES (@AppID, @Channel)", new { AppID = id, Channel = channel });
                            }

                            command.Reply($"Marked app {Colors.BLUE}{id}{Colors.NORMAL} ({Steam.GetAppName(id)}) as important in {Colors.BLUE}{channel}{Colors.NORMAL}.");
                        }

                        return;

                    case "sub":
                        if (Application.ImportantSubs.ContainsKey(id))
                        {
                            command.Reply($"Package {Colors.BLUE}{id}{Colors.NORMAL} ({Steam.GetPackageName(id)}) is already important.");
                        }
                        else
                        {
                            Application.ImportantSubs.Add(id, 1);

                            await using (var db = await Database.GetConnectionAsync())
                            {
                                await db.ExecuteAsync("INSERT INTO `ImportantSubs` (`SubID`) VALUES (@SubID)", new { SubID = id });
                            }

                            command.Reply($"Marked package {Colors.BLUE}{id}{Colors.NORMAL} ({Steam.GetPackageName(id)}) as important.");
                        }

                        return;
                    }

                    break;

                case "remove":
                    if (count < 3)
                    {
                        break;
                    }

                    if (!uint.TryParse(s[2], out id))
                    {
                        break;
                    }

                    switch (s[1])
                    {
                    case "app":
                        if (!Application.ImportantApps.TryGetValue(id, out var channels) || !channels.Contains(channel))
                        {
                            command.Reply($"App {Colors.BLUE}{id}{Colors.NORMAL} ({Steam.GetAppName(id)}) is not important in {Colors.BLUE}{channel}{Colors.NORMAL}.");
                        }
                        else
                        {
                            if (channels.Count > 1)
                            {
                                Application.ImportantApps[id].Remove(channel);
                            }
                            else
                            {
                                Application.ImportantApps.Remove(id);
                            }

                            await using (var db = await Database.GetConnectionAsync())
                            {
                                await db.ExecuteAsync("DELETE FROM `ImportantApps` WHERE `AppID` = @AppID AND `Channel` = @Channel", new { AppID = id, Channel = channel });
                            }

                            command.Reply($"Removed app {Colors.BLUE}{id}{Colors.NORMAL} ({Steam.GetAppName(id)}) from the important list in {Colors.BLUE}{channel}{Colors.NORMAL}.");
                        }

                        return;

                    case "sub":
                        if (!Application.ImportantSubs.ContainsKey(id))
                        {
                            command.Reply($"Package {Colors.BLUE}{id}{Colors.NORMAL} ({Steam.GetPackageName(id)}) is not important.");
                        }
                        else
                        {
                            Application.ImportantSubs.Remove(id);

                            await using (var db = await Database.GetConnectionAsync())
                            {
                                await db.ExecuteAsync("DELETE FROM `ImportantSubs` WHERE `SubID` = @SubID", new { SubID = id });
                            }

                            command.Reply($"Removed package {Colors.BLUE}{id}{Colors.NORMAL} ({Steam.GetPackageName(id)}) from the important list.");
                        }

                        return;
                    }

                    break;
                }
            }

            command.Reply($"Usage:{Colors.OLIVE} important reload {Colors.NORMAL}or{Colors.OLIVE} important <add/remove> <app/sub> <id>");
        }
コード例 #35
0
        public void OnMessage(CommandArguments command)
        {
            var matches = SteamLinkMatch.Matches(command.Message);

            foreach (Match match in matches)
            {
                var page = match.Groups["page"].Value;

                // Ignore sub pages, easier to do it here rather than in regex
                if (!string.IsNullOrEmpty(page))
                {
                    continue;
                }

                var    appType   = string.Empty;
                var    id        = uint.Parse(match.Groups["id"].Value);
                var    isPackage = match.Groups["type"].Value == "sub";
                string name;

                if (isPackage)
                {
                    name = Steam.GetPackageName(id);
                }
                else
                {
                    App data;

                    using (var db = Database.GetConnection())
                    {
                        data = db.Query <App>("SELECT `AppID`, `Apps`.`Name`, `LastKnownName`, `AppsTypes`.`DisplayName` as `AppTypeString` FROM `Apps` JOIN `AppsTypes` ON `Apps`.`AppType` = `AppsTypes`.`AppType` WHERE `AppID` = @AppID", new { AppID = id }).SingleOrDefault();
                    }

                    if (data.AppID == 0)
                    {
                        continue;
                    }

                    name    = string.IsNullOrEmpty(data.LastKnownName) ? data.Name : data.LastKnownName;
                    name    = Utils.RemoveControlCharacters(name);
                    appType = data.AppTypeString;
                }

                if (command.Message.IndexOf(name, StringComparison.CurrentCultureIgnoreCase) >= 0)
                {
                    continue;
                }

                string priceInfo = isPackage ? string.Empty : GetFormattedPrices(id);

                if (command.CommandType == ECommandType.SteamChatRoom)
                {
                    Steam.Instance.Friends.SendChatRoomMessage(command.ChatRoomID, EChatEntryType.ChatMsg, string.Format("» {0} {1} — {2}{3}", isPackage ? "Package" : "App", id, Colors.StripColors(name), priceInfo));

                    continue;
                }

                if (!isPackage && command.Recipient == "#steamlug" && (appType == "Game" || appType == "Application"))
                {
                    using (var db = Database.GetConnection())
                    {
                        var status = db.ExecuteScalar <string>("SELECT `Status` FROM `LinuxSupport` WHERE `AppID` = @AppID", new { AppID = id });

                        switch (status)
                        {
                        case "working":
                            priceInfo += " (✓ Confirmed for Linux)";
                            break;

                        case "beta":
                            priceInfo += " (Has a public Linux βeta)";
                            break;

                        default:
                            priceInfo += " (✘ Unknown Linux status)";
                            break;
                        }
                    }
                }

                IRC.Instance.SendReply(command.Recipient,
                                       string.Format("{0}» {1}{2} {3} —{4} {5}{6}{7}",
                                                     Colors.OLIVE,
                                                     Colors.NORMAL,
                                                     isPackage ? "Package" : appType,
                                                     id,
                                                     Colors.BLUE,
                                                     name,
                                                     Colors.LIGHTGRAY,
                                                     priceInfo
                                                     ),
                                       false
                                       );
            }
        }
コード例 #36
0
 public abstract void OnCommand(CommandArguments command);
コード例 #37
0
        public async void OnMessage(CommandArguments command)
        {
            var matches = SharedFileMatch.Matches(command.Message);

            foreach (Match match in matches)
            {
                if (!ulong.TryParse(match.Groups["pubfileid"].Value, out var pubFileId))
                {
                    continue;
                }

                Log.WriteInfo("Link Expander", "Will look up pubfile {0} for {1}", pubFileId, command);

                var pubFileRequest = new CPublishedFile_GetDetails_Request
                {
                    includevotes = true,
                };

                pubFileRequest.publishedfileids.Add(pubFileId);

                PublishedFileDetails details;

                try
                {
                    var callback = await PublishedFiles.SendMessage(api => api.GetDetails(pubFileRequest));

                    var response = callback.GetDeserializedResponse <CPublishedFile_GetDetails_Response>();
                    details = response.publishedfiledetails.FirstOrDefault();
                }
                catch (Exception e)
                {
                    Log.WriteError("Link Expander", "Failed to get pubfile details: {0}", e.Message);

                    continue;
                }

                if (details == null || (EResult)details.result != EResult.OK)
                {
                    continue;
                }

                string title;

                if (!string.IsNullOrWhiteSpace(details.title))
                {
                    title = details.title;
                }
                else if (!string.IsNullOrEmpty(details.file_description))
                {
                    title = details.file_description;
                }
                else
                {
                    title = details.filename;
                }

                if (title.Length > 49)
                {
                    title = title.Substring(0, 49) + "…";
                }

                var votesUp   = details.vote_data?.votes_up ?? 0;
                var votesDown = details.vote_data?.votes_down ?? 0;

                if (command.CommandType == ECommandType.SteamChatRoom)
                {
                    Steam.Instance.Friends.SendChatRoomMessage(command.ChatRoomID, EChatEntryType.ChatMsg,
                                                               string.Format("» {0}: {1} for {2} ({3:N0} views, {4:N0} \ud83d\udc4d, {5:N0} \ud83d\udc4e){6}",
                                                                             (EWorkshopFileType)details.file_type,
                                                                             title,
                                                                             details.app_name,
                                                                             details.views,
                                                                             votesUp,
                                                                             votesDown,
                                                                             details.spoiler_tag ? " :retreat: SPOILER" : ""
                                                                             )
                                                               );
                }
                else
                {
                    IRC.Instance.SendReply(command.Recipient,
                                           string.Format("{0}» {1}{2} {3}{4}{5} for {6}{7}{8} ({9:N0} views, {10:N0} \ud83d\udc4d, {11:N0} \ud83d\udc4e)",
                                                         Colors.OLIVE,
                                                         Colors.NORMAL,
                                                         (EWorkshopFileType)details.file_type,
                                                         Colors.BLUE,
                                                         title,
                                                         Colors.NORMAL,
                                                         Colors.BLUE,
                                                         details.app_name,
                                                         Colors.LIGHTGRAY,
                                                         details.views,
                                                         votesUp,
                                                         votesDown
                                                         ),
                                           false
                                           );
                }
            }
        }
コード例 #38
0
        public override async Task OnCommand(CommandArguments command)
        {
            if (string.IsNullOrWhiteSpace(command.Message))
            {
                command.Reply("Usage:{0} app <appid or partial game name>", Colors.OLIVE);

                return;
            }

            string name;

            if (!uint.TryParse(command.Message, out var appID))
            {
                appID = await TrySearchAppId(command);

                if (appID == 0)
                {
                    return;
                }
            }

            var tokenCallback = await Steam.Instance.Apps.PICSGetAccessTokens(appID, null);

            SteamApps.PICSRequest request;

            if (tokenCallback.AppTokens.ContainsKey(appID))
            {
                request = Utils.NewPICSRequest(appID, tokenCallback.AppTokens[appID]);
            }
            else
            {
                request = Utils.NewPICSRequest(appID);
            }

            var job = await Steam.Instance.Apps.PICSGetProductInfo(new List <SteamApps.PICSRequest> {
                request
            }, Enumerable.Empty <SteamApps.PICSRequest>());

            var callback = job.Results.FirstOrDefault(x => x.Apps.ContainsKey(appID));

            if (callback == null)
            {
                command.Reply("Unknown AppID: {0}{1}{2}", Colors.BLUE, appID, LicenseList.OwnedApps.ContainsKey(appID) ? SteamDB.StringCheckmark : string.Empty);

                return;
            }

            var info = callback.Apps[appID];

            if (info.KeyValues["common"]["name"].Value != null)
            {
                name = Utils.RemoveControlCharacters(info.KeyValues["common"]["name"].AsString());
            }
            else
            {
                name = Steam.GetAppName(info.ID);
            }

            info.KeyValues.SaveToFile(Path.Combine(Application.Path, "app", string.Format("{0}.vdf", info.ID)), false);

            command.Reply("{0}{1}{2} -{3} {4}{5} - Dump:{6} {7}{8}{9}{10}",
                          Colors.BLUE, name, Colors.NORMAL,
                          Colors.DARKBLUE, SteamDB.GetAppURL(info.ID), Colors.NORMAL,
                          Colors.DARKBLUE, SteamDB.GetRawAppURL(info.ID), Colors.NORMAL,
                          info.MissingToken ? SteamDB.StringNeedToken : string.Empty,
                          LicenseList.OwnedApps.ContainsKey(info.ID) ? SteamDB.StringCheckmark : string.Empty
                          );

            if (command.IsUserAdmin && !LicenseList.OwnedApps.ContainsKey(info.ID))
            {
                JobManager.AddJob(() => Steam.Instance.Apps.RequestFreeLicense(info.ID));
            }
        }
コード例 #39
0
        public override async Task OnCommand(CommandArguments command)
        {
            if (command.Message.Length == 0)
            {
                command.Reply("Usage:{0} players <appid or partial game name>", Colors.OLIVE);

                return;
            }

            uint   appID;
            string name;

            if (!uint.TryParse(command.Message, out appID))
            {
                name = command.Message;

                using (var webClient = new WebClient())
                {
                    webClient.QueryString.Add("x-algolia-application-id", "94HE6YATEI");
                    webClient.QueryString.Add("x-algolia-api-key", "2414d3366df67739fe6e73dad3f51a43");
                    webClient.QueryString.Add("hitsPerPage", "1");
                    webClient.QueryString.Add("attributesToHighlight", "null");
                    webClient.QueryString.Add("attributesToSnippet", "null");
                    webClient.QueryString.Add("attributesToRetrieve", "[\"objectID\"]");
                    webClient.QueryString.Add("facetFilters", "[[\"appType:Game\",\"appType:Application\"]]");
                    webClient.QueryString.Add("advancedSyntax", "true");
                    webClient.QueryString.Add("query", name);

                    var data = await webClient.DownloadStringTaskAsync("https://94he6yatei-dsn.algolia.net/1/indexes/steamdb/");

                    dynamic json = JsonConvert.DeserializeObject(data);

                    if (json.hits != null && json.hits.Count > 0)
                    {
                        appID = json.hits[0].objectID;
                    }
                }

                if (appID == 0)
                {
                    if (!Utils.ConvertUserInputToSQLSearch(ref name))
                    {
                        command.Reply("Your request is invalid or too short.");

                        return;
                    }

                    using (var db = Database.GetConnection())
                    {
                        appID = db.ExecuteScalar <uint>("SELECT `AppID` FROM `Apps` LEFT JOIN `AppsTypes` ON `Apps`.`AppType` = `AppsTypes`.`AppType` WHERE (`AppsTypes`.`Name` IN ('game', 'application', 'video', 'hardware') AND (`Apps`.`StoreName` LIKE @Name OR `Apps`.`Name` LIKE @Name)) OR (`AppsTypes`.`Name` = 'unknown' AND `Apps`.`LastKnownName` LIKE @Name) ORDER BY `LastUpdated` DESC LIMIT 1", new { Name = name });
                    }
                }

                if (appID == 0)
                {
                    command.Reply("Nothing was found matching your request.");

                    return;
                }
            }

            var callback = await Steam.Instance.UserStats.GetNumberOfCurrentPlayers(appID);

            if (appID == 0)
            {
                appID = 753;
            }

            string appType, type = "playing";

            name = Steam.GetAppName(appID, out appType);

            if (callback.Result != EResult.OK)
            {
                command.Reply("Unable to request player count for {0}{1}{2}: {3}{4}", Colors.BLUE, name, Colors.NORMAL, Colors.RED, callback.Result);

                return;
            }

            switch (appType)
            {
            case "Tool":
            case "Config":
            case "Application":
                type = "using";
                break;

            case "Legacy Media":
            case "Video":
                type = "watching";
                break;

            case "Guide":
                type = "reading";
                break;

            case "Hardware":
                type = "bricking";
                break;
            }

            command.Reply(
                "People {0} {1}{2}{3} right now: {4}{5:N0}{6} -{7} {8}",
                type,
                Colors.BLUE, name, Colors.NORMAL,
                Colors.OLIVE, callback.NumPlayers, Colors.NORMAL,
                Colors.DARKBLUE, SteamDB.GetAppURL(appID, "graphs")
                );
        }
コード例 #40
0
        public override void OnCommand(CommandArguments command)
        {
            if (command.CommandType != ECommandType.IRC || !IRC.IsRecipientChannel(command.Recipient))
            {
                CommandHandler.ReplyToCommand(command, "This command is only available in channels.");

                return;
            }

            var channel = command.Recipient;

            var s     = command.Message.Split(' ');
            var count = s.Length;

            if (count > 0)
            {
                switch (s[0])
                {
                case "reload":
                {
                    Application.ReloadImportant(command);
                    PICSTokens.Reload(command);
                    FileDownloader.ReloadFileList();

                    return;
                }

                case "add":
                {
                    if (count < 3)
                    {
                        break;
                    }

                    uint id;

                    if (!uint.TryParse(s[2], out id))
                    {
                        break;
                    }

                    switch (s[1])
                    {
                    case "app":
                    {
                        List <string> channels;
                        var           exists = Application.ImportantApps.TryGetValue(id, out channels);

                        if (exists && channels.Contains(channel))
                        {
                            CommandHandler.ReplyToCommand(command, "App {0}{1}{2} ({3}) is already important in {4}{5}{6}.", Colors.BLUE, id, Colors.NORMAL, Steam.GetAppName(id), Colors.BLUE, channel, Colors.NORMAL);
                        }
                        else
                        {
                            if (exists)
                            {
                                Application.ImportantApps[id].Add(channel);
                            }
                            else
                            {
                                Application.ImportantApps.Add(id, new List <string> {
                                            channel
                                        });
                            }

                            using (var db = Database.GetConnection())
                            {
                                db.Execute("INSERT INTO `ImportantApps` (`AppID`, `Channel`) VALUES (@AppID, @Channel)", new { AppID = id, Channel = channel });
                            }

                            CommandHandler.ReplyToCommand(command, "Marked app {0}{1}{2} ({3}) as important in {4}{5}{6}.", Colors.BLUE, id, Colors.NORMAL, Steam.GetAppName(id), Colors.BLUE, channel, Colors.NORMAL);
                        }

                        return;
                    }

                    case "sub":
                    {
                        if (Application.ImportantSubs.ContainsKey(id))
                        {
                            CommandHandler.ReplyToCommand(command, "Package {0}{1}{2} ({3}) is already important.", Colors.BLUE, id, Colors.NORMAL, Steam.GetPackageName(id));
                        }
                        else
                        {
                            Application.ImportantSubs.Add(id, 1);

                            using (var db = Database.GetConnection())
                            {
                                db.Execute("INSERT INTO `ImportantSubs` (`SubID`) VALUES (@SubID)", new { SubID = id });
                            }

                            CommandHandler.ReplyToCommand(command, "Marked package {0}{1}{2} ({3}) as important.", Colors.BLUE, id, Colors.NORMAL, Steam.GetPackageName(id));
                        }

                        return;
                    }
                    }

                    break;
                }

                case "remove":
                {
                    if (count < 3)
                    {
                        break;
                    }

                    uint id;

                    if (!uint.TryParse(s[2], out id))
                    {
                        break;
                    }

                    switch (s[1])
                    {
                    case "app":
                    {
                        List <string> channels;

                        if (!Application.ImportantApps.TryGetValue(id, out channels) || !channels.Contains(channel))
                        {
                            CommandHandler.ReplyToCommand(command, "App {0}{1}{2} ({3}) is not important in {4}{5}{6}.", Colors.BLUE, id, Colors.NORMAL, Steam.GetAppName(id), Colors.BLUE, channel, Colors.NORMAL);
                        }
                        else
                        {
                            if (channels.Count > 1)
                            {
                                Application.ImportantApps[id].Remove(channel);
                            }
                            else
                            {
                                Application.ImportantApps.Remove(id);
                            }

                            using (var db = Database.GetConnection())
                            {
                                db.Execute("DELETE FROM `ImportantApps` WHERE `AppID` = @AppID AND `Channel` = @Channel", new { AppID = id, Channel = channel });
                            }

                            CommandHandler.ReplyToCommand(command, "Removed app {0}{1}{2} ({3}) from the important list in {4}{5}{6}.", Colors.BLUE, id, Colors.NORMAL, Steam.GetAppName(id), Colors.BLUE, channel, Colors.NORMAL);
                        }

                        return;
                    }

                    case "sub":
                    {
                        if (!Application.ImportantSubs.ContainsKey(id))
                        {
                            CommandHandler.ReplyToCommand(command, "Package {0}{1}{2} ({3}) is not important.", Colors.BLUE, id, Colors.NORMAL, Steam.GetPackageName(id));
                        }
                        else
                        {
                            Application.ImportantSubs.Remove(id);

                            using (var db = Database.GetConnection())
                            {
                                db.Execute("DELETE FROM `ImportantSubs` WHERE `SubID` = @SubID", new { SubID = id });
                            }

                            CommandHandler.ReplyToCommand(command, "Removed package {0}{1}{2} ({3}) from the important list.", Colors.BLUE, id, Colors.NORMAL, Steam.GetPackageName(id));
                        }

                        return;
                    }
                    }

                    break;
                }

                case "queue":
                {
                    if (count < 3)
                    {
                        break;
                    }

                    uint id;

                    if (!uint.TryParse(s[2], out id))
                    {
                        break;
                    }

                    switch (s[1])
                    {
                    case "app":
                    {
                        string name;

                        using (var db = Database.GetConnection())
                        {
                            name = db.ExecuteScalar <string>("SELECT `Name` FROM `Apps` WHERE `AppID` = @AppID", new { AppID = id });
                        }

                        if (!string.IsNullOrEmpty(name))
                        {
                            StoreQueue.AddAppToQueue(id);

                            CommandHandler.ReplyToCommand(command, "App {0}{1}{2} ({3}) has been added to the store update queue.", Colors.BLUE, id, Colors.NORMAL, Utils.RemoveControlCharacters(name));

                            return;
                        }

                        CommandHandler.ReplyToCommand(command, "This app is not in the database.");

                        return;
                    }

                    case "sub":
                    {
                        if (id == 0)
                        {
                            CommandHandler.ReplyToCommand(command, "Sub 0 can not be queued.");

                            return;
                        }

                        string name;

                        using (var db = Database.GetConnection())
                        {
                            name = db.ExecuteScalar <string>("SELECT `Name` FROM `Subs` WHERE `SubID` = @SubID", new { SubID = id });
                        }

                        if (!string.IsNullOrEmpty(name))
                        {
                            StoreQueue.AddPackageToQueue(id);

                            CommandHandler.ReplyToCommand(command, "Package {0}{1}{2} ({3}) has been added to the store update queue.", Colors.BLUE, id, Colors.NORMAL, Utils.RemoveControlCharacters(name));

                            return;
                        }

                        CommandHandler.ReplyToCommand(command, "This package is not in the database.");

                        return;
                    }
                    }

                    break;
                }
                }
            }

            CommandHandler.ReplyToCommand(command, "Usage:{0} important reload {1}or{2} important <add/remove/queue> <app/sub> <id>", Colors.OLIVE, Colors.NORMAL, Colors.OLIVE);
        }
コード例 #41
0
        public static void ReloadImportant(CommandArguments command)
        {
            ReloadImportant();

            command.ReplyAsNotice = true;
            CommandHandler.ReplyToCommand(command, "Reloaded {0} important apps and {1} packages", ImportantApps.Count, ImportantSubs.Count);
        }
コード例 #42
0
        public static void Reload(CommandArguments command)
        {
            Reload();

            command.Notice("Reloaded {0} token overrides", SecretTokens.Count);
        }
コード例 #43
0
        public override async Task OnCommand(CommandArguments command)
        {
            if (string.IsNullOrWhiteSpace(command.Message))
            {
                command.Reply($"Usage:{Colors.OLIVE} players <appid or partial game name>");

                return;
            }

            if (!uint.TryParse(command.Message, out var appID))
            {
                appID = await AppCommand.TrySearchAppId(command);

                if (appID == 0)
                {
                    return;
                }
            }

            var task = Steam.Instance.UserStats.GetNumberOfCurrentPlayers(appID);

            task.Timeout = TimeSpan.FromSeconds(10);
            var callback = await task;

            if (appID == 0)
            {
                appID = 753;
            }

            var name = Steam.GetAppName(appID, out var appType);

            if (callback.Result != EResult.OK)
            {
                command.Reply($"Unable to request player count for {Colors.BLUE}{name}{Colors.NORMAL}: {Colors.RED}{callback.Result}{Colors.NORMAL} -{Colors.DARKBLUE} {SteamDB.GetAppUrl(appID, "graphs")}");

                return;
            }

            var  numPlayers = callback.NumPlayers;
            uint dailyPlayers;

            await using (var db = await Database.GetConnectionAsync())
            {
                dailyPlayers = await db.ExecuteScalarAsync <uint>("SELECT `MaxDailyPlayers` FROM `OnlineStats` WHERE `AppID` = @appID", new { appID });

                if (appID == 753 && numPlayers == 0)
                {
                    numPlayers = await db.ExecuteScalarAsync <uint>("SELECT `CurrentPlayers` FROM `OnlineStats` WHERE `AppID` = @appID", new { appID });
                }
            }

            if (dailyPlayers < numPlayers)
            {
                dailyPlayers = numPlayers;
            }

            var type = "playing";

            switch (appType)
            {
            case EAppType.Tool:
            case EAppType.Config:
            case EAppType.Application:
                type = "using";
                break;

            case EAppType.Media:
            case EAppType.Series:
            case EAppType.Video:
                type = "watching";
                break;

            case EAppType.Demo:
                type = "demoing";
                break;

            case EAppType.Guide:
            case EAppType.Comic:
                type = "reading";
                break;

            case EAppType.Hardware:
                type = "bricking";
                break;
            }

            command.Reply(
                $"{Colors.OLIVE}{numPlayers:N0}{Colors.NORMAL} {type} {Colors.BLUE}{name}{Colors.NORMAL} - 24h:{Colors.GREEN} {dailyPlayers:N0}{Colors.NORMAL} -{Colors.DARKBLUE} {SteamDB.GetAppUrl(appID, "graphs")}"
                );
        }
コード例 #44
0
 public abstract Task OnCommand(CommandArguments command);
コード例 #45
0
        public void OnMessage(CommandArguments command)
        {
            var matches = SteamLinkMatch.Matches(command.Message);

            foreach (Match match in matches)
            {
                var page = match.Groups["page"].Value;

                // Ignore sub pages, easier to do it here rather than in regex
                if (!string.IsNullOrEmpty(page))
                {
                    continue;
                }

                var    appType   = string.Empty;
                var    id        = uint.Parse(match.Groups["id"].Value);
                var    isPackage = match.Groups["type"].Value == "sub";
                string name;

                if (isPackage)
                {
                    name = Steam.GetPackageName(id);
                }
                else
                {
                    App data;

                    using (var db = Database.Get())
                    {
                        data = db.Query <App>("SELECT `AppID`, `Apps`.`Name`, `LastKnownName`, `AppsTypes`.`DisplayName` as `AppTypeString` FROM `Apps` JOIN `AppsTypes` ON `Apps`.`AppType` = `AppsTypes`.`AppType` WHERE `AppID` = @AppID", new { AppID = id }).SingleOrDefault();
                    }

                    if (data.AppID == 0)
                    {
                        continue;
                    }

                    name    = string.IsNullOrEmpty(data.LastKnownName) ? data.Name : data.LastKnownName;
                    name    = Utils.RemoveControlCharacters(name);
                    appType = data.AppTypeString;
                }

                if (command.Message.IndexOf(name, StringComparison.CurrentCultureIgnoreCase) >= 0)
                {
                    continue;
                }

                string priceInfo = isPackage ? string.Empty : GetFormattedPrices(id);

                IRC.Instance.SendReply(command.Recipient,
                                       string.Format("{0}» {1}{2} {3} —{4} {5}{6}{7}",
                                                     Colors.OLIVE,
                                                     Colors.NORMAL,
                                                     isPackage ? "Package" : appType,
                                                     id,
                                                     Colors.BLUE,
                                                     name,
                                                     Colors.LIGHTGRAY,
                                                     priceInfo
                                                     ),
                                       false
                                       );
            }
        }
コード例 #46
0
 private void HandleSteamMessage(CommandArguments commandData)
 {
     var message      = commandData.Message;
     var i            = message.IndexOf(' ');
     var inputCommand = i == -1 ? message.Substring(1) : message[1..i];
コード例 #47
0
ファイル: App.cs プロジェクト: rgooler/SteamDatabaseBackend
        public override async Task OnCommand(CommandArguments command)
        {
            if (string.IsNullOrWhiteSpace(command.Message))
            {
                command.Reply($"Usage:{Colors.OLIVE} app <appid or partial game name>");

                return;
            }

            string name;

            if (!uint.TryParse(command.Message, out var appID))
            {
                appID = await TrySearchAppId(command);

                if (appID == 0)
                {
                    return;
                }
            }

            var tokenTask = Steam.Instance.Apps.PICSGetAccessTokens(appID, null);

            tokenTask.Timeout = TimeSpan.FromSeconds(10);
            var tokenCallback = await tokenTask;

            SteamApps.PICSRequest request;

            if (tokenCallback.AppTokens.ContainsKey(appID))
            {
                request = PICSTokens.NewAppRequest(appID, tokenCallback.AppTokens[appID]);
            }
            else
            {
                request = PICSTokens.NewAppRequest(appID);
            }

            var infoTask = Steam.Instance.Apps.PICSGetProductInfo(new List <SteamApps.PICSRequest> {
                request
            }, Enumerable.Empty <SteamApps.PICSRequest>());

            infoTask.Timeout = TimeSpan.FromSeconds(10);
            var job      = await infoTask;
            var callback = job.Results?.FirstOrDefault(x => x.Apps.ContainsKey(appID));

            if (callback == null)
            {
                command.Reply($"Unknown AppID: {Colors.BLUE}{appID}{(LicenseList.OwnedApps.ContainsKey(appID) ? SteamDB.StringCheckmark : string.Empty)}");

                return;
            }

            var info = callback.Apps[appID];

            if (info.KeyValues["common"]["name"].Value != null)
            {
                name = Utils.LimitStringLength(Utils.RemoveControlCharacters(info.KeyValues["common"]["name"].AsString()));
            }
            else
            {
                name = Steam.GetAppName(info.ID);
            }

            info.KeyValues.SaveToFile(Path.Combine(Application.Path, "app", $"{info.ID}.vdf"), false);

            command.Reply($"{Colors.BLUE}{name}{Colors.NORMAL} -{Colors.DARKBLUE} {SteamDB.GetAppUrl(info.ID)}{Colors.NORMAL} - Dump:{Colors.DARKBLUE} {SteamDB.GetRawAppUrl(info.ID)}{Colors.NORMAL}{(info.MissingToken ? SteamDB.StringNeedToken : string.Empty)}{(LicenseList.OwnedApps.ContainsKey(info.ID) ? SteamDB.StringCheckmark : string.Empty)}");

            if (command.IsUserAdmin && !LicenseList.OwnedApps.ContainsKey(info.ID))
            {
                JobManager.AddJob(() => Steam.Instance.Apps.RequestFreeLicense(info.ID));
            }
        }
コード例 #48
0
        private static async void TryCommand(Command command, CommandArguments commandData)
        {
            try
            {
                await command.OnCommand(commandData);
            }
            catch (TaskCanceledException)
            {
                commandData.Reply("Your command timed out.");
            }
            catch (AsyncJobFailedException)
            {
                commandData.Reply("Steam says this job failed, unable to execute your command.");
            }
            catch (Exception e)
            {
                commandData.Reply("Exception: {0}", e.Message);

                ErrorReporter.Notify(e);
            }
        }
コード例 #49
0
        public override async Task OnCommand(CommandArguments command)
        {
            var s = command.Message.Split(' ');

            if (s.Length < 2)
            {
                command.Reply("Usage:{0} queue <app/sub> <id>", Colors.OLIVE);

                return;
            }

            if (!uint.TryParse(s[1], out var id))
            {
                command.Reply("Your ID does not look like a number.");

                return;
            }

            string name;

            switch (s[0])
            {
            case "app":
                using (var db = Database.Get())
                {
                    name = await db.ExecuteScalarAsync <string>("SELECT `Name` FROM `Apps` WHERE `AppID` = @AppID", new { AppID = id });
                }

                if (!string.IsNullOrEmpty(name))
                {
                    await StoreQueue.AddAppToQueue(id);

                    command.Reply("App {0}{1}{2} ({3}) has been added to the store update queue.", Colors.BLUE, id, Colors.NORMAL, Utils.RemoveControlCharacters(name));

                    return;
                }

                command.Reply("This app is not in the database.");

                return;

            case "package":
            case "sub":
                if (id == 0)
                {
                    command.Reply("Sub 0 can not be queued.");

                    return;
                }

                using (var db = Database.Get())
                {
                    name = await db.ExecuteScalarAsync <string>("SELECT `Name` FROM `Subs` WHERE `SubID` = @SubID", new { SubID = id });
                }

                if (!string.IsNullOrEmpty(name))
                {
                    await StoreQueue.AddPackageToQueue(id);

                    command.Reply("Package {0}{1}{2} ({3}) has been added to the store update queue.", Colors.BLUE, id, Colors.NORMAL, Utils.RemoveControlCharacters(name));

                    return;
                }

                command.Reply("This package is not in the database.");

                return;

            default:
                command.Reply("You can only queue apps and packages.");

                return;
            }
        }
コード例 #50
0
        public static void ReloadImportant(CommandArguments command)
        {
            ReloadImportant();

            command.Notice("Reloaded {0} important apps and {1} packages", ImportantApps.Count, ImportantSubs.Count);
        }
コード例 #51
0
        public void OnIRCMessage(object sender, ChatMessageEventArgs e)
        {
            var commandData = new CommandArguments
            {
                CommandType    = ECommandType.IRC,
                SenderIdentity = e.Sender,
                Recipient      = e.Recipient,
                Message        = e.Message
            };

            if (Steam.Instance.Client.IsConnected)
            {
                PubFileHandler.OnMessage(commandData);
            }

            LinkExpander.OnMessage(commandData);

            if (e.Message[0] != Settings.Current.IRC.CommandPrefix)
            {
                return;
            }

            var message      = (string)e.Message;
            var messageArray = message.Split(' ');
            var trigger      = messageArray[0];

            if (trigger.Length < 2)
            {
                return;
            }

            trigger = trigger.Substring(1);

            var command = RegisteredCommands.FirstOrDefault(cmd => cmd.Trigger.Equals(trigger));

            if (command == null)
            {
                return;
            }

            commandData.Message = message.Substring(messageArray[0].Length).Trim();

            if (command.IsSteamCommand && !Steam.Instance.Client.IsConnected)
            {
                commandData.Reply("Not connected to Steam.");

                return;
            }

            if (command.IsAdminCommand)
            {
                var ident = string.Format("{0}@{1}", e.Sender.Username, e.Sender.Hostname);

                if (!Settings.Current.IRC.Admins.Contains(ident))
                {
                    return;
                }
            }

            Log.WriteInfo("CommandHandler", "Handling IRC command \"{0}\" for {1}", message, commandData);

            TryCommand(command, commandData);
        }
コード例 #52
0
        public override async Task OnCommand(CommandArguments command)
        {
            await Task.Yield();

            if (command.Message.Length == 0)
            {
                command.Reply("Usage:{0} steamid <steamid> [individual/group/gamegroup]", Colors.OLIVE);

                return;
            }

            var args    = command.Message.Split(' ');
            var urlType = EVanityURLType.Default;

            if (args.Length > 1)
            {
                switch (args[1])
                {
                case "individual":
                    urlType = EVanityURLType.Individual;
                    break;

                case "group":
                    urlType = EVanityURLType.Group;
                    break;

                case "game":
                case "gamegroup":
                    urlType = EVanityURLType.OfficialGameGroup;
                    break;

                default:
                    command.Reply("Invalid vanity url type.");
                    return;
                }
            }

            SteamID steamID;

            if (urlType != EVanityURLType.Default || !TrySetSteamID(args[0], out steamID))
            {
                if (urlType == EVanityURLType.Default)
                {
                    urlType = EVanityURLType.Individual;
                }

                var eResult = ResolveVanityURL(args[0], urlType, out steamID);

                if (eResult != EResult.OK)
                {
                    command.Reply("Failed to resolve vanity url: {0}{1}", Colors.RED, eResult.ToString());

                    return;
                }
            }

            command.Reply(ExpandSteamID(steamID));

            if (!steamID.IsValid || (!steamID.IsIndividualAccount && !steamID.IsClanAccount))
            {
                return;
            }

            JobManager.TryRemoveJob(new JobID(steamID)); // Remove previous "job" if any

            JobManager.AddJob(
                () => FakePersonaStateJob(steamID),
                command
                );
        }
コード例 #53
0
        public void OnSteamFriendMessage(SteamFriends.FriendMsgCallback callback)
        {
            if (callback.EntryType != EChatEntryType.ChatMsg        // Is chat message
            ||  callback.Sender == Steam.Instance.Client.SteamID    // Is not sent by the bot
            ||  callback.Message[0] != Settings.Current.IRC.CommandPrefix
            ||  callback.Message.Contains('\n')                     // Does not contain new lines
            )
            {
                return;
            }

            var commandData = new CommandArguments
            {
                CommandType = ECommandType.SteamIndividual,
                SenderID = callback.Sender,
                Message = callback.Message
            };

            Log.WriteInfo("CommandHandler", "Handling Steam friend command \"{0}\" for {1}", callback.Message, commandData);

            HandleSteamMessage(commandData);
        }
コード例 #54
0
        public async void OnMessage(CommandArguments command)
        {
            var matches = SharedFileMatch.Matches(command.Message);

            foreach (Match match in matches)
            {
                if (!ulong.TryParse(match.Groups["pubfileid"].Value, out var pubFileId))
                {
                    continue;
                }

                Log.WriteInfo("Link Expander", "Will look up pubfile {0} for {1}", pubFileId, command);

                var pubFileRequest = new CPublishedFile_GetDetails_Request
                {
                    includevotes = true,
                };

                pubFileRequest.publishedfileids.Add(pubFileId);

                PublishedFileDetails details;

                try
                {
                    var task = PublishedFiles.SendMessage(api => api.GetDetails(pubFileRequest));
                    task.Timeout = TimeSpan.FromSeconds(10);
                    var callback = await task;
                    var response = callback.GetDeserializedResponse <CPublishedFile_GetDetails_Response>();
                    details = response.publishedfiledetails.FirstOrDefault();
                }
                catch (Exception e)
                {
                    Log.WriteError("Link Expander", "Failed to get pubfile details: {0}", e.Message);

                    continue;
                }

                if (details == null || (EResult)details.result != EResult.OK)
                {
                    continue;
                }

                string title;

                if (!string.IsNullOrWhiteSpace(details.title))
                {
                    title = details.title;
                }
                else if (!string.IsNullOrEmpty(details.file_description))
                {
                    title = details.file_description;
                }
                else
                {
                    title = details.filename;
                }

                if (title.Length > 49)
                {
                    title = title.Substring(0, 49) + "…";
                }

                var votesUp   = details.vote_data?.votes_up ?? 0;
                var votesDown = details.vote_data?.votes_down ?? 0;

                IRC.Instance.SendReply(command.Recipient,
                                       string.Format("{0}» {1}{2} {3}{4}{5} for {6}{7}{8} ({9:N0} views, {10:N0} \ud83d\udc4d, {11:N0} \ud83d\udc4e)",
                                                     Colors.OLIVE,
                                                     Colors.NORMAL,
                                                     (EWorkshopFileType)details.file_type,
                                                     Colors.BLUE,
                                                     Utils.RemoveControlCharacters(title),
                                                     Colors.NORMAL,
                                                     Colors.BLUE,
                                                     Utils.LimitStringLength(Utils.RemoveControlCharacters(details.app_name)),
                                                     Colors.LIGHTGRAY,
                                                     details.views,
                                                     votesUp,
                                                     votesDown
                                                     ),
                                       false
                                       );
            }
        }
コード例 #55
0
        private void HandleSteamMessage(CommandArguments commandData)
        {
            var message = commandData.Message;
            var i = message.IndexOf(' ');
            var inputCommand = i == -1 ? message.Substring(1) : message.Substring(1, i - 1);

            var command = RegisteredCommands.FirstOrDefault(cmd => cmd.Trigger.Equals(inputCommand));

            if (command == null)
            {
                return;
            }

            commandData.Message = i == -1 ? string.Empty : message.Substring(i).Trim();

            if (command.IsAdminCommand && !Settings.Current.SteamAdmins.Contains(commandData.SenderID.ConvertToUInt64()))
            {
                commandData.Reply("You're not an admin!");

                return;
            }

            TryCommand(command, commandData);
        }
コード例 #56
0
        public override async Task OnCommand(CommandArguments command)
        {
            if (command.Message.Length == 0 || !uint.TryParse(command.Message, out var subID))
            {
                command.Reply("Usage:{0} sub <subid>", Colors.OLIVE);

                return;
            }

            var tokenTask = Steam.Instance.Apps.PICSGetAccessTokens(null, subID);

            tokenTask.Timeout = TimeSpan.FromSeconds(10);
            var tokenCallback = await tokenTask;

            SteamApps.PICSRequest request;

            if (tokenCallback.PackageTokens.ContainsKey(subID))
            {
                request = PICSTokens.NewPackageRequest(subID, tokenCallback.PackageTokens[subID]);
            }
            else
            {
                request = PICSTokens.NewPackageRequest(subID);
            }

            var infoTask = Steam.Instance.Apps.PICSGetProductInfo(Enumerable.Empty <SteamApps.PICSRequest>(), new List <SteamApps.PICSRequest> {
                request
            });

            infoTask.Timeout = TimeSpan.FromSeconds(10);
            var job      = await infoTask;
            var callback = job.Results?.FirstOrDefault(x => x.Packages.ContainsKey(subID));

            if (callback == null)
            {
                command.Reply("Unknown SubID: {0}{1}{2}", Colors.BLUE, subID, LicenseList.OwnedSubs.ContainsKey(subID) ? SteamDB.StringCheckmark : string.Empty);

                return;
            }

            var info = callback.Packages[subID];

            if (!info.KeyValues.Children.Any())
            {
                command.Reply("No package info returned for SubID: {0}{1}{2}{3}",
                              Colors.BLUE, subID,
                              info.MissingToken ? SteamDB.StringNeedToken : string.Empty,
                              LicenseList.OwnedSubs.ContainsKey(subID) ? SteamDB.StringCheckmark : string.Empty
                              );

                return;
            }

            info.KeyValues.SaveToFile(Path.Combine(Application.Path, "sub", string.Format("{0}.vdf", info.ID)), false);

            command.Reply("{0}{1}{2} -{3} {4}{5} - Dump:{6} {7}{8}{9}{10}",
                          Colors.BLUE, Steam.GetPackageName(info.ID), Colors.NORMAL,
                          Colors.DARKBLUE, SteamDB.GetPackageUrl(info.ID), Colors.NORMAL,
                          Colors.DARKBLUE, SteamDB.GetRawPackageUrl(info.ID), Colors.NORMAL,
                          info.MissingToken ? SteamDB.StringNeedToken : string.Empty,
                          LicenseList.OwnedSubs.ContainsKey(info.ID) ? SteamDB.StringCheckmark : string.Empty
                          );
        }
コード例 #57
0
        public void OnIRCMessage(object sender, ChatMessageEventArgs e)
        {
            var commandData = new CommandArguments
            {
                CommandType = ECommandType.IRC,
                SenderIdentity = e.Sender,
                Recipient = e.Recipient,
                Message = e.Message
            };

            if (Steam.Instance.Client.IsConnected)
            {
                PubFileHandler.OnMessage(commandData);
            }

            LinkExpander.OnMessage(commandData);

            if (e.Message[0] != Settings.Current.IRC.CommandPrefix)
            {
                return;
            }

            var message = (string)e.Message;
            var messageArray = message.Split(' ');
            var trigger = messageArray[0];

            if (trigger.Length < 2)
            {
                return;
            }
                
            trigger = trigger.Substring(1);

            var command = RegisteredCommands.FirstOrDefault(cmd => cmd.Trigger.Equals(trigger));

            if (command == null)
            {
                return;
            }

            commandData.Message = message.Substring(messageArray[0].Length).Trim();

            if (command.IsSteamCommand && !Steam.Instance.Client.IsConnected)
            {
                commandData.Reply("Not connected to Steam.");

                return;
            }

            if (command.IsAdminCommand)
            {
                var ident = string.Format("{0}@{1}", e.Sender.Username, e.Sender.Hostname);

                if (!Settings.Current.IRC.Admins.Contains(ident))
                {
                    return;
                }
            }

            Log.WriteInfo("CommandHandler", "Handling IRC command \"{0}\" for {1}", message, commandData);

            TryCommand(command, commandData);
        }
コード例 #58
0
        public override async Task OnCommand(CommandArguments command)
        {
            if (command.Message.Length == 0)
            {
                command.Reply("Usage:{0} pubfile <pubfileid>", Colors.OLIVE);

                return;
            }

            if (!ulong.TryParse(command.Message, out var pubFileId))
            {
                command.Reply("Invalid Published File ID");

                return;
            }

            var pubFileRequest = new CPublishedFile_GetDetails_Request
            {
                includeadditionalpreviews = true,
                includechildren           = true,
                includetags        = true,
                includekvtags      = true,
                includevotes       = true,
                includeforsaledata = true,
                includemetadata    = true,
            };

            pubFileRequest.publishedfileids.Add(pubFileId);

            var task = PublishedFiles.SendMessage(api => api.GetDetails(pubFileRequest));

            task.Timeout = TimeSpan.FromSeconds(10);
            var callback = await task;
            var response = callback.GetDeserializedResponse <CPublishedFile_GetDetails_Response>();
            var details  = response.publishedfiledetails.FirstOrDefault();

            if (details == null)
            {
                command.Reply("Unable to make service request for published file info: the server returned no info");

                return;
            }

            var result = (EResult)details.result;

            if (result != EResult.OK)
            {
                command.Reply("Unable to get published file info: {0}{1}", Colors.RED, result);

                return;
            }

            var json = JsonConvert.SerializeObject(details, Formatting.Indented);

            File.WriteAllText(Path.Combine(Application.Path, "ugc", string.Format("{0}.json", details.publishedfileid)), json, Encoding.UTF8);

            command.Reply("{0}, Title: {1}{2}{3}, Creator: {4}{5}{6}, App: {7}{8}{9}{10}, File UGC: {11}{12}{13}, Preview UGC: {14}{15}{16} -{17} {18}",
                          (EWorkshopFileType)details.file_type,
                          Colors.BLUE, string.IsNullOrWhiteSpace(details.title) ? "[no title]" : details.title, Colors.NORMAL,
                          Colors.BLUE, new SteamID(details.creator).Render(true), Colors.NORMAL,
                          Colors.BLUE, details.creator_appid,
                          details.creator_appid == details.consumer_appid ? "" : string.Format(" (consumer {0})", details.consumer_appid),
                          Colors.NORMAL,
                          Colors.BLUE, details.hcontent_file, Colors.NORMAL,
                          Colors.BLUE, details.hcontent_preview, Colors.NORMAL,
                          Colors.DARKBLUE, SteamDB.GetUGCURL(details.publishedfileid)
                          );

            command.Notice("{0} - https://steamcommunity.com/sharedfiles/filedetails/?id={1}", details.file_url, details.publishedfileid);
        }
コード例 #59
0
        public void OnIRCMessage(object sender, ChatMessageEventArgs e)
        {
            var commandData = new CommandArguments
            {
                CommandType    = ECommandType.IRC,
                SenderIdentity = e.Sender,
                Nickname       = e.Sender.Nickname.ToString(),
                Recipient      = e.Recipient,
                Message        = e.Message
            };

            if (commandData.SenderIdentity.Hostname == "steamdb/discord-relay")
            {
                var match = DiscordRelayMessageRegex.Match(commandData.Message);

                if (!match.Success)
                {
                    return;
                }

                // Remove IRC colors, remove control characters, remove zero width space, add @ and a space
                commandData.Nickname = $"@{Utils.RemoveControlCharacters(Colors.StripColors(match.Groups["name"].Value.Replace("\u200B", "")))} ";
                commandData.Message  = match.Groups["message"].Value;
            }

            if (commandData.Message[0] != Settings.Current.IRC.CommandPrefix)
            {
                return;
            }

            var message      = commandData.Message;
            var messageArray = message.Split(' ');
            var trigger      = messageArray[0];

            if (trigger.Length < 2)
            {
                return;
            }

            trigger = trigger.Substring(1);

            var command = RegisteredCommands.Find(cmd => cmd.Trigger == trigger);

            if (command == null)
            {
                return;
            }

            commandData.Message = message.Substring(messageArray[0].Length).Trim();

            if (command.IsSteamCommand && !Steam.Instance.Client.IsConnected)
            {
                commandData.Reply("Not connected to Steam.");

                return;
            }

            var ident = $"{e.Sender.Username}@{e.Sender.Hostname}";

            commandData.IsUserAdmin = Settings.Current.IRC.Admins.Contains(ident);

            if (command.IsAdminCommand && !commandData.IsUserAdmin)
            {
                return;
            }

            Log.WriteInfo(nameof(CommandHandler), $"Handling IRC command \"{Utils.RemoveControlCharacters(Colors.StripColors(message))}\" for {commandData}");

            TryCommand(command, commandData);
        }
コード例 #60
0
        public override async Task OnCommand(CommandArguments command)
        {
            await Task.Yield();

            if (command.CommandType != ECommandType.IRC || !IRC.IsRecipientChannel(command.Recipient))
            {
                command.Reply("This command is only available in channels.");

                return;
            }

            var channel = command.Recipient;

            var  s     = command.Message.Split(' ');
            var  count = s.Length;
            uint id;

            if (count > 0)
            {
                switch (s[0])
                {
                case "reload":
                    Application.ReloadImportant(command);
                    PICSTokens.Reload(command);
                    FileDownloader.ReloadFileList();

                    return;

                case "add":
                    if (count < 3)
                    {
                        break;
                    }

                    if (!uint.TryParse(s[2], out id))
                    {
                        break;
                    }

                    switch (s[1])
                    {
                    case "app":
                        List <string> channels;
                        var           exists = Application.ImportantApps.TryGetValue(id, out channels);

                        if (exists && channels.Contains(channel))
                        {
                            command.Reply("App {0}{1}{2} ({3}) is already important in {4}{5}{6}.", Colors.BLUE, id, Colors.NORMAL, Steam.GetAppName(id), Colors.BLUE, channel, Colors.NORMAL);
                        }
                        else
                        {
                            if (exists)
                            {
                                Application.ImportantApps[id].Add(channel);
                            }
                            else
                            {
                                Application.ImportantApps.Add(id, new List <string> {
                                    channel
                                });
                            }

                            using (var db = Database.GetConnection())
                            {
                                db.Execute("INSERT INTO `ImportantApps` (`AppID`, `Channel`) VALUES (@AppID, @Channel)", new { AppID = id, Channel = channel });
                            }

                            command.Reply("Marked app {0}{1}{2} ({3}) as important in {4}{5}{6}.", Colors.BLUE, id, Colors.NORMAL, Steam.GetAppName(id), Colors.BLUE, channel, Colors.NORMAL);
                        }

                        return;

                    case "sub":
                        if (Application.ImportantSubs.ContainsKey(id))
                        {
                            command.Reply("Package {0}{1}{2} ({3}) is already important.", Colors.BLUE, id, Colors.NORMAL, Steam.GetPackageName(id));
                        }
                        else
                        {
                            Application.ImportantSubs.Add(id, 1);

                            using (var db = Database.GetConnection())
                            {
                                db.Execute("INSERT INTO `ImportantSubs` (`SubID`) VALUES (@SubID)", new { SubID = id });
                            }

                            command.Reply("Marked package {0}{1}{2} ({3}) as important.", Colors.BLUE, id, Colors.NORMAL, Steam.GetPackageName(id));
                        }

                        return;
                    }

                    break;

                case "remove":
                    if (count < 3)
                    {
                        break;
                    }

                    if (!uint.TryParse(s[2], out id))
                    {
                        break;
                    }

                    switch (s[1])
                    {
                    case "app":
                        List <string> channels;

                        if (!Application.ImportantApps.TryGetValue(id, out channels) || !channels.Contains(channel))
                        {
                            command.Reply("App {0}{1}{2} ({3}) is not important in {4}{5}{6}.", Colors.BLUE, id, Colors.NORMAL, Steam.GetAppName(id), Colors.BLUE, channel, Colors.NORMAL);
                        }
                        else
                        {
                            if (channels.Count > 1)
                            {
                                Application.ImportantApps[id].Remove(channel);
                            }
                            else
                            {
                                Application.ImportantApps.Remove(id);
                            }

                            using (var db = Database.GetConnection())
                            {
                                db.Execute("DELETE FROM `ImportantApps` WHERE `AppID` = @AppID AND `Channel` = @Channel", new { AppID = id, Channel = channel });
                            }

                            command.Reply("Removed app {0}{1}{2} ({3}) from the important list in {4}{5}{6}.", Colors.BLUE, id, Colors.NORMAL, Steam.GetAppName(id), Colors.BLUE, channel, Colors.NORMAL);
                        }

                        return;

                    case "sub":
                        if (!Application.ImportantSubs.ContainsKey(id))
                        {
                            command.Reply("Package {0}{1}{2} ({3}) is not important.", Colors.BLUE, id, Colors.NORMAL, Steam.GetPackageName(id));
                        }
                        else
                        {
                            Application.ImportantSubs.Remove(id);

                            using (var db = Database.GetConnection())
                            {
                                db.Execute("DELETE FROM `ImportantSubs` WHERE `SubID` = @SubID", new { SubID = id });
                            }

                            command.Reply("Removed package {0}{1}{2} ({3}) from the important list.", Colors.BLUE, id, Colors.NORMAL, Steam.GetPackageName(id));
                        }

                        return;
                    }

                    break;
                }
            }

            command.Reply("Usage:{0} important reload {1}or{2} important <add/remove> <app/sub> <id>", Colors.OLIVE, Colors.NORMAL, Colors.OLIVE);
        }