diff --git a/.gitignore b/.gitignore index ca16fd1..bcd938c 100644 --- a/.gitignore +++ b/.gitignore @@ -477,3 +477,4 @@ FodyWeavers.xsd # JetBrains Rider *.sln.iml +*.db \ No newline at end of file diff --git a/OpenAI.ChatGpt.AspNetCore/OpenAI.ChatGpt.AspNetCore.csproj b/OpenAI.ChatGpt.AspNetCore/OpenAI.ChatGpt.AspNetCore.csproj index 4fc48a3..bad232c 100644 --- a/OpenAI.ChatGpt.AspNetCore/OpenAI.ChatGpt.AspNetCore.csproj +++ b/OpenAI.ChatGpt.AspNetCore/OpenAI.ChatGpt.AspNetCore.csproj @@ -8,7 +8,7 @@ OpenAI.ChatGPT.AspNetCore https://github.com/rodion-m/ChatGPT_API_dotnet OpenAI ChatGPT integration for .NET with DI - 2.2.2 + 2.3.0 OpenAI Chat Completions API (ChatGPT) integration with easy DI supporting (Microsoft.Extensions.DependencyInjection). It allows you to use the API in your .NET applications. Also, the client supports streaming responses (like ChatGPT) via async streams. https://github.com/rodion-m/ChatGPT_API_dotnet net6.0;net7.0 diff --git a/OpenAI.ChatGpt.EntityFrameworkCore/OpenAI.ChatGpt.EntityFrameworkCore.csproj b/OpenAI.ChatGpt.EntityFrameworkCore/OpenAI.ChatGpt.EntityFrameworkCore.csproj index c99b4a3..2490eac 100644 --- a/OpenAI.ChatGpt.EntityFrameworkCore/OpenAI.ChatGpt.EntityFrameworkCore.csproj +++ b/OpenAI.ChatGpt.EntityFrameworkCore/OpenAI.ChatGpt.EntityFrameworkCore.csproj @@ -9,7 +9,7 @@ OpenAI.ChatGPT.EntityFrameworkCore https://github.com/rodion-m/ChatGPT_API_dotnet OpenAI ChatGPT integration for .NET with EF Core storage - 2.2.2 + 2.3.0 OpenAI Chat Completions API (ChatGPT) integration with DI and EF Core supporting. It allows you to use the API in your .NET applications. Also, the client supports streaming responses (like ChatGPT) via async streams. https://github.com/rodion-m/ChatGPT_API_dotnet net6.0;net7.0 diff --git a/OpenAI.ChatGpt/ChatGPT.cs b/OpenAI.ChatGpt/ChatGPT.cs index 383a540..fc714a3 100644 --- a/OpenAI.ChatGpt/ChatGPT.cs +++ b/OpenAI.ChatGpt/ChatGPT.cs @@ -11,7 +11,7 @@ namespace OpenAI.ChatGpt; public class ChatGPT : IDisposable { private readonly string _userId; - private readonly IChatHistoryStorage _chatHistoryStorage; + private readonly IChatHistoryStorage _storage; private readonly ITimeProvider _clock; private readonly ChatGPTConfig? _config; private readonly OpenAiClient _client; @@ -29,7 +29,7 @@ public ChatGPT( { _client = client ?? throw new ArgumentNullException(nameof(client)); _userId = userId ?? throw new ArgumentNullException(nameof(userId)); - _chatHistoryStorage = chatHistoryStorage ?? throw new ArgumentNullException(nameof(chatHistoryStorage)); + _storage = chatHistoryStorage ?? throw new ArgumentNullException(nameof(chatHistoryStorage)); _clock = clock ?? throw new ArgumentNullException(nameof(clock)); _config = config; } @@ -44,7 +44,7 @@ public ChatGPT( ChatGPTConfig? config) { _client = client ?? throw new ArgumentNullException(nameof(client)); - _chatHistoryStorage = chatHistoryStorage ?? throw new ArgumentNullException(nameof(chatHistoryStorage)); + _storage = chatHistoryStorage ?? throw new ArgumentNullException(nameof(chatHistoryStorage)); _clock = clock ?? throw new ArgumentNullException(nameof(clock)); _userId = Guid.Empty.ToString(); _config = config; @@ -71,12 +71,10 @@ public void Dispose() } /// Continues the last topic or starts a new one. - public async Task ContinueOrStartNewTopic( - DateTimeOffset? createdAt = null, - CancellationToken cancellationToken = default) + public async Task ContinueOrStartNewTopic(CancellationToken cancellationToken = default) { if (_currentChat is not null) return _currentChat; - var topic = await _chatHistoryStorage.GetMostRecentTopicOrNull(_userId, cancellationToken); + var topic = await _storage.GetMostRecentTopicOrNull(_userId, cancellationToken); return topic is null ? await StartNewTopic(cancellationToken: cancellationToken) : await SetTopic(topic, cancellationToken); @@ -91,13 +89,13 @@ public async Task StartNewTopic( CancellationToken cancellationToken = default) { config = ChatGPTConfig.CombineOrDefault(_config, config); - var topic = new Topic(_chatHistoryStorage.NewTopicId(), _userId, name, _clock.GetCurrentTime(), config); - await _chatHistoryStorage.AddTopic(topic, cancellationToken); + var topic = new Topic(_storage.NewTopicId(), _userId, name, _clock.GetCurrentTime(), config); + await _storage.AddTopic(topic, cancellationToken); initialDialog ??= config.GetInitialDialogOrNull(); if (initialDialog is not null) { var messages = ConvertToPersistentMessages(initialDialog, topic); - await _chatHistoryStorage.SaveMessages(_userId, topic.Id, messages, cancellationToken); + await _storage.SaveMessages(_userId, topic.Id, messages, cancellationToken); } _currentChat = CreateChat(topic, initialDialog is null, clearOnDisposal: clearOnDisposal); @@ -108,13 +106,13 @@ private IEnumerable ConvertToPersistentMessages(ChatCompl { return dialog.GetMessages() .Select(m => new PersistentChatMessage( - _chatHistoryStorage.NewMessageId(), _userId, topic.Id, _clock.GetCurrentTime(), m) + _storage.NewMessageId(), _userId, topic.Id, _clock.GetCurrentTime(), m) ); } public async Task SetTopic(Guid topicId, CancellationToken cancellationToken = default) { - var topic = await _chatHistoryStorage.GetTopic(_userId, topicId, cancellationToken); + var topic = await _storage.GetTopic(_userId, topicId, cancellationToken); if (topic is null) { throw new ArgumentException($"Chat with id {topicId} not found for user {_userId}"); @@ -132,12 +130,12 @@ private Task SetTopic(Topic topic, CancellationToken cancellationToken = d private Chat CreateChat(Topic topic, bool isNew, bool clearOnDisposal) { if (topic == null) throw new ArgumentNullException(nameof(topic)); - return new Chat(_chatHistoryStorage, _clock, _client, _userId, topic, isNew, clearOnDisposal); + return new Chat(_storage, _clock, _client, _userId, topic, isNew, clearOnDisposal); } public async Task> GetTopics(CancellationToken cancellationToken = default) { - var chats = await _chatHistoryStorage.GetTopics(_userId, cancellationToken); + var chats = await _storage.GetTopics(_userId, cancellationToken); return chats.ToList(); } diff --git a/OpenAI.ChatGpt/OpenAI.ChatGpt.csproj b/OpenAI.ChatGpt/OpenAI.ChatGpt.csproj index 39f5e3e..75b2024 100644 --- a/OpenAI.ChatGpt/OpenAI.ChatGpt.csproj +++ b/OpenAI.ChatGpt/OpenAI.ChatGpt.csproj @@ -10,7 +10,7 @@ OpenAI.ChatGPT https://github.com/rodion-m/ChatGPT_API_dotnet OpenAI ChatGPT integration for .NET - 2.2.2 + 2.3.0 .NET integration for ChatGPT with streaming responses supporting (like ChatGPT) via async streams. https://github.com/rodion-m/ChatGPT_API_dotnet MIT diff --git a/samples/ChatGpt.BlazorExample/ChatGpt.BlazorExample.csproj b/samples/ChatGpt.BlazorExample/ChatGpt.BlazorExample.csproj index 9d70c90..6c3c501 100644 --- a/samples/ChatGpt.BlazorExample/ChatGpt.BlazorExample.csproj +++ b/samples/ChatGpt.BlazorExample/ChatGpt.BlazorExample.csproj @@ -9,7 +9,7 @@ - + diff --git a/samples/ChatGpt.BlazorExample/Pages/Counter.razor b/samples/ChatGpt.BlazorExample/Pages/Counter.razor deleted file mode 100644 index ef23cb3..0000000 --- a/samples/ChatGpt.BlazorExample/Pages/Counter.razor +++ /dev/null @@ -1,18 +0,0 @@ -@page "/counter" - -Counter - -

