From 7e29999bfb9115d327a887c15ee4e57b2f9f5f29 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Peer=20Sch=C3=BCtt?=
<20603780+peerschuett@users.noreply.github.com>
Date: Wed, 9 Jul 2025 16:17:17 +0200
Subject: [PATCH] The template can now be created from an existing thread
---
app/MindWork AI Studio/Chat/ChatThread.cs | 6 +++-
app/MindWork AI Studio/Chat/ContentBlock.cs | 2 +-
.../Components/ChatComponent.razor | 3 +-
.../Components/ChatTemplateSelection.razor | 2 ++
.../Components/ChatTemplateSelection.razor.cs | 17 +++++++++++
.../Dialogs/ChatTemplateDialog.razor.cs | 20 +++++++++++++
.../SettingsDialogChatTemplate.razor.cs | 29 ++++++++++++++++++-
7 files changed, 75 insertions(+), 4 deletions(-)
diff --git a/app/MindWork AI Studio/Chat/ChatThread.cs b/app/MindWork AI Studio/Chat/ChatThread.cs
index c57e5160..c04e729f 100644
--- a/app/MindWork AI Studio/Chat/ChatThread.cs
+++ b/app/MindWork AI Studio/Chat/ChatThread.cs
@@ -68,7 +68,7 @@ public sealed record ChatThread
///
/// The current system prompt for the chat thread.
///
- public string SystemPrompt { get; init; } = string.Empty;
+ public string SystemPrompt { get; set; } = string.Empty;
///
/// The content blocks of the chat thread.
@@ -121,6 +121,10 @@ public sealed record ChatThread
}
}
+ // We need a way to save the changed system prompt in our chatThread.
+ // Otherwise, the chatThread will always tell us that it is using the default system prompt.
+ chatThread.SystemPrompt = systemPromptTextWithChatTemplate;
+
logger.LogInformation(logMessage);
//
diff --git a/app/MindWork AI Studio/Chat/ContentBlock.cs b/app/MindWork AI Studio/Chat/ContentBlock.cs
index a069c3d8..841cad69 100644
--- a/app/MindWork AI Studio/Chat/ContentBlock.cs
+++ b/app/MindWork AI Studio/Chat/ContentBlock.cs
@@ -28,7 +28,7 @@ public class ContentBlock
///
/// Should the content block be hidden from the user?
///
- public bool HideFromUser { get; init; }
+ public bool HideFromUser { get; set; }
public ContentBlock DeepClone() => new()
{
diff --git a/app/MindWork AI Studio/Components/ChatComponent.razor b/app/MindWork AI Studio/Components/ChatComponent.razor
index 66538eda..48420522 100644
--- a/app/MindWork AI Studio/Components/ChatComponent.razor
+++ b/app/MindWork AI Studio/Components/ChatComponent.razor
@@ -81,7 +81,8 @@
}
-
+
+
@if (this.SettingsManager.ConfigurationData.Workspace.StorageBehavior is WorkspaceStorageBehavior.STORE_CHATS_AUTOMATICALLY)
{
diff --git a/app/MindWork AI Studio/Components/ChatTemplateSelection.razor b/app/MindWork AI Studio/Components/ChatTemplateSelection.razor
index 7f9f09cf..624520de 100644
--- a/app/MindWork AI Studio/Components/ChatTemplateSelection.razor
+++ b/app/MindWork AI Studio/Components/ChatTemplateSelection.razor
@@ -18,6 +18,8 @@
+
+
@foreach (var chatTemplate in this.SettingsManager.ConfigurationData.ChatTemplates.GetAllChatTemplates())
{
diff --git a/app/MindWork AI Studio/Components/ChatTemplateSelection.razor.cs b/app/MindWork AI Studio/Components/ChatTemplateSelection.razor.cs
index e624884c..25b72e11 100644
--- a/app/MindWork AI Studio/Components/ChatTemplateSelection.razor.cs
+++ b/app/MindWork AI Studio/Components/ChatTemplateSelection.razor.cs
@@ -1,3 +1,4 @@
+using AIStudio.Chat;
using AIStudio.Dialogs.Settings;
using AIStudio.Settings;
@@ -11,6 +12,12 @@ public partial class ChatTemplateSelection : MSGComponentBase
[Parameter]
public ChatTemplate CurrentChatTemplate { get; set; } = ChatTemplate.NO_CHAT_TEMPLATE;
+ [Parameter]
+ public bool CanChatThreadBeUsedForTemplate { get; set; }
+
+ [Parameter]
+ public ChatThread? CurrentChatThread { get; set; }
+
[Parameter]
public EventCallback CurrentChatTemplateChanged { get; set; }
@@ -36,4 +43,14 @@ public partial class ChatTemplateSelection : MSGComponentBase
var dialogParameters = new DialogParameters();
await this.DialogService.ShowAsync(T("Open Chat Template Options"), dialogParameters, DialogOptions.FULLSCREEN);
}
+
+ private async Task CreateNewChatTemplateFromChat()
+ {
+ var dialogParameters = new DialogParameters
+ {
+ { x => x.CreateTemplateFromExistingChatThread, true },
+ { x => x.ExistingChatThread, this.CurrentChatThread }
+ };
+ await this.DialogService.ShowAsync(T("Open Chat Template Options"), dialogParameters, DialogOptions.FULLSCREEN);
+ }
}
\ No newline at end of file
diff --git a/app/MindWork AI Studio/Dialogs/ChatTemplateDialog.razor.cs b/app/MindWork AI Studio/Dialogs/ChatTemplateDialog.razor.cs
index 7a8b6765..9fb9b52a 100644
--- a/app/MindWork AI Studio/Dialogs/ChatTemplateDialog.razor.cs
+++ b/app/MindWork AI Studio/Dialogs/ChatTemplateDialog.razor.cs
@@ -53,6 +53,12 @@ public partial class ChatTemplateDialog : MSGComponentBase
[Parameter]
public bool AllowProfileUsage { get; set; } = true;
+ [Parameter]
+ public bool CreateFromExistingChatThread { get; set; }
+
+ [Parameter]
+ public ChatThread? ExistingChatThread { get; set; }
+
[Inject]
private ILogger Logger { get; init; } = null!;
@@ -90,6 +96,20 @@ public partial class ChatTemplateDialog : MSGComponentBase
this.dataEditingPreviousName = this.DataName.ToLowerInvariant();
this.dataExampleConversation = this.ExampleConversation.Select(n => n.DeepClone()).ToList();
}
+
+ if (this.CreateFromExistingChatThread)
+ {
+ this.DataSystemPrompt = this.ExistingChatThread!.SystemPrompt;
+ this.dataExampleConversation = this.ExistingChatThread!.Blocks.Select(n => n.DeepClone()).ToList();
+ this.DataName = this.ExistingChatThread!.Name;
+
+ // the contentblocks that we copy are visible to the user, and we don't want to show them while using the template
+ foreach (var item in this.dataExampleConversation)
+ {
+ item.HideFromUser = true;
+ }
+
+ }
await base.OnInitializedAsync();
}
diff --git a/app/MindWork AI Studio/Dialogs/Settings/SettingsDialogChatTemplate.razor.cs b/app/MindWork AI Studio/Dialogs/Settings/SettingsDialogChatTemplate.razor.cs
index 8ca3118a..ac8e10e3 100644
--- a/app/MindWork AI Studio/Dialogs/Settings/SettingsDialogChatTemplate.razor.cs
+++ b/app/MindWork AI Studio/Dialogs/Settings/SettingsDialogChatTemplate.razor.cs
@@ -1,16 +1,43 @@
+using AIStudio.Chat;
using AIStudio.Settings;
+using Microsoft.AspNetCore.Components;
namespace AIStudio.Dialogs.Settings;
public partial class SettingsDialogChatTemplate : SettingsDialogBase
{
+
+ [Parameter]
+ public bool CreateTemplateFromExistingChatThread { get; set; }
+
+ [Parameter]
+ public ChatThread? ExistingChatThread { get; set; }
+
+ #region Overrides of ComponentBase
+
+ ///
+ protected override async Task OnInitializedAsync()
+ {
+ await base.OnInitializedAsync();
+ if (this.CreateTemplateFromExistingChatThread)
+ await this.AddChatTemplate();
+ }
+
+ #endregion
+
private async Task AddChatTemplate()
{
var dialogParameters = new DialogParameters
{
{ x => x.IsEditing, false },
};
-
+
+ if (this.CreateTemplateFromExistingChatThread)
+ {
+ dialogParameters.Add(x => x.CreateFromExistingChatThread, this.CreateTemplateFromExistingChatThread);
+ dialogParameters.Add(x => x.ExistingChatThread, this.ExistingChatThread);
+ }
+
var dialogReference = await this.DialogService.ShowAsync(T("Add Chat Template"), dialogParameters, DialogOptions.FULLSCREEN);
var dialogResult = await dialogReference.Result;
if (dialogResult is null || dialogResult.Canceled)