Exemplo n.º 1
0
        public async Task StartAsync(IDialogContext context)
        {
            if (context == null)
            {
                throw new ArgumentNullException(nameof(context));
            }

            if (await ConversationHelpers.RelayMessageToAgentIfThereIsAnOpenResearchProject(context))
            {
                // end the context
                context.Done<object>(null);
            }
            else
            {
                await context.PostWithRetryAsync("Hi, this is EIBot. I can help with many todos. For instance, booking an appointment. " +
                                        "Lets start with what do you need?");
                context.Wait(MessageReceivedAsync);
            }
        }
        public async Task StartAsync(IDialogContext context)
        {
            if (context == null)
            {
                throw new ArgumentNullException(nameof(context));
            }

            if (await ConversationHelpers.RelayMessageToAgentIfThereIsAnOpenResearchProject(context))
            {
                // end the context
                context.Done <object>(null);
            }
            else
            {
                await context.PostWithRetryAsync("Sorry, I am not following you.");

                context.Call(new UserHelpDialog(), EndHelpDialog);
            }
        }
Exemplo n.º 3
0
        public async Task StartAsync(IDialogContext context)
        {
            if (context == null)
            {
                throw new ArgumentNullException(nameof(context));
            }

            _isSms = context.Activity.ChannelId == ActivityHelper.SmsChannelId;
            _minHoursToCompleteResearch = Convert.ToInt32(ConfigurationManager.AppSettings["ResearchProjectViaTeamsMinHours"]);

            if (await ConversationHelpers.RelayMessageToAgentIfThereIsAnOpenResearchProject(context))
            {
                context.Done <object>(null);
            }
            else
            {
                // check we know alias associated with this phone number
                UserTable userTable = new UserTable();
                var       botUsers  = await userTable.GetUserByChannelSpecificId(context.Activity.ChannelId, context.Activity.From.Id);

                if (botUsers.Length == 0)
                {
                    context.Call(new PromptText(
                                     "Hi, I’m here to help you get started. \n\n" +
                                     "When we're done, I'll email you a research report with the info you want.\n\n" +
                                     "What's your Microsoft alias?",
                                     $"Please try again. Alias needs to be at least {MinAliasCharLength} characters long.",
                                     "Sorry, I didn't get that. too many attempts. Please try again later.", 2, MinAliasCharLength), OnAliasReceivedAsync);
                }
                else
                {
                    // we have the alias
                    var user = botUsers.First();
                    context.UserData.SetValue(UserProfileHelper.UserProfileKey, user);
                    context.Call(new PromptText(
                                     $"Hey {user.Alias}, tell me what you want to know and I'll kick off a research project.\n\n\n\n" +
                                     "Or say 'example' to see some examples.",
                                     $"Please try again. Response needs to be at least {MinDescriptionCharLength} characters long.",
                                     "Sorry, I didn't get that. too many attempts. Please try again later.", 2, MinDescriptionCharLength),
                                 OnDescriptionOrExampleRequestReceivedAsync);
                }
            }
        }
Exemplo n.º 4
0
        public async Task StartAsync(IDialogContext context)
        {
            if (context == null)
            {
                throw new ArgumentNullException(nameof(context));
            }

            _isSms = context.Activity.ChannelId == ActivityHelper.SmsChannelId;

            if (await ConversationHelpers.RelayMessageToAgentIfThereIsAnOpenResearchProject(context))
            {
                // end the context
                context.Done <object>(null);
            }
            else
            {
                var smsPrompt = "Hello, I am Expert Intelligence Bot. I'll collect some information to get started, " +
                                "then a human freelancer will review your request and follow up. \n\n\n\n" +
                                "Would you like web research?\n\n\n\n" +
                                "You can say: 'yes' or 'no'.";
                var teamsPrompt = "Hello! I am Expert Intelligence Bot.\n\nI am supported by experts who can work for you.\n\n " +
                                  "I'll collect some information to get started, then a human freelancer will review your request and follow up. " +
                                  $"You can also send me a text request via SMS text message on your phone at {ConfigurationManager.AppSettings["BotPhoneNumber"]} \n\n\n\n" +
                                  "Would you like web research?\n\n\n\n" +
                                  "You can say: 'yes' or 'no'.";
                var choiceDialog = new PromptYesNo(
                    _isSms ? smsPrompt : teamsPrompt,
                    "Sorry I didn't get that. Please say 'yes' if you want to continue with requesting web research",
                    "Sorry I still don't get it if you want to continue with web research. Please reply to start again.", 2);
                context.Call(choiceDialog, OnResearchConfirmationReceivedAsync);

                // introduce the bot
                //IMessageActivity message = _isSms ? BuildIntroMessageForSms(context) : BuildIntroMessageForTeams(context);
                //await context.PostWithRetryAsync(message);
                //context.Wait(OnProjectTypeReceivedAsync);
            }
        }
