Skip to content
Merged
Show file tree
Hide file tree
Changes from 2 commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 2 additions & 2 deletions CS/DashboardAIAssistant.csproj
Original file line number Diff line number Diff line change
Expand Up @@ -22,8 +22,8 @@
<PackageReference Include="DevExpress.AIIntegration.OpenAI" Version="25.1.*-*" />
<PackageReference Include="Azure.AI.OpenAI" Version="2.2.0-beta.4" />
<PackageReference Include="Azure.AI.OpenAI.Assistants" Version="1.0.0-beta.4" />
<PackageReference Include="Microsoft.Extensions.AI" Version="9.4.3-preview.1.25230.7" />
<PackageReference Include="Microsoft.Extensions.AI.OpenAI" Version="9.4.3-preview.1.25230.7" />
<PackageReference Include="Microsoft.Extensions.AI" Version="9.5.0" />
<PackageReference Include="Microsoft.Extensions.AI.OpenAI" Version="9.5.0-preview.1.25265.7" />
</ItemGroup>

<ItemGroup>
Expand Down
14 changes: 5 additions & 9 deletions CS/Services/AIAssistantCreator.cs
Original file line number Diff line number Diff line change
Expand Up @@ -20,28 +20,24 @@ public AIAssistantCreator(OpenAIClient client, string deployment) {
this.deployment = deployment;
}

