/// <summary>
        /// 发布路由。
        /// </summary>
        /// <param name="routes">路由集合。</param>
        public void Publish(IEnumerable<RouteDescriptor> routes)
        {
            //排序。
            var routesArray = routes
                .OrderByDescending(r => r.Priority)
                .ToArray();

            //发布前事件。
            _routePublisherEventHandlers.Invoke(i => i.Publishing(routesArray), NullLogger.Instance);

            using (_routeCollection.GetWriteLock())
            {
                //释放现有路由。
                _routeCollection
                    .OfType<HubRoute>().Invoke(x => x.ReleaseShell(_shellSettings), NullLogger.Instance);
                var routeList = new List<RouteBase>(_routeCollection);

                //添加新路由
                foreach (var routeDescriptor in routesArray)
                {
                    //根据Route得到扩展描述符
                    ExtensionDescriptorEntry extensionDescriptor = null;
                    if (routeDescriptor.Route is Route)
                    {
                        object extensionId;
                        var route = routeDescriptor.Route as Route;
                        if (route.DataTokens != null && route.DataTokens.TryGetValue("area", out extensionId) ||
                            route.Defaults != null && route.Defaults.TryGetValue("area", out extensionId))
                        {
                            extensionDescriptor = _extensionManager.GetExtension(extensionId.ToString());
                        }
                    }
                    else if (routeDescriptor.Route is IRouteWithArea)
                    {
                        var route = routeDescriptor.Route as IRouteWithArea;
                        extensionDescriptor = _extensionManager.GetExtension(route.Area);
                    }

                    //加载会话状态信息。
                    var sessionState = SessionStateBehavior.Default;
                    if (extensionDescriptor != null)
                    {
                        if (routeDescriptor.SessionState == SessionStateBehavior.Default)
                        {
                            var descriptor = extensionDescriptor.Descriptor;
                            if (descriptor.Keys.Contains("SessionState"))
                                Enum.TryParse(descriptor["SessionState"], true, out sessionState);
                        }
                    }

                    //设置SessionState
                    var sessionStateBehavior = routeDescriptor.SessionState == SessionStateBehavior.Default
                        ? sessionState
                        : routeDescriptor.SessionState;

                    //创建外壳路由
                    var shellRoute = new ShellRoute(routeDescriptor.Route, _shellSettings, _webWorkContextAccessor,
                        _runningShellTable)
                    {
                        IsHttpRoute = routeDescriptor is HttpRouteDescriptor,
                        SessionState = sessionStateBehavior
                    };

                    //区域
                    var area = extensionDescriptor == null ? string.Empty : extensionDescriptor.Id;

                    //尝试查找已存在的集线器路由
                    var matchedHubRoute = routeList.FirstOrDefault(x =>
                    {
                        var hubRoute = x as HubRoute;
                        if (hubRoute == null)
                        {
                            return false;
                        }

                        return routeDescriptor.Priority == hubRoute.Priority &&
                               hubRoute.Area.Equals(area, StringComparison.OrdinalIgnoreCase) &&
                               hubRoute.Name == routeDescriptor.Name;
                    }) as HubRoute;

                    //创建新的集线器路由。
                    if (matchedHubRoute == null)
                    {
                        matchedHubRoute = new HubRoute(routeDescriptor.Name, area, routeDescriptor.Priority,
                            _runningShellTable);

                        int index;
                        for (index = 0; index < routeList.Count; index++)
                        {
                            var hubRoute = routeList[index] as HubRoute;
                            if (hubRoute == null)
                            {
                                continue;
                            }
                            if (hubRoute.Priority < matchedHubRoute.Priority)
                            {
                                break;
                            }
                        }
                        routeList.Insert(index, matchedHubRoute);
                    }

                    matchedHubRoute.Add(shellRoute, _shellSettings);
                }

                //清空现有路由。
                _routeCollection.Clear();
                foreach (var item in routeList)
                {
                    if (item is HubRoute)
                    {
                        _routeCollection.Add((item as HubRoute).Name, item);
                    }
                    else
                    {
                        _routeCollection.Add(item);
                    }
                }
            }

            //发布后事件。
            _routePublisherEventHandlers.Invoke(i => i.Published(routesArray), NullLogger.Instance);
        }
        internal static HubRouteTableData DeserializeHubRouteTableData(JsonElement element)
        {
            Optional <string>                  name   = default;
            Optional <string>                  etag   = default;
            Optional <string>                  type   = default;
            ResourceIdentifier                 id     = default;
            Optional <IList <HubRoute> >       routes = default;
            Optional <IList <string> >         labels = default;
            Optional <IReadOnlyList <string> > associatedConnections  = default;
            Optional <IReadOnlyList <string> > propagatingConnections = default;
            Optional <ProvisioningState>       provisioningState      = default;

            foreach (var property in element.EnumerateObject())
            {
                if (property.NameEquals("name"))
                {
                    name = property.Value.GetString();
                    continue;
                }
                if (property.NameEquals("etag"))
                {
                    etag = property.Value.GetString();
                    continue;
                }
                if (property.NameEquals("type"))
                {
                    type = property.Value.GetString();
                    continue;
                }
                if (property.NameEquals("id"))
                {
                    id = property.Value.GetString();
                    continue;
                }
                if (property.NameEquals("properties"))
                {
                    if (property.Value.ValueKind == JsonValueKind.Null)
                    {
                        property.ThrowNonNullablePropertyIsNull();
                        continue;
                    }
                    foreach (var property0 in property.Value.EnumerateObject())
                    {
                        if (property0.NameEquals("routes"))
                        {
                            if (property0.Value.ValueKind == JsonValueKind.Null)
                            {
                                property0.ThrowNonNullablePropertyIsNull();
                                continue;
                            }
                            List <HubRoute> array = new List <HubRoute>();
                            foreach (var item in property0.Value.EnumerateArray())
                            {
                                array.Add(HubRoute.DeserializeHubRoute(item));
                            }
                            routes = array;
                            continue;
                        }
                        if (property0.NameEquals("labels"))
                        {
                            if (property0.Value.ValueKind == JsonValueKind.Null)
                            {
                                property0.ThrowNonNullablePropertyIsNull();
                                continue;
                            }
                            List <string> array = new List <string>();
                            foreach (var item in property0.Value.EnumerateArray())
                            {
                                array.Add(item.GetString());
                            }
                            labels = array;
                            continue;
                        }
                        if (property0.NameEquals("associatedConnections"))
                        {
                            if (property0.Value.ValueKind == JsonValueKind.Null)
                            {
                                property0.ThrowNonNullablePropertyIsNull();
                                continue;
                            }
                            List <string> array = new List <string>();
                            foreach (var item in property0.Value.EnumerateArray())
                            {
                                array.Add(item.GetString());
                            }
                            associatedConnections = array;
                            continue;
                        }
                        if (property0.NameEquals("propagatingConnections"))
                        {
                            if (property0.Value.ValueKind == JsonValueKind.Null)
                            {
                                property0.ThrowNonNullablePropertyIsNull();
                                continue;
                            }
                            List <string> array = new List <string>();
                            foreach (var item in property0.Value.EnumerateArray())
                            {
                                array.Add(item.GetString());
                            }
                            propagatingConnections = array;
                            continue;
                        }
                        if (property0.NameEquals("provisioningState"))
                        {
                            if (property0.Value.ValueKind == JsonValueKind.Null)
                            {
                                property0.ThrowNonNullablePropertyIsNull();
                                continue;
                            }
                            provisioningState = new ProvisioningState(property0.Value.GetString());
                            continue;
                        }
                    }
                    continue;
                }
            }
            return(new HubRouteTableData(id, name.Value, etag.Value, type.Value, Optional.ToList(routes), Optional.ToList(labels), Optional.ToList(associatedConnections), Optional.ToList(propagatingConnections), Optional.ToNullable(provisioningState)));
        }
        public void Publish(IEnumerable<RouteDescriptor> routes)
        {
            var routesArray = routes
                .OrderByDescending(r => r.Priority)
                .ToArray();

            // this is not called often, but is intended to surface problems before
            // the actual collection is modified
            var preloading = new RouteCollection();
            foreach (var routeDescriptor in routesArray) {

                // extract the WebApi route implementation
                var httpRouteDescriptor = routeDescriptor as HttpRouteDescriptor;
                if (httpRouteDescriptor != null) {
                    var httpRouteCollection = new RouteCollection();
                    httpRouteCollection.MapHttpRoute(httpRouteDescriptor.Name, httpRouteDescriptor.RouteTemplate, httpRouteDescriptor.Defaults, httpRouteDescriptor.Constraints);
                    routeDescriptor.Route = httpRouteCollection.First();
                }

                preloading.Add(routeDescriptor.Name, routeDescriptor.Route);
            }

            using (_routeCollection.GetWriteLock()) {
                // existing routes are removed while the collection is briefly inaccessable
                _routeCollection
                    .OfType<HubRoute>()
                    .ForEach(x => x.ReleaseShell(_shellSettings));

                // new routes are added
                foreach (var routeDescriptor in routesArray) {
                    // Loading session state information.
                    var defaultSessionState = SessionStateBehavior.Default;

                    ExtensionDescriptor extensionDescriptor = null;
                    if(routeDescriptor.Route is Route) {
                        object extensionId;
                        var route = routeDescriptor.Route as Route;
                        if(route.DataTokens != null && route.DataTokens.TryGetValue("area", out extensionId) ||
                           route.Defaults != null && route.Defaults.TryGetValue("area", out extensionId)) {
                            extensionDescriptor = _extensionManager.GetExtension(extensionId.ToString());
                        }
                    }
                    else if(routeDescriptor.Route is IRouteWithArea) {
                        var route = routeDescriptor.Route as IRouteWithArea;
                        extensionDescriptor = _extensionManager.GetExtension(route.Area);
                    }

                    if (extensionDescriptor != null) {
                        // if session state is not define explicitly, use the one define for the extension
                        if (routeDescriptor.SessionState == SessionStateBehavior.Default) {
                            Enum.TryParse(extensionDescriptor.SessionState, true /*ignoreCase*/, out defaultSessionState);
                        }
                    }

                    // Route-level setting overrides module-level setting (from manifest).
                    var sessionStateBehavior = routeDescriptor.SessionState == SessionStateBehavior.Default ? defaultSessionState : routeDescriptor.SessionState ;

                    var shellRoute = new ShellRoute(routeDescriptor.Route, _shellSettings, _workContextAccessor, _runningShellTable) {
                        IsHttpRoute = routeDescriptor is HttpRouteDescriptor,
                        SessionState = sessionStateBehavior
                    };

                    var area = extensionDescriptor == null ? "" : extensionDescriptor.Id;

                    var matchedHubRoute = _routeCollection.FirstOrDefault(x => {
                        var hubRoute = x as HubRoute;
                        if (hubRoute == null) {
                            return false;
                        }

                        return routeDescriptor.Priority == hubRoute.Priority && hubRoute.Area.Equals(area, StringComparison.OrdinalIgnoreCase) && hubRoute.Name == routeDescriptor.Name;
                    }) as HubRoute;

                    if (matchedHubRoute == null) {
                        matchedHubRoute = new HubRoute(routeDescriptor.Name, area, routeDescriptor.Priority, _runningShellTable);

                        int index;
                        for (index = 0; index < _routeCollection.Count; index++) {
                            var hubRoute = _routeCollection[index] as HubRoute;
                            if (hubRoute == null) {
                                continue;
                            }
                            if (hubRoute.Priority < matchedHubRoute.Priority) {
                                break;
                            }
                        }

                        _routeCollection.Insert(index, matchedHubRoute);
                    }

                    matchedHubRoute.Add(shellRoute, _shellSettings);
                }
            }
        }
