private IEnumerable <ResponseMessage> HandleNBitStack(IncomingMessage incomingMessage)
    {
        var genericAnswerKeywords = new List <string>()
        {
            "question", "i have a question", "i need help"
        };

        if (genericAnswerKeywords.Contains(incomingMessage.RawText.ToLower()))
        {
            yield return(incomingMessage.IndicateTypingOnChannel());

            _statsPlugin.IncrementState("Helper:BlindlyHelped");
            yield return(incomingMessage.ReplyToChannel(
                             $"Perhaps you should look at https://nbitstack.com/c/btcpayserver and see if there is already an answer for you there, @{incomingMessage.Username}"));
        }

        var discourseSearchKeywords = new List <string>()
        {
            "how can i", "i need help with"
        };

        if (discourseSearchKeywords.Any(s => incomingMessage.RawText.ToLower().StartsWith(s.ToLower())))
        {
            var discourseUrl = "https://nbitstack.com";
            var searchText   = incomingMessage.RawText;
            discourseSearchKeywords.ForEach(s => { searchText = searchText.Replace(s, ""); });
            yield return(incomingMessage.IndicateTypingOnChannel());

            var message = $"Maybe this can help: {discourseUrl}/search?q={Url.Encode(searchText.Trim())}";

            _statsPlugin.IncrementState("RedirectedToDiscourseSearch:Count");
            yield return(incomingMessage.ReplyToChannel(message));
        }
    }
예제 #2
0
        private IEnumerable <ResponseMessage> AddPostmortemLinkToIncidentHandler(IncomingMessage incomingMessage, IValidHandle matchedHandle)
        {
            yield return(incomingMessage.IndicateTypingOnChannel());

            if (!this.incidentManagementPlugin.IncidentCommandUserInputWellFormatted(incomingMessage.TargetedText))
            {
                yield return(incomingMessage.ReplyToChannel($"Please provide postmortem link. Help: {this.postmortemIncidentHelpText}"));
            }

            var postmortemLink = TextHelper.GetIncidentText($"{Configuration.Prefix} postmortem", incomingMessage.TargetedText);

            var incident = this.incidentManagementPlugin.UpdateIncidentWithPostmortem(postmortemLink, incomingMessage.Username, incomingMessage.Channel);

            if (incident == null)
            {
                yield return
                    (incomingMessage
                     .ReplyToChannel("Sorry, no open incident was found attached to this channel. Was the incident already closed?"));
            }
            else
            {
                yield return(incomingMessage.ReplyToChannel(
                                 $"Incident #{incident.FriendlyId} has been updated with a postmortem link. "
                                 + $"Once the postmortem and incident are complete, please run {this.closeIncidentHelpText} to close the incident."));
            }
        }
예제 #3
0
        private IEnumerable <ResponseMessage> JiraHandler(IncomingMessage message, IValidHandle matchedHandle)
        {
            string searchTerm = message.TargetedText.Substring(matchedHandle.HandleHelpText.Length).Trim();

            if (string.IsNullOrEmpty(searchTerm))
            {
                yield return(message.ReplyToChannel($"Please give me something to search, e.g. {matchedHandle} trains"));
            }
            else
            {
                yield return(message.IndicateTypingOnChannel());

                string url         = _configReader.GetConfigEntry <string>("jira:url");
                string prefix      = _configReader.GetConfigEntry <string>("jira:prefix");
                string base64Token = _configReader.GetConfigEntry <string>("jira:base64Token");

                if (string.IsNullOrEmpty(url) && string.IsNullOrEmpty(prefix) && string.IsNullOrEmpty(base64Token))
                {
                    _statsPlugin.IncrementState("Jira:Failed");
                    yield return(message.ReplyToChannel("Woops, looks like settings for Jira is not configured properly. Please ask the admin to fix this"));
                }
                else
                {
                    string messageToAnswer = GetDataFromJira(message.RawText, url, prefix, base64Token);
                    yield return(message.ReplyToChannel(messageToAnswer));
                }
            }
        }