Exemplo n.º 5
0
        private async Task OnDeadlineSelected(IDialogContext context, IAwaitable<IEnumerable<DateTime>> result)
        {
            try
            {
                // "result" contains the date (or array of dates) returned from the prompt
                IEnumerable<DateTime> momentOrRange = await result;
                var deadline = momentOrRange.First(); // DeadlinePrompt.MomentOrRangeToString(momentOrRange);

                // Store date
                context.ConversationData.SetValue("deadline", deadline);

                var description = context.ConversationData.GetValue<string>("description");

                string mobilePhone = string.Empty;
                string alias = string.Empty;

                if (!context.UserData.TryGetValue(UserProfileHelper.UserProfileKey, out UserProfile userProfile))
                {
                    mobilePhone = userProfile.MobilePhone;
                    alias = userProfile.Alias;
                }

                var vsoTicketNumber = await VsoHelper.CreateTaskInVso(VsoHelper.VirtualAssistanceTaskType,
                    context.Activity.From.Name,
                    description,
                    ConfigurationManager.AppSettings["AgentToAssignVsoTasksTo"],
                    deadline,
                    "",
                    null,
                    context.Activity.ChannelId);

                MicrosoftAppCredentials.TrustServiceUrl(ActivityHelper.TeamsServiceEndpoint);

                AdaptiveCard card = new AdaptiveCard();
                card.Body.Add(new AdaptiveTextBlock()
                {
                    Text = $"New Virtual Assistance request from {context.Activity.From.Name}. VSO:{vsoTicketNumber}",
                    Size = AdaptiveTextSize.Large,
                    Wrap = true,
                    Separator = true
                });
                var summary = new AdaptiveFactSet
                {
                    Facts = new List<AdaptiveFact>
                    {
                        new AdaptiveFact("Who", context.Activity.From.Name),
                        new AdaptiveFact("What", description),
                        new AdaptiveFact("When", deadline.ToString()),
                        new AdaptiveFact("Vso", vsoTicketNumber.ToString()),
                    }
                };
                card.Body.Add(summary);

                using (var connectorClient = await BotConnectorUtility.BuildConnectorClientAsync(ActivityHelper.TeamsServiceEndpoint))
                {
                    var channelInfo = GetHardcodedChannelId();
                    context.ConversationData.SetValue("VsoId", vsoTicketNumber);
                    context.ConversationData.SetValue("EndUserConversationId", context.Activity.Conversation.Id);

                    var conversationResourceResponse = await ConversationHelpers.CreateAgentConversation(channelInfo,
                        card,
                        $"New research request from {context.Activity.Recipient.Name}",
                        connectorClient,
                        vsoTicketNumber,
                        context.Activity as IMessageActivity);

                    EndUserAndAgentConversationMappingState state =
                        new EndUserAndAgentConversationMappingState(vsoTicketNumber.ToString(),
                            context.Activity.From.Name,
                            context.Activity.From.Id,
                            context.Activity.Conversation.Id,
                            conversationResourceResponse.Id);

                    await state.SaveInVso(vsoTicketNumber.ToString());
                }

                await context.PostWithRetryAsync("Thank you! I have posted following to internal agents. " +
                                                 "I will be in touch with you shortly. " +
                                                 $"Please use reference #{vsoTicketNumber} for this request in future. " +
                                                 $"What: {description}. When: {deadline}.");

                context.Done<object>(null);
            }
            catch (TooManyAttemptsException)
            {
                await context.PostWithRetryAsync("TooManyAttemptsException. Restarting now...");
            }
            catch (System.Exception e)
            {
                WebApiConfig.TelemetryClient.TrackException(e, new Dictionary<string, string>
                {
                    {"dialog", "InternetResearchDialog" },
                    {"function", "OnDeadlineSelected" }
                });
                throw;
            }
        }
        private async Task OnConfirmResearchDialog(IDialogContext context, IAwaitable <bool> result)
        {
            if (result == null)
            {
                throw new InvalidOperationException((nameof(result)) + Strings.NullException);
            }

            var sendIt = await result;

            if (sendIt)
            {
                var additionalInfoFromUser = context.ConversationData.GetValue <string>(AdditionalInfoKey);
                var description            = context.ConversationData.GetValue <string>(DescriptionKey);
                var deadline = DateTime.Parse(context.ConversationData.GetValue <string>(DeadlineKey));

                var vsoTicketNumber = await VsoHelper.CreateTaskInVso(VsoHelper.ResearchTaskType,
                                                                      context.Activity.From.Name,
                                                                      description + Environment.NewLine + additionalInfoFromUser,
                                                                      ConfigurationManager.AppSettings["AgentToAssignVsoTasksTo"],
                                                                      deadline,
                                                                      "",
                                                                      userProfile,
                                                                      context.Activity.ChannelId);

                context.ConversationData.SetValue(VsoIdKey, vsoTicketNumber);
                context.ConversationData.SetValue(EndUserConversationIdKey, context.Activity.Conversation.Id);

                try
                {
                    var    conversationTitle   = $"Web research request from {userProfile} via {context.Activity.ChannelId} due {deadline}";
                    string agentConversationId = await ConversationHelpers.CreateAgentConversationEx(context,
                                                                                                     conversationTitle,
                                                                                                     CreateCardForAgent(context,
                                                                                                                        additionalInfoFromUser,
                                                                                                                        description,
                                                                                                                        deadline,
                                                                                                                        vsoTicketNumber),
                                                                                                     userProfile);

                    EndUserAndAgentConversationMappingState state =
                        new EndUserAndAgentConversationMappingState(vsoTicketNumber.ToString(),
                                                                    context.Activity.From.Name,
                                                                    context.Activity.From.Id,
                                                                    context.Activity.Conversation.Id,
                                                                    agentConversationId);

                    await state.SaveInVso(vsoTicketNumber.ToString());

                    await context.PostWithRetryAsync("Sure. I have sent your request to a freelancer. " +
                                                     $"Please use #{vsoTicketNumber} for referencing this request in future. " +
                                                     "At this point, any message you send will be sent directly to the freelancer. They may take time to respond, " +
                                                     "or may have clarifying questions which I will relay back to you.");

                    context.Done <object>(true);
                }
                catch (System.Exception e)
                {
                    await context.PostWithRetryAsync("Sorry, I ran into an issue while connecting with agent. Please try again later.");

                    WebApiConfig.TelemetryClient.TrackException(e, new Dictionary <string, string> {
                        { "function", "OnConfirmResearchDialog.CreateAgentConversation" }
                    });
                    context.Done <object>(false);
                }
            }
            else
            {
                await context.PostWithRetryAsync("Okay, I have cancelled this request.");

                context.Done <object>(false);
            }
        }