public async Task<(string assistantId, string threadId)> CreateAssistantAsync(Stream data, string fileName, string instructions, bool useFileSearchTool = true, CancellationToken ct = default) {
public async Task<(string assistantId, string threadId)> CreateAssistantAndThreadAsync(Stream data, string fileName, string instructions, CancellationToken ct = default) {
data.Position = 0;

ClientResult<OpenAIFile> fileResponse = await fileClient.UploadFileAsync(data, fileName, FileUploadPurpose.Assistants, ct);
OpenAIFile file = fileResponse.Value;

var resources = new ToolResources() {
CodeInterpreter = new CodeInterpreterToolResources(),
FileSearch = useFileSearchTool ? new FileSearchToolResources() : null
CodeInterpreter = new CodeInterpreterToolResources()
};
resources.FileSearch?.NewVectorStores.Add(new VectorStoreCreationHelper([file.Id]));
resources.CodeInterpreter.FileIds.Add(file.Id);

AssistantCreationOptions assistantCreationOptions = new AssistantCreationOptions() {
Name = Guid.NewGuid().ToString(),
Instructions = instructions,
ToolResources = resources
ToolResources = resources,
Tools = { new CodeInterpreterToolDefinition() }
};
assistantCreationOptions.Tools.Add(new CodeInterpreterToolDefinition());
if (useFileSearchTool) {
assistantCreationOptions.Tools.Add(new FileSearchToolDefinition());
}


ClientResult<Assistant> assistantResponse = await assistantClient.CreateAssistantAsync(deployment, assistantCreationOptions, ct);
ClientResult<AssistantThread> threadResponse = await assistantClient.CreateThreadAsync(cancellationToken: ct);
Expand Down
2 changes: 1 addition & 1 deletion CS/Services/AIAssistantProvider.cs
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@ public async Task<string> CreateAssistant(Stream fileContent, string prompt) {
Guard.ArgumentIsNotNullOrEmpty(prompt, nameof(prompt));

string assistantName = Guid.NewGuid().ToString();
(string assistantId, string threadId) = await assistantCreator.CreateAssistantAsync(fileContent, $"{assistantName}.xlsx", prompt, false);
(string assistantId, string threadId) = await assistantCreator.CreateAssistantAndThreadAsync(fileContent, $"{assistantName}.xlsx", prompt);

IAIAssistant assistant = await assistantFactory.GetAssistant(assistantId, threadId);
await assistant.InitializeAsync();
Expand Down
4 changes: 2 additions & 2 deletions CS/Services/IAIAssistantProvider.cs
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@
namespace DashboardAIAssistant.Services {
public interface IAIAssistantProvider {
Task<string> CreateAssistant(Stream fileContent, string prompt);
IAIAssistant GetAssistant(string assistantId);
void DisposeAssistant(string assistantId);
IAIAssistant GetAssistant(string assistantName);
void DisposeAssistant(string assistantName);
}
}
15 changes: 10 additions & 5 deletions CS/wwwroot/js/aiChatCustomItem.js
Original file line number Diff line number Diff line change
Expand Up @@ -143,11 +143,16 @@ let AIChatCustomItem = (function() {
};

normalizeAIResponse(text) {
text = text.replace(/【\d+:\d+†[^\】]+】/g, "");
let html = marked.parse(text);
if (/<p>\.\s*<\/p>\s*$/.test(html))
html = html.replace(/<p>\.\s*<\/p>\s*$/, "")
return html;
if (text) {
text = text.replace(/【\d+:\d+†[^\】]+】/g, "");
let html = marked.parse(text);
if (/<p>\.\s*<\/p>\s*$/.test(html))
html = html.replace(/<p>\.\s*<\/p>\s*$/, "")
return html;
}
else {
return "Please try again later."
}
}

renderAssistantMessage(instance, message) {
Expand Down
25 changes: 19 additions & 6 deletions README.md
Original file line number Diff line number Diff line change
@@ -1,5 +1,4 @@
<!-- default badges list -->
![](https://img.shields.io/endpoint?url=https://codecentral.devexpress.com/api/v1/VersionRange/938296554/25.1.2%2B)
[![](https://img.shields.io/badge/Open_in_DevExpress_Support_Center-FF7200?style=flat-square&logo=DevExpress&logoColor=white)](https://supportcenter.devexpress.com/ticket/details/T1279614)
[![](https://img.shields.io/badge/📖_How_to_use_DevExpress_Examples-e9f6fc?style=flat-square)](https://docs.devexpress.com/GeneralInformation/403183)
[![](https://img.shields.io/badge/💬_Leave_Feedback-feecdd?style=flat-square)](#does-this-example-address-your-development-requirementsobjectives)
Expand All @@ -14,8 +13,14 @@ The AI Assistant reviews and analyzes all data displayed in the dashboard to ans

**Please note that AI Assistant initialization takes time. The assistant is ready for interaction once Microsoft Azure scans the source document on the server side.**

> [!Important]
> We use version **9.4.3-preview.1.25230.7** of the _Microsoft.Extensions.AI.*_ libraries in our source code. We do not guarantee compatibility or correct operation with higher versions.
> [!Note]
> We use the following versions of the `Microsoft.Extensions.AI.*` libraries in our source code:
>
> - Microsoft.Extensions.AI.Abstractions: **9.5.0**
> - Microsoft.Extensions.AI: **9.5.0**
> - Microsoft.Extensions.AI.OpenAI: **9.5.0-preview.1.25265.7**
>
> We do not guarantee compatibility or correct operation with higher versions.

## Implementation Details

Expand Down Expand Up @@ -81,13 +86,20 @@ public interface IAIAssistantProvider {
}
```

The `AIAssistantCreator.CreateAssistantAndThreadAsync` method uploads a file to OpenAI, configures tool resources, creates an assistant with specified instructions and tools, initializes a new thread, and returns the assistant and thread IDs. The generated assistant and thread IDs are then passed to the `IAIAssistantFactory.GetAssistant` method, which returns an `IAIAssistant` instance. The created instance is added to the application's assistant collection and is referenced by its unique name.

For information on OpenAI Assistants, refer to the following documents:
- [OpenAI Assistants API overview](https://platform.openai.com/docs/assistants/overview)
- [Azure OpenAI: OpenAI Assistants client library for .NET](https://learn.microsoft.com/en-us/dotnet/api/overview/azure/ai.openai.assistants-readme?view=azure-dotnet-preview)
- [OpenAI .NET API library](https://github.com/openai/openai-dotnet)

You can review and tailor AI assistant instructions in the following file: [AssistantHelper.cs](./CS/Services/AssistantHelper.cs)

Files to Review:
- [AIAssistantProvider.cs](./CS/Services/AIAssistantProvider.cs)
- [IAIAssistantProvider.cs](./CS/Services/IAIAssistantProvider.cs)
- [AssistantHelper.cs](./CS/Services/AssistantHelper.cs)

- [AIAssistantProvider.cs](./CS/Services/AIAssistantProvider.cs)
- [AIAssistantProvider.cs](./CS/Services/AIAssistantProvider.cs)
- [AIAssistantCreator.cs](./CS/Services/AIAssistantCreator.cs)

### Create an AI Assistant Custom Item

Expand Down Expand Up @@ -197,6 +209,7 @@ async onMessageEntered(e) {
- [IAIAssistantProvider.cs](./CS/Services/IAIAssistantProvider.cs)
- [AIChatController.cs](./CS/Controllers/AIChatController.cs)
- [AssistantHelper.cs](./CS/Services/AssistantHelper.cs)
- [AIAssistantCreator.cs](./CS/Services/AIAssistantCreator.cs)

## Documentation

Expand Down