예제 #1
0
        internal async Task <string> Try(SocketMessage msg)
        {
            if (msg is SocketUserMessage &&
                msg.Channel is SocketTextChannel &&
                !msg.Author.IsBot &&
                !msg.Author.IsWebhook &&
                msg.Attachments.Count == 1)
            {
                var attachment = msg.Attachments.First();
                {
                    var fileType = System.IO.Path.GetExtension(attachment.Url);
                    if ((fileType == ".txt" || fileType == ".log" || fileType == ".cs") && attachment.Size < 1000000)
                    {
                        var fileContent = await HttpClient.GetStringAsync(attachment.Url);

                        var botAnswer = new StringBuilder();

                        CommonIssues.CheckCommonLogError(fileContent, botAnswer, msg.Author);

                        await CommonIssues.CheckModsVersion(fileContent, botAnswer, msg.Author);

                        var pasteResult = await PostBin(fileContent);

                        if (pasteResult.IsSuccess)
                        {
                            botAnswer.AppendLine(
                                $"Automatic pastebin for {msg.Author.Username} {attachment.Filename} file: {pasteResult.FullUrl}");
                            return(botAnswer.ToString());
                        }
                        else
                        {
                            Logger.Log(
                                $"Failed to make pastebin for {msg.Author.Username} {attachment.Filename}, size: {attachment.Size}. HTTP Error code {pasteResult.StatusCode}");
                        }
                    }
                }
            }

            return(string.Empty);
        }
예제 #2
0
        internal async Task <string> Try(SocketMessage msg)
        {
            if (msg is SocketUserMessage &&
                msg.Channel is SocketTextChannel &&
                !msg.Author.IsBot &&
                !msg.Author.IsWebhook &&
                msg.Channel.Name.Equals("tech-support") &&
                msg.Attachments.Count == 1)
            {
                var attachment = msg.Attachments.First();
                {
                    var fileType = System.IO.Path.GetExtension(attachment.Url);
                    if (fileType == ".png")
                    {
                        Logger.Log("Preparing a query for Yandex.");

                        var botAnswer   = new StringBuilder();
                        var queryResult = await QueryYandex(attachment.Url);

                        Logger.Log("Checking for common log errors.");
                        CommonIssues.CheckCommonLogError(queryResult.ImageText, botAnswer, msg.Author);

                        Logger.Log("Checking for outdated mods.");
                        var hasOutdatedMods = await CommonIssues.CheckModsVersion(queryResult.ImageText, botAnswer, msg.Author);

                        if (hasOutdatedMods)
                        {
                            // Found mods, so its probably a console log that is screenshot, lets add a tag so its for sure recognized
                            // Todo: handle tags better directly
                            queryResult.HasModLoadingText = true;
                        }

                        Logger.Log("Checking if its a version mismatch problem");
                        if (queryResult.ImageText.Contains("version mismatch", StringComparison.InvariantCultureIgnoreCase) ||
                            queryResult.ImageText.Contains("Yours=MOD", StringComparison.InvariantCultureIgnoreCase))
                        {
                            botAnswer.AppendLine($"{msg.Author.Mention}, looks like you just uploaded a screenshot of a lobby game version mismatch.");
                            botAnswer.AppendLine(CommonIssues.VersionMismatch);
                            botAnswer.AppendLine("If the issue is something else, just wait for help.");

                            return(botAnswer.ToString());
                        }

                        Logger.Log("Checking if its a console image");
                        if (queryResult.IsAConsole())
                        {
                            botAnswer.AppendLine($"{msg.Author.Mention}, looks like you just uploaded a screenshot of a BepinEx console / log file." +
                                                 Environment.NewLine +
                                                 "Know that most of the time, a full log is way more useful for finding what your problem is.");

                            if (msg.Content.Contains("crash", StringComparison.InvariantCultureIgnoreCase))
                            {
                                botAnswer.AppendLine(CommonIssues.CrashLogLocation);
                            }
                            else
                            {
                                botAnswer.AppendLine("You can find such log file in your `Risk of Rain 2/BepInEx/` folder, " +
                                                     "the file is called `LogOutput.log`.");
                            }

                            botAnswer.AppendLine("Drag the file in this channel so that other users can help you !");
                            return(botAnswer.ToString());
                        }

                        Logger.Log("Checking if its a window explorer image");
                        if (queryResult.IsWindowExplorer() &&
                            (queryResult.ImageText.Contains("bepin", StringComparison.InvariantCultureIgnoreCase) ||
                             queryResult.ImageText.Contains("risk of rain", StringComparison.InvariantCultureIgnoreCase)))
                        {
                            var channel    = msg.Channel as SocketGuildChannel;
                            var faqChannel = channel.Guild.Channels.FirstOrDefault(guildChannel =>
                                                                                   guildChannel.Name.Equals("faq"));

                            botAnswer.AppendLine($"{msg.Author.Mention}, looks like you just uploaded a screenshot of a Windows Explorer in your game folder.");
                            if (faqChannel != null)
                            {
                                botAnswer.AppendLine(
                                    "If you are struggling installing BepInEx / R2API: " + Environment.NewLine +
                                    $"There is a video and an image at the bottom of the <#{faqChannel.Id}> that explains how to install them properly.");
                            }
                            botAnswer.AppendLine("If the issue is something else, just wait for help.");

                            return(botAnswer.ToString());
                        }
                    }
                }
            }

            return(string.Empty);
        }
