mirror of
https://github.com/MindWorkAI/AI-Studio.git
synced 2026-10-14 13:53:48 +00:00
Add enterprise config support via env vars & Windows registry (#491)
This commit is contained in:
1 parent
b88b78a08e
commit
e8cfce05fe
33 files changed
+1061
-98
No files matched your search
@@ -0,0 +1,75 @@
|
||||
using AIStudio.Tools.PluginSystem;
|
||||
|
||||
namespace AIStudio.Tools.Services;
|
||||
|
||||
public sealed class EnterpriseEnvironmentService(ILogger<TemporaryChatService> logger, RustService rustService) : BackgroundService
|
||||
{
|
||||
public static EnterpriseEnvironment CURRENT_ENVIRONMENT;
|
||||
|
||||
private static readonly TimeSpan CHECK_INTERVAL = TimeSpan.FromMinutes(16);
|
||||
|
||||
#region Overrides of BackgroundService
|
||||
|
||||
protected override async Task ExecuteAsync(CancellationToken stoppingToken)
|
||||
{
|
||||
logger.LogInformation("The enterprise environment service was initialized.");
|
||||
|
||||
await this.StartUpdating();
|
||||
while (!stoppingToken.IsCancellationRequested)
|
||||
{
|
||||
await Task.Delay(CHECK_INTERVAL, stoppingToken);
|
||||
await this.StartUpdating();
|
||||
}
|
||||
}
|
||||
|
||||
#endregion
|
||||
|
||||
private async Task StartUpdating()
|
||||
{
|
||||
try
|
||||
{
|
||||
logger.LogInformation("Starting update of the enterprise environment.");
|
||||
|
||||
var enterpriseRemoveConfigId = await rustService.EnterpriseEnvRemoveConfigId();
|
||||
var isPlugin2RemoveInUse = PluginFactory.AvailablePlugins.Any(plugin => plugin.Id == enterpriseRemoveConfigId);
|
||||
if (enterpriseRemoveConfigId != Guid.Empty && isPlugin2RemoveInUse)
|
||||
{
|
||||
logger.LogWarning($"The enterprise environment configuration ID '{enterpriseRemoveConfigId}' must be removed.");
|
||||
PluginFactory.RemovePluginAsync(enterpriseRemoveConfigId);
|
||||
}
|
||||
|
||||
var enterpriseConfigServerUrl = await rustService.EnterpriseEnvConfigServerUrl();
|
||||
var enterpriseConfigId = await rustService.EnterpriseEnvConfigId();
|
||||
var nextEnterpriseEnvironment = new EnterpriseEnvironment(enterpriseConfigServerUrl, enterpriseConfigId);
|
||||
if (CURRENT_ENVIRONMENT != nextEnterpriseEnvironment)
|
||||
{
|
||||
logger.LogInformation("The enterprise environment has changed. Updating the current environment.");
|
||||
CURRENT_ENVIRONMENT = nextEnterpriseEnvironment;
|
||||
|
||||
switch (enterpriseConfigServerUrl)
|
||||
{
|
||||
case null when enterpriseConfigId == Guid.Empty:
|
||||
logger.LogInformation("AI Studio runs without an enterprise configuration.");
|
||||
break;
|
||||
|
||||
case null:
|
||||
logger.LogWarning($"AI Studio runs with an enterprise configuration id ('{enterpriseConfigId}'), but the configuration server URL is not set.");
|
||||
break;
|
||||
|
||||
case not null when enterpriseConfigId == Guid.Empty:
|
||||
logger.LogWarning($"AI Studio runs with an enterprise configuration server URL ('{enterpriseConfigServerUrl}'), but the configuration ID is not set.");
|
||||
break;
|
||||
|
||||
default:
|
||||
logger.LogInformation($"AI Studio runs with an enterprise configuration id ('{enterpriseConfigId}') and configuration server URL ('{enterpriseConfigServerUrl}').");
|
||||
await PluginFactory.TryDownloadingConfigPluginAsync(enterpriseConfigId, enterpriseConfigServerUrl);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
logger.LogError(e, "An error occurred while updating the enterprise environment.");
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,68 @@
|
||||
namespace AIStudio.Tools.Services;
|
||||
|
||||
public sealed partial class RustService
|
||||
{
|
||||
/// <summary>
|
||||
/// Tries to read the enterprise environment for the current user's configuration ID.
|
||||
/// </summary>
|
||||
/// <returns>
|
||||
/// Returns the empty Guid when the environment is not set or the request fails.
|
||||
/// Otherwise, the configuration ID.
|
||||
/// </returns>
|
||||
public async Task<Guid> EnterpriseEnvConfigId()
|
||||
{
|
||||
var result = await this.http.GetAsync("/system/enterprise/config/id");
|
||||
if (!result.IsSuccessStatusCode)
|
||||
{
|
||||
this.logger!.LogError($"Failed to query the enterprise configuration ID: '{result.StatusCode}'");
|
||||
return Guid.Empty;
|
||||
}
|
||||
|
||||
Guid.TryParse(await result.Content.ReadAsStringAsync(), out var configurationId);
|
||||
return configurationId;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Tries to read the enterprise environment for a configuration ID, which must be removed.
|
||||
/// </summary>
|
||||
/// <remarks>
|
||||
/// Removing a configuration ID is necessary when the user moved to another department or
|
||||
/// left the company, or when the configuration ID is no longer valid.
|
||||
/// </remarks>
|
||||
/// <returns>
|
||||
/// Returns the empty Guid when the environment is not set or the request fails.
|
||||
/// Otherwise, the configuration ID.
|
||||
/// </returns>
|
||||
public async Task<Guid> EnterpriseEnvRemoveConfigId()
|
||||
{
|
||||
var result = await this.http.DeleteAsync("/system/enterprise/config/id");
|
||||
if (!result.IsSuccessStatusCode)
|
||||
{
|
||||
this.logger!.LogError($"Failed to query the enterprise configuration ID for removal: '{result.StatusCode}'");
|
||||
return Guid.Empty;
|
||||
}
|
||||
|
||||
Guid.TryParse(await result.Content.ReadAsStringAsync(), out var configurationId);
|
||||
return configurationId;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Tries to read the enterprise environment for the current user's configuration server URL.
|
||||
/// </summary>
|
||||
/// <returns>
|
||||
/// Returns null when the environment is not set or the request fails.
|
||||
/// Otherwise, the configuration server URL.
|
||||
/// </returns>
|
||||
public async Task<string> EnterpriseEnvConfigServerUrl()
|
||||
{
|
||||
var result = await this.http.GetAsync("/system/enterprise/config/server");
|
||||
if (!result.IsSuccessStatusCode)
|
||||
{
|
||||
this.logger!.LogError($"Failed to query the enterprise configuration server URL: '{result.StatusCode}'");
|
||||
return string.Empty;
|
||||
}
|
||||
|
||||
var serverUrl = await result.Content.ReadAsStringAsync();
|
||||
return string.IsNullOrWhiteSpace(serverUrl) ? string.Empty : serverUrl;
|
||||
}
|
||||
}
|
||||
@@ -3,13 +3,11 @@ using AIStudio.Settings.DataModel;
|
||||
|
||||
namespace AIStudio.Tools.Services;
|
||||
|
||||
public class TemporaryChatService(ILogger<TemporaryChatService> logger, SettingsManager settingsManager) : BackgroundService
|
||||
public sealed class TemporaryChatService(ILogger<TemporaryChatService> logger, SettingsManager settingsManager) : BackgroundService
|
||||
{
|
||||
private static readonly TimeSpan CHECK_INTERVAL = TimeSpan.FromDays(1);
|
||||
private static bool IS_INITIALIZED;
|
||||
|
||||
private readonly ILogger<TemporaryChatService> logger = logger;
|
||||
|
||||
#region Overrides of BackgroundService
|
||||
|
||||
protected override async Task ExecuteAsync(CancellationToken stoppingToken)
|
||||
@@ -17,12 +15,12 @@ public class TemporaryChatService(ILogger<TemporaryChatService> logger, Settings
|
||||
while (!stoppingToken.IsCancellationRequested && !IS_INITIALIZED)
|
||||
await Task.Delay(TimeSpan.FromSeconds(3), stoppingToken);
|
||||
|
||||
this.logger.LogInformation("The temporary chat maintenance service was initialized.");
|
||||
logger.LogInformation("The temporary chat maintenance service was initialized.");
|
||||
|
||||
await settingsManager.LoadSettings();
|
||||
if(settingsManager.ConfigurationData.Workspace.StorageTemporaryMaintenancePolicy is WorkspaceStorageTemporaryMaintenancePolicy.NO_AUTOMATIC_MAINTENANCE)
|
||||
{
|
||||
this.logger.LogWarning("Automatic maintenance of temporary chat storage is disabled. Exiting maintenance service.");
|
||||
logger.LogWarning("Automatic maintenance of temporary chat storage is disabled. Exiting maintenance service.");
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -38,11 +36,11 @@ public class TemporaryChatService(ILogger<TemporaryChatService> logger, Settings
|
||||
|
||||
private Task StartMaintenance()
|
||||
{
|
||||
this.logger.LogInformation("Starting maintenance of temporary chat storage.");
|
||||
logger.LogInformation("Starting maintenance of temporary chat storage.");
|
||||
var temporaryDirectories = Path.Join(SettingsManager.DataDirectory, "tempChats");
|
||||
if(!Directory.Exists(temporaryDirectories))
|
||||
{
|
||||
this.logger.LogWarning("Temporary chat storage directory does not exist. End maintenance.");
|
||||
logger.LogWarning("Temporary chat storage directory does not exist. End maintenance.");
|
||||
return Task.CompletedTask;
|
||||
}
|
||||
|
||||
@@ -67,12 +65,12 @@ public class TemporaryChatService(ILogger<TemporaryChatService> logger, Settings
|
||||
|
||||
if(deleteChat)
|
||||
{
|
||||
this.logger.LogInformation($"Deleting temporary chat storage directory '{tempChatDirPath}' due to maintenance policy.");
|
||||
logger.LogInformation($"Deleting temporary chat storage directory '{tempChatDirPath}' due to maintenance policy.");
|
||||
Directory.Delete(tempChatDirPath, true);
|
||||
}
|
||||
}
|
||||
|
||||
this.logger.LogInformation("Finished maintenance of temporary chat storage.");
|
||||
logger.LogInformation("Finished maintenance of temporary chat storage.");
|
||||
return Task.CompletedTask;
|
||||
}
|
||||
|
||||
|
||||
Reference in new issue
Block a user