예제 #4
0
        private IEnumerable <ResponseMessage> Handler(IncomingMessage message, IValidHandle matchedHandle)
        {
            if (!_authorizationPlugin.HasPermission("tflights", message.UserEmail))
            {
                yield return(message.ReplyToChannel("Nope! Ask for access first.")); yield break;
            }

            yield return(message.IndicateTypingOnChannel());

            var results = _flightFinderClient.Find().GetAwaiter().GetResult();

            var attachments = results
                              .OrderBy(x => x.Departure)
                              .Take(15)
                              .Select(x => new Attachment
            {
                Text  = GetText(x),
                Color = GetColor(x)
            })
                              .ToList();

            attachments.Add(new Attachment
            {
                Fallback = "Book  your flights at https://www.flypgs.com/en",
                Color    = "#000"
            }.AddAttachmentAction("Book flights", "https://www.flypgs.com/en"));


            yield return(message.ReplyToChannel("Cheapest upcoming weekend flights from London to Istanbul - Friday evening to Sunday evening:", attachments));
        }
예제 #5
0
        private IEnumerable <ResponseMessage> ApplicationDetailHandler(IncomingMessage incomingMessage, IValidHandle matchedHandle)
        {
            yield return(incomingMessage.IndicateTypingOnChannel());

            if (NewRelicPlugin.ApplicationDetailTargetedCommandMisformed(incomingMessage.TargetedText))
            {
                yield return(incomingMessage.ReplyToChannel($"NewRelic application detail command was not formatted correctly. Help: {this.applicationDetailHelpText}"));

                yield break;
            }

            var applicationName        = this.newRelicPlugin.GetApplicationNameFromTargetedText(incomingMessage.TargetedText);
            var applicationAttachments = this.newRelicPlugin.GetApplicationDetailsFiltered(applicationName);

            if (!applicationAttachments.Any())
            {
                yield return(incomingMessage.ReplyToChannel(
                                 $"No applications were found in NewRelic with the name `{applicationName}`"));
            }
            else
            {
                foreach (var responseMessage in ChuckAttachmentsAndReplyToChannel(
                             incomingMessage,
                             applicationAttachments,
                             $"There were {applicationAttachments.Count} application(s) found for that name. They are:"))
                {
                    yield return(responseMessage);
                }
            }
        }
예제 #6
0
        private IEnumerable <ResponseMessage> UnhealthyApplicationsDetailHandler(IncomingMessage incomingMessage, IValidHandle matchedHandle)
        {
            yield return(incomingMessage.IndicateTypingOnChannel());

            string title;
            var    applicationAttachments = new List <Attachment>();

            try
            {
                applicationAttachments = this.newRelicPlugin.GetUnhealthyApplicationsDetail();

                title = applicationAttachments.Any()
                                                        ? $"There are {applicationAttachments.Count} unhealthy applications in NewRelic. Those are:"
                                                        : $"There are no unhealthy applications in NewRelic.";
            }
            catch (Exception e)
            {
                Console.WriteLine(e);
                title = "An exception occurred when retrieving an list of the applications from NewRelic.";
            }

            foreach (var responseMessage in ChuckAttachmentsAndReplyToChannel(incomingMessage, applicationAttachments, title))
            {
                yield return(responseMessage);
            }
        }
        private IEnumerable <ResponseMessage> NewIncidentHandler(IncomingMessage incomingMessage, IValidHandle matchedHandle)
        {
            yield return(incomingMessage.IndicateTypingOnChannel());

            if (!this.incidentManagementPlugin.IncidentCommandUserInputWellFormatted(incomingMessage.TargetedText))
            {
                yield return(incomingMessage.ReplyToChannel($"Please provide incident title. Help: {this.newIncidentHelpText}"));

                yield break;
            }

            var incidentText = TextHelper.GetIncidentText($"{Configuration.Prefix} new", incomingMessage.TargetedText);

            var incident = this.incidentManagementPlugin.DeclareNewIncident(incidentText, incomingMessage.Username);

            if (incident == null)
            {
                yield return
                    (incomingMessage
                     .ReplyToChannel("Sorry, no warrooms are available so this incident cannot be created."));
            }
            else
            {
                yield return(incomingMessage.ReplyToChannel($"Incident #{ incident.FriendlyId } has been declared and bound to #{ incident.ChannelName } channel."));
            }
        }
