public void ResponseWithNoDetailReturnsCanSendFalse()
        {
            var request = new ProgressiveResponse();
            var result  = request.CanSend();

            Assert.False(result);
        }
        public async Task ResponseWithNoDetailReturnsNull()
        {
            var request = new ProgressiveResponse();
            var result  = await request.Send(null);

            Assert.Null(result);
        }
        public async Task ResponseWithNullDirectiveReturnsNull()
        {
            var request = new ProgressiveResponse {
                Header = new ProgressiveResponseHeader("test"), Client = new HttpClient()
            };
            var result = await request.Send(null);

            Assert.Null(result);
        }
        public async Task ResponseWithNoClientReturnsNull()
        {
            var request = new ProgressiveResponse {
                Header = new ProgressiveResponseHeader("test")
            };
            var result = await request.Send(new VoicePlayerSpeakDirective("test"));

            Assert.Null(result);
        }
示例#5
0
        private Task <HttpResponseMessage> SendProgressiveResponse(SkillRequest request)
        {
            if (ProgressiveResponse.IsSupported(request))
            {
                var response  = new ProgressiveResponse(request);
                var directive = new VoicePlayerSpeakDirective("Getting car park information");
                return(response.Send(directive));
            }

            return(Task.FromResult((HttpResponseMessage)null));
        }
示例#6
0
        public async Task SendProgressResponseAsync(IBotResponse response)
        {
            var progressiveResponse = new ProgressiveResponse(_request);
            var speechResponse      = await progressiveResponse.SendSpeech(response.Speak);

            if (speechResponse.IsSuccessStatusCode)
            {
                Log("Progress Response successful");
            }
            else
            {
                Log("Progress Response unsuccessful");
            }
        }
        public static async Task <IActionResult> Run(
            [HttpTrigger(AuthorizationLevel.Function, "get", "post", Route = null)] HttpRequest req,
            ILogger log)
        {
            string json = await req.ReadAsStringAsync();

            var skillRequest = JsonConvert.DeserializeObject <SkillRequest>(json);

            var requestType = skillRequest.GetRequestType();

            SkillResponse response = null;

            if (requestType == typeof(LaunchRequest))
            {
                response = ResponseBuilder.Tell("Hello .NET Iasi");
            }
            else if (requestType == typeof(IntentRequest))
            {
                var intentRequest = skillRequest.Request as IntentRequest;

                if (intentRequest.Intent.Name == "BestProgrammingLanguage")
                {
                    response = ResponseBuilder.Tell("The best programming language is C#");
                }
                else if (intentRequest.Intent.Name == "LightSwitch")
                {
                    var state = intentRequest.Intent.Slots["state"].Value;
                    if (state == "off")
                    {
                        var progressiveResponse = new ProgressiveResponse(skillRequest);
                        await progressiveResponse.SendSpeech("The lights will be turned off");

                        await LightSwitcher.TurnOff();

                        response = ResponseBuilder.Tell("The lights are now off");
                    }
                }
            }

            return(new OkObjectResult(response));
        }
 public static async Task AlexaSendProgressiveResponse(this ITurnContext context, string content)
 {
     var progressiveResponse = new ProgressiveResponse(context.GetAlexaRequestBody());
     await progressiveResponse.SendSpeech(content);
 }
