public static async Task <IActionResult> StartTripDemo([HttpTrigger(AuthorizationLevel.Anonymous, "post", Route = "tripdemos")] HttpRequest req,
                                                               [OrchestrationClient] DurableOrchestrationClient context,
                                                               ILogger log)
        {
            try
            {
                string        requestBody = new StreamReader(req.Body).ReadToEnd();
                TripDemoState demoState   = JsonConvert.DeserializeObject <TripDemoState>(requestBody);

                // The demo instance id is the trip code + -D. This is to make sure that a Trip Manager and a monitor can co-exist
                var instanceId = $"{demoState.Code}-D";
                await StartInstance(context, demoState, instanceId, log);

                //NOTE: Unfortunately this does not work the same way as before when it was using HttpMessageResponse
                //var reqMessage = req.ToHttpRequestMessage();
                //var res = context.CreateCheckStatusResponse(reqMessage, trip.Code);
                //res.Headers.RetryAfter = new RetryConditionHeaderValue(TimeSpan.FromSeconds(10));
                //return (ActionResult)new OkObjectResult(res.Content);
                return((ActionResult) new OkObjectResult("NOTE: No status URLs are returned!"));
            }
            catch (Exception ex)
            {
                var error = $"StartTripDemo failed: {ex.Message}";
                log.LogError(error);
                return(new BadRequestObjectResult(error));
            }
        }
        public static async Task <TripDemoState> RetrieveRouteItems([ActivityTrigger] TripDemoState state,
                                                                    ILogger log)
        {
            log.LogInformation($"RetrieveRouteItems starting....");
            // Supply the trip source & destination points
            state.RouteLocations = await ServiceFactory.GetRoutesService().RetrieveRouteItems(state.Source, state.Destination);

            return(state);
        }
Exemplo n.º 3
0
        public async Task Enqueue(TripDemoState tripDemoState)
        {
            await InitializeStorage();

            if (_tripDemosQueue != null)
            {
                await _tripDemosQueue.SendMessageAsync(JsonConvert.SerializeObject(tripDemoState));
            }
        }
        public async Task Enqueue(TripDemoState tripDemoState)
        {
            await InitializeStorage();

            if (_tripDemosQueue != null)
            {
                var queueMessage = new CloudQueueMessage(JsonConvert.SerializeObject(tripDemoState));
                await _tripDemosQueue.AddMessageAsync(queueMessage);
            }
        }
 public static async Task StartTripDemoViaQueueTrigger(
     [OrchestrationClient] DurableOrchestrationClient context,
     [QueueTrigger("%TripDemosQueue%", Connection = "AzureWebJobsStorage")] TripDemoState demoState,
     ILogger log)
 {
     try
     {
         // The demo instance id is the trip code + -D. This is to make sure that a Trip Manager and a monitor can co-exist
         var instanceId = $"{demoState.Code}-D";
         await StartInstance(context, demoState, instanceId, log);
     }
     catch (Exception ex)
     {
         var error = $"StartTripDemoViaQueueTrigger failed: {ex.Message}";
         log.LogError(error);
     }
 }
        //TODO: Implement Get Trip Demo Instances, Restart Trip Demo Instances and Terminate Trip Demo Instances if Persist to table storage if persist instances is activated

        /** PRIVATE **/
        private static async Task StartInstance(DurableOrchestrationClient context, TripDemoState state, string instanceId, ILogger log)
        {
            try
            {
                var reportStatus = await context.GetStatusAsync(instanceId);

                string runningStatus = reportStatus == null ? "NULL" : reportStatus.RuntimeStatus.ToString();
                log.LogInformation($"Instance running status: '{runningStatus}'.");

                if (reportStatus == null || reportStatus.RuntimeStatus != OrchestrationRuntimeStatus.Running)
                {
                    await context.StartNewAsync("O_DemoTrip", instanceId, state);

                    log.LogInformation($"Started a new trip demo = '{instanceId}'.");

                    // TODO: Persist to table storage if persist instances is activated
                }
            }
            catch (Exception ex)
            {
                throw ex;
            }
        }
 public static async Task Cleanup([ActivityTrigger] TripDemoState state,
                                  ILogger log)
 {
     log.LogInformation($"Cleanup for {state.Code} starting....");
     // TODO: Really nothing to do
 }
        public static async Task <object> DemoTrip(
            [OrchestrationTrigger] DurableOrchestrationContext context,
            ILogger log)
        {
            TripDemoState state = context.GetInput <TripDemoState>();

            if (!context.IsReplaying)
            {
                log.LogInformation($"DemoTrip {state.Code} starting.....");
            }

            try
            {
                var trip = await context.CallActivityAsync <TripItem>("A_TD_RetrieveTrip", state.Code);

                if (trip == null)
                {
                    throw new Exception($"Trip with code {trip.Code} is not found!");
                }

                if (trip.EndDate != null)
                {
                    throw new Exception($"Trip with code {trip.Code} already ended!");
                }

                if (trip.Type == TripTypes.Normal)
                {
                    throw new Exception($"Trip with code {trip.Code} is not a demo!");
                }

                // Retrieve time settings
                var settings = await context.CallActivityAsync <TripTimeSettings>("A_TD_RetrieveSettings", trip.Code);

                // Run every x seconds
                DateTime nextUpdate = context.CurrentUtcDateTime.AddSeconds(settings.IntervalInSeconds);
                await context.CreateTimer(nextUpdate, CancellationToken.None);

                // Retrieve trip route locations if needed
                if (state.RouteLocations.Count == 0)
                {
                    state = await context.CallActivityAsync <TripDemoState>("A_TD_RetrieveRouteItems", state);
                }

                if (state.RouteLocations.Count == 0)
                {
                    throw new Exception($"Trip with code {trip.Code} has no routes!");
                }

                // Assign a driver
                if (trip.Driver == null && trip.AvailableDrivers.Count > 0)
                {
                    await context.CallActivityAsync("A_TD_AssignDriver", trip);
                }

                // Navigate to a new route location
                if (trip.Driver != null)
                {
                    state = await context.CallActivityAsync <TripDemoState>("A_TD_Navigate", new TripDemoInfo()
                    {
                        State = state,
                        Trip  = trip
                    });
                }

                // Check for completion
                if (state.CurrentRouteIndex < state.RouteLocations.Count)
                {
                    // Reload the instance with a new state
                    context.ContinueAsNew(state);
                }
            }
            catch (Exception e)
            {
                if (!context.IsReplaying)
                {
                    log.LogInformation($"Caught an error from an activity: {e.Message}");
                }

                await context.CallActivityAsync <string>("A_TO_Cleanup", state);

                return(new
                {
                    Error = "Failed to process trip",
                    Message = e.Message
                });
            }

            return(new
            {
                State = state
            });
        }