Example #4
0
        /// <summary>
        /// 发布路由。
        /// </summary>
        /// <param name="routes">路由集合。</param>
        public void Publish(IEnumerable <RouteDescriptor> routes)
        {
            //排序。
            var routesArray = routes
                              .OrderByDescending(r => r.Priority)
                              .ToArray();

            //发布前事件。
            _routePublisherEventHandlers.Invoke(i => i.Publishing(routesArray), NullLogger.Instance);

            using (_routeCollection.GetWriteLock())
            {
                //释放现有路由。
                _routeCollection
                .OfType <HubRoute>().Invoke(x => x.ReleaseShell(_shellSettings), NullLogger.Instance);
                var routeList = new List <RouteBase>(_routeCollection);

                //添加新路由
                foreach (var routeDescriptor in routesArray)
                {
                    //根据Route得到扩展描述符
                    ExtensionDescriptorEntry extensionDescriptor = null;
                    if (routeDescriptor.Route is Route)
                    {
                        object extensionId;
                        var    route = routeDescriptor.Route as Route;
                        if (route.DataTokens != null && route.DataTokens.TryGetValue("area", out extensionId) ||
                            route.Defaults != null && route.Defaults.TryGetValue("area", out extensionId))
                        {
                            extensionDescriptor = _extensionManager.GetExtension(extensionId.ToString());
                        }
                    }
                    else if (routeDescriptor.Route is IRouteWithArea)
                    {
                        var route = routeDescriptor.Route as IRouteWithArea;
                        extensionDescriptor = _extensionManager.GetExtension(route.Area);
                    }

                    //加载会话状态信息。
                    var sessionState = SessionStateBehavior.Default;
                    if (extensionDescriptor != null)
                    {
                        if (routeDescriptor.SessionState == SessionStateBehavior.Default)
                        {
                            var descriptor = extensionDescriptor.Descriptor;
                            if (descriptor.Keys.Contains("SessionState"))
                            {
                                Enum.TryParse(descriptor["SessionState"], true, out sessionState);
                            }
                        }
                    }

                    //设置SessionState
                    var sessionStateBehavior = routeDescriptor.SessionState == SessionStateBehavior.Default
                        ? sessionState
                        : routeDescriptor.SessionState;

                    //创建外壳路由
                    var shellRoute = new ShellRoute(routeDescriptor.Route, _shellSettings, _webWorkContextAccessor,
                                                    _runningShellTable)
                    {
                        IsHttpRoute  = routeDescriptor is HttpRouteDescriptor,
                        SessionState = sessionStateBehavior
                    };

                    //区域
                    var area = extensionDescriptor == null ? string.Empty : extensionDescriptor.Id;

                    //尝试查找已存在的集线器路由
                    var matchedHubRoute = routeList.FirstOrDefault(x =>
                    {
                        var hubRoute = x as HubRoute;
                        if (hubRoute == null)
                        {
                            return(false);
                        }

                        return(routeDescriptor.Priority == hubRoute.Priority &&
                               hubRoute.Area.Equals(area, StringComparison.OrdinalIgnoreCase) &&
                               hubRoute.Name == routeDescriptor.Name);
                    }) as HubRoute;

                    //创建新的集线器路由。
                    if (matchedHubRoute == null)
                    {
                        matchedHubRoute = new HubRoute(routeDescriptor.Name, area, routeDescriptor.Priority,
                                                       _runningShellTable);

                        int index;
                        for (index = 0; index < routeList.Count; index++)
                        {
                            var hubRoute = routeList[index] as HubRoute;
                            if (hubRoute == null)
                            {
                                continue;
                            }
                            if (hubRoute.Priority < matchedHubRoute.Priority)
                            {
                                break;
                            }
                        }
                        routeList.Insert(index, matchedHubRoute);
                    }

                    matchedHubRoute.Add(shellRoute, _shellSettings);
                }

                //清空现有路由。
                _routeCollection.Clear();
                foreach (var item in routeList)
                {
                    if (item is HubRoute)
                    {
                        _routeCollection.Add((item as HubRoute).Name, item);
                    }
                    else
                    {
                        _routeCollection.Add(item);
                    }
                }
            }

            //发布后事件。
            _routePublisherEventHandlers.Invoke(i => i.Published(routesArray), NullLogger.Instance);
        }