Initial project import

This commit is contained in:
2026-07-24 23:11:20 +08:00
commit 6396eabb87
372 changed files with 49682 additions and 0 deletions
@@ -0,0 +1,96 @@
namespace MiaoJiZhang.Api.Services;
public interface ILlmClient
{
bool IsEnabled { get; }
Task<IntentResult?> TryParseIntentAsync(string userText, CancellationToken ct = default);
Task<string?> TryGenerateReplyAsync(string systemPrompt, string userText, CancellationToken ct = default);
Task<IReadOnlyList<ImageParseResult>?> AnalyzeImageAsync(
byte[] imageBytes,
string mimeType,
CancellationToken ct = default);
Task<(bool Ok, string? Error)> TestConnectionAsync(CancellationToken ct = default);
Task<AgentRunResponse> RunAgentAsync(
string systemPrompt,
string userText,
IReadOnlyList<AgentToolDefinition> tools,
Func<AgentToolCall, CancellationToken, Task<string>> executeTool,
Func<string, CancellationToken, Task>? onToken = null,
Func<string, CancellationToken, Task>? onToolRunning = null,
CancellationToken ct = default);
/// <summary>流式生成回复。将 LLM 返回的 token 逐个写入 writer,完成时返回。</summary>
Task StreamReplyAsync(
string systemPrompt,
string userText,
Func<string, CancellationToken, Task> onToken,
CancellationToken ct = default);
}
public record AgentToolDefinition(
string Name,
string Description,
object Parameters);
public record AgentToolCall(
string CallId,
string Name,
string Arguments);
public record AgentRunResponse(
string Text,
int ToolCallCount);
public record ImageParseResult(
string Type,
decimal Amount,
string CategoryName,
string? PaymentMethod,
string Note,
DateTime? OccurredAt);
public class NullLlmClient : ILlmClient
{
public bool IsEnabled => false;
public Task<IntentResult?> TryParseIntentAsync(
string userText,
CancellationToken ct = default) =>
Task.FromResult<IntentResult?>(null);
public Task<string?> TryGenerateReplyAsync(
string systemPrompt,
string userText,
CancellationToken ct = default) =>
Task.FromResult<string?>(null);
public Task<IReadOnlyList<ImageParseResult>?> AnalyzeImageAsync(
byte[] imageBytes,
string mimeType,
CancellationToken ct = default) =>
Task.FromResult<IReadOnlyList<ImageParseResult>?>(null);
public Task<(bool Ok, string? Error)> TestConnectionAsync(
CancellationToken ct = default) =>
Task.FromResult<(bool, string?)>((false, "API Key 为空"));
public Task<AgentRunResponse> RunAgentAsync(
string systemPrompt,
string userText,
IReadOnlyList<AgentToolDefinition> tools,
Func<AgentToolCall, CancellationToken, Task<string>> executeTool,
Func<string, CancellationToken, Task>? onToken = null,
Func<string, CancellationToken, Task>? onToolRunning = null,
CancellationToken ct = default) =>
Task.FromResult(new AgentRunResponse("", 0));
public async Task StreamReplyAsync(
string systemPrompt,
string userText,
Func<string, CancellationToken, Task> onToken,
CancellationToken ct = default)
{
await Task.CompletedTask;
}
}