diff --git a/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.Domain.Shared/LINGYUN.Abp.AIManagement.Domain.Shared.csproj b/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.Domain.Shared/LINGYUN.Abp.AIManagement.Domain.Shared.csproj
index 148c75c26..9f7983f9b 100644
--- a/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.Domain.Shared/LINGYUN.Abp.AIManagement.Domain.Shared.csproj
+++ b/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.Domain.Shared/LINGYUN.Abp.AIManagement.Domain.Shared.csproj
@@ -14,6 +14,11 @@
+
+
+
+
+
diff --git a/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.Domain.Shared/LINGYUN/Abp/AIManagement/Localization/Resources/en.json b/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.Domain.Shared/LINGYUN/Abp/AIManagement/Localization/Resources/en.json
index a9c8dcc3f..d29ec98c1 100644
--- a/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.Domain.Shared/LINGYUN/Abp/AIManagement/Localization/Resources/en.json
+++ b/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.Domain.Shared/LINGYUN/Abp/AIManagement/Localization/Resources/en.json
@@ -1,5 +1,7 @@
{
"culture": "en",
"texts": {
+ "DisplayName:MaxLatestHistoryMessagesToKeep": "Carry the recent conversation records",
+ "Description:MaxLatestHistoryMessagesToKeep": "When a user initiates a conversation with a large model, the upper limit of the user's recent conversation history that is carried along."
}
}
\ No newline at end of file
diff --git a/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.Domain.Shared/LINGYUN/Abp/AIManagement/Localization/Resources/zh-Hans.json b/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.Domain.Shared/LINGYUN/Abp/AIManagement/Localization/Resources/zh-Hans.json
index c5ad81326..6eb63499b 100644
--- a/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.Domain.Shared/LINGYUN/Abp/AIManagement/Localization/Resources/zh-Hans.json
+++ b/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.Domain.Shared/LINGYUN/Abp/AIManagement/Localization/Resources/zh-Hans.json
@@ -1,5 +1,7 @@
{
"culture": "zh-Hans",
"texts": {
+ "DisplayName:MaxLatestHistoryMessagesToKeep": "携带最近对话记录",
+ "Description:MaxLatestHistoryMessagesToKeep": "用户发起与大模型对话时,携带用户最近对话记录的上限."
}
}
\ No newline at end of file
diff --git a/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.Domain.Shared/LINGYUN/Abp/AIManagement/Messages/UserMessageRecordConsts.cs b/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.Domain.Shared/LINGYUN/Abp/AIManagement/Messages/UserMessageRecordConsts.cs
new file mode 100644
index 000000000..e51d5365a
--- /dev/null
+++ b/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.Domain.Shared/LINGYUN/Abp/AIManagement/Messages/UserMessageRecordConsts.cs
@@ -0,0 +1,5 @@
+namespace LINGYUN.Abp.AIManagement.Messages;
+public static class UserMessageRecordConsts
+{
+ public static int MaxConversationIdLength { get; set; } = 64;
+}
diff --git a/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.Domain.Shared/LINGYUN/Abp/AIManagement/Messages/UserTextMessageRecordConsts.cs b/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.Domain.Shared/LINGYUN/Abp/AIManagement/Messages/UserTextMessageRecordConsts.cs
new file mode 100644
index 000000000..184b93ab0
--- /dev/null
+++ b/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.Domain.Shared/LINGYUN/Abp/AIManagement/Messages/UserTextMessageRecordConsts.cs
@@ -0,0 +1,5 @@
+namespace LINGYUN.Abp.AIManagement.Messages;
+public static class UserTextMessageRecordConsts
+{
+ public static int MaxContentLength { get; set; } = 1024;
+}
diff --git a/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.Domain/LINGYUN.Abp.AIManagement.Domain.csproj b/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.Domain/LINGYUN.Abp.AIManagement.Domain.csproj
index 3a58fe260..2cc7884dc 100644
--- a/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.Domain/LINGYUN.Abp.AIManagement.Domain.csproj
+++ b/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.Domain/LINGYUN.Abp.AIManagement.Domain.csproj
@@ -18,6 +18,7 @@
+
diff --git a/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.Domain/LINGYUN/Abp/AIManagement/AbpAIManagementDomainMappers.cs b/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.Domain/LINGYUN/Abp/AIManagement/AbpAIManagementDomainMappers.cs
new file mode 100644
index 000000000..1993a46f5
--- /dev/null
+++ b/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.Domain/LINGYUN/Abp/AIManagement/AbpAIManagementDomainMappers.cs
@@ -0,0 +1,15 @@
+using LINGYUN.Abp.AI.Models;
+using LINGYUN.Abp.AIManagement.Messages;
+using Riok.Mapperly.Abstractions;
+using Volo.Abp.Mapperly;
+using Volo.Abp.ObjectExtending;
+
+namespace LINGYUN.Abp.AIManagement;
+
+[Mapper(RequiredMappingStrategy = RequiredMappingStrategy.Target)]
+[MapExtraProperties(DefinitionChecks = MappingPropertyDefinitionChecks.None)]
+public partial class UserTextMessageRecordToUserTextMessageMapper : MapperBase
+{
+ public override partial UserTextMessage Map(UserTextMessageRecord source);
+ public override partial void Map(UserTextMessageRecord source, UserTextMessage destination);
+}
diff --git a/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.Domain/LINGYUN/Abp/AIManagement/Messages/IUserTextMessageRecordRepository.cs b/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.Domain/LINGYUN/Abp/AIManagement/Messages/IUserTextMessageRecordRepository.cs
new file mode 100644
index 000000000..6ecb5ab8a
--- /dev/null
+++ b/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.Domain/LINGYUN/Abp/AIManagement/Messages/IUserTextMessageRecordRepository.cs
@@ -0,0 +1,14 @@
+using System;
+using System.Collections.Generic;
+using System.Threading;
+using System.Threading.Tasks;
+using Volo.Abp.Domain.Repositories;
+
+namespace LINGYUN.Abp.AIManagement.Messages;
+public interface IUserTextMessageRecordRepository : IBasicRepository
+{
+ Task> GetHistoryMessagesAsync(
+ string conversationId,
+ int maxResultCount = 0,
+ CancellationToken cancellationToken = default);
+}
diff --git a/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.Domain/LINGYUN/Abp/AIManagement/Messages/UserMessageRecord.cs b/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.Domain/LINGYUN/Abp/AIManagement/Messages/UserMessageRecord.cs
new file mode 100644
index 000000000..559a4f189
--- /dev/null
+++ b/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.Domain/LINGYUN/Abp/AIManagement/Messages/UserMessageRecord.cs
@@ -0,0 +1,69 @@
+using LINGYUN.Abp.AIManagement.Workspaces;
+using System;
+using Volo.Abp;
+using Volo.Abp.Data;
+using Volo.Abp.Domain.Entities.Auditing;
+using Volo.Abp.MultiTenancy;
+
+namespace LINGYUN.Abp.AIManagement.Messages;
+public abstract class UserMessageRecord : AuditedAggregateRoot, IMultiTenant
+{
+ public Guid? TenantId { get; private set; }
+
+ public string Workspace { get; private set; }
+
+ public string? ConversationId { get; private set; }
+
+ public string? ReplyMessage { get; private set; }
+
+ protected UserMessageRecord()
+ {
+ ExtraProperties = new ExtraPropertyDictionary();
+ this.SetDefaultsForExtraProperties();
+ }
+
+ public UserMessageRecord(
+ Guid id,
+ string workspace,
+ Guid? tenantId = null)
+ : base(id)
+ {
+ TenantId = tenantId;
+ Workspace = workspace;
+ }
+
+ public virtual UserMessageRecord WithConversationId(string conversationId)
+ {
+ ConversationId = Check.NotNullOrWhiteSpace(conversationId, nameof(conversationId), UserMessageRecordConsts.MaxConversationIdLength);
+ return this;
+ }
+
+ public virtual UserMessageRecord WithReply(string replyMessage)
+ {
+ ReplyMessage = replyMessage;
+ return this;
+ }
+
+ public void Patch(UserMessageRecord otherMessage)
+ {
+ if (ConversationId != otherMessage.ConversationId)
+ {
+ ConversationId = otherMessage.ConversationId;
+ }
+
+ if (ReplyMessage != otherMessage.ReplyMessage)
+ {
+ ReplyMessage = otherMessage.ReplyMessage;
+ }
+
+ if (!this.HasSameExtraProperties(otherMessage))
+ {
+ ExtraProperties.Clear();
+
+ foreach (var property in otherMessage.ExtraProperties)
+ {
+ ExtraProperties.Add(property.Key, property.Value);
+ }
+ }
+ }
+}
diff --git a/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.Domain/LINGYUN/Abp/AIManagement/Messages/UserMessageStore.cs b/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.Domain/LINGYUN/Abp/AIManagement/Messages/UserMessageStore.cs
new file mode 100644
index 000000000..04dd720a3
--- /dev/null
+++ b/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.Domain/LINGYUN/Abp/AIManagement/Messages/UserMessageStore.cs
@@ -0,0 +1,111 @@
+using LINGYUN.Abp.AI.Messages;
+using LINGYUN.Abp.AI.Models;
+using LINGYUN.Abp.AIManagement.Settings;
+using System;
+using System.Collections.Generic;
+using System.Threading.Tasks;
+using Volo.Abp.DependencyInjection;
+using Volo.Abp.Guids;
+using Volo.Abp.MultiTenancy;
+using Volo.Abp.ObjectMapping;
+using Volo.Abp.Settings;
+
+namespace LINGYUN.Abp.AIManagement.Messages;
+
+[Dependency(ReplaceServices = true)]
+public class UserMessageStore : IUserMessageStore, ITransientDependency
+{
+ private readonly ICurrentTenant _currentTenant;
+ private readonly IGuidGenerator _guidGenerator;
+ private readonly ISettingProvider _settingProvider;
+ private readonly IObjectMapper _objectMapper;
+ private readonly IUserTextMessageRecordRepository _messageRecordRepository;
+
+ public UserMessageStore(
+ ICurrentTenant currentTenant,
+ IGuidGenerator guidGenerator,
+ ISettingProvider settingProvider,
+ IObjectMapper objectMapper,
+ IUserTextMessageRecordRepository messageRecordRepository)
+ {
+ _currentTenant = currentTenant;
+ _guidGenerator = guidGenerator;
+ _settingProvider = settingProvider;
+ _objectMapper = objectMapper;
+ _messageRecordRepository = messageRecordRepository;
+ }
+
+ public async virtual Task> GetHistoryMessagesAsync(string conversationId)
+ {
+ var maxLatestHistoryMessagesToKeep = await _settingProvider.GetAsync(AIManagementSettingNames.UserMessage.MaxLatestHistoryMessagesToKeep, 0);
+ if (maxLatestHistoryMessagesToKeep < 1)
+ {
+ return Array.Empty();
+ }
+
+ var userTextMessages = await _messageRecordRepository.GetHistoryMessagesAsync(conversationId, maxLatestHistoryMessagesToKeep);
+
+ return _objectMapper.Map, IEnumerable>(userTextMessages);
+ }
+
+ public async virtual Task SaveMessageAsync(UserMessage message)
+ {
+ var messageId = message.Id;
+ if (messageId.IsNullOrWhiteSpace())
+ {
+ messageId = _guidGenerator.Create().ToString();
+ message.WithMessageId(messageId);
+ }
+
+ await StoreMessageAsync(Guid.Parse(messageId), message);
+
+ return messageId;
+ }
+
+ protected async virtual Task StoreMessageAsync(Guid messageId, UserMessage message)
+ {
+ switch (message)
+ {
+ case UserTextMessage textMessage:
+ await StoreUserTextMessageAsync(messageId, textMessage);
+ break;
+ }
+ }
+
+ protected async virtual Task StoreUserTextMessageAsync(Guid messageId, UserTextMessage textMessage)
+ {
+ var textMessageRecord = await _messageRecordRepository.FindAsync(messageId);
+ if (textMessageRecord == null)
+ {
+ textMessageRecord = new UserTextMessageRecord(
+ messageId,
+ textMessage.Workspace,
+ textMessage.Content,
+ _currentTenant.Id);
+
+ UpdateUserMessageRecord(textMessageRecord, textMessage);
+
+ await _messageRecordRepository.InsertAsync(textMessageRecord);
+ }
+ else
+ {
+ textMessageRecord.WithContent(textMessage.Content);
+
+ UpdateUserMessageRecord(textMessageRecord, textMessage);
+
+ await _messageRecordRepository.UpdateAsync(textMessageRecord);
+ }
+ }
+
+ private static void UpdateUserMessageRecord(UserMessageRecord messageRecord, UserMessage message)
+ {
+ if (!message.ConversationId.IsNullOrWhiteSpace())
+ {
+ messageRecord.WithConversationId(message.ConversationId);
+ }
+ if (!message.ReplyMessage.IsNullOrWhiteSpace())
+ {
+ messageRecord.WithConversationId(message.ReplyMessage);
+ }
+ }
+}
diff --git a/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.Domain/LINGYUN/Abp/AIManagement/Messages/UserTextMessageRecord.cs b/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.Domain/LINGYUN/Abp/AIManagement/Messages/UserTextMessageRecord.cs
new file mode 100644
index 000000000..874790b9b
--- /dev/null
+++ b/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.Domain/LINGYUN/Abp/AIManagement/Messages/UserTextMessageRecord.cs
@@ -0,0 +1,27 @@
+using System;
+using Volo.Abp;
+
+namespace LINGYUN.Abp.AIManagement.Messages;
+public class UserTextMessageRecord : UserMessageRecord
+{
+ public string Content { get; private set; }
+
+ public UserTextMessageRecord()
+ {
+ }
+
+ public UserTextMessageRecord(
+ Guid id,
+ string workspace,
+ string content,
+ Guid? tenantId = null) : base(id, workspace, tenantId)
+ {
+ WithContent(content);
+ }
+
+ public virtual UserTextMessageRecord WithContent(string content)
+ {
+ Content = Check.NotNullOrWhiteSpace(content, nameof(content), UserTextMessageRecordConsts.MaxContentLength);
+ return this;
+ }
+}
diff --git a/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.Domain/LINGYUN/Abp/AIManagement/Settings/AIManagementSettingDefinitionProvider.cs b/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.Domain/LINGYUN/Abp/AIManagement/Settings/AIManagementSettingDefinitionProvider.cs
new file mode 100644
index 000000000..c862256fc
--- /dev/null
+++ b/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.Domain/LINGYUN/Abp/AIManagement/Settings/AIManagementSettingDefinitionProvider.cs
@@ -0,0 +1,22 @@
+using LINGYUN.Abp.AIManagement.Localization;
+using Volo.Abp.Localization;
+using Volo.Abp.Settings;
+
+namespace LINGYUN.Abp.AIManagement.Settings;
+public class AIManagementSettingDefinitionProvider : SettingDefinitionProvider
+{
+ public override void Define(ISettingDefinitionContext context)
+ {
+ context.Add(
+ new SettingDefinition(
+ AIManagementSettingNames.UserMessage.MaxLatestHistoryMessagesToKeep,
+ defaultValue: "5",
+ displayName: L("DisplayName:MaxLatestHistoryMessagesToKeep"),
+ description: L("Description:MaxLatestHistoryMessagesToKeep")));
+ }
+
+ private static ILocalizableString L(string name)
+ {
+ return LocalizableString.Create(name);
+ }
+}
diff --git a/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.Domain/LINGYUN/Abp/AIManagement/Settings/AIManagementSettingNames.cs b/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.Domain/LINGYUN/Abp/AIManagement/Settings/AIManagementSettingNames.cs
new file mode 100644
index 000000000..3cdb8355d
--- /dev/null
+++ b/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.Domain/LINGYUN/Abp/AIManagement/Settings/AIManagementSettingNames.cs
@@ -0,0 +1,10 @@
+namespace LINGYUN.Abp.AIManagement.Settings;
+public static class AIManagementSettingNames
+{
+ public const string Prefix = "Abp.AIManagement";
+
+ public static class UserMessage
+ {
+ public const string MaxLatestHistoryMessagesToKeep = Prefix + ".MaxLatestHistoryMessagesToKeep";
+ }
+}
diff --git a/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.EntityFrameworkCore/LINGYUN/Abp/AIManagement/EntityFrameworkCore/AIManagementDbContext.cs b/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.EntityFrameworkCore/LINGYUN/Abp/AIManagement/EntityFrameworkCore/AIManagementDbContext.cs
index 790174fb2..865365326 100644
--- a/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.EntityFrameworkCore/LINGYUN/Abp/AIManagement/EntityFrameworkCore/AIManagementDbContext.cs
+++ b/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.EntityFrameworkCore/LINGYUN/Abp/AIManagement/EntityFrameworkCore/AIManagementDbContext.cs
@@ -1,4 +1,5 @@
-using LINGYUN.Abp.AIManagement.Workspaces;
+using LINGYUN.Abp.AIManagement.Messages;
+using LINGYUN.Abp.AIManagement.Workspaces;
using Microsoft.EntityFrameworkCore;
using Volo.Abp.Data;
using Volo.Abp.EntityFrameworkCore;
@@ -8,7 +9,8 @@ namespace LINGYUN.Abp.AIManagement.EntityFrameworkCore;
[ConnectionStringName(AbpAIManagementDbProperties.ConnectionStringName)]
public class AIManagementDbContext : AbpDbContext, IAIManagementDbContext
{
- public DbSet Workspaces { get; set; }
+ public DbSet WorkspaceDefinitions { get; set; }
+ public DbSet UserTextMessageRecords { get; set; }
public AIManagementDbContext(
DbContextOptions options) : base(options)
{
diff --git a/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.EntityFrameworkCore/LINGYUN/Abp/AIManagement/EntityFrameworkCore/AIManagementDbContextModelBuilderExtensions.cs b/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.EntityFrameworkCore/LINGYUN/Abp/AIManagement/EntityFrameworkCore/AIManagementDbContextModelBuilderExtensions.cs
index 46de47d01..181054e54 100644
--- a/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.EntityFrameworkCore/LINGYUN/Abp/AIManagement/EntityFrameworkCore/AIManagementDbContextModelBuilderExtensions.cs
+++ b/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.EntityFrameworkCore/LINGYUN/Abp/AIManagement/EntityFrameworkCore/AIManagementDbContextModelBuilderExtensions.cs
@@ -1,4 +1,5 @@
using JetBrains.Annotations;
+using LINGYUN.Abp.AIManagement.Messages;
using LINGYUN.Abp.AIManagement.Workspaces;
using Microsoft.EntityFrameworkCore;
using Volo.Abp;
@@ -12,6 +13,21 @@ public static class AIManagementDbContextModelBuilderExtensions
{
Check.NotNull(builder, nameof(builder));
+ builder.Entity(b =>
+ {
+ b.ToTable(AbpAIManagementDbProperties.DbTablePrefix + "UserTextMessages", AbpAIManagementDbProperties.DbSchema);
+
+ b.ConfigureByConvention();
+
+ b.Property(x => x.Workspace).HasMaxLength(WorkspaceDefinitionRecordConsts.MaxNameLength).IsRequired();
+ b.Property(x => x.ConversationId).HasMaxLength(UserMessageRecordConsts.MaxConversationIdLength);
+ b.Property(x => x.Content).HasMaxLength(UserTextMessageRecordConsts.MaxContentLength).IsRequired();
+
+ b.HasIndex(x => new { x.TenantId, x.ConversationId });
+
+ b.ApplyObjectExtensionMappings();
+ });
+
if (builder.IsHostDatabase())
{
builder.Entity(b =>
diff --git a/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.EntityFrameworkCore/LINGYUN/Abp/AIManagement/EntityFrameworkCore/AbpAIManagementEntityFrameworkCoreModule.cs b/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.EntityFrameworkCore/LINGYUN/Abp/AIManagement/EntityFrameworkCore/AbpAIManagementEntityFrameworkCoreModule.cs
index 870cad669..0371fb3fd 100644
--- a/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.EntityFrameworkCore/LINGYUN/Abp/AIManagement/EntityFrameworkCore/AbpAIManagementEntityFrameworkCoreModule.cs
+++ b/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.EntityFrameworkCore/LINGYUN/Abp/AIManagement/EntityFrameworkCore/AbpAIManagementEntityFrameworkCoreModule.cs
@@ -1,4 +1,5 @@
-using LINGYUN.Abp.AIManagement.Workspaces;
+using LINGYUN.Abp.AIManagement.Messages;
+using LINGYUN.Abp.AIManagement.Workspaces;
using Microsoft.Extensions.DependencyInjection;
using Volo.Abp.EntityFrameworkCore;
using Volo.Abp.Modularity;
@@ -16,6 +17,8 @@ public class AbpAIManagementEntityFrameworkCoreModule : AbpModule
{
options.AddDefaultRepositories();
+ options.AddRepository();
+
options.AddRepository();
});
}
diff --git a/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.EntityFrameworkCore/LINGYUN/Abp/AIManagement/EntityFrameworkCore/EfCoreUserTextMessageRecordRepository.cs b/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.EntityFrameworkCore/LINGYUN/Abp/AIManagement/EntityFrameworkCore/EfCoreUserTextMessageRecordRepository.cs
new file mode 100644
index 000000000..6d1ddc943
--- /dev/null
+++ b/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.EntityFrameworkCore/LINGYUN/Abp/AIManagement/EntityFrameworkCore/EfCoreUserTextMessageRecordRepository.cs
@@ -0,0 +1,31 @@
+using LINGYUN.Abp.AIManagement.Messages;
+using Microsoft.EntityFrameworkCore;
+using System;
+using System.Collections.Generic;
+using System.Linq;
+using System.Threading;
+using System.Threading.Tasks;
+using Volo.Abp.Domain.Repositories.EntityFrameworkCore;
+using Volo.Abp.EntityFrameworkCore;
+
+namespace LINGYUN.Abp.AIManagement.EntityFrameworkCore;
+public class EfCoreUserTextMessageRecordRepository : EfCoreRepository, IUserTextMessageRecordRepository
+{
+ public EfCoreUserTextMessageRecordRepository(
+ IDbContextProvider dbContextProvider)
+ : base(dbContextProvider)
+ {
+ }
+
+ public async virtual Task> GetHistoryMessagesAsync(
+ string conversationId,
+ int maxResultCount = 0,
+ CancellationToken cancellationToken = default)
+ {
+ return await (await GetQueryableAsync())
+ .Where(x => x.ConversationId == conversationId)
+ .OrderByDescending(x => x.CreationTime)
+ .Take(maxResultCount)
+ .ToListAsync(GetCancellationToken(cancellationToken));
+ }
+}
diff --git a/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.EntityFrameworkCore/LINGYUN/Abp/AIManagement/EntityFrameworkCore/IAIManagementDbContext.cs b/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.EntityFrameworkCore/LINGYUN/Abp/AIManagement/EntityFrameworkCore/IAIManagementDbContext.cs
index 8a6f5fa6f..d253a4aa6 100644
--- a/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.EntityFrameworkCore/LINGYUN/Abp/AIManagement/EntityFrameworkCore/IAIManagementDbContext.cs
+++ b/aspnet-core/modules/ai/LINGYUN.Abp.AIManagement.EntityFrameworkCore/LINGYUN/Abp/AIManagement/EntityFrameworkCore/IAIManagementDbContext.cs
@@ -1,4 +1,5 @@
-using LINGYUN.Abp.AIManagement.Workspaces;
+using LINGYUN.Abp.AIManagement.Messages;
+using LINGYUN.Abp.AIManagement.Workspaces;
using Microsoft.EntityFrameworkCore;
using Volo.Abp.Data;
using Volo.Abp.EntityFrameworkCore;
@@ -8,5 +9,6 @@ namespace LINGYUN.Abp.AIManagement.EntityFrameworkCore;
[ConnectionStringName(AbpAIManagementDbProperties.ConnectionStringName)]
public interface IAIManagementDbContext : IEfCoreDbContext
{
- DbSet Workspaces { get; }
+ DbSet WorkspaceDefinitions { get; }
+ DbSet UserTextMessageRecords { get; }
}