Released plugin system, I18N support, and default language plugins (#488)

This commit is contained in:
Thorsten Sommer 2025-05-31 12:04:58 +02:00 committed by GitHub
parent 437da0fd9b
commit 69610ea908
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
10 changed files with 37 additions and 39 deletions

View File

@ -2281,6 +2281,9 @@ UI_TEXT_CONTENT["AISTUDIO::DIALOGS::DATASOURCEERI_V1DIALOG::T1847791252"] = "Upd
-- Failed to connect to the ERI v1 server. The message was: {0}
UI_TEXT_CONTENT["AISTUDIO::DIALOGS::DATASOURCEERI_V1DIALOG::T2150703468"] = "Failed to connect to the ERI v1 server. The message was: {0}"
-- Failed to load the auth. secret from the operating system. The message was: {0}. You might ignore this message and provide the secret again.
UI_TEXT_CONTENT["AISTUDIO::DIALOGS::DATASOURCEERI_V1DIALOG::T2209069174"] = "Failed to load the auth. secret from the operating system. The message was: {0}. You might ignore this message and provide the secret again."
-- Add
UI_TEXT_CONTENT["AISTUDIO::DIALOGS::DATASOURCEERI_V1DIALOG::T2646845972"] = "Add"

View File

@ -4,14 +4,10 @@
<ExpansionPanel HeaderIcon="@Icons.Material.Filled.Apps" HeaderText="@T("App Options")">
@if (PreviewFeatures.PRE_PLUGINS_2025.IsEnabled(this.SettingsManager))
<ConfigurationSelect OptionDescription="@T("Language behavior")" SelectedValue="@(() => this.SettingsManager.ConfigurationData.App.LanguageBehavior)" Data="@ConfigurationSelectDataFactory.GetLangBehaviorData()" SelectionUpdate="@(selectedValue => _ = this.UpdateLangBehaviour(selectedValue))" OptionHelp="@T("Select the language behavior for the app. The default is to use the system language. You might want to choose a language manually?")"/>
@if (this.SettingsManager.ConfigurationData.App.LanguageBehavior is LangBehavior.MANUAL)
{
<ConfigurationSelect OptionDescription="@T("Language behavior")" SelectedValue="@(() => this.SettingsManager.ConfigurationData.App.LanguageBehavior)" Data="@ConfigurationSelectDataFactory.GetLangBehaviorData()" SelectionUpdate="@(selectedValue => _ = this.UpdateLangBehaviour(selectedValue))" OptionHelp="@T("Select the language behavior for the app. The default is to use the system language. You might want to choose a language manually?")"/>
@if (this.SettingsManager.ConfigurationData.App.LanguageBehavior is LangBehavior.MANUAL)
{
<ConfigurationSelect OptionDescription="@T("Language")" SelectedValue="@(() => this.SettingsManager.ConfigurationData.App.LanguagePluginId)" Data="@ConfigurationSelectDataFactory.GetLanguagesData()" SelectionUpdate="@(selectedValue => _ = this.UpdateManuallySelectedLanguage(selectedValue))" OptionHelp="@T("Select the language for the app.")"/>
}
<ConfigurationSelect OptionDescription="@T("Language")" SelectedValue="@(() => this.SettingsManager.ConfigurationData.App.LanguagePluginId)" Data="@ConfigurationSelectDataFactory.GetLanguagesData()" SelectionUpdate="@(selectedValue => _ = this.UpdateManuallySelectedLanguage(selectedValue))" OptionHelp="@T("Select the language for the app.")"/>
}
<ConfigurationSelect OptionDescription="@T("Color theme")" SelectedValue="@(() => this.SettingsManager.ConfigurationData.App.PreferredTheme)" Data="@ConfigurationSelectDataFactory.GetThemesData()" SelectionUpdate="@(selectedValue => this.SettingsManager.ConfigurationData.App.PreferredTheme = selectedValue)" OptionHelp="@T("Choose the color theme that best suits for you.")"/>

View File

@ -116,7 +116,7 @@ public partial class DataSourceERI_V1Dialog : MSGComponentBase, ISecretId
else
{
this.dataSecret = string.Empty;
this.dataSecretStorageIssue = $"Failed to load the auth. secret from the operating system. The message was: {requestedSecret.Issue}. You might ignore this message and provide the secret again.";
this.dataSecretStorageIssue = string.Format(T("Failed to load the auth. secret from the operating system. The message was: {0}. You might ignore this message and provide the secret again."), requestedSecret.Issue);
await this.form.Validate();
}
}