예제 #8
0
        private IEnumerable <ResponseMessage> ListRecentIncidentHandler(IncomingMessage incomingMessage, IValidHandle matchedHandle)
        {
            yield return(incomingMessage.IndicateTypingOnChannel());

            var recentIncidentAttachments = this.incidentManagementPlugin.GetRecentIncidents();

            yield return(incomingMessage.ReplyToChannel($"There were { recentIncidentAttachments.Count } recent incident(s):", recentIncidentAttachments));
        }
예제 #9
0
        private IEnumerable <ResponseMessage> GenericCommandHandler(IncomingMessage incomingMessage, string command)
        {
            Exception           exception          = null;
            HttpResponseMessage apiResponseMessage = null;

            yield return(incomingMessage.IndicateTypingOnChannel());

            if (this.lboPlugin.CommandMisformed(incomingMessage.TargetedText))
            {
                yield return(incomingMessage.ReplyToChannel($"Command was not formatted correctly. Help: '{GetHelpText(command)}'"));

                yield break;
            }

            var lboRequest = new LoadBalancerRequest(incomingMessage.TargetedText);

            var appliance = this.lboPlugin.GetAppliance(lboRequest.ApplianceName);

            if (appliance == null)
            {
                yield return(incomingMessage.ReplyToChannel($"No appliance could be found with the name:{lboRequest.ApplianceName}. Help: '{GetHelpText(command)}'"));

                yield break;
            }

            try
            {
                apiResponseMessage = this.lboPlugin.MakeApiRequest(appliance, lboRequest);
            }
            catch (Exception e)
            {
                this.log.Error(e);
                exception = e;
            }

            if (this.lboPlugin.ApiRequestThrewException(apiResponseMessage, exception))
            {
                yield return(incomingMessage.ReplyToChannel($"An exception occured when communicating to applicance '{appliance.Name} ({appliance.ApiUrl})."));

                yield break;
            }

            var lbResponse = this.lboPlugin.ParseApiResponse(apiResponseMessage);

            if (lbResponse.Contains("Error"))
            {
                yield return(incomingMessage.ReplyToChannel($"An error occured when issuing command against VIP {lboRequest.Vip} for RIP {lboRequest.Rip}. Check the VIP and RIP names are valided for applicance `{appliance.Name}` ({appliance.ApiUrl})."));

                yield break;
            }

            yield return(incomingMessage.ReplyToChannel($"{lbResponse}"));
        }
        private IEnumerable <ResponseMessage> JokeHandler(IncomingMessage message, IValidHandle matchedHandle)
        {
            yield return(message.IndicateTypingOnChannel());

            var jokeResponse = new Random().Next(0, 100) < 80 ? GetChuckNorrisJoke() : GetMommaJoke();

            _statsPlugin.IncrementState("Jokes:Told");
            var jokeString = $"{{ {jokeResponse.SelectToken("$..joke").Parent} }}";
            var joke       = JsonConvert.DeserializeObject <JokeContainer>(jokeString);

            yield return(message.ReplyToChannel(joke.Joke));
        }