示例#9
0
        public async Task HandleRequest()
        {
            await RequestProcessHelper.ProcessRequest("CustomIntentHandler.HandleRequest()", "Custom Intent", async() =>
            {
                IntentRequest request = Core.Request.GetRequest().Request as IntentRequest;

                // get slot resolution
                string slotValue;
                ProgressiveResponse progressiveResponse = new ProgressiveResponse(Core.Request.GetRequest());
                Slot slot = request.Intent.Slots[AlexaRequestType.CustomSlot];

                string rawValue = slot.Value;
                Core.Logger.Write("CustomIntentHandler.HandleRequest()", $"Sub intent raw slot value: {rawValue}");

                try
                {
                    ResolutionAuthority[] resolution     = slot.Resolution.Authorities;
                    ResolutionValueContainer[] container = resolution[0].Values;
                    slotValue = container[0].Value.Name;

                    Core.Logger.Write("CustomIntentHandler.HandleRequest()", $"Sub intent processed slot value: {slotValue}");
                }
                catch
                {
                    slotValue = rawValue;
                }

                // if user says list
                if (slotValue.Equals("List"))
                {
                    Core.State.UserState.Stage = Stage.Menu;
                    Core.Response.SetSpeech(false, false, SpeechTemplate.ListItems);
                }

                // if user says random or shuffle
                else if (slotValue.Equals("Random") || (slotValue.Equals("Shuffle")))
                {
                    Random mediaRandom          = new Random();
                    List <MediaItem> mediaItems = MediaItems.GetMediaItems();
                    MediaItem currentMediaItem  = mediaItems[mediaRandom.Next(mediaItems.Count)];

                    // update database context
                    Core.State.UserState.Shuffle    = true;
                    Core.State.UserState.OffsetInMS = 0;
                    Core.State.UserState.Index      = currentMediaItem.Id;
                    Core.State.UserState.Token      = currentMediaItem.FileName;

                    await progressiveResponse.SendSpeech($"Playing a random recording. {currentMediaItem.Title}. To call me back, say cancel. ");

                    if (Core.Device.HasScreen)
                    {
                        Core.State.UserState.Stage = Stage.Video;
                        Core.Response.AddVideoApp(currentMediaItem.VideoSource, currentMediaItem.Title, currentMediaItem.FileName);
                    }
                    else
                    {
                        Core.State.UserState.Stage = Stage.Audio;
                        Core.Response.AddAudioPlayer(PlayBehavior.ReplaceAll, currentMediaItem.AudioSource, currentMediaItem.FileName);
                    }
                }
                else
                {
                    if (slotValue != null && slotValue != string.Empty)
                    {
                        List <MediaItem> mediaItems    = MediaItems.GetMediaItems();
                        List <MediaItem> selectedMedia = ItemSelectHelper.SelectItems(mediaItems, "Title", slotValue);

                        // query possible entries
                        if (selectedMedia.Any())
                        {
                            if (selectedMedia.Count > 1)
                            {
                                StringBuilder sb = new StringBuilder();
                                sb.Append($"I found {selectedMedia.Count} recordings matching {slotValue}. ");
                                Core.Logger.Write("CustomIntentHandler.HandleRequest()", $"{selectedMedia.Count} matching items found for {slotValue}");

                                foreach (MediaItem mediaItem in selectedMedia)
                                {
                                    sb.Append(mediaItem.Title + ". ");
                                }

                                sb.Append("Please choose one of the following. ");
                                Core.Response.SetSpeech(false, false, sb.ToString());
                            }
                            else
                            {
                                MediaItem mediaItem = selectedMedia[0];
                                Core.Logger.Write("CustomIntentHandler.HandleRequest()", $"Item requested: {mediaItem.Title}");

                                Core.State.UserState.Index = mediaItem.Id;
                                Core.State.UserState.Token = mediaItem.FileName;

                                // source type will differ based on the display interface
                                string url = Core.Device.HasScreen ? mediaItem.VideoSource : mediaItem.AudioSource;
                                Core.Logger.Write("CustomIntentHandler.HandleRequest()", $"File source url: {url}");

                                await progressiveResponse.SendSpeech($"Playing {mediaItem.Title}. ");

                                if (Core.Device.HasScreen)
                                {
                                    Core.State.UserState.Stage = Stage.Video;
                                    Core.Response.AddVideoApp(url, mediaItem.Title, mediaItem.FileName);
                                }
                                else
                                {
                                    Core.State.UserState.Stage = Stage.Audio;
                                    Core.Response.AddAudioPlayer(PlayBehavior.ReplaceAll, url, Core.State.UserState.Token);
                                }
                            }
                        }
                        else
                        {
                            Core.State.UserState.Stage = Stage.Menu;
                            Core.Response.SetSpeech(false, false, $"I could not find any recording matching {slotValue}. Try saying list, or shuffle. ");
                        }
                    }
                }
            });
        }
