コード例 #1
0
        private bool TryMatchStarMapping(StringSegment host, StringSegment hostOnly, StringSegment path, out ShellSettings result)
        {
            if (TryMatchInternal("*." + host, "*." + hostOnly, path, out result))
            {
                return(true);
            }

            var index = -1;

            // Take the longest subdomain and look for a mapping
            while (-1 != (index = host.IndexOf('.', index + 1)))
            {
                if (TryMatchInternal("*" + host.Subsegment(index), "*" + hostOnly.Subsegment(index), path, out result))
                {
                    return(true);
                }
            }

            result = null;
            return(false);
        }
コード例 #2
0
        private bool TryMatchInternal(StringSegment host, StringSegment hostOnly, StringSegment path, out ShellSettings result)
        {
            // 1. Search for Host:Port + Prefix match

            if (host.Length == 0 || !_shellsByHostAndPrefix.TryGetValue(GetHostAndPrefix(host, path), out result))
            {
                // 2. Search for Host + Prefix match

                if (host.Length == hostOnly.Length || !_shellsByHostAndPrefix.TryGetValue(GetHostAndPrefix(hostOnly, path), out result))
                {
                    // 3. Search for Host:Port only match

                    if (host.Length == 0 || !_shellsByHostAndPrefix.TryGetValue(GetHostAndPrefix(host, "/"), out result))
                    {
                        // 4. Search for Host only match

                        if (host.Length == hostOnly.Length || !_shellsByHostAndPrefix.TryGetValue(GetHostAndPrefix(hostOnly, "/"), out result))
                        {
                            // 5. Search for Prefix only match

                            if (!_shellsByHostAndPrefix.TryGetValue(GetHostAndPrefix("", path), out result))
                            {
                                result = null;
                                return(false);
                            }
                        }
                    }
                }
            }

            return(true);
        }
コード例 #3
0
 private bool TryMatchStarMapping(StringSegment host, StringSegment hostOnly, StringSegment path, out ShellSettings result)
 {
     if (this.TryMatchInternal(StringSegment.op_Implicit(string.Concat("*.", host.ToString())), StringSegment.op_Implicit(string.Concat("*.", hostOnly.ToString())), path, out result))
     {
         return(true);
     }
     V_0 = -1;
     do
     {
         stackVariable21 = host.IndexOf('.', V_0 + 1);
         V_0             = stackVariable21;
         if (-1 != stackVariable21)
         {
             continue;
         }
         result = null;
         return(false);
     }while (!this.TryMatchInternal(StringSegment.op_Implicit(string.Concat("*", host.Subsegment(V_0).ToString())), StringSegment.op_Implicit(string.Concat("*", hostOnly.Subsegment(V_0).ToString())), path, out result));
     return(true);
 }
コード例 #4
0
 public bool TryGetSettings(string name, out ShellSettings settings)
 {
     settings = LoadSettings().First();
     return(true);
 }
コード例 #5
0
 public Task UpdateShellSettingsAsync(ShellSettings settings)
 {
     _shellSettingsManager.SaveSettings(settings);
     return(ReloadShellContextAsync(settings));
 }