예제 #3
0
        private async Task MsgWatcherAsync(SocketMessage smsg)
        {
            if (smsg.Author.IsBot ||
                smsg.Author.IsWebhook ||
                !(smsg is SocketUserMessage msg))
            {
                return;
            }

            var channel = smsg.Channel;
            var isDM    = channel is SocketDMChannel;

            if (channel is not SocketTextChannel && !isDM)
            {
                return;
            }

            var isTestChannel = channel.Name == "help-test";
            var isHelp        = isTestChannel || channel.Name == "help";
            var isOther       = channel.Name == "mod-programming" || isDM;

            if (!isHelp && !isOther)
            {
                return;
            }

            var content = msg.Content?.SafeNormalize().Replace("\r\n", "\n") ?? string.Empty;

            bool ContainsAny(params string[] testStrings)
            {
                return(testStrings.Any(testStr => content.Contains(testStr, StringComparison.InvariantCultureIgnoreCase)));
            }

            bool ContainsAll(params string[] testStrings)
            {
                return(testStrings.All(testStr => content.Contains(testStr, StringComparison.InvariantCultureIgnoreCase)));
            }

            bool canBeHelped = false;

            // Process commands
            if (isHelp)
            {
                if (content == "nohelp" || ContainsAny("i hate robots", "i hate bots", "i hate chika"))
                {
                    SetCanBeHelped(msg.Author.Id, false);
                    await msg.ReplyAsync($"I will no longer try to help you");

                    return;
                }

                if (content == "yeshelp")
                {
                    SetCanBeHelped(msg.Author.Id, true);
                    await msg.ReplyAsync($"I will try to help you again");

                    return;
                }

                if (content == "givelog")
                {
                    await channel.SendMessageAsync(OutputLogPleaseGive);

                    return;
                }

                if (!_userCanBeHelped.TryGetValue(msg.Author.Id, out canBeHelped))
                {
                    canBeHelped = !UserIsCounselor(msg.Author as SocketGuildUser);
                    SetCanBeHelped(msg.Author.Id, canBeHelped);
                }

                if (content == "chikahelp" || msg.MentionedUsers.Any(x => x.Id == Client.CurrentUser.Id))
                {
                    await msg.ReplyAsync($"Hello!\nI **will{(canBeHelped != true ? " not" : "")}** automatically try to help when you post a question or send your output_log.txt.\nHere are my commands:\nnohelp - I will no longer try to help you (default for Counsellors)\nyeshelp - I will resume trying to help you\ngivelog - Show instructions on how to get the output_log.txt file\ngood bot - Mark my last reply as useful\nbad bot - Mark my last reply as needing improvement");
                }
            }

            if (isTestChannel || isDM)
            {
                canBeHelped = true;
            }

            // Vanity stuff
            if (content.Equals("chika", StringComparison.OrdinalIgnoreCase) ||
                content.Equals("bot", StringComparison.OrdinalIgnoreCase) ||
                ContainsAny("chikarin", "techinician chikarin", "help bot", "i hate robots"))
            {
                await AddReaction(msg, _emotePeek);
            }
            else if (content.Equals("good bot", StringComparison.OrdinalIgnoreCase))
            {
                Logger.Log("I was called a **good bot** - " + msg.GetJumpUrl());
                await AddReaction(msg, _emoteYay);
            }
            else if (content.Equals("bad bot", StringComparison.OrdinalIgnoreCase))
            {
                Logger.Log("I was called a **bad bot** - " + msg.GetJumpUrl());
                await AddReaction(msg, _emoteCry);
            }

            // Get attachment contents + pastebin
            var textAttachments = msg.Attachments.Where(x =>
            {
                var fileType = Path.GetExtension(x.Url).ToLowerInvariant();
                return(fileType == ".txt" || fileType == ".log" || fileType == ".cs" || fileType == ".md");
            }).ToList();

            var textsToProcess  = new List <string>();
            var kkmanLog        = string.Empty;
            var listOfPastebins = new List <string>();

            foreach (var textAttachment in textAttachments)
            {
                var fileContent = await _httpClient.GetStringAsync(textAttachment.Url);

                if (textAttachment.Size > _maxLogFileSize)
                {
                    continue;
                }

                fileContent = fileContent.SafeNormalize().Replace("\r\n", "\n");

                if (FileIsValidLogFile(textAttachment))
                {
                    fileContent = CleanUpLogDuplicates(fileContent);
                    textsToProcess.Add(fileContent);
                }
                else if (textAttachment.Filename.StartsWith("kkmanager", StringComparison.OrdinalIgnoreCase))
                {
                    kkmanLog = fileContent;
                }

                // todo reenable?
                //try
                //{
                //    var cleanFileContent = CleanUpLogForPastebin(fileContent);
                //    var pasteBinUrl = await _autoPastebin.Try(cleanFileContent).WithTimeout(TimeSpan.FromSeconds(3), CancellationToken.None);
                //    if (!string.IsNullOrWhiteSpace(pasteBinUrl))
                //        listOfPastebins.Add($"Pastebin link for {(fileContent.Length > cleanFileContent.Length ? "cleaned " : "")}{textAttachment}: {pasteBinUrl}");
                //}
                //catch (Exception e)
                //{
                //    Logger.Log($"Automatic pastebin for {msg.GetJumpUrl()} failed: {e}");
                //}
            }

            if (listOfPastebins.Any())
            {
                await channel.SendMessageAsync(string.Join("\n", listOfPastebins));
            }

            if (canBeHelped != true)
            {
                return;
            }

            // try to find if we can help
            if (isHelp || isDM)
            {
                var listOfSins            = new List <string>();
                var canBeFixedWithHfpatch = false;

                if (!string.IsNullOrWhiteSpace(kkmanLog))
                {
                    if (kkmanLog.Contains("Failed to parse update manifest file") &&
                        kkmanLog.Contains("at Updates KKManager.Updater.Data.UpdateInfo.Deserialize"))
                    {
                        listOfSins.Add(
                            "Your KKManager might be outdated, which causes updates to fail. Check <https://github.com/IllusionMods/KKManager/releases/latest> for the latest version and update if necessary.");
                    }
                }

                foreach (var textAttachment in textAttachments)
                {
                    if (textAttachment.Size > _maxLogFileSize && FileIsValidLogFile(textAttachment))
                    {
                        listOfSins.Add(
                            $"Your log file {textAttachment.Filename} is extremely large and can't be parsed. Usually this means that something is very wrong with your game. Restart the game and reproduce your issue as quickly as possible to keep the log size small.");
                        canBeFixedWithHfpatch = true;
                    }
                    else
                    {
                        if (textAttachments.All(x =>
                                                !string.Equals(x.Filename, "output_log.txt", StringComparison.OrdinalIgnoreCase)))
                        {
                            if (string.Equals(textAttachment.Filename, "LogOutput.log",
                                              StringComparison.OrdinalIgnoreCase))
                            {
                                listOfSins.Add(
                                    "It looks like you uploaded the `BepInEx\\LogOutput.log` log file. Please send your `output_log.txt` file instead, it's much more useful for us. This file should exist in your game's root directory (next to the Koikatsu exe).");
                            }
                            else if (string.Equals(textAttachment.Filename, "error.log",
                                                   StringComparison.OrdinalIgnoreCase))
                            {
                                listOfSins.Add(
                                    "It looks like you uploaded the `error.log` log file. Please send your `output_log.txt` file instead, it's much more useful for us. This file should exist in your game's root directory (next to the Koikatsu exe).");
                            }
                        }
                    }
                }

                foreach (var logText in textsToProcess)
                {
                    try
                    {
                        CommonIssues.CheckCommonLogError(logText, listOfSins, ref canBeFixedWithHfpatch);

                        CommonIssues.CheckModsVersion(logText, listOfSins);
                    }
                    catch (Exception e)
                    {
                        Logger.Log($"Exception while checking for common errors in {msg.GetJumpUrl()}\n{e}");
                    }
                }