示例#10
0
        public async Task HandleRequest()
        {
            await RequestProcessHelper.ProcessRequest("BuiltInIntentHandler.HandleRequest()", "Built In Intent", async() =>
            {
                // get the most recent media index & sub intent
                int currentMediaIndex = Core.State.UserState.Index;
                string subIntentType  = Core.Request.GetSubIntentType();

                Core.Logger.Write("BuiltInIntentHandler.HandleRequest()", $"Current media index: {currentMediaIndex}");
                Core.Logger.Write("BuiltInIntentHandler.HandleRequest()", $"User is at: {Core.State.UserState.Stage}");


                // get media item components
                List <MediaItem> mediaItems = MediaItems.GetMediaItems();
                MediaItem currentMediaItem  = mediaItems[currentMediaIndex];


                // set response components
                Random random = new Random();
                ProgressiveResponse progressiveResponse = new ProgressiveResponse(Core.Request.GetRequest());
                List <string> stopSpeeches = new List <string> {
                    SpeechTemplate.GoodBye, SpeechTemplate.SeeYouSoon, SpeechTemplate.SeeYouNextTime
                };


                // direct sub intent into a matching handler
                switch (subIntentType)
                {
#warning check if help is accessible from audioplayer and what happens
                // handle help intent
                case AlexaRequestType.BuiltInHelp:
                    Core.State.UserState.Stage = Stage.Menu;
                    Core.Response.SetSpeech(false, false, SpeechTemplate.Help);
                    break;

                // handle stop intent
                case AlexaRequestType.BuiltInStop:
                    Core.State.UserState.Stage = Stage.Menu;;
                    Core.Response.StopAudioPlayer();
                    Core.Response.SetSpeech(false, true, stopSpeeches[random.Next(stopSpeeches.Count)]);
                    break;

                // handle pause intent
                case AlexaRequestType.BuiltInPause:
                    Core.State.UserState.Stage      = Stage.Menu;
                    Core.State.UserState.Token      = Core.Request.GetRequest().Context.AudioPlayer.Token;
                    Core.State.UserState.OffsetInMS = Convert.ToInt32(Core.Request.GetRequest().Context.AudioPlayer.OffsetInMilliseconds);

                    Core.Response.StopAudioPlayer();
                    Core.Response.SetSpeech(false, true, stopSpeeches[random.Next(stopSpeeches.Count)]);
                    break;

                // handle cancel intent
                case AlexaRequestType.BuiltInCancel:
                    if (Core.State.UserState.Stage.Equals(Stage.Audio))
                    {
                        Core.State.UserState.Stage      = Stage.Menu;
                        Core.State.UserState.Token      = Core.Request.GetRequest().Context.AudioPlayer.Token;
                        Core.State.UserState.OffsetInMS = Convert.ToInt32(Core.Request.GetRequest().Context.AudioPlayer.OffsetInMilliseconds);

                        Core.Response.StopAudioPlayer();
                        Core.Response.SetSpeech(false, false, SpeechTemplate.Intro);
                    }
                    else
                    {
                        Core.Response.SetSpeech(false, false, SpeechTemplate.NoUnderstand);
                    }
                    break;

                // handle next intent
                case AlexaRequestType.BuiltInNext:
                    if (Core.State.UserState.Stage.Equals(Stage.Audio))
                    {
                        MediaItem nextMediaItem = mediaItems.Find(m => m.Id.Equals(currentMediaIndex + 1));

                        if (nextMediaItem != null)
                        {
                            await progressiveResponse.SendSpeech($"Playing next recording, {nextMediaItem.Title}. ");
                            Core.Logger.Write("BuiltInIntentHandler.HandleRequest()", $"Next media item name: {nextMediaItem.Title}");

                            Core.State.UserState.OffsetInMS = 0;
                            Core.State.UserState.Stage      = Stage.Audio;
                            Core.State.UserState.Index      = nextMediaItem.Id;
                            Core.State.UserState.Token      = nextMediaItem.FileName;

                            Core.Response.AddAudioPlayer(PlayBehavior.ReplaceAll, nextMediaItem.AudioSource, nextMediaItem.FileName);
                        }
                        else
                        {
                            Core.Logger.Write("BuiltInIntentHandler.HandleRequest()", "Next media item is not available");
                            Core.Response.SetSpeech(false, false, SpeechTemplate.NoNext);
                            Core.State.UserState.Stage = Stage.Pause;
                        }
                    }
                    else
                    {
                        Core.Response.SetSpeech(false, false, SpeechTemplate.NoUnderstand);
                    }
                    break;

                // handle previous intent
                case AlexaRequestType.BuiltInPrevious:
                    if (Core.State.UserState.Stage.Equals(Stage.Audio))
                    {
                        MediaItem previousMediaItem = mediaItems.Find(m => m.Id.Equals(currentMediaIndex - 1));

                        if (previousMediaItem != null)
                        {
                            await progressiveResponse.SendSpeech($"Playing previous recording, {previousMediaItem.Title}. ");
                            Core.Logger.Write("BuiltInIntentHandler.HandleRequest()", $"Previous media item name: {previousMediaItem.Title}");

                            Core.State.UserState.OffsetInMS = 0;
                            Core.State.UserState.Stage      = Stage.Audio;
                            Core.State.UserState.Index      = previousMediaItem.Id;
                            Core.State.UserState.Token      = previousMediaItem.FileName;

                            Core.Response.AddAudioPlayer(PlayBehavior.ReplaceAll, previousMediaItem.AudioSource, previousMediaItem.FileName);
                        }
                        else
                        {
                            Core.Logger.Write("BuiltInIntentHandler.HandleRequest()", "Previous media item is not available");
                            Core.Response.SetSpeech(false, false, SpeechTemplate.NoPrevious);
                            Core.State.UserState.Stage = Stage.Pause;
                        }
                    }
                    else
                    {
                        Core.Response.SetSpeech(false, false, SpeechTemplate.NoUnderstand);
                    }
                    break;

                // handle start over intent
                case AlexaRequestType.BuiltInStartOver:
                    if (Core.State.UserState.Stage.Equals(Stage.Audio))
                    {
                        await progressiveResponse.SendSpeech($"Playing from the first recording. {mediaItems[0].Title}. ");
                        Core.State.UserState.OffsetInMS = 0;
                        Core.State.UserState.Stage      = Stage.Audio;
                        Core.State.UserState.Token      = mediaItems[0].Title;
                        Core.Response.AddAudioPlayer(PlayBehavior.ReplaceAll, mediaItems[0].AudioSource, mediaItems[0].Title, 0);
                    }
                    else
                    {
                        Core.Response.SetSpeech(false, false, SpeechTemplate.NoUnderstand);
                    }
                    break;

                // handle resume intent
                case AlexaRequestType.BuiltInResume:
                    if (Core.State.UserState.Stage.Equals(Stage.Pause))
                    {
                        Core.State.UserState.Stage = Stage.Audio;
                        Core.Response.AddAudioPlayer(PlayBehavior.ReplaceAll, currentMediaItem.AudioSource, Core.State.UserState.Token, Core.State.UserState.OffsetInMS);

                        if (Core.State.UserState.EnqueuedToken != null)
                        {
                            Core.Response.AddDirective(new AudioPlayerPlayDirective()
                            {
                                PlayBehavior = PlayBehavior.Enqueue,
                                AudioItem    = new AudioItem()
                                {
                                    Stream = new AudioItemStream()
                                    {
                                        OffsetInMilliseconds = 0,
                                        Url   = mediaItems[currentMediaIndex + 1].AudioSource,
                                        Token = mediaItems[currentMediaIndex + 1].Title,
                                        ExpectedPreviousToken = Core.State.UserState.Token
                                    }
                                }
                            });
                        }
                    }
                    else
                    {
                        Core.Response.SetSpeech(false, false, SpeechTemplate.NoUnderstand);
                    }
                    break;

                // handle repeat intent
                case AlexaRequestType.BuiltInRepeat:
                    if (Core.State.UserState.Stage.Equals(Stage.Audio))
                    {
                        await progressiveResponse.SendSpeech($"Repeating {currentMediaItem.Title}");
                        Core.State.UserState.OffsetInMS = 0;
                        Core.State.UserState.Stage      = Stage.Audio;
                        Core.State.UserState.Token      = currentMediaItem.Title;
                        Core.Response.AddAudioPlayer(PlayBehavior.ReplaceAll, currentMediaItem.AudioSource, currentMediaItem.Title, 0);
                    }
                    else
                    {
                        Core.Response.SetSpeech(false, false, SpeechTemplate.Intro);
                    }
                    break;

                // handle unknown intent
                default:
                    bool endSession = Core.State.UserState.NumReprompt > 5 ? true : false;
                    Core.Logger.Write("BuiltInIntentHandler.HandleRequest()", "Intent was not recognized, directing into the default case handler");
                    Core.Response.SetSpeech(false, endSession, SpeechTemplate.NoUnderstand);
                    Core.State.UserState.Stage = Stage.Menu;
                    Core.State.UserState.NumReprompt++;
                    if (endSession)
                    {
                        Core.State.UserState.NumReprompt = 0;
                    }
                    break;
                }
            });
        }