コード例 #6
0
        public async Task SaveSettingsAsync(ShellSettings settings)
        {
            await _semaphore.WaitAsync();

            try
            {
                await EnsureConfigurationAsync();

                if (settings == null)
                {
                    throw new ArgumentNullException(nameof(settings));
                }

                var configuration = new ConfigurationBuilder()
                                    .AddConfiguration(_configuration)
                                    .AddConfiguration(_configuration.GetSection(settings.Name))
                                    .Build();

                var shellSettings = new ShellSettings()
                {
                    Name = settings.Name
                };

                configuration.Bind(shellSettings);

                var configSettings = JObject.FromObject(shellSettings);
                var tenantSettings = JObject.FromObject(settings);

                foreach (var property in configSettings)
                {
                    var tenantValue = tenantSettings.Value <string>(property.Key);
                    var configValue = configSettings.Value <string>(property.Key);

                    if (tenantValue != configValue)
                    {
                        tenantSettings[property.Key] = tenantValue;
                    }
                    else
                    {
                        tenantSettings[property.Key] = null;
                    }
                }

                tenantSettings.Remove("Name");

                await _settingsSources.SaveAsync(settings.Name, tenantSettings.ToObject <Dictionary <string, string> >());

                var tenantConfig = new JObject();

                var sections = settings.ShellConfiguration.GetChildren()
                               .Where(s => !s.GetChildren().Any())
                               .ToArray();

                foreach (var section in sections)
                {
                    if (settings[section.Key] != configuration[section.Key])
                    {
                        tenantConfig[section.Key] = settings[section.Key];
                    }
                    else
                    {
                        tenantConfig[section.Key] = null;
                    }
                }

                tenantConfig.Remove("Name");

                await _tenantConfigSemaphore.WaitAsync();

                try
                {
                    await _tenantConfigSources.SaveAsync(settings.Name, tenantConfig.ToObject <Dictionary <string, string> >());
                }
                finally
                {
                    _tenantConfigSemaphore.Release();
                }
            }
            finally
            {
                _semaphore.Release();
            }
        }
コード例 #7
0
 public void UpdateShellSettings(ShellSettings settings)
 {
     _shellSettingsManager.SaveSettings(settings);
     ReloadShellContext(settings);
 }
コード例 #8
0
 public async Task <IServiceScope> GetScopeAsync(ShellSettings settings)
 {
     return((await GetScopeAndContextAsync(settings)).Scope);
 }
コード例 #9
0
        private bool TryMatchInternal(string host, string appRelativePath, bool fallbackToDefault, out ShellSettings result)
        {
            // We can skip some checks for port matching if we know the host doesn't contain one
            var hasPort = host.Contains(':');

            // 1. Search for Host:Port + Prefix match

            if (!hasPort || !_shellsByHostAndPrefix.TryGetValue(GetHostAndPrefix(host, appRelativePath, true), out result))
            {
                // 2. Search for Host + Prefix match

                if (!_shellsByHostAndPrefix.TryGetValue(GetHostAndPrefix(host, appRelativePath, false), out result))
                {
                    // 3. Search for Host:Port only match

                    if (!hasPort || !_shellsByHostAndPrefix.TryGetValue(GetHostAndPrefix(host, "/", true), out result))
                    {
                        // 4. Search for Host only match

                        if (!_shellsByHostAndPrefix.TryGetValue(GetHostAndPrefix(host, "/", false), out result))
                        {
                            // 5. Search for Prefix only match

                            if (!_shellsByHostAndPrefix.TryGetValue(GetHostAndPrefix("", appRelativePath, false), out result))
                            {
                                result = null;
                                return(false);
                            }
                        }
                    }
                }
            }

            return(true);
        }
コード例 #10
0
 public Task ChangedAsync(ShellDescriptor descriptor, ShellSettings settings)
 {
     return(this.ReleaseShellContextAsync(settings));
 }
コード例 #11
0
        private bool TryMatchStarMapping(string host, string appRelativePath, bool fallbackToDefault, out ShellSettings result)
        {
            if (TryMatchInternal("*." + host, appRelativePath, fallbackToDefault, out result))
            {
                return(true);
            }

            var index = -1;

            // Take the longest subdomain and look for a mapping
            while (-1 != (index = host.IndexOf('.', index + 1)))
            {
                if (TryMatchInternal("*" + host.Substring(index), appRelativePath, fallbackToDefault, out result))
                {
                    return(true);
                }
            }

            result = null;
            return(false);
        }
コード例 #12
0
 public Task SaveSettingsAsync(ShellSettings shellSettings)
 {
     return(Task.get_CompletedTask());
 }
コード例 #13
0
 public Task <IEnumerable <ShellSettings> > LoadSettingsAsync()
 {
     stackVariable1    = new ShellSettings[1];
     stackVariable1[0] = this.CreateDefaultSettings();
     return(Task.FromResult <IEnumerable <ShellSettings> >(stackVariable1.AsEnumerable <ShellSettings>()));
 }