Counter

- -

Current count: @currentCount

- - - -@code { - private int currentCount = 0; - - private void IncrementCount() - { - currentCount++; - } -} diff --git a/samples/ChatGpt.BlazorExample/Pages/Index.razor b/samples/ChatGpt.BlazorExample/Pages/Index.razor index 2d5fef3..1bd27de 100644 --- a/samples/ChatGpt.BlazorExample/Pages/Index.razor +++ b/samples/ChatGpt.BlazorExample/Pages/Index.razor @@ -1,10 +1,12 @@ @page "/" @using OpenAI.ChatGpt.AspNetCore @using OpenAI.ChatGpt +@using OpenAI.ChatGpt.Interfaces @using OpenAI.ChatGpt.Models @using OpenAI.ChatGpt.Models.ChatCompletion @inject IJSRuntime JsRuntime @inject ChatGPTFactory ChatGPTFactory +@inject IChatHistoryStorage ChatHistoryStorage Index @if (_messages is null) @@ -77,7 +79,7 @@ @foreach (var item in _messages) {
- @if (item.role == item.content) + @if (item.role == ChatCompletionRoles.User) {
Human @@ -134,6 +136,7 @@ else bool _processing = false; int _totalTokens = 0; private Chat _chat; + private string _userId = "test-user-id"; protected override async Task OnInitializedAsync() { @@ -144,9 +147,10 @@ else private async Task CreateNewChat() { if(_chat != null) await _chat.DisposeAsync(); - var chatGpt = await ChatGPTFactory.Create("test-user-id"); - _chat = await chatGpt.StartNewTopic("Test Topic", clearOnDisposal: true); - + var chatGpt = await ChatGPTFactory.Create(_userId); + _chat = await chatGpt.ContinueOrStartNewTopic(); + _messages = (await _chat.GetMessages()).Select(m => (m.Role, m.Content)) + .ToList(); } protected override async Task OnAfterRenderAsync(bool firstRender) @@ -180,7 +184,7 @@ else _messages.Add((ChatCompletionRoles.User, _prompt)); _messages.Add((ChatCompletionRoles.Assistant, response)); - //TotalTokens = _chat.LastResponse.Usage.TotalTokens; + _totalTokens = (int) (_chat.LastResponse?.Usage.TotalTokens ?? 0); } catch (Exception ex) { @@ -204,6 +208,7 @@ else async Task RestartChatGpt() { _prompt = "Write a 10 word description of OpenAI ChatGPT"; + await ChatHistoryStorage.ClearTopics(_userId, default); await CreateNewChat(); _messages = new(); _totalTokens = 0; diff --git a/samples/ChatGpt.BlazorExample/Shared/NavMenu.razor b/samples/ChatGpt.BlazorExample/Shared/NavMenu.razor index a35de07..a62083d 100644 --- a/samples/ChatGpt.BlazorExample/Shared/NavMenu.razor +++ b/samples/ChatGpt.BlazorExample/Shared/NavMenu.razor @@ -14,16 +14,6 @@ Home
- -