Exemplo n.º 9
0
        public async Task TripCreated(TripItem trip, int activeTrips)
        {
            var error = "";

            try
            {
                // Start a trip manager
                if (!_settingService.IsEnqueueToOrchestrators())
                {
                    var baseUrl = _settingService.GetStartTripManagerOrchestratorBaseUrl();
                    var key     = _settingService.GetStartTripManagerOrchestratorApiKey();
                    if (string.IsNullOrEmpty(baseUrl) || string.IsNullOrEmpty(key))
                    {
                        throw new Exception("Trip manager orchestrator base URL and key must be both provided");
                    }

                    await Utilities.Post <dynamic, dynamic>(null, trip, $"{baseUrl}/tripmanagers?code={key}", new Dictionary <string, string>());
                }
                else
                {
                    await _storageService.Enqueue(trip);
                }

                // Send an event telemetry
                _loggerService.Log("Trip created", new Dictionary <string, string>
                {
                    { "Code", trip.Code },
                    { "Passenger", $"{trip.Passenger.FirstName} {trip.Passenger.LastName}" },
                    { "Destination", $"{trip.Destination.Latitude} - {trip.Destination.Longitude}" },
                    { "Mode", $"{trip.Type}" }
                });

                // Send a metric telemetry
                _loggerService.Log("Active trips", activeTrips);

                if (trip.Type == TripTypes.Demo)
                {
                    var tripDemoState = new TripDemoState();
                    tripDemoState.Code   = trip.Code;
                    tripDemoState.Source = new TripLocation()
                    {
                        Latitude = trip.Source.Latitude, Longitude = trip.Source.Longitude
                    };
                    tripDemoState.Destination = new TripLocation()
                    {
                        Latitude = trip.Destination.Latitude, Longitude = trip.Destination.Longitude
                    };

                    if (!_settingService.IsEnqueueToOrchestrators())
                    {
                        var baseUrl = _settingService.GetStartTripDemoOrchestratorBaseUrl();
                        var key     = _settingService.GetStartTripDemoOrchestratorApiKey();
                        if (string.IsNullOrEmpty(baseUrl) || string.IsNullOrEmpty(key))
                        {
                            throw new Exception("Trip demo orchestrator base URL and key must be both provided");
                        }
                        await Utilities.Post <dynamic, dynamic>(null, tripDemoState, $"{baseUrl}/tripdemos?code={key}", new Dictionary <string, string>());
                    }
                    else
                    {
                        await _storageService.Enqueue(tripDemoState);
                    }
                }
            }
            catch (Exception ex)
            {
                error = $"Error while starting the trip manager: {ex.Message}";
                throw new Exception(error);
            }
            finally
            {
                _loggerService.Log($"{LOG_TAG} - TripCreated - Error: {error}");
            }
        }