コード例 #14
0
        public async Task UpdateShellSettingsAsync(ShellSettings settings)
        {
            await _shellSettingsManager.SaveSettingsAsync(settings);

            await ReloadShellContextAsync(settings);
        }
コード例 #15
0
 public Task SaveSettingsAsync(ShellSettings shellSettings) => Task.CompletedTask;
コード例 #16
0
 public void SaveSettings(ShellSettings shellSettings)
 {
 }
コード例 #17
0
ファイル: ShellHost.cs プロジェクト: petedavis/OrchardCore
 /// <summary>
 /// A feature is enabled / disabled, the tenant needs to be released so that a new shell will be built.
 /// </summary>
 public Task ChangedAsync(ShellDescriptor descriptor, ShellSettings settings)
 => ReleaseShellContextAsync(settings);
コード例 #18
0
        public async Task <(IServiceScope Scope, ShellContext ShellContext)> GetScopeAndContextAsync(ShellSettings settings)
        {
            IServiceScope scope        = null;
            ShellContext  shellContext = null;

            while (scope == null)
            {
                if (!_shellContexts.TryGetValue(settings.Name, out shellContext))
                {
                    shellContext = await GetOrCreateShellContextAsync(settings);
                }

                // We create a scope before checking if the shell has been released.
                scope = shellContext.CreateScope();

                // If CreateScope() returned null, the shell is released. We then remove it and
                // retry with the hope to get one that won't be released before we create a scope.
                if (scope == null)
                {
                    // If the context is released, it is removed from the dictionary so that
                    // a new call on 'GetScope' will recreate a new shell context.
                    _shellContexts.TryRemove(settings.Name, out var value);
                }
            }

            return(scope, shellContext);
        }
コード例 #19
0
ファイル: ShellHost.cs プロジェクト: petedavis/OrchardCore
        /// <summary>
        /// Reloads the settings and releases the shell so that a new one will be
        /// built for subsequent requests, while existing requests get flushed.
        /// </summary>
        /// <param name="settings">The <see cref="ShellSettings"/> to reload.</param>
        /// <param name="eventSource">
        /// Whether the related <see cref="ShellEvent"/> is invoked.
        /// </param>
        public async Task ReloadShellContextAsync(ShellSettings settings, bool eventSource = true)
        {
            if (ReloadingAsync != null && eventSource && settings.State != TenantState.Initializing)
            {
                foreach (var d in ReloadingAsync.GetInvocationList())
                {
                    await((ShellEvent)d)(settings.Name);
                }
            }

            // A disabled shell still in use will be released by its last scope.
            if (!CanReleaseShell(settings))
            {
                _runningShellTable.Remove(settings);
                return;
            }

            if (settings.State != TenantState.Initializing)
            {
                settings = await _shellSettingsManager.LoadSettingsAsync(settings.Name);
            }

            var count = 0;

            while (count < ReloadShellMaxRetriesCount)
            {
                count++;

                if (_shellContexts.TryRemove(settings.Name, out var context))
                {
                    _runningShellTable.Remove(settings);
                    context.Release();
                }

                // Add a 'PlaceHolder' allowing to retrieve the settings until the shell will be rebuilt.
                if (!_shellContexts.TryAdd(settings.Name, new ShellContext.PlaceHolder {
                    Settings = settings
                }))
                {
                    // Atomicity: We may have been the last to load the settings but unable to add the shell.
                    continue;
                }

                _shellSettings[settings.Name] = settings;

                if (CanRegisterShell(settings))
                {
                    _runningShellTable.Add(settings);
                }

                if (settings.State == TenantState.Initializing)
                {
                    return;
                }

                var currentVersionId = settings.VersionId;

                settings = await _shellSettingsManager.LoadSettingsAsync(settings.Name);

                // Consistency: We may have been the last to add the shell but not with the last settings.
                if (settings.VersionId == currentVersionId)
                {
                    return;
                }
            }

            throw new ShellHostReloadException(
                      $"Unable to reload the tenant '{settings.Name}' as too many concurrent processes are trying to do so.");
        }