예제 #11
0
        private IEnumerable <ResponseMessage> FlickrHandler(IncomingMessage message, IValidHandle matchedHandle)
        {
            string searchTerm = message.TargetedText.Substring(matchedHandle.HandleHelpText.Length).Trim();

            if (string.IsNullOrEmpty(searchTerm))
            {
                yield return(message.ReplyToChannel($"Please give me something to search, e.g. {matchedHandle} trains"));
            }
            else
            {
                yield return(message.IndicateTypingOnChannel());

                string apiKey = _configReader.GetConfigEntry <string>("flickr:apiKey");

                if (string.IsNullOrEmpty(apiKey))
                {
                    _statsPlugin.IncrementState("Flickr:Failed");
                    yield return(message.ReplyToChannel("Woops, looks like a Flickr API Key has not been entered. Please ask the admin to fix this"));
                }
                else
                {
                    var flickr = new Flickr(apiKey);

                    var options = new PhotoSearchOptions {
                        Tags = searchTerm, PerPage = 50, Page = 1
                    };
                    PhotoCollection photos = flickr.PhotosSearch(options);

                    if (photos.Any())
                    {
                        _statsPlugin.IncrementState("Flickr:Sent");

                        int   i          = new Random().Next(0, photos.Count);
                        Photo photo      = photos[i];
                        var   attachment = new Attachment
                        {
                            AuthorName = photo.OwnerName,
                            Fallback   = photo.Description,
                            ImageUrl   = photo.LargeUrl,
                            ThumbUrl   = photo.ThumbnailUrl
                        };

                        yield return(message.ReplyToChannel($"Here is your picture about '{searchTerm}'", attachment));
                    }
                    else
                    {
                        _statsPlugin.IncrementState("Flickr:Failed");
                        yield return(message.ReplyToChannel($"Sorry @{message.Username}, I couldn't find anything about {searchTerm}"));
                    }
                }
            }
        }
예제 #12
0
        private IEnumerable <ResponseMessage> PurgeZone(IncomingMessage incomingMessage, IValidHandle matchedHandle)
        {
            yield return(incomingMessage.IndicateTypingOnChannel());

            if (!CommandWellFormatted(incomingMessage.TargetedText, requiredCommandLength: 4))
            {
                yield return(incomingMessage.ReplyToChannel($"Command was not formatted correctly. Help: {GetPurgeZoneHelpText()}"));

                yield break;
            }

            var zoneName = GetCleanZoneName(GetPositionalElementFromTargetText(incomingMessage.TargetedText, position: 3));
            var result   = this.cloudflarePlugin.PurgeZone(zoneName);

            yield return(incomingMessage.ReplyToChannel(result.Message));
        }
예제 #13
0
        private IEnumerable <ResponseMessage> ListActiveIncidentHandler(IncomingMessage incomingMessage, IValidHandle matchedHandle)
        {
            yield return(incomingMessage.IndicateTypingOnChannel());

            var openIncidentAttachments = this.incidentManagementPlugin.GetOpenIncidents();

            if (openIncidentAttachments.Any())
            {
                yield return(incomingMessage.ReplyToChannel(
                                 $"There are {openIncidentAttachments.Count} incident(s) currently open:",
                                 openIncidentAttachments));
            }
            else
            {
                yield return(incomingMessage.ReplyToChannel(
                                 $"Great news! There's no active incidents at the moment. If you need to declare a new incident, run { this.newIncidentHelpText }."));
            }
        }
예제 #14
0
        private IEnumerable <ResponseMessage> CloseIncidentHandler(IncomingMessage incomingMessage, IValidHandle matchedHandle)
        {
            yield return(incomingMessage.IndicateTypingOnChannel());

            var incident = this.incidentManagementPlugin.CloseIncident(incomingMessage.Username, incomingMessage.Channel);

            if (incident == null)
            {
                yield return(incomingMessage.ReplyToChannel(
                                 $"Sorry, no incident was found attached to this channel that could be closed. Was the incident resolved yet, already closed or missing the postmortem? "
                                 + $"If it the incident hasn't been marked as resolved, run {this.resolveIncidentHelpText} first. If the incident is resolved but missing the postmortem, run {this.postmortemIncidentHelpText} along with the postmortem link first."));
            }
            else
            {
                yield return(incomingMessage.ReplyToChannel($"Incident #{ incident.FriendlyId } succesfully closed. Please prepare the postmortem on Jive using incident/postmortem id { incident.FriendlyId }.\n"
                                                            + "Channel will now be marked as available."));
            }
        }
예제 #15
0
        private IEnumerable <ResponseMessage> JokeHandler(IncomingMessage message, string matchedHandle)
        {
            yield return(message.IndicateTypingOnChannel());

            IRestResponse jokeResponse = new Random().Next(0, 100) < 80 ? GetTambalJoke() : GetMommaJoke();

            if (jokeResponse.StatusCode == HttpStatusCode.OK)
            {
                _statsPlugin.IncrementState("Jokes:Told");
                var joke = JsonConvert.DeserializeObject <JokeContainer>(jokeResponse.Content);

                yield return(message.ReplyToChannel(joke.Joke));
            }
            else
            {
                _statsPlugin.IncrementState("Jokes:Failed");
                yield return(message.ReplyToChannel($"Dam, I can't think of one. [{jokeResponse.StatusCode}]"));
            }
        }