示例#11
0
        private async Task <IActionResult> ProcessStep(SkillRequest request, Coordinates coords)
        {
            Session session = request.Session;
            var     state   = new State(Database.Context, session);

            Logger.LogInformation(LoggingEvents.Game, "User reaches coordinates {0}", coords);
            Logger.LogTrace(LoggingEvents.Game, "{0} moves, last reached {1}", state.MovesCount, state.LastReached);

            if (!coords.IsValid)
            {
                // Something went wrong
                Logger.LogError(LoggingEvents.Game, "Invalid coordinates");

                var response = ResponseBuilder.Ask(
                    new SsmlOutputSpeech {
                    Ssml = @"<speak>Non ho capito. Ripeti le coordinate per favore.</speak>"
                },
                    new Reprompt {
                    OutputSpeech = new SsmlOutputSpeech {
                        Ssml = @"<speak>Quali sono le <emphasis level=""moderate"">coordinate</emphasis> dello spazio in cui ti trovi?</speak>"
                    }
                }
                    );
                return(Ok(response));
            }

            if (state.IsSessionStart)
            {
                // First position, can ignore direction
                if (Chessboard.IsStartPosition(coords))
                {
                    Direction startDir = Chessboard.GetStartDirection(coords);
                    Logger.LogDebug(LoggingEvents.Game, "User in {0} should look towards {1}", coords, startDir);

                    Coordinates effectiveTarget = new Coordinates(coords.Column, coords.Row, startDir);
                    state.RecordDestination(effectiveTarget, true);

                    if (effectiveTarget.Direction != coords.Direction)
                    {
                        // Hint at correct direction
                        var progResp = new ProgressiveResponse(request);
                        await progResp.SendSpeech(string.Format(
                                                      "OK. Sei in {0}, {1}. Assicurati di girarti verso {2}.",
                                                      effectiveTarget.Column.FromColumnIndex(),
                                                      effectiveTarget.Row,
                                                      effectiveTarget.Direction.Value.ToLocale()
                                                      ));

                        coords = effectiveTarget;
                    }
                }
                else
                {
                    Logger.LogDebug(LoggingEvents.Game, "User in {0}, not a valid starting position", coords);

                    return(Ok(ResponseBuilder.Ask("Devi partire in uno spazio sul bordo della scacchiera. Spostati e dimmi dove sei.", null)));
                }
            }
            else if (!coords.Direction.HasValue)
            {
                // Not first position, requires direction:
                // register coordinates in session and ask for direction
                if (session.Attributes == null)
                {
                    session.Attributes = new Dictionary <string, object>();
                }
                session.Attributes["row"] = coords.Row;
                session.Attributes["col"] = coords.Column;

                var response = ResponseBuilder.Ask(
                    new SsmlOutputSpeech {
                    Ssml = @"<speak>OK. In che direzione stai guardando?</speak>"
                },
                    new Reprompt {
                    OutputSpeech = new SsmlOutputSpeech {
                        Ssml = @"<speak>Dimmi in che <emphasis level=""moderate"">direzione</emphasis> stai guardando.</speak>"
                    }
                },
                    session
                    );
                return(Ok(response));
            }

            session.Attributes = new Dictionary <string, object>(); // clean up session attributes

            // Check for destination to reach
            var destination = state.LastDestination;

            if (destination.HasValue)
            {
                if (destination.Value.Equals(coords))
                {
                    Logger.LogInformation(LoggingEvents.Game, "Correct cell");

                    state.ReachDestination();

                    var progResp = new ProgressiveResponse(request);
                    await progResp.SendSpeech("Sei nel posto giusto!");
                }
                else if (destination.Value.LocationEquals(coords))
                {
                    Logger.LogInformation(LoggingEvents.Game, "Wrong direction, expected {0}", destination.Value);

                    var response = ResponseBuilder.Ask("Stai guardando nella direzione sbagliata. Riprova.", null, session);
                    return(Ok(response));
                }
                else
                {
                    Logger.LogInformation(LoggingEvents.Game, "Wrong cell, expected {0}", destination.Value);

                    var response = ResponseBuilder.Ask("Purtroppo sei nella casella sbagliata. Riprova.", null, session);
                    return(Ok(response));
                }
            }

            if (state.MovesCount >= Chessboard.MaxLevel)
            {
                Logger.LogInformation(LoggingEvents.Game, "User completed last level");

                return(Ok(ResponseBuilder.Tell(
                              new SsmlOutputSpeech {
                    Ssml = @"<speak>Complimenti! Hai completato <emphasis level=""moderate"">Cody Maze</emphasis> con successo.</speak>"
                }
                              )));
            }

            // Assign new destination
            Logger.LogInformation(LoggingEvents.Game, "Generating new destination (step {0})", state.MovesCount);
            (var mazeDestination, var instructions) = Chessboard.GenerateMazeForLevel(coords, state.MovesCount);
            if (!mazeDestination.IsValid)
            {
                Logger.LogError(LoggingEvents.Game, "Invalid coordinates generated for maze level {0}", state.MovesCount);
                return(await InternalError());
            }
            state.RecordDestination(mazeDestination);

            return(Ok(ResponseBuilder.Ask(
                          new SsmlOutputSpeech {
                Ssml = string.Format(
                    @"<speak>Esegui le seguenti istruzioni{1}. <emphasis level=""strong"">{0}</emphasis>.</speak>",
                    instructions,
                    (state.MovesCount <= 2) ? " e poi dimmi le tue coordinate e direzione" : string.Empty
                    )
            }, new Reprompt {
                OutputSpeech = new SsmlOutputSpeech {
                    Ssml = string.Format(
                        @"<speak>Esegui le istruzioni. <emphasis level=""strong"">{0}</emphasis>.</speak>",
                        instructions
                        )
                }
            },
                          session
                          )));
        }