コード例 #20
0
 public ShellSettings(ShellSettings settings)
 {
     _settings      = new ShellConfiguration(settings._settings);
     _configuration = new ShellConfiguration(settings.Name, settings._configuration);
     Name           = settings.Name;
 }
コード例 #21
0
ファイル: ShellHost.cs プロジェクト: petedavis/OrchardCore
 /// <summary>
 /// Tries to retrieve the shell settings associated with the specified tenant.
 /// </summary>
 public bool TryGetSettings(string name, out ShellSettings settings) => _shellSettings.TryGetValue(name, out settings);
コード例 #22
0
 private bool TryMatchInternal(StringSegment host, StringSegment hostOnly, StringSegment path, out ShellSettings result)
 {
     if (host.get_Length() != 0 && this._shellsByHostAndPrefix.TryGetValue(this.GetHostAndPrefix(host, path), out result) || host.get_Length() != hostOnly.get_Length() && this._shellsByHostAndPrefix.TryGetValue(this.GetHostAndPrefix(hostOnly, path), out result) || host.get_Length() != 0 && this._shellsByHostAndPrefix.TryGetValue(this.GetHostAndPrefix(host, StringSegment.op_Implicit("/")), out result) || host.get_Length() != hostOnly.get_Length() && this._shellsByHostAndPrefix.TryGetValue(this.GetHostAndPrefix(hostOnly, StringSegment.op_Implicit("/")), out result) || this._shellsByHostAndPrefix.TryGetValue(this.GetHostAndPrefix(StringSegment.op_Implicit(""), path), out result))
     {
         return(true);
     }
     result = null;
     return(false);
 }
コード例 #23
0
ファイル: ShellHost.cs プロジェクト: petedavis/OrchardCore
 /// <summary>
 /// Whether or not a shell can be released and removed from the list, false if disabled and still in use.
 /// Note: A disabled shell still in use will be released by its last scope, and keeping it in the list
 /// prevents a consumer from creating a new one that would have a null service provider.
 /// </summary>
 private bool CanReleaseShell(ShellSettings settings)
 {
     return(settings.State != TenantState.Disabled || _shellContexts.TryGetValue(settings.Name, out var value) && value.ActiveScopes == 0);
 }
コード例 #24
0
        async Task IShellDescriptorManagerEventHandler.ChangedAsync(ShellDescriptor descriptor, ShellSettings settings)
        {
            // deduce and apply state changes involved
            var shellState = await _stateManager.GetShellStateAsync();

            foreach (var feature in descriptor.Features)
            {
                var featureId    = feature.Id;
                var featureState = shellState.Features.SingleOrDefault(f => f.Id == featureId);
                if (featureState == null)
                {
                    featureState = new ShellFeatureState
                    {
                        Id = featureId
                    };
                }
                if (!featureState.IsInstalled)
                {
                    await _stateManager.UpdateInstalledStateAsync(featureState, ShellFeatureState.State.Rising);
                }
                if (!featureState.IsEnabled)
                {
                    await _stateManager.UpdateEnabledStateAsync(featureState, ShellFeatureState.State.Rising);
                }
            }
            foreach (var featureState in shellState.Features)
            {
                var featureId = featureState.Id;
                if (descriptor.Features.Any(f => f.Id == featureId))
                {
                    continue;
                }
                if (!featureState.IsDisabled)
                {
                    await _stateManager.UpdateEnabledStateAsync(featureState, ShellFeatureState.State.Falling);
                }
            }

            FireApplyChangesIfNeeded();
        }
 public ShellSettingsWithTenants(ShellSettings shellSettings) : base(shellSettings.Configuration)
 {
     Features = shellSettings
                .Configuration
                .Where(x => x.Key.StartsWith("Features") && x.Value != null).Select(x => x.Value).ToArray();
 }