예제 #16
0
        private IEnumerable <ResponseMessage> ResolveIncidentHandler(IncomingMessage incomingMessage, IValidHandle matchedHandle)
        {
            yield return(incomingMessage.IndicateTypingOnChannel());

            var incident = this.incidentManagementPlugin.ResolveIncident(incomingMessage.Username, incomingMessage.Channel);

            if (incident == null)
            {
                yield return(incomingMessage.ReplyToChannel(
                                 "Sorry, no unresolved incident was found attached to this channel. Was the incident already resolved or closed?"));
            }
            else
            {
                yield return(incomingMessage.ReplyToChannel(
                                 $"Incident #{incident.FriendlyId} succesfully resolved. Please run {this.postmortemIncidentHelpText} followed "
                                 + $"by the postmortem link to add the postmortem to this incident, if not already done. "
                                 + $"To create a new postmortem using the template, please go here { this.incidentManagementPlugin.PostmortemTemplateLink }."));
            }
        }
예제 #17
0
    private IEnumerable <ResponseMessage> HandleJokes(IncomingMessage incomingMessage)
    {
        var bcashKeywords = new List <string>()
        {
            "bcash", "bitcoin cash", "tell me a joke"
        };

        if (bcashKeywords.Contains(incomingMessage.RawText.ToLower()))
        {
            yield return(incomingMessage.IndicateTypingOnChannel());

            _statsPlugin.IncrementState("Jokes:Told");

            yield return(incomingMessage.ReplyToChannel(jokes[_r.Next(0, jokes.Count)].Content));
        }

        if (incomingMessage.RawText.ToLower().StartsWith("addjoke:"))
        {
            var joke = incomingMessage.RawText.Substring("addjoke:".Length);
            jokes.Add(new Joke()
            {
                Content = joke
            });
            _jsonStoragePlugin.SaveFile("jokes", jokes.ToArray());
            yield return(incomingMessage.ReplyDirectlyToUser("joke added!"));
        }

        if (incomingMessage.RawText.ToLower().StartsWith("removejoke:"))
        {
            var joke = incomingMessage.RawText.Substring("removejoke:".Length);
            if (jokes.Any(joke1 => joke == joke1.Content))
            {
                var jokeIndex = jokes.FindIndex(joke1 => joke == joke1.Content);

                jokes.RemoveAt(jokeIndex);
                _jsonStoragePlugin.SaveFile("jokes", jokes.ToArray());
                yield return(incomingMessage.ReplyDirectlyToUser("joke removed!"));
            }
        }
    }
예제 #18
0
        private IEnumerable <ResponseMessage> ApplicationMetricsHandler(IncomingMessage incomingMessage, IValidHandle matchedHandle)
        {
            yield return(incomingMessage.IndicateTypingOnChannel());

            yield return(incomingMessage.ReplyToChannel($"Sorry this command isn't supported yet."));

            yield break;

            //if (NewRelicPlugin.ApplicationDetailTargetedCommandMisformed(incomingMessage.TargetedText))
            //{
            //	yield return incomingMessage.ReplyToChannel($"NewRelic application metrics command was not formatted correctly. Help: {this.applicationMetricsHelpText}");
            //	yield break;
            //}

            //var application = this.newRelicPlugin.GetApplicationFromTargetedText(incomingMessage.TargetedText);
            //if (application == null)
            //{
            //	yield return incomingMessage.ReplyToChannel($"No NewRelic application could be found with the ID specified. Help: {this.applicationMetricsHelpText}");
            //	yield break;
            //}

            //yield return incomingMessage.ReplyToChannel(this.newRelicPlugin.GetSummaryMetricsText(application.Id));
        }