示例#12
0
        public async Task <SkillResponse> FunctionHandler(SkillRequest input, ILambdaContext context)
        {
            // Skill currently only in German so set culture statical
            CultureInfo.CurrentCulture = CultureInfo.GetCultureInfo("de-DE");

            skillRequest   = input;
            progResponse   = new ProgressiveResponse(skillRequest);
            this.context   = context;
            settingsClient = new SettingsClient(input);
            session        = input.Session;
            if (session.Attributes == null)
            {
                session.Attributes = new Dictionary <string, object>();
            }

            if (input.Request is LaunchRequest)
            {
                return(ResponseBuilder.AskWithCard(
                           Properties.Speech.Starter,
                           Properties.Speech.StarterTitle,
                           Properties.Speech.StarterContent,
                           null,
                           session
                           ));
            }
            else if (input.Request is IntentRequest intentRequest)
            {
                var intent = intentRequest.Intent;

                context.Logger.LogLine($"IntentRequest {intent.Name}, Attributes: {string.Join(";", input.Session?.Attributes.Select(kp => $"{kp.Key}: {kp.Value}"))}");
                context.Logger.LogLine($"Slots {string.Join(";", intent.Slots.Select(s => $"{s.Key}: {s.Value.Value}"))}");

                if (intent.Name == Properties.Resources.TripSearchIntentName)
                {
                    if (GetCounter(completeFailCounter) >= 2)
                    {
                        return(ResponseBuilder.Tell(
                                   Properties.Speech.CompleteFail
                                   ));
                    }

                    var sourceSlot       = intent.Slots[Properties.Resources.TripSearchSrcSlotName];
                    var destintationSlot = intent.Slots[Properties.Resources.TripSearchDstSlotName];

                    var source = sourceSlot.Value;
                    IEnumerable <Destination> foundSources = null;
                    if (string.IsNullOrWhiteSpace(source))
                    {
                        if (input.Context.Geolocation == null)
                        {
                            return(ResponseBuilder.TellWithAskForPermissionConsentCard(
                                       Properties.Speech.RequestGeoLocation,
                                       new[] { geoLocationPermission }.AsEnumerable(),
                                       session
                                       ));
                        }
                        else
                        {
                            var coords = input.Context.Geolocation.Coordinate;
                            context.Logger.LogLine($"Geo lat: {coords.Latitude}, lon: {coords.Longitude}");
                            foundSources = await searcher.FindDestinationByGeo(
                                coords.Latitude,
                                coords.Longitude
                                );
                        }
                    }
                    else
                    {
                        await progResponse.SendSpeech(
                            string.Format(Properties.Speech.SearchingForDestinations, source)
                            );

                        foundSources = await searcher.FindDestinationByName(source);
                    }

                    var destination = destintationSlot.Value;

                    await progResponse.SendSpeech(
                        string.Format(Properties.Speech.SearchingForDestinations, destination)
                        );

                    var foundDestinations = await searcher.FindDestinationByName(destination);

                    if (foundSources.Count() != 1 && foundDestinations.Count() != 1)
                    {
                        IncreaseCounter(completeFailCounter);

                        return(ResponseBuilder.AskWithCard(
                                   string.Format(Properties.Speech.SourceAndDestinationNotFound, source, destination),
                                   Properties.Speech.SourceAndDestinationNotFoundTitle,
                                   string.Format("Die Orte {0} und {1} kenne ich nicht. Versuche es bitte noch einmal von vorne.",
                                                 source, destination),
                                   null,
                                   session
                                   ));
                    }
                    else if (foundSources.Count() != 1)
                    {
                        input.Session.Attributes["destinationDst"] = foundDestinations.First();

                        if (string.IsNullOrWhiteSpace(source))
                        {
                            return(ResponseBuilder.AskWithCard(
                                       string.Format(Properties.Speech.SourceGeoNotFound),
                                       Properties.Speech.SourceNotFoundTitle,
                                       "Den Startort konnte ich lieder nicht ermitteln. Versuche es vielleicht diesen explizit zu nennen.",
                                       null,
                                       session
                                       ));
                        }
                        else
                        {
                            return(ResponseBuilder.AskWithCard(
                                       string.Format(Properties.Speech.SourceNotFound, source, foundSources.First().Name),
                                       Properties.Speech.SourceNotFoundTitle,
                                       string.Format("Den Startort {0} kenne ich lieder nicht. Versuche es mit: Der Ort ist {1}.",
                                                     source, foundSources.First().Name),
                                       null,
                                       session
                                       ));
                        }
                    }
                    else if (foundDestinations.Count() != 1)
                    {
                        input.Session.Attributes["sourceDst"] = foundSources.First();

                        return(ResponseBuilder.AskWithCard(
                                   string.Format(Properties.Speech.DestinationNotFound, destination, foundDestinations.First().Name),
                                   Properties.Speech.DestinationNotFoundTitle,
                                   string.Format("Den Zielort {0} kenne ich leider nicht. Versuche es mit: Der Ort ist {1}.",
                                                 destination, foundDestinations.First().Name),
                                   null,
                                   session
                                   ));
                    }

                    var time = DateTime.Now;
                    return(await SearchForTrips(foundSources.First(), foundDestinations.First()));
                }
                else if (intent.Name == Properties.Resources.SpecifyLocationIntentName)
                {
                    if (GetCounter(locationFailCounter) >= 2)
                    {
                        return(ResponseBuilder.Tell(
                                   Properties.Speech.LocationFail
                                   ));
                    }

                    var source      = GetAttributeAs <Destination>("sourceDst");
                    var destination = GetAttributeAs <Destination>("destinationDst");
                    if (source == null && destination == null)
                    {
                        return(ResponseBuilder.Ask(
                                   Properties.Speech.WrongOrderSpecLoc,
                                   null
                                   ));
                    }

                    var locationSlot = intent.Slots[Properties.Resources.SpecifyLocationLocSlotName];;
                    var location     = locationSlot.Value;

                    await progResponse.SendSpeech(
                        string.Format(Properties.Speech.SearchingForDestinations, location)
                        );

                    var foundLocations = await searcher.FindDestinationByName(location);

                    if (foundLocations.Count() != 1)
                    {
                        IncreaseCounter(locationFailCounter);

                        return(ResponseBuilder.AskWithCard(
                                   string.Format(Properties.Speech.DestinationNotFound, location, foundLocations.First().Name),
                                   source == null
                                ? Properties.Speech.SourceNotFoundTitle
                                : Properties.Speech.DestinationNotFoundTitle,
                                   string.Format("Den {0} {1} kenne ich leider nicht. Versuche es mit: Der Ort ist {2}.",
                                                 source == null ? "Startort" : "Zielort",
                                                 location, foundLocations.First().Name),
                                   null,
                                   session
                                   ));
                    }
                    else
                    {
                        if (source == null)
                        {
                            source = foundLocations.First();
                        }
                        if (destination == null)
                        {
                            destination = foundLocations.First();
                        }

                        var time = DateTime.Now;
                        return(await SearchForTrips(source, destination));
                    }
                }
                else
                {
                    // TODO Better response for unknown intent
                    return(ResponseBuilder.Tell(Properties.Speech.InvalidRequest));
                }
            }
            else
            {
                return(ResponseBuilder.Tell(Properties.Speech.InvalidRequest));
            }
        }