Exemplo n.º 7
0
        private async Task CreateProject(IDialogContext context)
        {
            try
            {
                var description = context.ConversationData.GetValue <string>(DescriptionKey);
                var userProfile = context.UserData.GetValue <UserProfile>(UserProfileHelper.UserProfileKey);
                var deadline    = DateTime.UtcNow.AddHours(_minHoursToCompleteResearch);

                var vsoTicketNumber = await VsoHelper.CreateTaskInVso(VsoHelper.ResearchTaskType,
                                                                      context.Activity.From.Name,
                                                                      description,
                                                                      ConfigurationManager.AppSettings["AgentToAssignVsoTasksTo"],
                                                                      deadline,
                                                                      "",
                                                                      userProfile,
                                                                      context.Activity.ChannelId);

                context.ConversationData.SetValue(VsoIdKey, vsoTicketNumber);
                context.ConversationData.SetValue(EndUserConversationIdKey, context.Activity.Conversation.Id);

                var    conversationTitle   = $"Web research request from {userProfile} via {context.Activity.ChannelId} due {deadline}";
                string agentConversationId = await ConversationHelpers.CreateAgentConversationEx(context,
                                                                                                 conversationTitle,
                                                                                                 CreateCardForAgent(context,
                                                                                                                    description,
                                                                                                                    deadline,
                                                                                                                    vsoTicketNumber,
                                                                                                                    userProfile),
                                                                                                 userProfile);

                EndUserAndAgentConversationMappingState state =
                    new EndUserAndAgentConversationMappingState(vsoTicketNumber.ToString(),
                                                                context.Activity.From.Name,
                                                                context.Activity.From.Id,
                                                                context.Activity.Conversation.Id,
                                                                agentConversationId);

                await state.SaveInVso(vsoTicketNumber.ToString());

                WebApiConfig.TelemetryClient.TrackEvent("CreateProject", new Dictionary <string, string>()
                {
                    { "from", context.Activity.From.Name },
                    { UserProfileHelper.UserProfileKey, userProfile.ToString() },
                    { DescriptionKey, description },
                    { "deadline", deadline.ToString() },
                    { VsoIdKey, vsoTicketNumber.ToString() },
                });

                await context.PostWithRetryAsync($"OK, your research project is #{vsoTicketNumber}. " +
                                                 $"We'll get to work on this shortly and send you a confirmation email.\n\n\n\n" +
                                                 $"In the meantime, feel free to tell me more, like: " +
                                                 $"what do you want to do with this info?");

                context.Done <object>(true);
            }
            catch (System.Exception e)
            {
                try
                {
                    if (context.ConversationData.TryGetValue(VsoIdKey, out string vsoTicketNumber))
                    {
                        // close this ticket
                        await VsoHelper.CloseProject(Convert.ToInt32(vsoTicketNumber));
                    }
                }
                catch (System.Exception exception)
                {
                    WebApiConfig.TelemetryClient.TrackException(exception, new Dictionary <string, string>
                    {
                        { "debugNote", "Error closing project during exception received in CreateProject" },
                        { "CreateProjectException", e.ToString() },
                    });
                }
                await context.PostWithRetryAsync("Sorry, I ran into an issue while connecting with agent. Please try again later.");

                WebApiConfig.TelemetryClient.TrackException(e, new Dictionary <string, string> {
                    { "function", "OnConfirmResearchDialog.CreateAgentConversation" }
                });
                context.Done <object>(false);
            }
        }