예제 #1
0
        public async Task <FocusManageResult> Update(string userId, FocusUpdateRequest focusUpdateRequest)
        {
            if (null != focusUpdateRequest.Location)
            {
                await _focusGeofenceService.UpdateFocusItems(userId, focusUpdateRequest.Location);
            }
            var res         = new FocusManageResult();
            var activeItems = await focusStore.GetActiveAsync(userId);

            var updatedItemIds = new HashSet <string>(focusUpdateRequest.ItemSyncResult != null ?
                                                      focusUpdateRequest.ItemSyncResult.ChangedItems.Select(v => v.Id) :
                                                      new string[0]);

            foreach (var item in activeItems)
            {
                var evt = await calendarServiceClient.Users[userId].Feeds[item.CalendarEventFeedId].Events.Get(item.CalendarEventId);
                TransitDirections directions;
                if (null != focusUpdateRequest.ItemSyncResult && (
                        focusUpdateRequest.ItemSyncResult.AddedItems.Any(v => v.Id == item.Id) ||
                        focusUpdateRequest.ItemSyncResult.ChangedItems.Any(v => v.Id == item.Id)) ||
                    null == item.DirectionsMetadata?.Key)
                {
                    directions = await GetFreshDirections(userId, evt, item, focusUpdateRequest.Location);
                }
                else
                {
                    var directionsRes = await GetCachedDirectionsOrNew(userId, evt, item, focusUpdateRequest.Location);

                    directions = directionsRes.Directions;
                    if (directionsRes.IsNew)
                    {
                        updatedItemIds.Add(item.Id);
                    }
                    if (null != directions &&
                        null != focusUpdateRequest.ChangedDirections && focusUpdateRequest.ChangedDirections.Contains(
                            item.DirectionsMetadata.Key))
                    {
                        await logger.LogForFocusItem(userId, item.Id, $"Received direction updates for {evt.Subject}", DigitTraceAction.DirectionsUpdate);

                        updatedItemIds.Add(item.Id);
                    }
                }
                DateTimeOffset indicateTime;
                if (null == directions)
                {
                    await logger.LogForFocusItem(userId, item.Id, $"No departure time found, using {FocusConstants.DefaultTravelTime.TotalMinutes:0} minutes for {evt.Subject}");

                    indicateTime = evt.Start - FocusConstants.DefaultTravelTime;
                }
                else
                {
                    indicateTime = directions.Routes[item.DirectionsMetadata.PeferredRoute].DepatureTime;
                }
                item.IndicateTime = indicateTime;
                await focusStore.UpdateIndicateTime(item.Id, indicateTime);

                res.ActiveItems.Add(new FocusItemWithExternalData()
                {
                    Start              = item.Start,
                    IndicateTime       = item.IndicateTime,
                    CalendarEvent      = evt,
                    Directions         = directions,
                    DirectionsMetadata = item.DirectionsMetadata,
                    End = item.End,
                    Id  = item.Id
                });
            }
            await _focusGeofenceService.RefreshGeofencesForActiveNavigations(userId, res, DateTimeOffset.Now);

            var active = await focusStore.GetActiveItem(userId);

            var activeItemChanged = await focusStore.UpdateActiveItem(userId, active?.Id);

            if (activeItemChanged || (null != active && updatedItemIds.Contains(active.Id)))
            {
                if (null != active)
                {
                    await Task.WhenAll(focusSubscribers.Select(v => v.ActiveItemChanged(userId, res.ActiveItems.Where(d => d.Id == active.Id).Single())));
                }
                else
                {
                    await Task.WhenAll(focusSubscribers.Select(v => v.ActiveItemChanged(userId, null)));
                }
            }
            if (updatedItemIds.Count > 0)
            {
                await Task.WhenAll(focusSubscribers.Select(v => v.ActiveItemsChanged(userId, res)));
            }
            return(res);
        }
예제 #2
0
        public async Task<Plan> GetPlan(string userId, DateTimeOffset from, DateTimeOffset to)
        {

            string start = "#home";

            var syncResult = await _focusCalendarSyncService.SyncAsync(userId, from, to);
            var items = (await _focusStore.GetTimeRangeAsync(userId, from, to)).OrderBy(d => d.Start);
            var directionsList = new List<DirectionsResult>();
            var focusItemsList = new List<FocusItem>();
            DateTimeOffset? getup = null;
            bool first = true;
            foreach (var e in items)
            {
                var calendarItem = syncResult.Events.Where(c => c.Id == e.CalendarEventId && c.FeedId == e.CalendarEventFeedId).SingleOrDefault();
                if (null != calendarItem)
                {
                    if (first)
                    {

                    }
                    focusItemsList.Add(e);
                    var address = calendarItem.GetFormattedAddress();
                    if (!string.IsNullOrEmpty(address))
                    {
                        var directions = await _travelServiceClient.Users[userId]
                            .Directions.Transit.Get(start, address, calendarItem.Start);
                        var route = DirectionUtils.SelectRoute(directions);
                        if (null == directions.NotFound)
                        {
                            if (first)
                            {
                                getup = route.DepatureTime - TimeSpan.FromHours(1);
                            }
                            directionsList.Add(directions);
                            await _focusStore.UpdateDirections(e.Id, directions, 0);
                            await _focusStore.UpdateIndicateTime(e.Id, route.DepatureTime);
                            e.IndicateTime = route.DepatureTime;
                            e.DirectionsMetadata = new DirectionsMetadata()
                            {
                                Error = directions.NotFound?.Reason,
                                Key = directions.CacheKey,
                                PeferredRoute = 0,
                                TravelStatus = TravelStatus.UnStarted
                            };
                        }
                        else
                        {
                            await _focusStore.UpdateDirections(e.Id, directions, null);
                            e.DirectionsMetadata = new DirectionsMetadata()
                            {
                                Error = directions.NotFound?.Reason,
                                Key = directions.CacheKey,
                                PeferredRoute = 0,
                                TravelStatus = TravelStatus.UnStarted
                            };
                        }
                        start = address;
                    }
                    first = false;
                }
            }
            var plan = new Plan()
            {
                Events = syncResult.Events,
                Directions = directionsList.ToArray(),
                FocusItems = items.ToArray(),
                GetUp = getup
            };
            return plan;
        }