예제 #19
0
        private IEnumerable <ResponseMessage> DnsLookupHandler(IncomingMessage incomingMessage, IValidHandle matchedHandle)
        {
            yield return(incomingMessage.IndicateTypingOnChannel());

            if (!DnsLookupCommandWellFormatted(incomingMessage.TargetedText))
            {
                yield return(incomingMessage.ReplyToChannel($"Command was not formatted correctly. Help: {GetHelpText(Lookup)}"));

                yield break;
            }

            var hostToLookup = DnsPlugin.GetHostFromMessage(incomingMessage.TargetedText);
            var ipAddresses  = DnsPlugin.LookUpIpFromCommandText(hostToLookup);

            if (ipAddresses == null)
            {
                yield return(incomingMessage.ReplyToChannel($"Error looking up requested host '{hostToLookup}'. No result were returned."));

                yield break;
            }

            yield return(incomingMessage.ReplyToChannel($"dns lookup for '{hostToLookup}' returned: {DnsPlugin.GetIpAddressesAsText(ipAddresses)}"));
        }
예제 #20
0
 private IEnumerable <ResponseMessage> Handler(IncomingMessage message, IValidHandle matchedHandle)
 {
     yield return(message.IndicateTypingOnChannel());
 }
예제 #21
0
    private IEnumerable <ResponseMessage> DiscourseSearch(IncomingMessage incomingMessage, IValidHandle validHandle)
    {
        var genericAnswerKeywords = new List <string>()
        {
            "question", "i have a question", "i need help"
        };

        if (genericAnswerKeywords.Contains(incomingMessage.RawText.ToLower()))
        {
            yield return(incomingMessage.IndicateTypingOnChannel());

            _statsPlugin.IncrementState("Helper:BlindlyHelped");
            yield return(incomingMessage.ReplyToChannel(
                             $"Perhaps you should look at https://nbitstack.com/c/btcpayserver and see if there is already an answer for you there, @{incomingMessage.Username}"));
        }

        var discourseSearchKeywords = new List <string>()
        {
            "how can i", "i need help with"
        };

        if (discourseSearchKeywords.Any(s => incomingMessage.RawText.ToLower().StartsWith(s.ToLower())))
        {
            var discourseUrl = "https://nbitstack.com";
            var searchText   = incomingMessage.RawText;
            discourseSearchKeywords.ForEach(s => { searchText = searchText.Replace(s, ""); });
            yield return(incomingMessage.IndicateTypingOnChannel());

            var message = $"Maybe this can help: {discourseUrl}/search?q={Url.Encode(searchText.Trim())}";

            _statsPlugin.IncrementState("RedirectedToDiscourseSearch:Count");
            yield return(incomingMessage.ReplyToChannel(message));
        }


        var bcashKeywords = new List <string>()
        {
            "bcash", "bitcoin cash", "tell me a joke"
        };

        if (bcashKeywords.Contains(incomingMessage.RawText.ToLower()))
        {
            yield return(incomingMessage.IndicateTypingOnChannel());

            _statsPlugin.IncrementState("Jokes:Told");

            yield return(incomingMessage.ReplyToChannel(jokes[_r.Next(0, jokes.Count)].Content));
        }

        if (incomingMessage.RawText.ToLower().StartsWith("addjoke:"))
        {
            var joke = incomingMessage.RawText.Substring("addjoke:".Length);
            jokes.Add(new Joke()
            {
                Content = joke
            });
            _jsonStoragePlugin.SaveFile("jokes", jokes.ToArray());
            yield return(incomingMessage.ReplyDirectlyToUser("joke added!"));
        }
        if (incomingMessage.RawText.ToLower().StartsWith("removejoke:"))
        {
            var joke = incomingMessage.RawText.Substring("removejoke:".Length);
            if (jokes.Any(joke1 => joke == joke1.Content))
            {
                var jokeIndex = jokes.FindIndex(joke1 => joke == joke1.Content);

                jokes.RemoveAt(jokeIndex);
                _jsonStoragePlugin.SaveFile("jokes", jokes.ToArray());
                yield return(incomingMessage.ReplyDirectlyToUser("joke removed!"));
            }
        }
    }