View File

@ -196,26 +196,22 @@ public partial class MainLayout : LayoutComponentBase, IMessageBusReceiver, ILan
break;
case Event.STARTUP_PLUGIN_SYSTEM:
if(PreviewFeatures.PRE_PLUGINS_2025.IsEnabled(this.SettingsManager))
_ = Task.Run(async () =>
{
_ = Task.Run(async () =>
// Set up the plugin system:
if (PluginFactory.Setup())
{
// Set up the plugin system:
if (PluginFactory.Setup())
{
// Ensure that all internal plugins are present:
await PluginFactory.EnsureInternalPlugins();
// Ensure that all internal plugins are present:
await PluginFactory.EnsureInternalPlugins();
// Load (but not start) all plugins, without waiting for them:
var pluginLoadingTimeout = new CancellationTokenSource(TimeSpan.FromSeconds(5));
await PluginFactory.LoadAll(pluginLoadingTimeout.Token);
// Set up hot reloading for plugins:
PluginFactory.SetUpHotReloading();
}
});
}
// Load (but not start) all plugins, without waiting for them:
var pluginLoadingTimeout = new CancellationTokenSource(TimeSpan.FromSeconds(5));
await PluginFactory.LoadAll(pluginLoadingTimeout.Token);
// Set up hot reloading for plugins:
PluginFactory.SetUpHotReloading();
}
});
break;
case Event.PLUGINS_RELOADED:
@ -246,9 +242,7 @@ public partial class MainLayout : LayoutComponentBase, IMessageBusReceiver, ILan
if (PreviewFeatures.PRE_WRITER_MODE_2024.IsEnabled(this.SettingsManager))
yield return new(T("Writer"), Icons.Material.Filled.Create, palette.DarkLighten, palette.GrayLight, Routes.WRITER, false);
if (PreviewFeatures.PRE_PLUGINS_2025.IsEnabled(this.SettingsManager))
yield return new(T("Plugins"), Icons.Material.TwoTone.Extension, palette.DarkLighten, palette.GrayLight, Routes.PLUGINS, false);
yield return new(T("Plugins"), Icons.Material.TwoTone.Extension, palette.DarkLighten, palette.GrayLight, Routes.PLUGINS, false);
yield return new(T("Supporters"), Icons.Material.Filled.Favorite, palette.Error.Value, "#801a00", Routes.SUPPORTERS, false);
yield return new(T("About"), Icons.Material.Filled.Info, palette.DarkLighten, palette.GrayLight, Routes.ABOUT, false);
yield return new(T("Settings"), Icons.Material.Filled.Settings, palette.DarkLighten, palette.GrayLight, Routes.SETTINGS, false);

View File

@ -51,15 +51,12 @@
}
</MudStack>
@if (PreviewFeatures.PRE_PLUGINS_2025.IsEnabled(this.SettingsManager))
{
<MudText Typo="Typo.h4" Class="mb-2 mr-3 mt-6">
@T("AI Studio Development")
</MudText>
<MudStack Row="@true" Wrap="@Wrap.Wrap" Class="mb-3">
<AssistantBlock TSettings="SettingsDialogI18N" Name="@T("Localization")" Description="@T("Translate AI Studio text content into other languages")" Icon="@Icons.Material.Filled.Translate" Link="@Routes.ASSISTANT_AI_STUDIO_I18N"/>
</MudStack>
}
<MudText Typo="Typo.h4" Class="mb-2 mr-3 mt-6">
@T("AI Studio Development")
</MudText>
<MudStack Row="@true" Wrap="@Wrap.Wrap" Class="mb-3">
<AssistantBlock TSettings="SettingsDialogI18N" Name="@T("Localization")" Description="@T("Translate AI Studio text content into other languages")" Icon="@Icons.Material.Filled.Translate" Link="@Routes.ASSISTANT_AI_STUDIO_I18N"/>
</MudStack>
</InnerScrolling>
</div>

