From 4eded5360b38d2ec956c83bcc8d47088951aa5e6 Mon Sep 17 00:00:00 2001 From: token <239573049@qq.com> Date: Wed, 20 Mar 2024 02:25:09 +0800 Subject: [PATCH 1/3] =?UTF-8?q?=E5=A2=9E=E5=8A=A0=E5=A4=9A=E6=A8=A1?= =?UTF-8?q?=E5=9E=8B=E9=80=82=E9=85=8D?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../ChatApplication/Dto/ChatApplicationDto.cs | 5 + .../Aggregates/ChatApplication.cs | 5 + .../FastWiki.Service/FastWiki.Service.csproj | 13 +- .../20240319175703_AddChatType.Designer.cs | 477 ++++++++++++++++++ .../Migrations/20240319175703_AddChatType.cs | 50 ++ .../Migrations/WikiDbContextModelSnapshot.cs | 16 +- src/Service/FastWiki.Service/Program.cs | 15 +- .../FastWiki.Service/Service/ModuleService.cs | 37 ++ .../FastWiki.Service/Service/OpenAIService.cs | 44 +- 9 files changed, 631 insertions(+), 31 deletions(-) create mode 100644 src/Service/FastWiki.Service/Migrations/20240319175703_AddChatType.Designer.cs create mode 100644 src/Service/FastWiki.Service/Migrations/20240319175703_AddChatType.cs create mode 100644 src/Service/FastWiki.Service/Service/ModuleService.cs diff --git a/src/Contracts/FastWiki.Service.Contracts/ChatApplication/Dto/ChatApplicationDto.cs b/src/Contracts/FastWiki.Service.Contracts/ChatApplication/Dto/ChatApplicationDto.cs index 9dcb6243..2d1b0b2f 100644 --- a/src/Contracts/FastWiki.Service.Contracts/ChatApplication/Dto/ChatApplicationDto.cs +++ b/src/Contracts/FastWiki.Service.Contracts/ChatApplication/Dto/ChatApplicationDto.cs @@ -67,4 +67,9 @@ public class ChatApplicationDto /// 匹配相似度 /// public double Relevancy { get; set; } = 0.4; + + /// + /// AI模型类型 + /// + public string ChatType { get; set; } } \ No newline at end of file diff --git a/src/Service/FastWiki.Service/Domain/ChatApplications/Aggregates/ChatApplication.cs b/src/Service/FastWiki.Service/Domain/ChatApplications/Aggregates/ChatApplication.cs index a1835e48..b968e7a1 100644 --- a/src/Service/FastWiki.Service/Domain/ChatApplications/Aggregates/ChatApplication.cs +++ b/src/Service/FastWiki.Service/Domain/ChatApplications/Aggregates/ChatApplication.cs @@ -101,4 +101,9 @@ 利用微软Semantic Kernel进行深度学习和自然语言处理,结合.NET /// 显示引用文件 /// public bool ShowSourceFile { get; set; } + + /// + /// AI模型类型 + /// + public string ChatType { get; set; } } \ No newline at end of file diff --git a/src/Service/FastWiki.Service/FastWiki.Service.csproj b/src/Service/FastWiki.Service/FastWiki.Service.csproj index 868fee94..4f4f404a 100644 --- a/src/Service/FastWiki.Service/FastWiki.Service.csproj +++ b/src/Service/FastWiki.Service/FastWiki.Service.csproj @@ -30,16 +30,19 @@ - - - - - + + + + + + + + diff --git a/src/Service/FastWiki.Service/Migrations/20240319175703_AddChatType.Designer.cs b/src/Service/FastWiki.Service/Migrations/20240319175703_AddChatType.Designer.cs new file mode 100644 index 00000000..fc1d7175 --- /dev/null +++ b/src/Service/FastWiki.Service/Migrations/20240319175703_AddChatType.Designer.cs @@ -0,0 +1,477 @@ +// +using System; +using FastWiki.Service.DataAccess; +using Microsoft.EntityFrameworkCore; +using Microsoft.EntityFrameworkCore.Infrastructure; +using Microsoft.EntityFrameworkCore.Migrations; +using Microsoft.EntityFrameworkCore.Storage.ValueConversion; +using Npgsql.EntityFrameworkCore.PostgreSQL.Metadata; + +#nullable disable + +namespace FastWiki.Service.Migrations +{ + [DbContext(typeof(WikiDbContext))] + [Migration("20240319175703_AddChatType")] + partial class AddChatType + { + /// + protected override void BuildTargetModel(ModelBuilder modelBuilder) + { +#pragma warning disable 612, 618 + modelBuilder + .HasAnnotation("ProductVersion", "8.0.0") + .HasAnnotation("Relational:MaxIdentifierLength", 63); + + NpgsqlModelBuilderExtensions.UseIdentityByDefaultColumns(modelBuilder); + + modelBuilder.Entity("FastWiki.Service.Domain.ChatApplications.Aggregates.ChatApplication", b => + { + b.Property("Id") + .HasColumnType("text"); + + b.Property("ChatModel") + .IsRequired() + .HasColumnType("text"); + + b.Property("ChatType") + .IsRequired() + .HasColumnType("text"); + + b.Property("CreationTime") + .HasColumnType("timestamp without time zone"); + + b.Property("Creator") + .HasColumnType("uuid"); + + b.Property("IsDeleted") + .HasColumnType("boolean"); + + b.Property("MaxResponseToken") + .HasColumnType("integer"); + + b.Property("ModificationTime") + .HasColumnType("timestamp without time zone"); + + b.Property("Modifier") + .HasColumnType("uuid"); + + b.Property("Name") + .IsRequired() + .HasColumnType("text"); + + b.Property("NoReplyFoundTemplate") + .HasColumnType("text"); + + b.Property("Opener") + .IsRequired() + .HasColumnType("text"); + + b.Property("Parameter") + .IsRequired() + .HasColumnType("text"); + + b.Property("Prompt") + .IsRequired() + .HasColumnType("text"); + + b.Property("ReferenceUpperLimit") + .HasColumnType("integer"); + + b.Property("Relevancy") + .HasColumnType("double precision"); + + b.Property("ShowSourceFile") + .HasColumnType("boolean"); + + b.Property("Temperature") + .HasColumnType("double precision"); + + b.Property("Template") + .IsRequired() + .HasColumnType("text"); + + b.Property("WikiIds") + .IsRequired() + .HasColumnType("text"); + + b.HasKey("Id"); + + b.HasIndex("Name"); + + b.ToTable("wiki-chat-application", (string)null); + }); + + modelBuilder.Entity("FastWiki.Service.Domain.ChatApplications.Aggregates.ChatDialog", b => + { + b.Property("Id") + .HasColumnType("text"); + + b.Property("ApplicationId") + .IsRequired() + .HasColumnType("text"); + + b.Property("ChatId") + .HasColumnType("text"); + + b.Property("CreationTime") + .HasColumnType("timestamp without time zone"); + + b.Property("Creator") + .HasColumnType("uuid"); + + b.Property("Description") + .IsRequired() + .HasColumnType("text"); + + b.Property("IsDeleted") + .HasColumnType("boolean"); + + b.Property("ModificationTime") + .HasColumnType("timestamp without time zone"); + + b.Property("Modifier") + .HasColumnType("uuid"); + + b.Property("Name") + .IsRequired() + .HasColumnType("text"); + + b.Property("Type") + .HasColumnType("integer"); + + b.HasKey("Id"); + + b.HasIndex("ChatId"); + + b.ToTable("wiki-chat-dialog", (string)null); + }); + + modelBuilder.Entity("FastWiki.Service.Domain.ChatApplications.Aggregates.ChatDialogHistory", b => + { + b.Property("Id") + .HasColumnType("text"); + + b.Property("ChatDialogId") + .IsRequired() + .HasColumnType("text"); + + b.Property("Content") + .IsRequired() + .HasMaxLength(-1) + .HasColumnType("text"); + + b.Property("CreationTime") + .HasColumnType("timestamp without time zone"); + + b.Property("Creator") + .HasColumnType("uuid"); + + b.Property("Current") + .HasColumnType("boolean"); + + b.Property("IsDeleted") + .HasColumnType("boolean"); + + b.Property("ModificationTime") + .HasColumnType("timestamp without time zone"); + + b.Property("Modifier") + .HasColumnType("uuid"); + + b.Property("ReferenceFile") + .IsRequired() + .HasColumnType("text"); + + b.Property("TokenConsumption") + .HasColumnType("integer"); + + b.Property("Type") + .HasColumnType("integer"); + + b.HasKey("Id"); + + b.HasIndex("ChatDialogId"); + + b.HasIndex("Creator"); + + b.ToTable("wiki-chat-dialog-history", (string)null); + }); + + modelBuilder.Entity("FastWiki.Service.Domain.ChatApplications.Aggregates.ChatShare", b => + { + b.Property("Id") + .HasColumnType("text"); + + b.Property("APIKey") + .HasColumnType("text"); + + b.Property("AvailableQuantity") + .HasColumnType("integer"); + + b.Property("AvailableToken") + .HasColumnType("bigint"); + + b.Property("ChatApplicationId") + .IsRequired() + .HasColumnType("text"); + + b.Property("CreationTime") + .HasColumnType("timestamp without time zone"); + + b.Property("Creator") + .HasColumnType("uuid"); + + b.Property("Expires") + .HasColumnType("timestamp without time zone"); + + b.Property("ModificationTime") + .HasColumnType("timestamp without time zone"); + + b.Property("Modifier") + .HasColumnType("uuid"); + + b.Property("Name") + .IsRequired() + .HasColumnType("text"); + + b.Property("UsedToken") + .HasColumnType("bigint"); + + b.HasKey("Id"); + + b.HasIndex("ChatApplicationId"); + + b.ToTable("wiki-chat-share", (string)null); + }); + + modelBuilder.Entity("FastWiki.Service.Domain.Storage.Aggregates.FileStorage", b => + { + b.Property("Id") + .ValueGeneratedOnAdd() + .HasColumnType("bigint"); + + NpgsqlPropertyBuilderExtensions.UseIdentityByDefaultColumn(b.Property("Id")); + + b.Property("CreationTime") + .HasColumnType("timestamp without time zone"); + + b.Property("Creator") + .HasColumnType("uuid"); + + b.Property("FullName") + .IsRequired() + .HasColumnType("text"); + + b.Property("IsCompression") + .HasColumnType("boolean"); + + b.Property("IsDeleted") + .HasColumnType("boolean"); + + b.Property("ModificationTime") + .HasColumnType("timestamp without time zone"); + + b.Property("Modifier") + .HasColumnType("uuid"); + + b.Property("Name") + .IsRequired() + .HasMaxLength(100) + .HasColumnType("character varying(100)"); + + b.Property("Path") + .IsRequired() + .HasMaxLength(200) + .HasColumnType("character varying(200)"); + + b.Property("Size") + .HasColumnType("bigint"); + + b.HasKey("Id"); + + b.ToTable("wiki-file-storages", (string)null); + }); + + modelBuilder.Entity("FastWiki.Service.Domain.Users.Aggregates.User", b => + { + b.Property("Id") + .ValueGeneratedOnAdd() + .HasColumnType("uuid"); + + b.Property("Account") + .IsRequired() + .HasColumnType("text"); + + b.Property("Avatar") + .IsRequired() + .HasColumnType("text"); + + b.Property("CreationTime") + .HasColumnType("timestamp without time zone"); + + b.Property("Creator") + .HasColumnType("uuid"); + + b.Property("Email") + .IsRequired() + .HasColumnType("text"); + + b.Property("IsDeleted") + .HasColumnType("boolean"); + + b.Property("IsDisable") + .HasColumnType("boolean"); + + b.Property("ModificationTime") + .HasColumnType("timestamp without time zone"); + + b.Property("Modifier") + .HasColumnType("uuid"); + + b.Property("Name") + .IsRequired() + .HasMaxLength(100) + .HasColumnType("character varying(100)"); + + b.Property("Password") + .IsRequired() + .HasMaxLength(100) + .HasColumnType("character varying(100)"); + + b.Property("Phone") + .IsRequired() + .HasColumnType("text"); + + b.Property("Role") + .HasColumnType("integer"); + + b.Property("Salt") + .IsRequired() + .HasColumnType("text"); + + b.HasKey("Id"); + + b.ToTable("wiki-users", (string)null); + + b.HasData( + new + { + Id = new Guid("a899e701-4d58-4809-843f-a024e3bf629c"), + Account = "admin", + Avatar = "https://blog-simple.oss-cn-shenzhen.aliyuncs.com/Avatar.jpg", + CreationTime = new DateTime(2024, 3, 19, 17, 57, 2, 871, DateTimeKind.Utc).AddTicks(3601), + Email = "239573049@qq.com", + IsDeleted = false, + IsDisable = false, + ModificationTime = new DateTime(2024, 3, 19, 17, 57, 2, 871, DateTimeKind.Utc).AddTicks(3603), + Name = "admin", + Password = "2f204309fb0afa4c2bdba7b2904ea10e", + Phone = "13049809673", + Role = 1, + Salt = "ab3b086ec59a45cfbf65398ad8f64fdb" + }); + }); + + modelBuilder.Entity("FastWiki.Service.Domain.Wikis.Aggregates.Wiki", b => + { + b.Property("Id") + .ValueGeneratedOnAdd() + .HasColumnType("bigint"); + + NpgsqlPropertyBuilderExtensions.UseIdentityByDefaultColumn(b.Property("Id")); + + b.Property("CreationTime") + .HasColumnType("timestamp without time zone"); + + b.Property("Creator") + .HasColumnType("uuid"); + + b.Property("EmbeddingModel") + .IsRequired() + .HasColumnType("text"); + + b.Property("Icon") + .IsRequired() + .HasColumnType("text"); + + b.Property("IsDeleted") + .HasColumnType("boolean"); + + b.Property("Model") + .IsRequired() + .HasColumnType("text"); + + b.Property("ModificationTime") + .HasColumnType("timestamp without time zone"); + + b.Property("Modifier") + .HasColumnType("uuid"); + + b.Property("Name") + .IsRequired() + .HasMaxLength(100) + .HasColumnType("character varying(100)"); + + b.HasKey("Id"); + + b.HasIndex("Name"); + + b.ToTable("wiki-wikis", (string)null); + }); + + modelBuilder.Entity("FastWiki.Service.Domain.Wikis.Aggregates.WikiDetail", b => + { + b.Property("Id") + .ValueGeneratedOnAdd() + .HasColumnType("bigint"); + + NpgsqlPropertyBuilderExtensions.UseIdentityByDefaultColumn(b.Property("Id")); + + b.Property("CreationTime") + .HasColumnType("timestamp without time zone"); + + b.Property("Creator") + .HasColumnType("bigint"); + + b.Property("DataCount") + .HasColumnType("integer"); + + b.Property("FileId") + .HasColumnType("bigint"); + + b.Property("FileName") + .IsRequired() + .HasMaxLength(100) + .HasColumnType("character varying(100)"); + + b.Property("ModificationTime") + .HasColumnType("timestamp without time zone"); + + b.Property("Modifier") + .HasColumnType("bigint"); + + b.Property("Path") + .IsRequired() + .HasMaxLength(200) + .HasColumnType("character varying(200)"); + + b.Property("State") + .HasColumnType("integer"); + + b.Property("Type") + .IsRequired() + .HasMaxLength(100) + .HasColumnType("character varying(100)"); + + b.Property("WikiId") + .HasColumnType("bigint"); + + b.HasKey("Id"); + + b.ToTable("wiki-wiki-details", (string)null); + }); +#pragma warning restore 612, 618 + } + } +} diff --git a/src/Service/FastWiki.Service/Migrations/20240319175703_AddChatType.cs b/src/Service/FastWiki.Service/Migrations/20240319175703_AddChatType.cs new file mode 100644 index 00000000..b61fc0ff --- /dev/null +++ b/src/Service/FastWiki.Service/Migrations/20240319175703_AddChatType.cs @@ -0,0 +1,50 @@ +using System; +using Microsoft.EntityFrameworkCore.Migrations; + +#nullable disable + +namespace FastWiki.Service.Migrations +{ + /// + public partial class AddChatType : Migration + { + /// + protected override void Up(MigrationBuilder migrationBuilder) + { + migrationBuilder.DeleteData( + table: "wiki-users", + keyColumn: "Id", + keyValue: new Guid("2bef435d-fe59-4f7a-8a8a-2939c08dbeed")); + + migrationBuilder.AddColumn( + name: "ChatType", + table: "wiki-chat-application", + type: "text", + nullable: false, + defaultValue: ""); + + migrationBuilder.InsertData( + table: "wiki-users", + columns: new[] { "Id", "Account", "Avatar", "CreationTime", "Creator", "Email", "IsDeleted", "IsDisable", "ModificationTime", "Modifier", "Name", "Password", "Phone", "Role", "Salt" }, + values: new object[] { new Guid("a899e701-4d58-4809-843f-a024e3bf629c"), "admin", "https://blog-simple.oss-cn-shenzhen.aliyuncs.com/Avatar.jpg", new DateTime(2024, 3, 19, 17, 57, 2, 871, DateTimeKind.Utc).AddTicks(3601), null, "239573049@qq.com", false, false, new DateTime(2024, 3, 19, 17, 57, 2, 871, DateTimeKind.Utc).AddTicks(3603), null, "admin", "2f204309fb0afa4c2bdba7b2904ea10e", "13049809673", 1, "ab3b086ec59a45cfbf65398ad8f64fdb" }); + } + + /// + protected override void Down(MigrationBuilder migrationBuilder) + { + migrationBuilder.DeleteData( + table: "wiki-users", + keyColumn: "Id", + keyValue: new Guid("a899e701-4d58-4809-843f-a024e3bf629c")); + + migrationBuilder.DropColumn( + name: "ChatType", + table: "wiki-chat-application"); + + migrationBuilder.InsertData( + table: "wiki-users", + columns: new[] { "Id", "Account", "Avatar", "CreationTime", "Creator", "Email", "IsDeleted", "IsDisable", "ModificationTime", "Modifier", "Name", "Password", "Phone", "Role", "Salt" }, + values: new object[] { new Guid("2bef435d-fe59-4f7a-8a8a-2939c08dbeed"), "admin", "https://blog-simple.oss-cn-shenzhen.aliyuncs.com/Avatar.jpg", new DateTime(2024, 3, 14, 17, 52, 13, 176, DateTimeKind.Utc).AddTicks(7297), null, "239573049@qq.com", false, false, new DateTime(2024, 3, 14, 17, 52, 13, 176, DateTimeKind.Utc).AddTicks(7299), null, "admin", "0eae0a1d2cc30beefde867611cb04904", "13049809673", 2, "0c9e851a82e9434085e20cfb3818319a" }); + } + } +} diff --git a/src/Service/FastWiki.Service/Migrations/WikiDbContextModelSnapshot.cs b/src/Service/FastWiki.Service/Migrations/WikiDbContextModelSnapshot.cs index d153e198..7ca50a4a 100644 --- a/src/Service/FastWiki.Service/Migrations/WikiDbContextModelSnapshot.cs +++ b/src/Service/FastWiki.Service/Migrations/WikiDbContextModelSnapshot.cs @@ -31,6 +31,10 @@ protected override void BuildModel(ModelBuilder modelBuilder) .IsRequired() .HasColumnType("text"); + b.Property("ChatType") + .IsRequired() + .HasColumnType("text"); + b.Property("CreationTime") .HasColumnType("timestamp without time zone"); @@ -350,19 +354,19 @@ protected override void BuildModel(ModelBuilder modelBuilder) b.HasData( new { - Id = new Guid("2bef435d-fe59-4f7a-8a8a-2939c08dbeed"), + Id = new Guid("a899e701-4d58-4809-843f-a024e3bf629c"), Account = "admin", Avatar = "https://blog-simple.oss-cn-shenzhen.aliyuncs.com/Avatar.jpg", - CreationTime = new DateTime(2024, 3, 14, 17, 52, 13, 176, DateTimeKind.Utc).AddTicks(7297), + CreationTime = new DateTime(2024, 3, 19, 17, 57, 2, 871, DateTimeKind.Utc).AddTicks(3601), Email = "239573049@qq.com", IsDeleted = false, IsDisable = false, - ModificationTime = new DateTime(2024, 3, 14, 17, 52, 13, 176, DateTimeKind.Utc).AddTicks(7299), + ModificationTime = new DateTime(2024, 3, 19, 17, 57, 2, 871, DateTimeKind.Utc).AddTicks(3603), Name = "admin", - Password = "0eae0a1d2cc30beefde867611cb04904", + Password = "2f204309fb0afa4c2bdba7b2904ea10e", Phone = "13049809673", - Role = 2, - Salt = "0c9e851a82e9434085e20cfb3818319a" + Role = 1, + Salt = "ab3b086ec59a45cfbf65398ad8f64fdb" }); }); diff --git a/src/Service/FastWiki.Service/Program.cs b/src/Service/FastWiki.Service/Program.cs index 3a8d1407..355effc1 100644 --- a/src/Service/FastWiki.Service/Program.cs +++ b/src/Service/FastWiki.Service/Program.cs @@ -1,3 +1,4 @@ +using AIDotNet.OpenAI; using AspNetCoreRateLimit; using FastWiki.Service; using FastWiki.Service.Backgrounds; @@ -27,9 +28,8 @@ builder.Services.Configure(builder.Configuration.GetSection("IpRateLimit")); builder.Services.AddSingleton(); -builder.Services.AddInMemoryRateLimiting(); - -var app = builder.Services.AddCors(options => +builder.Services.AddInMemoryRateLimiting() + .AddCors(options => { options.AddPolicy("AllowAll", builder => builder @@ -96,9 +96,12 @@ .UseUoW() .UseRepository(); }) - .AddResponseCompression() - .AddAutoInject() - .AddServices(builder, option => option.MapHttpMethodsForUnmatched = ["Post"]); + .AddResponseCompression(); + +builder.Services.AddAutoInject(); + + +var app = builder.Services.AddServices(builder, option => option.MapHttpMethodsForUnmatched = ["Post"]); app.Use((async (context, next) => { diff --git a/src/Service/FastWiki.Service/Service/ModuleService.cs b/src/Service/FastWiki.Service/Service/ModuleService.cs new file mode 100644 index 00000000..153c7251 --- /dev/null +++ b/src/Service/FastWiki.Service/Service/ModuleService.cs @@ -0,0 +1,37 @@ +using AIDotNet.Abstractions; +using AIDotNet.OpenAI; +using AIDotNet.SparkDesk; + +namespace FastWiki.Service.Service; + +public sealed class ModuleService : ApplicationService +{ + static ModuleService() + { + ChatServices.Add(OpenAIOptions.ServiceName, new OpenAiService(new OpenAIOptions() + { + Client = new HttpClient(), + })); + + ChatServices.Add(SparkDeskOptions.ServiceName, new SparkDeskService(new SparkDeskOptions())); + } + + /// + /// 获取所有支持的对话类型 + /// + /// + public async Task> GetChatTypes() + => IADNChatCompletionService.ServiceNames; + + private static readonly Dictionary ChatServices = new(); + + public static IADNChatCompletionService GetChatService(string serviceName) + { + if (ChatServices.TryGetValue(serviceName, out var service)) + { + return service; + } + + throw new NotSupportedException($"不支持的对话类型:{serviceName}"); + } +} \ No newline at end of file diff --git a/src/Service/FastWiki.Service/Service/OpenAIService.cs b/src/Service/FastWiki.Service/Service/OpenAIService.cs index 4e20a551..b5ac4e77 100644 --- a/src/Service/FastWiki.Service/Service/OpenAIService.cs +++ b/src/Service/FastWiki.Service/Service/OpenAIService.cs @@ -1,11 +1,13 @@ using System.Text; using System.Text.Json; +using AIDotNet.OpenAI; using FastWiki.Service.Application.Storage.Queries; using FastWiki.Service.Contracts.OpenAI; using FastWiki.Service.Domain.Storage.Aggregates; using FastWiki.Service.Infrastructure; using FastWiki.Service.Infrastructure.Helper; using Microsoft.SemanticKernel.ChatCompletion; +using Microsoft.SemanticKernel.Connectors.OpenAI; namespace FastWiki.Service.Service; @@ -82,13 +84,13 @@ public static async Task Completions(HttpContext context) // 如果chatShareId不存在则返回让下面扣款 getAPIKeyChatShareQuery.Result = chatShareInfoQuery.Result; - + var chatApplicationQuery = new ChatApplicationInfoQuery(chatShareInfoQuery.Result.ChatApplicationId); await eventBus.PublishAsync(chatApplicationQuery); chatApplication = chatApplicationQuery?.Result; - + } else { @@ -177,16 +179,15 @@ public static async Task Completions(HttpContext context) sourceFile.AddRange(fileQuery.Result); } + // 删除最后一个消息 + module.messages.RemoveAt(module.messages.Count - 1); + module.messages.Add(new ChatCompletionRequestMessage() + { + content = prompt, + role = "user" + }); } - // 删除最后一个消息 - module.messages.RemoveAt(module.messages.Count - 1); - module.messages.Add(new ChatCompletionRequestMessage() - { - content = prompt, - role = "user" - }); - // 添加用户输入,并且计算请求token数量 module.messages.ForEach(x => { @@ -229,12 +230,26 @@ public static async Task Completions(HttpContext context) } } - var wikiMemoryService = context.RequestServices.GetRequiredService(); + if (chatApplication.ChatType.IsNullOrEmpty()) + { + // 防止没有设置对话类型 + chatApplication.ChatType = OpenAIOptions.ServiceName; + } + + var chatStream = ModuleService.GetChatService(chatApplication.ChatType); + + var setting = new OpenAIPromptExecutionSettings + { + MaxTokens = chatApplication.MaxResponseToken, + Temperature = chatApplication.Temperature, + ExtensionData = new Dictionary() + }; + setting.ExtensionData.TryAdd(AIDotNet.Abstractions.Constant.API_KEY, OpenAIOption.ChatToken); + setting.ExtensionData.TryAdd(AIDotNet.Abstractions.Constant.API_URL, OpenAIOption.ChatEndpoint); - var chatStream = wikiMemoryService.CreateOpenAIChatCompletionService(chatApplication.ChatModel); var output = new StringBuilder(); - await foreach (var item in chatStream.GetStreamingChatMessageContentsAsync(chatHistory)) + await foreach (var item in chatStream.GetStreamingChatMessageContentsAsync(chatHistory,setting)) { if (item.Content.IsNullOrEmpty()) { @@ -281,7 +296,8 @@ await context.WriteOpenAiResultAsync(item.Content, module.model, Guid.NewGuid(). await eventBus.PublishAsync(chatDialogHistory); #endregion - + + //对于对话扣款 if (getAPIKeyChatShareQuery?.Result != null) { var updateChatShareCommand = new DeductTokenCommand(getAPIKeyChatShareQuery.Result.Id, From c78776742437e2afe035d5ad6ac75c2c9bf077dc Mon Sep 17 00:00:00 2001 From: token <239573049@qq.com> Date: Thu, 21 Mar 2024 02:18:05 +0800 Subject: [PATCH 2/3] =?UTF-8?q?=E5=A2=9E=E5=8A=A0=E6=A8=A1=E5=9E=8B?= =?UTF-8?q?=E7=AE=A1=E7=90=86=E7=95=8C=E9=9D=A2=20=E5=A2=9E=E5=8A=A0?= =?UTF-8?q?=E6=A8=A1=E5=9E=8B=E7=AE=A1=E7=90=86=E8=AE=BE=E8=AE=A1=20?= =?UTF-8?q?=E5=A2=9E=E5=8A=A0=E6=A8=A1=E5=9E=8B=E6=97=A5=E5=BF=97=E8=AE=B0?= =?UTF-8?q?=E5=BD=95=20=E4=BC=98=E5=8C=96=E4=BB=A3=E7=A0=81?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- FastWiki.sln | 21 + .../Dto/UpdateChatApplicationInput.cs | 2 + .../Model/CreateFastModeInput.cs | 36 + .../Model/FastModelDto.cs | 53 + .../Model/Commands/CreateFastModeCommand.cs | 9 + .../Model/Commands/RemoveFastModelCommand.cs | 7 + .../Application/Model/ModelCommandHandler.cs | 28 + .../Application/Model/ModelQueryHandler.cs | 28 + .../Model/Queries/GetModelListQuery.cs | 8 + .../Repositories/Model/FastModelRepository.cs | 48 + .../DataAccess/WikiDbContext.cs | 39 + .../Domain/Model/Aggregates/FastModel.cs | 75 + .../Domain/Model/Aggregates/ModelLogger.cs | 70 + .../Repositories/IFastModelRepository.cs | 36 + .../FastWiki.Service/FastWiki.Service.csproj | 5 +- ...0320172045_AddFastModel_Logger.Designer.cs | 608 +++ .../20240320172045_AddFastModel_Logger.cs | 134 + .../Migrations/WikiDbContextModelSnapshot.cs | 141 +- .../FastWiki.Service/Service/ModelService.cs | 83 + .../FastWiki.Service/Service/ModuleService.cs | 37 - .../FastWiki.Service/Service/OpenAIService.cs | 3 +- web/src/App.tsx | 7 + web/src/components/FastChatInput.tsx | 1 - web/src/layouts/(desktop)/index.tsx | 8 +- web/src/models/index.d.ts | 1 + .../app-detail/feautres/AppDetailInfo.tsx | 32 +- web/src/pages/model/(desktop)/index.tsx | 65 + web/src/pages/model/(mobile)/index.tsx | 7 + web/src/pages/model/features/CreateModel.tsx | 116 + web/src/pages/model/features/ModelList.tsx | 112 + web/src/pages/model/page.tsx | 7 + web/src/services/ModelService.ts | 40 + web/yarn.lock | 4195 +++++++++++++++++ 33 files changed, 6013 insertions(+), 49 deletions(-) create mode 100644 src/Contracts/FastWiki.Service.Contracts/Model/CreateFastModeInput.cs create mode 100644 src/Contracts/FastWiki.Service.Contracts/Model/FastModelDto.cs create mode 100644 src/Service/FastWiki.Service/Application/Model/Commands/CreateFastModeCommand.cs create mode 100644 src/Service/FastWiki.Service/Application/Model/Commands/RemoveFastModelCommand.cs create mode 100644 src/Service/FastWiki.Service/Application/Model/ModelCommandHandler.cs create mode 100644 src/Service/FastWiki.Service/Application/Model/ModelQueryHandler.cs create mode 100644 src/Service/FastWiki.Service/Application/Model/Queries/GetModelListQuery.cs create mode 100644 src/Service/FastWiki.Service/DataAccess/Repositories/Model/FastModelRepository.cs create mode 100644 src/Service/FastWiki.Service/Domain/Model/Aggregates/FastModel.cs create mode 100644 src/Service/FastWiki.Service/Domain/Model/Aggregates/ModelLogger.cs create mode 100644 src/Service/FastWiki.Service/Domain/Model/Repositories/IFastModelRepository.cs create mode 100644 src/Service/FastWiki.Service/Migrations/20240320172045_AddFastModel_Logger.Designer.cs create mode 100644 src/Service/FastWiki.Service/Migrations/20240320172045_AddFastModel_Logger.cs create mode 100644 src/Service/FastWiki.Service/Service/ModelService.cs delete mode 100644 src/Service/FastWiki.Service/Service/ModuleService.cs create mode 100644 web/src/pages/model/(desktop)/index.tsx create mode 100644 web/src/pages/model/(mobile)/index.tsx create mode 100644 web/src/pages/model/features/CreateModel.tsx create mode 100644 web/src/pages/model/features/ModelList.tsx create mode 100644 web/src/pages/model/page.tsx create mode 100644 web/src/services/ModelService.ts create mode 100644 web/yarn.lock diff --git a/FastWiki.sln b/FastWiki.sln index 4ba60a6b..3417cb3b 100644 --- a/FastWiki.sln +++ b/FastWiki.sln @@ -27,6 +27,12 @@ Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Infrastructure", "Infrastru EndProject Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "FastWiki.Infrastructure.Common", "src\Infrastructure\FastWiki.Infrastructure.Common\FastWiki.Infrastructure.Common.csproj", "{0C90BE14-96EC-4E1B-A017-258E36ED6B1C}" EndProject +Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "AIDotNet.Abstractions", "..\AIDotNet.API\src\AIDotNet.Abstractions\AIDotNet.Abstractions.csproj", "{F5FC30A0-5CE7-4D27-BFDA-3E7581D2FC70}" +EndProject +Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "AIDotNet.OpenAI", "..\AIDotNet.API\src\extensions\AIDotNet.OpenAI\AIDotNet.OpenAI.csproj", "{B420B7E3-38AB-445C-8789-E2E0736F46C7}" +EndProject +Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "AIDotNet.SparkDesk", "..\AIDotNet.API\src\extensions\AIDotNet.SparkDesk\AIDotNet.SparkDesk.csproj", "{A45EDC61-1937-4894-B165-CAEFF71230D2}" +EndProject Global GlobalSection(SolutionConfigurationPlatforms) = preSolution Debug|Any CPU = Debug|Any CPU @@ -45,6 +51,18 @@ Global {0C90BE14-96EC-4E1B-A017-258E36ED6B1C}.Debug|Any CPU.Build.0 = Debug|Any CPU {0C90BE14-96EC-4E1B-A017-258E36ED6B1C}.Release|Any CPU.ActiveCfg = Release|Any CPU {0C90BE14-96EC-4E1B-A017-258E36ED6B1C}.Release|Any CPU.Build.0 = Release|Any CPU + {F5FC30A0-5CE7-4D27-BFDA-3E7581D2FC70}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {F5FC30A0-5CE7-4D27-BFDA-3E7581D2FC70}.Debug|Any CPU.Build.0 = Debug|Any CPU + {F5FC30A0-5CE7-4D27-BFDA-3E7581D2FC70}.Release|Any CPU.ActiveCfg = Release|Any CPU + {F5FC30A0-5CE7-4D27-BFDA-3E7581D2FC70}.Release|Any CPU.Build.0 = Release|Any CPU + {B420B7E3-38AB-445C-8789-E2E0736F46C7}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {B420B7E3-38AB-445C-8789-E2E0736F46C7}.Debug|Any CPU.Build.0 = Debug|Any CPU + {B420B7E3-38AB-445C-8789-E2E0736F46C7}.Release|Any CPU.ActiveCfg = Release|Any CPU + {B420B7E3-38AB-445C-8789-E2E0736F46C7}.Release|Any CPU.Build.0 = Release|Any CPU + {A45EDC61-1937-4894-B165-CAEFF71230D2}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {A45EDC61-1937-4894-B165-CAEFF71230D2}.Debug|Any CPU.Build.0 = Debug|Any CPU + {A45EDC61-1937-4894-B165-CAEFF71230D2}.Release|Any CPU.ActiveCfg = Release|Any CPU + {A45EDC61-1937-4894-B165-CAEFF71230D2}.Release|Any CPU.Build.0 = Release|Any CPU EndGlobalSection GlobalSection(SolutionProperties) = preSolution HideSolutionNode = FALSE @@ -56,6 +74,9 @@ Global {EF8AE318-7534-4687-8663-BB6B5F5DE5F2} = {789CE025-90BF-4A37-B13A-9E6CFE9F7F4C} {D6D3A051-B8FE-4356-B582-921A6726ED40} = {2A86D1DF-3A54-483F-9F59-0F2F82ED7834} {0C90BE14-96EC-4E1B-A017-258E36ED6B1C} = {D6D3A051-B8FE-4356-B582-921A6726ED40} + {F5FC30A0-5CE7-4D27-BFDA-3E7581D2FC70} = {D6D3A051-B8FE-4356-B582-921A6726ED40} + {B420B7E3-38AB-445C-8789-E2E0736F46C7} = {D6D3A051-B8FE-4356-B582-921A6726ED40} + {A45EDC61-1937-4894-B165-CAEFF71230D2} = {D6D3A051-B8FE-4356-B582-921A6726ED40} EndGlobalSection GlobalSection(ExtensibilityGlobals) = postSolution SolutionGuid = {C6848D28-988E-4785-AF4D-2554B6E6F9E4} diff --git a/src/Contracts/FastWiki.Service.Contracts/ChatApplication/Dto/UpdateChatApplicationInput.cs b/src/Contracts/FastWiki.Service.Contracts/ChatApplication/Dto/UpdateChatApplicationInput.cs index 8b7877c0..4dd77764 100644 --- a/src/Contracts/FastWiki.Service.Contracts/ChatApplication/Dto/UpdateChatApplicationInput.cs +++ b/src/Contracts/FastWiki.Service.Contracts/ChatApplication/Dto/UpdateChatApplicationInput.cs @@ -6,6 +6,8 @@ public class UpdateChatApplicationInput public string Name { get; set; } + public string ChatType { get; set; } + /// /// 提示词 /// diff --git a/src/Contracts/FastWiki.Service.Contracts/Model/CreateFastModeInput.cs b/src/Contracts/FastWiki.Service.Contracts/Model/CreateFastModeInput.cs new file mode 100644 index 00000000..a64c4e65 --- /dev/null +++ b/src/Contracts/FastWiki.Service.Contracts/Model/CreateFastModeInput.cs @@ -0,0 +1,36 @@ +namespace FastWiki.Service.Contracts.Model; + +public class CreateFastModeInput +{ + public string Name { get; set; } + + /// + /// ģ + /// + public string Type { get; set; } + + /// + /// ģʹַ + /// + public string Url { get; set; } + + /// + /// ģԿ + /// + public string ApiKey { get; set; } + + /// + /// + /// + public string Description { get; set; } + + /// + /// AIֵ֧ģ + /// + public List Models { get; set; } = []; + + /// + /// ȼ + /// + public int Order { get; set; } +} \ No newline at end of file diff --git a/src/Contracts/FastWiki.Service.Contracts/Model/FastModelDto.cs b/src/Contracts/FastWiki.Service.Contracts/Model/FastModelDto.cs new file mode 100644 index 00000000..e30c52bd --- /dev/null +++ b/src/Contracts/FastWiki.Service.Contracts/Model/FastModelDto.cs @@ -0,0 +1,53 @@ +namespace FastWiki.Service.Contracts.Model; + +public class FastModelDto +{ + public string Id { get; set; } + + public string Name { get; set; } + + /// + /// ģ + /// + public string Type { get; set; } + + /// + /// ģʹַ + /// + public string Url { get; set; } + + /// + /// ģԿ + /// + public string ApiKey { get; set; } + + /// + /// + /// + public string Description { get; set; } + + /// + /// AIֵ֧ģ + /// + public List Models { get; set; } = []; + + /// + /// ȼ + /// + public int Order { get; set; } + + /// + /// ʱ + /// + public long TestTime { get; set; } + + /// + /// + /// + public long UsedQuota { get; set; } + + /// + /// + /// + public bool Enable { get; set; } +} \ No newline at end of file diff --git a/src/Service/FastWiki.Service/Application/Model/Commands/CreateFastModeCommand.cs b/src/Service/FastWiki.Service/Application/Model/Commands/CreateFastModeCommand.cs new file mode 100644 index 00000000..a7bc17fc --- /dev/null +++ b/src/Service/FastWiki.Service/Application/Model/Commands/CreateFastModeCommand.cs @@ -0,0 +1,9 @@ +using FastWiki.Service.Contracts.Model; + +namespace FastWiki.Service.Application.Model.Commands; + +/// +/// ģ +/// +/// +public record CreateFastModeCommand(CreateFastModeInput Input) : Command; \ No newline at end of file diff --git a/src/Service/FastWiki.Service/Application/Model/Commands/RemoveFastModelCommand.cs b/src/Service/FastWiki.Service/Application/Model/Commands/RemoveFastModelCommand.cs new file mode 100644 index 00000000..ecde4f2e --- /dev/null +++ b/src/Service/FastWiki.Service/Application/Model/Commands/RemoveFastModelCommand.cs @@ -0,0 +1,7 @@ +namespace FastWiki.Service.Application.Model.Commands; + +/// +/// ɾָģ +/// +/// +public record RemoveFastModelCommand(string Id): Command; \ No newline at end of file diff --git a/src/Service/FastWiki.Service/Application/Model/ModelCommandHandler.cs b/src/Service/FastWiki.Service/Application/Model/ModelCommandHandler.cs new file mode 100644 index 00000000..187b0ae9 --- /dev/null +++ b/src/Service/FastWiki.Service/Application/Model/ModelCommandHandler.cs @@ -0,0 +1,28 @@ +using FastWiki.Service.Application.Model.Commands; +using FastWiki.Service.Domain.Model.Aggregates; +using FastWiki.Service.Domain.Model.Repositories; + +namespace FastWiki.Service.Application.Model; + +public sealed class ModelCommandHandler(IFastModelRepository fastModelRepository) +{ + [EventHandler] + public async Task CreateFastModeAsync(CreateFastModeCommand command) + { + if (await fastModelRepository.ExistAsync(command.Input.Name)) + { + throw new UserFriendlyException("ģѴ"); + } + + var model = new FastModel(command.Input.Name, command.Input.Type, command.Input.Url, command.Input.ApiKey, + command.Input.Description, command.Input.Models, command.Input.Order); + + await fastModelRepository.AddAsync(model); + } + + [EventHandler] + public async Task RemoveFastModelAsync(RemoveFastModelCommand command) + { + await fastModelRepository.RemoveAsync(command.Id); + } +} \ No newline at end of file diff --git a/src/Service/FastWiki.Service/Application/Model/ModelQueryHandler.cs b/src/Service/FastWiki.Service/Application/Model/ModelQueryHandler.cs new file mode 100644 index 00000000..a5c920b4 --- /dev/null +++ b/src/Service/FastWiki.Service/Application/Model/ModelQueryHandler.cs @@ -0,0 +1,28 @@ +using FastWiki.Service.Application.Model.Queries; +using FastWiki.Service.Contracts.Model; +using FastWiki.Service.Domain.Model.Repositories; + +namespace FastWiki.Service.Application.Model; + +public sealed class ModelQueryHandler(IFastModelRepository fastModelRepository) +{ + [EventHandler] + public async Task GetModelListAsync(GetModelListQuery query) + { + var models = await fastModelRepository.GetModelListAsync(query.Keyword, query.Page, query.PageSize); + + var count = await fastModelRepository.GetModelCountAsync(query.Keyword); + + query.Result = new PaginatedListBase + { + Result = models.Select(x => new FastModelDto + { + Id = x.Id, + Name = x.Name, + Type = x.Type, + Description = x.Description + }).ToList(), + Total = count + }; + } +} \ No newline at end of file diff --git a/src/Service/FastWiki.Service/Application/Model/Queries/GetModelListQuery.cs b/src/Service/FastWiki.Service/Application/Model/Queries/GetModelListQuery.cs new file mode 100644 index 00000000..ca61af34 --- /dev/null +++ b/src/Service/FastWiki.Service/Application/Model/Queries/GetModelListQuery.cs @@ -0,0 +1,8 @@ +using FastWiki.Service.Contracts.Model; + +namespace FastWiki.Service.Application.Model.Queries; + +public record GetModelListQuery(string Keyword, int Page, int PageSize) : Query> +{ + public override PaginatedListBase Result { get; set; } +} \ No newline at end of file diff --git a/src/Service/FastWiki.Service/DataAccess/Repositories/Model/FastModelRepository.cs b/src/Service/FastWiki.Service/DataAccess/Repositories/Model/FastModelRepository.cs new file mode 100644 index 00000000..b15669cc --- /dev/null +++ b/src/Service/FastWiki.Service/DataAccess/Repositories/Model/FastModelRepository.cs @@ -0,0 +1,48 @@ +using FastWiki.Service.Domain.Model.Aggregates; +using FastWiki.Service.Domain.Model.Repositories; + +namespace FastWiki.Service.DataAccess.Repositories.Model; + +public sealed class FastModelRepository : Repository, IFastModelRepository +{ + public FastModelRepository(WikiDbContext context, IUnitOfWork unitOfWork) : base(context, unitOfWork) + { + } + + + public async Task> GetModelListAsync(string keyword, int page, int pageSize) + { + var query = CreateModelQuery(keyword); + return await query.Skip((page - 1) * pageSize).Take(pageSize).ToListAsync(); + } + + public async Task GetModelCountAsync(string keyword) + { + var query = CreateModelQuery(keyword); + return await query.LongCountAsync(); + } + + public Task ExistAsync(string name) + { + return Context.FastModels.AsNoTracking().AnyAsync(x => x.Name == name); + } + + public async Task RemoveAsync(string id) + { + var result = await Context.FastModels.Where(x => x.Id == id).ExecuteDeleteAsync(); + + return result > 0; + } + + private IQueryable CreateModelQuery(string keyword) + { + var query = Context.FastModels.AsQueryable(); + if (!string.IsNullOrEmpty(keyword)) + { + query = query.Where(x => + x.Name.Contains(keyword) || x.Type.Contains(keyword) || x.Description.Contains(keyword)); + } + + return query.AsNoTracking(); + } +} \ No newline at end of file diff --git a/src/Service/FastWiki.Service/DataAccess/WikiDbContext.cs b/src/Service/FastWiki.Service/DataAccess/WikiDbContext.cs index 62d80dea..8f4c40c1 100644 --- a/src/Service/FastWiki.Service/DataAccess/WikiDbContext.cs +++ b/src/Service/FastWiki.Service/DataAccess/WikiDbContext.cs @@ -1,5 +1,6 @@ using FastWiki.Service.Domain.Storage.Aggregates; using System.Text.Json; +using FastWiki.Service.Domain.Model.Aggregates; namespace FastWiki.Service.DataAccess; @@ -21,6 +22,10 @@ public class WikiDbContext(MasaDbContextOptions options) : MasaDb public DbSet ChatShares { get; set; } + public DbSet FastModels { get; set; } + + public DbSet ModelLoggers { get; set; } + protected override void OnModelCreatingExecuting(ModelBuilder modelBuilder) { base.OnModelCreatingExecuting(modelBuilder); @@ -126,6 +131,40 @@ private static void ConfigEntities(ModelBuilder modelBuilder) entity.HasIndex(x => x.ChatApplicationId); }); + modelBuilder.Entity(entity => + { + entity.ToTable("wiki-fast-models"); + entity.HasKey(e => e.Id); + + entity.HasIndex(x => x.Name); + entity.HasIndex(x => x.Type); + + entity.Property(e => e.Name).HasMaxLength(30); + entity.Property(e => e.Type).HasMaxLength(100); + entity.Property(e => e.Url).HasMaxLength(200); + entity.Property(e => e.ApiKey).HasMaxLength(100); + entity.Property(e => e.Description).HasMaxLength(200); + entity.Property(e => e.Models).HasMaxLength(-1); + + entity.Property(x => x.Models) + .HasConversion(item => JsonSerializer.Serialize(item, new JsonSerializerOptions()), + item => JsonSerializer.Deserialize>(item, new JsonSerializerOptions())); + }); + + modelBuilder.Entity(entity => + { + entity.ToTable("wiki-model-logger"); + entity.HasKey(e => e.Id); + entity.Property(e => e.Id).ValueGeneratedOnAdd(); + + entity.HasIndex(x => x.FastModelId); + entity.HasIndex(x => x.UserId); + entity.HasIndex(x => x.ApplicationId); + entity.HasIndex(x => x.ApiKey); + entity.HasIndex(x => x.Type); + entity.HasIndex(x => x.CreationTime); + }); + var user = new User("admin", "admin", "Aa123456", "https://blog-simple.oss-cn-shenzhen.aliyuncs.com/Avatar.jpg", "239573049@qq.com", "13049809673", false, RoleType.Admin); diff --git a/src/Service/FastWiki.Service/Domain/Model/Aggregates/FastModel.cs b/src/Service/FastWiki.Service/Domain/Model/Aggregates/FastModel.cs new file mode 100644 index 00000000..445fb2c9 --- /dev/null +++ b/src/Service/FastWiki.Service/Domain/Model/Aggregates/FastModel.cs @@ -0,0 +1,75 @@ +namespace FastWiki.Service.Domain.Model.Aggregates; + +public sealed class FastModel : FullAggregateRoot +{ + public string Name { get; set; } + + /// + /// ģ + /// + public string Type { get; set; } + + /// + /// ģʹַ + /// + public string Url { get; set; } + + /// + /// ģԿ + /// + public string ApiKey { get; set; } + + /// + /// + /// + public string Description { get; set; } + + /// + /// AIֵ֧ģ + /// + public List Models { get; set; } = []; + + /// + /// ȼ + /// + public int Order { get; set; } + + /// + /// ʱ + /// + public long? TestTime { get; set; } + + /// + /// + /// + public long UsedQuota { get; set; } + + /// + /// + /// + public bool Enable { get; private set; } + + protected FastModel() + { + } + + public FastModel(string name, string type, string url, string apiKey, string description, List models, + int order) + { + Id = Guid.NewGuid().ToString("N"); + Name = name; + Type = type; + Url = url; + ApiKey = apiKey; + Description = description; + Models = models; + Order = order; + TestTime = null; + SetEnable(true); + } + + public void SetEnable(bool enable) + { + Enable = enable; + } +} \ No newline at end of file diff --git a/src/Service/FastWiki.Service/Domain/Model/Aggregates/ModelLogger.cs b/src/Service/FastWiki.Service/Domain/Model/Aggregates/ModelLogger.cs new file mode 100644 index 00000000..fc2cca2e --- /dev/null +++ b/src/Service/FastWiki.Service/Domain/Model/Aggregates/ModelLogger.cs @@ -0,0 +1,70 @@ +namespace FastWiki.Service.Domain.Model.Aggregates; + +public sealed class ModelLogger : Entity +{ + public DateTime CreationTime { get; protected set; } + + /// + /// 󶨵ģID + /// + public string FastModelId { get; set; } + + /// + /// ûId + /// + public Guid? UserId { get; set; } + + /// + /// ӦId + /// + public string? ApplicationId { get; set; } + + /// + /// Key + /// + public string ApiKey { get; set; } + + /// + /// ־ + /// + public string Type { get; set; } + + /// + /// ʹģ + /// + public string Model { get; set; } + + /// + /// ʾʹToken + /// + public int PromptCount { get; set; } + + /// + /// ȫʹToken + /// + public int ComplementCount { get; set; } + + /// + /// + /// + public string Description { get; set; } + + protected ModelLogger() + { + } + + public ModelLogger(string fastModelId, Guid? userId, string? applicationId, string apiKey, string type, + string model, int promptCount, int complementCount, string description) + { + FastModelId = fastModelId; + UserId = userId; + ApplicationId = applicationId; + ApiKey = apiKey; + Type = type; + Model = model; + PromptCount = promptCount; + ComplementCount = complementCount; + Description = description; + CreationTime = DateTime.Now; + } +} \ No newline at end of file diff --git a/src/Service/FastWiki.Service/Domain/Model/Repositories/IFastModelRepository.cs b/src/Service/FastWiki.Service/Domain/Model/Repositories/IFastModelRepository.cs new file mode 100644 index 00000000..41453eef --- /dev/null +++ b/src/Service/FastWiki.Service/Domain/Model/Repositories/IFastModelRepository.cs @@ -0,0 +1,36 @@ +using FastWiki.Service.Domain.Model.Aggregates; + +namespace FastWiki.Service.Domain.Model.Repositories; + +public interface IFastModelRepository : IRepository +{ + /// + /// ȡģб + /// + /// + /// + /// + /// + Task> GetModelListAsync(string keyword, int page, int pageSize); + + /// + /// ȡģ + /// + /// + /// + Task GetModelCountAsync(string keyword); + + /// + /// жģǷ + /// + /// + /// + Task ExistAsync(string name); + + /// + /// ɾָģ + /// + /// + /// + Task RemoveAsync(string id); +} \ No newline at end of file diff --git a/src/Service/FastWiki.Service/FastWiki.Service.csproj b/src/Service/FastWiki.Service/FastWiki.Service.csproj index 4f4f404a..c7c5702f 100644 --- a/src/Service/FastWiki.Service/FastWiki.Service.csproj +++ b/src/Service/FastWiki.Service/FastWiki.Service.csproj @@ -40,14 +40,13 @@ - - - + + diff --git a/src/Service/FastWiki.Service/Migrations/20240320172045_AddFastModel_Logger.Designer.cs b/src/Service/FastWiki.Service/Migrations/20240320172045_AddFastModel_Logger.Designer.cs new file mode 100644 index 00000000..0284f6e2 --- /dev/null +++ b/src/Service/FastWiki.Service/Migrations/20240320172045_AddFastModel_Logger.Designer.cs @@ -0,0 +1,608 @@ +// +using System; +using FastWiki.Service.DataAccess; +using Microsoft.EntityFrameworkCore; +using Microsoft.EntityFrameworkCore.Infrastructure; +using Microsoft.EntityFrameworkCore.Migrations; +using Microsoft.EntityFrameworkCore.Storage.ValueConversion; +using Npgsql.EntityFrameworkCore.PostgreSQL.Metadata; + +#nullable disable + +namespace FastWiki.Service.Migrations +{ + [DbContext(typeof(WikiDbContext))] + [Migration("20240320172045_AddFastModel_Logger")] + partial class AddFastModel_Logger + { + /// + protected override void BuildTargetModel(ModelBuilder modelBuilder) + { +#pragma warning disable 612, 618 + modelBuilder + .HasAnnotation("ProductVersion", "8.0.0") + .HasAnnotation("Relational:MaxIdentifierLength", 63); + + NpgsqlModelBuilderExtensions.UseIdentityByDefaultColumns(modelBuilder); + + modelBuilder.Entity("FastWiki.Service.Domain.ChatApplications.Aggregates.ChatApplication", b => + { + b.Property("Id") + .HasColumnType("text"); + + b.Property("ChatModel") + .IsRequired() + .HasColumnType("text"); + + b.Property("ChatType") + .IsRequired() + .HasColumnType("text"); + + b.Property("CreationTime") + .HasColumnType("timestamp without time zone"); + + b.Property("Creator") + .HasColumnType("uuid"); + + b.Property("IsDeleted") + .HasColumnType("boolean"); + + b.Property("MaxResponseToken") + .HasColumnType("integer"); + + b.Property("ModificationTime") + .HasColumnType("timestamp without time zone"); + + b.Property("Modifier") + .HasColumnType("uuid"); + + b.Property("Name") + .IsRequired() + .HasColumnType("text"); + + b.Property("NoReplyFoundTemplate") + .HasColumnType("text"); + + b.Property("Opener") + .IsRequired() + .HasColumnType("text"); + + b.Property("Parameter") + .IsRequired() + .HasColumnType("text"); + + b.Property("Prompt") + .IsRequired() + .HasColumnType("text"); + + b.Property("ReferenceUpperLimit") + .HasColumnType("integer"); + + b.Property("Relevancy") + .HasColumnType("double precision"); + + b.Property("ShowSourceFile") + .HasColumnType("boolean"); + + b.Property("Temperature") + .HasColumnType("double precision"); + + b.Property("Template") + .IsRequired() + .HasColumnType("text"); + + b.Property("WikiIds") + .IsRequired() + .HasColumnType("text"); + + b.HasKey("Id"); + + b.HasIndex("Name"); + + b.ToTable("wiki-chat-application", (string)null); + }); + + modelBuilder.Entity("FastWiki.Service.Domain.ChatApplications.Aggregates.ChatDialog", b => + { + b.Property("Id") + .HasColumnType("text"); + + b.Property("ApplicationId") + .IsRequired() + .HasColumnType("text"); + + b.Property("ChatId") + .HasColumnType("text"); + + b.Property("CreationTime") + .HasColumnType("timestamp without time zone"); + + b.Property("Creator") + .HasColumnType("uuid"); + + b.Property("Description") + .IsRequired() + .HasColumnType("text"); + + b.Property("IsDeleted") + .HasColumnType("boolean"); + + b.Property("ModificationTime") + .HasColumnType("timestamp without time zone"); + + b.Property("Modifier") + .HasColumnType("uuid"); + + b.Property("Name") + .IsRequired() + .HasColumnType("text"); + + b.Property("Type") + .HasColumnType("integer"); + + b.HasKey("Id"); + + b.HasIndex("ChatId"); + + b.ToTable("wiki-chat-dialog", (string)null); + }); + + modelBuilder.Entity("FastWiki.Service.Domain.ChatApplications.Aggregates.ChatDialogHistory", b => + { + b.Property("Id") + .HasColumnType("text"); + + b.Property("ChatDialogId") + .IsRequired() + .HasColumnType("text"); + + b.Property("Content") + .IsRequired() + .HasMaxLength(-1) + .HasColumnType("text"); + + b.Property("CreationTime") + .HasColumnType("timestamp without time zone"); + + b.Property("Creator") + .HasColumnType("uuid"); + + b.Property("Current") + .HasColumnType("boolean"); + + b.Property("IsDeleted") + .HasColumnType("boolean"); + + b.Property("ModificationTime") + .HasColumnType("timestamp without time zone"); + + b.Property("Modifier") + .HasColumnType("uuid"); + + b.Property("ReferenceFile") + .IsRequired() + .HasColumnType("text"); + + b.Property("TokenConsumption") + .HasColumnType("integer"); + + b.Property("Type") + .HasColumnType("integer"); + + b.HasKey("Id"); + + b.HasIndex("ChatDialogId"); + + b.HasIndex("Creator"); + + b.ToTable("wiki-chat-dialog-history", (string)null); + }); + + modelBuilder.Entity("FastWiki.Service.Domain.ChatApplications.Aggregates.ChatShare", b => + { + b.Property("Id") + .HasColumnType("text"); + + b.Property("APIKey") + .HasColumnType("text"); + + b.Property("AvailableQuantity") + .HasColumnType("integer"); + + b.Property("AvailableToken") + .HasColumnType("bigint"); + + b.Property("ChatApplicationId") + .IsRequired() + .HasColumnType("text"); + + b.Property("CreationTime") + .HasColumnType("timestamp without time zone"); + + b.Property("Creator") + .HasColumnType("uuid"); + + b.Property("Expires") + .HasColumnType("timestamp without time zone"); + + b.Property("ModificationTime") + .HasColumnType("timestamp without time zone"); + + b.Property("Modifier") + .HasColumnType("uuid"); + + b.Property("Name") + .IsRequired() + .HasColumnType("text"); + + b.Property("UsedToken") + .HasColumnType("bigint"); + + b.HasKey("Id"); + + b.HasIndex("ChatApplicationId"); + + b.ToTable("wiki-chat-share", (string)null); + }); + + modelBuilder.Entity("FastWiki.Service.Domain.Model.Aggregates.FastModel", b => + { + b.Property("Id") + .HasColumnType("text"); + + b.Property("ApiKey") + .IsRequired() + .HasMaxLength(100) + .HasColumnType("character varying(100)"); + + b.Property("CreationTime") + .HasColumnType("timestamp without time zone"); + + b.Property("Creator") + .HasColumnType("uuid"); + + b.Property("Description") + .IsRequired() + .HasMaxLength(200) + .HasColumnType("character varying(200)"); + + b.Property("Enable") + .HasColumnType("boolean"); + + b.Property("IsDeleted") + .HasColumnType("boolean"); + + b.Property("Models") + .IsRequired() + .HasMaxLength(-1) + .HasColumnType("text"); + + b.Property("ModificationTime") + .HasColumnType("timestamp without time zone"); + + b.Property("Modifier") + .HasColumnType("uuid"); + + b.Property("Name") + .IsRequired() + .HasMaxLength(30) + .HasColumnType("character varying(30)"); + + b.Property("Order") + .HasColumnType("integer"); + + b.Property("TestTime") + .HasColumnType("bigint"); + + b.Property("Type") + .IsRequired() + .HasMaxLength(100) + .HasColumnType("character varying(100)"); + + b.Property("Url") + .IsRequired() + .HasMaxLength(200) + .HasColumnType("character varying(200)"); + + b.Property("UsedQuota") + .HasColumnType("bigint"); + + b.HasKey("Id"); + + b.HasIndex("Name"); + + b.HasIndex("Type"); + + b.ToTable("wiki-fast-models", (string)null); + }); + + modelBuilder.Entity("FastWiki.Service.Domain.Model.Aggregates.ModelLogger", b => + { + b.Property("Id") + .ValueGeneratedOnAdd() + .HasColumnType("bigint"); + + NpgsqlPropertyBuilderExtensions.UseIdentityByDefaultColumn(b.Property("Id")); + + b.Property("ApiKey") + .IsRequired() + .HasColumnType("text"); + + b.Property("ApplicationId") + .HasColumnType("text"); + + b.Property("ComplementCount") + .HasColumnType("integer"); + + b.Property("CreationTime") + .HasColumnType("timestamp without time zone"); + + b.Property("Description") + .IsRequired() + .HasColumnType("text"); + + b.Property("FastModelId") + .IsRequired() + .HasColumnType("text"); + + b.Property("Model") + .IsRequired() + .HasColumnType("text"); + + b.Property("PromptCount") + .HasColumnType("integer"); + + b.Property("Type") + .IsRequired() + .HasColumnType("text"); + + b.Property("UserId") + .HasColumnType("uuid"); + + b.HasKey("Id"); + + b.HasIndex("ApiKey"); + + b.HasIndex("ApplicationId"); + + b.HasIndex("CreationTime"); + + b.HasIndex("FastModelId"); + + b.HasIndex("Type"); + + b.HasIndex("UserId"); + + b.ToTable("wiki-model-logger", (string)null); + }); + + modelBuilder.Entity("FastWiki.Service.Domain.Storage.Aggregates.FileStorage", b => + { + b.Property("Id") + .ValueGeneratedOnAdd() + .HasColumnType("bigint"); + + NpgsqlPropertyBuilderExtensions.UseIdentityByDefaultColumn(b.Property("Id")); + + b.Property("CreationTime") + .HasColumnType("timestamp without time zone"); + + b.Property("Creator") + .HasColumnType("uuid"); + + b.Property("FullName") + .IsRequired() + .HasColumnType("text"); + + b.Property("IsCompression") + .HasColumnType("boolean"); + + b.Property("IsDeleted") + .HasColumnType("boolean"); + + b.Property("ModificationTime") + .HasColumnType("timestamp without time zone"); + + b.Property("Modifier") + .HasColumnType("uuid"); + + b.Property("Name") + .IsRequired() + .HasMaxLength(100) + .HasColumnType("character varying(100)"); + + b.Property("Path") + .IsRequired() + .HasMaxLength(200) + .HasColumnType("character varying(200)"); + + b.Property("Size") + .HasColumnType("bigint"); + + b.HasKey("Id"); + + b.ToTable("wiki-file-storages", (string)null); + }); + + modelBuilder.Entity("FastWiki.Service.Domain.Users.Aggregates.User", b => + { + b.Property("Id") + .ValueGeneratedOnAdd() + .HasColumnType("uuid"); + + b.Property("Account") + .IsRequired() + .HasColumnType("text"); + + b.Property("Avatar") + .IsRequired() + .HasColumnType("text"); + + b.Property("CreationTime") + .HasColumnType("timestamp without time zone"); + + b.Property("Creator") + .HasColumnType("uuid"); + + b.Property("Email") + .IsRequired() + .HasColumnType("text"); + + b.Property("IsDeleted") + .HasColumnType("boolean"); + + b.Property("IsDisable") + .HasColumnType("boolean"); + + b.Property("ModificationTime") + .HasColumnType("timestamp without time zone"); + + b.Property("Modifier") + .HasColumnType("uuid"); + + b.Property("Name") + .IsRequired() + .HasMaxLength(100) + .HasColumnType("character varying(100)"); + + b.Property("Password") + .IsRequired() + .HasMaxLength(100) + .HasColumnType("character varying(100)"); + + b.Property("Phone") + .IsRequired() + .HasColumnType("text"); + + b.Property("Role") + .HasColumnType("integer"); + + b.Property("Salt") + .IsRequired() + .HasColumnType("text"); + + b.HasKey("Id"); + + b.ToTable("wiki-users", (string)null); + + b.HasData( + new + { + Id = new Guid("1bca921f-0f35-42e5-8cef-c530e36c8f54"), + Account = "admin", + Avatar = "https://blog-simple.oss-cn-shenzhen.aliyuncs.com/Avatar.jpg", + CreationTime = new DateTime(2024, 3, 20, 17, 20, 45, 551, DateTimeKind.Utc).AddTicks(5537), + Email = "239573049@qq.com", + IsDeleted = false, + IsDisable = false, + ModificationTime = new DateTime(2024, 3, 20, 17, 20, 45, 551, DateTimeKind.Utc).AddTicks(5538), + Name = "admin", + Password = "22cf0ff8fc2d1a8c008cbbdad311ed4a", + Phone = "13049809673", + Role = 1, + Salt = "19520e9012974aa7ad93a908f373a81e" + }); + }); + + modelBuilder.Entity("FastWiki.Service.Domain.Wikis.Aggregates.Wiki", b => + { + b.Property("Id") + .ValueGeneratedOnAdd() + .HasColumnType("bigint"); + + NpgsqlPropertyBuilderExtensions.UseIdentityByDefaultColumn(b.Property("Id")); + + b.Property("CreationTime") + .HasColumnType("timestamp without time zone"); + + b.Property("Creator") + .HasColumnType("uuid"); + + b.Property("EmbeddingModel") + .IsRequired() + .HasColumnType("text"); + + b.Property("Icon") + .IsRequired() + .HasColumnType("text"); + + b.Property("IsDeleted") + .HasColumnType("boolean"); + + b.Property("Model") + .IsRequired() + .HasColumnType("text"); + + b.Property("ModificationTime") + .HasColumnType("timestamp without time zone"); + + b.Property("Modifier") + .HasColumnType("uuid"); + + b.Property("Name") + .IsRequired() + .HasMaxLength(100) + .HasColumnType("character varying(100)"); + + b.HasKey("Id"); + + b.HasIndex("Name"); + + b.ToTable("wiki-wikis", (string)null); + }); + + modelBuilder.Entity("FastWiki.Service.Domain.Wikis.Aggregates.WikiDetail", b => + { + b.Property("Id") + .ValueGeneratedOnAdd() + .HasColumnType("bigint"); + + NpgsqlPropertyBuilderExtensions.UseIdentityByDefaultColumn(b.Property("Id")); + + b.Property("CreationTime") + .HasColumnType("timestamp without time zone"); + + b.Property("Creator") + .HasColumnType("bigint"); + + b.Property("DataCount") + .HasColumnType("integer"); + + b.Property("FileId") + .HasColumnType("bigint"); + + b.Property("FileName") + .IsRequired() + .HasMaxLength(100) + .HasColumnType("character varying(100)"); + + b.Property("ModificationTime") + .HasColumnType("timestamp without time zone"); + + b.Property("Modifier") + .HasColumnType("bigint"); + + b.Property("Path") + .IsRequired() + .HasMaxLength(200) + .HasColumnType("character varying(200)"); + + b.Property("State") + .HasColumnType("integer"); + + b.Property("Type") + .IsRequired() + .HasMaxLength(100) + .HasColumnType("character varying(100)"); + + b.Property("WikiId") + .HasColumnType("bigint"); + + b.HasKey("Id"); + + b.ToTable("wiki-wiki-details", (string)null); + }); +#pragma warning restore 612, 618 + } + } +} diff --git a/src/Service/FastWiki.Service/Migrations/20240320172045_AddFastModel_Logger.cs b/src/Service/FastWiki.Service/Migrations/20240320172045_AddFastModel_Logger.cs new file mode 100644 index 00000000..ee7b8e88 --- /dev/null +++ b/src/Service/FastWiki.Service/Migrations/20240320172045_AddFastModel_Logger.cs @@ -0,0 +1,134 @@ +using System; +using Microsoft.EntityFrameworkCore.Migrations; +using Npgsql.EntityFrameworkCore.PostgreSQL.Metadata; + +#nullable disable + +namespace FastWiki.Service.Migrations +{ + /// + public partial class AddFastModel_Logger : Migration + { + /// + protected override void Up(MigrationBuilder migrationBuilder) + { + migrationBuilder.DeleteData( + table: "wiki-users", + keyColumn: "Id", + keyValue: new Guid("a899e701-4d58-4809-843f-a024e3bf629c")); + + migrationBuilder.CreateTable( + name: "wiki-fast-models", + columns: table => new + { + Id = table.Column(type: "text", nullable: false), + Name = table.Column(type: "character varying(30)", maxLength: 30, nullable: false), + Type = table.Column(type: "character varying(100)", maxLength: 100, nullable: false), + Url = table.Column(type: "character varying(200)", maxLength: 200, nullable: false), + ApiKey = table.Column(type: "character varying(100)", maxLength: 100, nullable: false), + Description = table.Column(type: "character varying(200)", maxLength: 200, nullable: false), + Models = table.Column(type: "text", maxLength: -1, nullable: false), + Order = table.Column(type: "integer", nullable: false), + TestTime = table.Column(type: "bigint", nullable: true), + UsedQuota = table.Column(type: "bigint", nullable: false), + Enable = table.Column(type: "boolean", nullable: false), + Creator = table.Column(type: "uuid", nullable: true), + CreationTime = table.Column(type: "timestamp without time zone", nullable: false), + Modifier = table.Column(type: "uuid", nullable: true), + ModificationTime = table.Column(type: "timestamp without time zone", nullable: false), + IsDeleted = table.Column(type: "boolean", nullable: false) + }, + constraints: table => + { + table.PrimaryKey("PK_wiki-fast-models", x => x.Id); + }); + + migrationBuilder.CreateTable( + name: "wiki-model-logger", + columns: table => new + { + Id = table.Column(type: "bigint", nullable: false) + .Annotation("Npgsql:ValueGenerationStrategy", NpgsqlValueGenerationStrategy.IdentityByDefaultColumn), + CreationTime = table.Column(type: "timestamp without time zone", nullable: false), + FastModelId = table.Column(type: "text", nullable: false), + UserId = table.Column(type: "uuid", nullable: true), + ApplicationId = table.Column(type: "text", nullable: true), + ApiKey = table.Column(type: "text", nullable: false), + Type = table.Column(type: "text", nullable: false), + Model = table.Column(type: "text", nullable: false), + PromptCount = table.Column(type: "integer", nullable: false), + ComplementCount = table.Column(type: "integer", nullable: false), + Description = table.Column(type: "text", nullable: false) + }, + constraints: table => + { + table.PrimaryKey("PK_wiki-model-logger", x => x.Id); + }); + + migrationBuilder.InsertData( + table: "wiki-users", + columns: new[] { "Id", "Account", "Avatar", "CreationTime", "Creator", "Email", "IsDeleted", "IsDisable", "ModificationTime", "Modifier", "Name", "Password", "Phone", "Role", "Salt" }, + values: new object[] { new Guid("1bca921f-0f35-42e5-8cef-c530e36c8f54"), "admin", "https://blog-simple.oss-cn-shenzhen.aliyuncs.com/Avatar.jpg", new DateTime(2024, 3, 20, 17, 20, 45, 551, DateTimeKind.Utc).AddTicks(5537), null, "239573049@qq.com", false, false, new DateTime(2024, 3, 20, 17, 20, 45, 551, DateTimeKind.Utc).AddTicks(5538), null, "admin", "22cf0ff8fc2d1a8c008cbbdad311ed4a", "13049809673", 1, "19520e9012974aa7ad93a908f373a81e" }); + + migrationBuilder.CreateIndex( + name: "IX_wiki-fast-models_Name", + table: "wiki-fast-models", + column: "Name"); + + migrationBuilder.CreateIndex( + name: "IX_wiki-fast-models_Type", + table: "wiki-fast-models", + column: "Type"); + + migrationBuilder.CreateIndex( + name: "IX_wiki-model-logger_ApiKey", + table: "wiki-model-logger", + column: "ApiKey"); + + migrationBuilder.CreateIndex( + name: "IX_wiki-model-logger_ApplicationId", + table: "wiki-model-logger", + column: "ApplicationId"); + + migrationBuilder.CreateIndex( + name: "IX_wiki-model-logger_CreationTime", + table: "wiki-model-logger", + column: "CreationTime"); + + migrationBuilder.CreateIndex( + name: "IX_wiki-model-logger_FastModelId", + table: "wiki-model-logger", + column: "FastModelId"); + + migrationBuilder.CreateIndex( + name: "IX_wiki-model-logger_Type", + table: "wiki-model-logger", + column: "Type"); + + migrationBuilder.CreateIndex( + name: "IX_wiki-model-logger_UserId", + table: "wiki-model-logger", + column: "UserId"); + } + + /// + protected override void Down(MigrationBuilder migrationBuilder) + { + migrationBuilder.DropTable( + name: "wiki-fast-models"); + + migrationBuilder.DropTable( + name: "wiki-model-logger"); + + migrationBuilder.DeleteData( + table: "wiki-users", + keyColumn: "Id", + keyValue: new Guid("1bca921f-0f35-42e5-8cef-c530e36c8f54")); + + migrationBuilder.InsertData( + table: "wiki-users", + columns: new[] { "Id", "Account", "Avatar", "CreationTime", "Creator", "Email", "IsDeleted", "IsDisable", "ModificationTime", "Modifier", "Name", "Password", "Phone", "Role", "Salt" }, + values: new object[] { new Guid("a899e701-4d58-4809-843f-a024e3bf629c"), "admin", "https://blog-simple.oss-cn-shenzhen.aliyuncs.com/Avatar.jpg", new DateTime(2024, 3, 19, 17, 57, 2, 871, DateTimeKind.Utc).AddTicks(3601), null, "239573049@qq.com", false, false, new DateTime(2024, 3, 19, 17, 57, 2, 871, DateTimeKind.Utc).AddTicks(3603), null, "admin", "2f204309fb0afa4c2bdba7b2904ea10e", "13049809673", 1, "ab3b086ec59a45cfbf65398ad8f64fdb" }); + } + } +} diff --git a/src/Service/FastWiki.Service/Migrations/WikiDbContextModelSnapshot.cs b/src/Service/FastWiki.Service/Migrations/WikiDbContextModelSnapshot.cs index 7ca50a4a..3fed48bc 100644 --- a/src/Service/FastWiki.Service/Migrations/WikiDbContextModelSnapshot.cs +++ b/src/Service/FastWiki.Service/Migrations/WikiDbContextModelSnapshot.cs @@ -242,6 +242,137 @@ protected override void BuildModel(ModelBuilder modelBuilder) b.ToTable("wiki-chat-share", (string)null); }); + modelBuilder.Entity("FastWiki.Service.Domain.Model.Aggregates.FastModel", b => + { + b.Property("Id") + .HasColumnType("text"); + + b.Property("ApiKey") + .IsRequired() + .HasMaxLength(100) + .HasColumnType("character varying(100)"); + + b.Property("CreationTime") + .HasColumnType("timestamp without time zone"); + + b.Property("Creator") + .HasColumnType("uuid"); + + b.Property("Description") + .IsRequired() + .HasMaxLength(200) + .HasColumnType("character varying(200)"); + + b.Property("Enable") + .HasColumnType("boolean"); + + b.Property("IsDeleted") + .HasColumnType("boolean"); + + b.Property("Models") + .IsRequired() + .HasMaxLength(-1) + .HasColumnType("text"); + + b.Property("ModificationTime") + .HasColumnType("timestamp without time zone"); + + b.Property("Modifier") + .HasColumnType("uuid"); + + b.Property("Name") + .IsRequired() + .HasMaxLength(30) + .HasColumnType("character varying(30)"); + + b.Property("Order") + .HasColumnType("integer"); + + b.Property("TestTime") + .HasColumnType("bigint"); + + b.Property("Type") + .IsRequired() + .HasMaxLength(100) + .HasColumnType("character varying(100)"); + + b.Property("Url") + .IsRequired() + .HasMaxLength(200) + .HasColumnType("character varying(200)"); + + b.Property("UsedQuota") + .HasColumnType("bigint"); + + b.HasKey("Id"); + + b.HasIndex("Name"); + + b.HasIndex("Type"); + + b.ToTable("wiki-fast-models", (string)null); + }); + + modelBuilder.Entity("FastWiki.Service.Domain.Model.Aggregates.ModelLogger", b => + { + b.Property("Id") + .ValueGeneratedOnAdd() + .HasColumnType("bigint"); + + NpgsqlPropertyBuilderExtensions.UseIdentityByDefaultColumn(b.Property("Id")); + + b.Property("ApiKey") + .IsRequired() + .HasColumnType("text"); + + b.Property("ApplicationId") + .HasColumnType("text"); + + b.Property("ComplementCount") + .HasColumnType("integer"); + + b.Property("CreationTime") + .HasColumnType("timestamp without time zone"); + + b.Property("Description") + .IsRequired() + .HasColumnType("text"); + + b.Property("FastModelId") + .IsRequired() + .HasColumnType("text"); + + b.Property("Model") + .IsRequired() + .HasColumnType("text"); + + b.Property("PromptCount") + .HasColumnType("integer"); + + b.Property("Type") + .IsRequired() + .HasColumnType("text"); + + b.Property("UserId") + .HasColumnType("uuid"); + + b.HasKey("Id"); + + b.HasIndex("ApiKey"); + + b.HasIndex("ApplicationId"); + + b.HasIndex("CreationTime"); + + b.HasIndex("FastModelId"); + + b.HasIndex("Type"); + + b.HasIndex("UserId"); + + b.ToTable("wiki-model-logger", (string)null); + }); + modelBuilder.Entity("FastWiki.Service.Domain.Storage.Aggregates.FileStorage", b => { b.Property("Id") @@ -354,19 +485,19 @@ protected override void BuildModel(ModelBuilder modelBuilder) b.HasData( new { - Id = new Guid("a899e701-4d58-4809-843f-a024e3bf629c"), + Id = new Guid("1bca921f-0f35-42e5-8cef-c530e36c8f54"), Account = "admin", Avatar = "https://blog-simple.oss-cn-shenzhen.aliyuncs.com/Avatar.jpg", - CreationTime = new DateTime(2024, 3, 19, 17, 57, 2, 871, DateTimeKind.Utc).AddTicks(3601), + CreationTime = new DateTime(2024, 3, 20, 17, 20, 45, 551, DateTimeKind.Utc).AddTicks(5537), Email = "239573049@qq.com", IsDeleted = false, IsDisable = false, - ModificationTime = new DateTime(2024, 3, 19, 17, 57, 2, 871, DateTimeKind.Utc).AddTicks(3603), + ModificationTime = new DateTime(2024, 3, 20, 17, 20, 45, 551, DateTimeKind.Utc).AddTicks(5538), Name = "admin", - Password = "2f204309fb0afa4c2bdba7b2904ea10e", + Password = "22cf0ff8fc2d1a8c008cbbdad311ed4a", Phone = "13049809673", Role = 1, - Salt = "ab3b086ec59a45cfbf65398ad8f64fdb" + Salt = "19520e9012974aa7ad93a908f373a81e" }); }); diff --git a/src/Service/FastWiki.Service/Service/ModelService.cs b/src/Service/FastWiki.Service/Service/ModelService.cs new file mode 100644 index 00000000..2d00f973 --- /dev/null +++ b/src/Service/FastWiki.Service/Service/ModelService.cs @@ -0,0 +1,83 @@ +using AIDotNet.Abstractions; +using AIDotNet.OpenAI; +using AIDotNet.SparkDesk; +using FastWiki.Service.Application.Model.Commands; +using FastWiki.Service.Application.Model.Queries; +using FastWiki.Service.Contracts.Model; +using FastWiki.Service.Domain.Model.Aggregates; +using Constant = FastWiki.Service.Contracts.Constant; + +namespace FastWiki.Service.Service; + +public sealed class ModelService : ApplicationService +{ + static ModelService() + { + ChatServices.Add(OpenAIOptions.ServiceName, new OpenAiService(new OpenAIOptions() + { + Client = new HttpClient(), + })); + + ChatServices.Add(SparkDeskOptions.ServiceName, new SparkDeskService(new SparkDeskOptions())); + } + + /// + /// 获取所有支持的对话类型 + /// + /// + public List GetChatTypes() + => IADNChatCompletionService.ServiceNames; + + private static readonly Dictionary ChatServices = new(); + + public static IADNChatCompletionService GetChatService(string serviceName) + { + if (ChatServices.TryGetValue(serviceName, out var service)) + { + return service; + } + + throw new NotSupportedException($"不支持的对话类型:{serviceName}"); + } + + /// + /// 获取模型列表 + /// + /// + /// + /// + /// + [Authorize(Roles = Constant.Role.Admin)] + public async Task> GetModelListAsync(string keyword, int page, int pageSize) + { + var query = new GetModelListQuery(keyword, page, pageSize); + + await EventBus.PublishAsync(query); + + return query.Result; + } + + /// + /// 创建模型 + /// + /// + [Authorize(Roles = Constant.Role.Admin)] + public async Task CreateFastModelAsync(CreateFastModeInput input) + { + var command = new CreateFastModeCommand(input); + + await EventBus.PublishAsync(command); + } + + /// + /// 删除指定模型 + /// + /// + [Authorize(Roles = Constant.Role.Admin)] + public async Task RemoveFastModelAsync(string id) + { + var command = new RemoveFastModelCommand(id); + + await EventBus.PublishAsync(command); + } +} \ No newline at end of file diff --git a/src/Service/FastWiki.Service/Service/ModuleService.cs b/src/Service/FastWiki.Service/Service/ModuleService.cs deleted file mode 100644 index 153c7251..00000000 --- a/src/Service/FastWiki.Service/Service/ModuleService.cs +++ /dev/null @@ -1,37 +0,0 @@ -using AIDotNet.Abstractions; -using AIDotNet.OpenAI; -using AIDotNet.SparkDesk; - -namespace FastWiki.Service.Service; - -public sealed class ModuleService : ApplicationService -{ - static ModuleService() - { - ChatServices.Add(OpenAIOptions.ServiceName, new OpenAiService(new OpenAIOptions() - { - Client = new HttpClient(), - })); - - ChatServices.Add(SparkDeskOptions.ServiceName, new SparkDeskService(new SparkDeskOptions())); - } - - /// - /// 获取所有支持的对话类型 - /// - /// - public async Task> GetChatTypes() - => IADNChatCompletionService.ServiceNames; - - private static readonly Dictionary ChatServices = new(); - - public static IADNChatCompletionService GetChatService(string serviceName) - { - if (ChatServices.TryGetValue(serviceName, out var service)) - { - return service; - } - - throw new NotSupportedException($"不支持的对话类型:{serviceName}"); - } -} \ No newline at end of file diff --git a/src/Service/FastWiki.Service/Service/OpenAIService.cs b/src/Service/FastWiki.Service/Service/OpenAIService.cs index b5ac4e77..94910c05 100644 --- a/src/Service/FastWiki.Service/Service/OpenAIService.cs +++ b/src/Service/FastWiki.Service/Service/OpenAIService.cs @@ -236,12 +236,13 @@ public static async Task Completions(HttpContext context) chatApplication.ChatType = OpenAIOptions.ServiceName; } - var chatStream = ModuleService.GetChatService(chatApplication.ChatType); + var chatStream = ModelService.GetChatService(chatApplication.ChatType); var setting = new OpenAIPromptExecutionSettings { MaxTokens = chatApplication.MaxResponseToken, Temperature = chatApplication.Temperature, + ModelId = chatApplication.ChatModel, ExtensionData = new Dictionary() }; setting.ExtensionData.TryAdd(AIDotNet.Abstractions.Constant.API_KEY, OpenAIOption.ChatToken); diff --git a/web/src/App.tsx b/web/src/App.tsx index c10a5f44..86b9fc05 100644 --- a/web/src/App.tsx +++ b/web/src/App.tsx @@ -20,6 +20,8 @@ const Wiki = lazy(() => import('./pages/wiki/page')); const Register = lazy(() => import('./pages/register/page')); +const Model = lazy(() => import('./pages/model/page')); + const router = createBrowserRouter([{ path: '/', element: @@ -56,6 +58,11 @@ const router = createBrowserRouter([{ }, + { + path: '/model', element: + + + }, ] }, { path: '/login', diff --git a/web/src/components/FastChatInput.tsx b/web/src/components/FastChatInput.tsx index cfe2e319..68069576 100644 --- a/web/src/components/FastChatInput.tsx +++ b/web/src/components/FastChatInput.tsx @@ -104,7 +104,6 @@ export default function FastChatInput({ }); let url; - debugger; if (id) { url = '/v1/chat/completions?chatId=' + application.id + "&chatDialogId=" + dialog.id + "&chatShareId=" + id; diff --git a/web/src/layouts/(desktop)/index.tsx b/web/src/layouts/(desktop)/index.tsx index 27c1bb95..02b71753 100644 --- a/web/src/layouts/(desktop)/index.tsx +++ b/web/src/layouts/(desktop)/index.tsx @@ -1,5 +1,5 @@ import { ActionIcon, Logo, SideNav, Tooltip } from "@lobehub/ui"; -import { Album, Settings2, Box, User, BotMessageSquare } from 'lucide-react'; +import { Album, Settings2, Box, User, BotMessageSquare ,Brain} from 'lucide-react'; import { memo, useEffect, useState } from "react"; import { Flexbox } from 'react-layout-kit'; import { Outlet } from "react-router-dom"; @@ -32,6 +32,12 @@ const DesktopLayout = memo(() => { description: '知识库', path: '/wiki', role: 'admin, user' + }, { + icon: Brain, + key: 'model', + description: '模型管理', + path: '/model', + role: 'admin' }, { icon: User, key: 'user', diff --git a/web/src/models/index.d.ts b/web/src/models/index.d.ts index 45759c12..e6a6dd6c 100644 --- a/web/src/models/index.d.ts +++ b/web/src/models/index.d.ts @@ -3,6 +3,7 @@ export interface ChatApplicationDto { name: string; prompt: string; chatModel: string; + chatType: string; temperature: number; maxResponseToken: number; template: string; diff --git a/web/src/pages/app-detail/feautres/AppDetailInfo.tsx b/web/src/pages/app-detail/feautres/AppDetailInfo.tsx index 750eaad2..8070a206 100644 --- a/web/src/pages/app-detail/feautres/AppDetailInfo.tsx +++ b/web/src/pages/app-detail/feautres/AppDetailInfo.tsx @@ -5,6 +5,7 @@ import styled from 'styled-components'; import { ChatApplicationDto } from "../../../models"; import { PutChatApplications } from "../../../services/ChatApplicationService"; import { GetWikisList } from "../../../services/WikiService"; +import { GetChatTypes } from "../../../services/ModelService"; interface IAppDetailInfoProps { value: ChatApplicationDto @@ -38,6 +39,7 @@ const AppDetailInfo = memo(({ value }: IAppDetailInfoProps) => { if (value === undefined) return null; const [model, setModel] = useState([] as any[]); + const [chatModul, setChatModul] = useState([] as any[]); const [wiki, setWiki] = useState([] as any[]); const [input,] = useState({ keyword: '', @@ -53,6 +55,13 @@ const AppDetailInfo = memo(({ value }: IAppDetailInfoProps) => { })); }); + GetChatTypes() + .then((chatModul) => { + setChatModul(chatModul.map((item: string) => { + return { label: item, value: item } + })); + }); + loadingWiki(); }, []); @@ -80,6 +89,26 @@ const AppDetailInfo = memo(({ value }: IAppDetailInfoProps) => { return ( + + 大模型类型 +