View File

@ -2283,6 +2283,9 @@ UI_TEXT_CONTENT["AISTUDIO::DIALOGS::DATASOURCEERI_V1DIALOG::T1847791252"] = "Akt
-- Failed to connect to the ERI v1 server. The message was: {0}
UI_TEXT_CONTENT["AISTUDIO::DIALOGS::DATASOURCEERI_V1DIALOG::T2150703468"] = "Verbindung zum ERI v1-Server fehlgeschlagen. Die Meldung war: {0}"
-- Failed to load the auth. secret from the operating system. The message was: {0}. You might ignore this message and provide the secret again.
UI_TEXT_CONTENT["AISTUDIO::DIALOGS::DATASOURCEERI_V1DIALOG::T2209069174"] = "Die Information zur Authentifizierung konnte nicht vom Betriebssystem geladen werden. Die Meldung war: {0}. Sie können diese Meldung ignorieren und die Information (z.B. den API-Schlüssel) erneut eingeben."
-- Add
UI_TEXT_CONTENT["AISTUDIO::DIALOGS::DATASOURCEERI_V1DIALOG::T2646845972"] = "Hinzufügen"

View File

@ -2283,6 +2283,9 @@ UI_TEXT_CONTENT["AISTUDIO::DIALOGS::DATASOURCEERI_V1DIALOG::T1847791252"] = "Upd
-- Failed to connect to the ERI v1 server. The message was: {0}
UI_TEXT_CONTENT["AISTUDIO::DIALOGS::DATASOURCEERI_V1DIALOG::T2150703468"] = "Failed to connect to the ERI v1 server. The message was: {0}"
-- Failed to load the auth. secret from the operating system. The message was: {0}. You might ignore this message and provide the secret again.
UI_TEXT_CONTENT["AISTUDIO::DIALOGS::DATASOURCEERI_V1DIALOG::T2209069174"] = "Failed to load the auth. secret from the operating system. The message was: {0}. You might ignore this message and provide the secret again."
-- Add
UI_TEXT_CONTENT["AISTUDIO::DIALOGS::DATASOURCEERI_V1DIALOG::T2646845972"] = "Add"

View File

@ -29,6 +29,8 @@ public static class PreviewFeaturesExtensions
public static bool IsReleased(this PreviewFeatures feature) => feature switch
{
PreviewFeatures.PRE_READ_PDF_2025 => true,
PreviewFeatures.PRE_PLUGINS_2025 => true,
_ => false
};

View File

@ -19,14 +19,12 @@ public static class PreviewVisibilityExtensions
if (visibility >= PreviewVisibility.PROTOTYPE)
{
features.Add(PreviewFeatures.PRE_READ_PDF_2025);
features.Add(PreviewFeatures.PRE_RAG_2024);
}
if (visibility >= PreviewVisibility.EXPERIMENTAL)
{
features.Add(PreviewFeatures.PRE_WRITER_MODE_2024);
features.Add(PreviewFeatures.PRE_PLUGINS_2025);
}
return features;

View File

@ -1,4 +1,6 @@
# v0.9.46, build 221 (2025-06-xx xx:xx UTC)
- We just finished the first version of our plugin system. Right now, there are language plugins to help localize AI Studio. In the future, companies will be able to give their employees a predefined setup through a plugin. Youll also be able to develop custom assistants as plugins. Languages and assistants will be available in public repositories, and AI Studio will have an app-store-like view for easy access. Were proud to have set the foundation with this version.
- Completed the I18N system and made all 1,847 AI Studio text contents localizable.
- AI Studio comes with two standard plugins: one for English (US) and one for German (Germany). When you start AI Studio, it tries to pick the language set on your operating system. If your language isn't supported yet, it uses English instead.
- Added the ability to configure the maximum number of results returned per request for all data sources. Please note that this feature remains in preview and is not visible to all users.
- Added more text content to the I18N system & added the German translation for it.
- Added the Pandoc integration, which enables us to use Pandoc for data processing (e.g., RAG) and for generating files (e.g., Office documents). We thank Nils `nilskruthoff` for the excellent contribution.