复制
┌───────────────┐ ┌─────────────┐
│ 主界面UI │◄─────►│ 会话管理模块 │
└───────┬───────┘ └──────┬──────┘
│ │
▼ ▼
┌───────────────┐ ┌─────────────┐
│ API通信模块 │ │ 文件存储模块 │
└───────┬───────┘ └───────┬─────┘
│ │
▼ ▼
┌───────────────────────────────┐
│ SiliconFlow API │
└───────────────────────────────┘
用户操作流程:
1. 新建会话 → 生成sessionID → 创建空todu文件
2. 输入问题 → 调用API → 解析响应 → 更新todu
3. 切换会话 → 加载对应todu文件 → 刷新界面
二、核心模块分工
1.1.界面交互模块
- 负责控件事件处理
- 管理界面状态刷新
- 提供用户输入验证
1.2.会话管理模块
- 维护会话列表和当前会话状态
- 处理会话切换时的数据加载/保存
- 生成唯一sessionID
1.3.API通信模块
- 构造符合规范的请求报文
- 处理API响应和错误码
- 结果解析和数据结构转换
1.4.文件存储模块
- 管理todu目录的文件存储
- 实现JSON格式的序列化/反序列化
- 文件变更监控和自动保存
三、主要类实现代码(精简版)
- 1.会话管理核心类
cs
csharp复制
public class SessionManager
{
private string _currentSessionId;
private readonly string _workspacePath = Path.Combine(AppDomain.CurrentDomain.BaseDirectory, "todu");
public void InitWorkspace()
{
if (!Directory.Exists(_workspacePath))
Directory.CreateDirectory(_workspacePath);
}
public string CreateNewSession()
{
var sessionId = Guid.NewGuid().ToString("N");
File.WriteAllText(GetSessionFilePath(sessionId), "[]");
return sessionId;
}
public void SwitchSession(string sessionId)
{
_currentSessionId = sessionId;
if (!File.Exists(GetSessionFilePath(sessionId)))
throw new FileNotFoundException("Session file missing");
}
public List<TodoItem> GetCurrentTodos()
{
return JsonConvert.DeserializeObject<List<TodoItem>>(
File.ReadAllText(GetSessionFilePath(_currentSessionId))
);
}
private string GetSessionFilePath(string sessionId)
=> Path.Combine(_workspacePath, $"{sessionId}.json");
}
2.API通信处理类
cs
csharp复制
public class TodoApiClient
{
private const string ApiEndpoint = "https://api.siliconflow.cn/v1/chat/completions";
public async Task<List<TodoItem>> GenerateTodosAsync(string question)
{
using var client = new HttpClient();
client.DefaultRequestHeaders.Authorization =
new AuthenticationHeaderValue("Bearer", "[YOUR_API_KEY]");
var request = new
{
model = "deepseek-ai/DeepSeek-V3",
messages = new[] {
new {
role = "user",
content = $"请根据以下问题生成规范的待办事项列表:{question}。按JSON数组格式返回"
}
},
response_format = new { type = "json_object" }
};
var response = await client.PostAsync(ApiEndpoint,
new StringContent(JsonConvert.SerializeObject(request), Encoding.UTF8, "application/json"));
var responseObj = JObject.Parse(await response.Content.ReadAsStringAsync());
return ParseTodoJson(responseObj["choices"][0]["message"]["content"].ToString());
}
private List<TodoItem> ParseTodoJson(string json)
{
// 示例响应格式:{ "todos": [{...}] }
return JObject.Parse(json)["todos"]?
.Select(t => new TodoItem {
Id = Guid.NewGuid(),
Content = t["content"].ToString(),
Created = DateTime.Now
}).ToList() ?? new List<TodoItem>();
}
}
3.文件存储服务
cs
csharp复制
public class TodoFileManager
{
private FileSystemWatcher _watcher;
public void SetupFileWatcher(Action<string> onChange)
{
_watcher = new FileSystemWatcher
{
Path = Path.Combine(AppDomain.CurrentDomain.BaseDirectory, "todu"),
Filter = "*.json",
NotifyFilter = NotifyFilters.LastWrite
};
_watcher.Changed += (s, e) => onChange(e.Name.Replace(".json", ""));
_watcher.EnableRaisingEvents = true;
}
public void SaveTodos(string sessionId, List<TodoItem> todos)
{
var json = JsonConvert.SerializeObject(todos, Formatting.Indented);
File.WriteAllText(GetFilePath(sessionId), json, Encoding.UTF8);
}
private string GetFilePath(string sessionId)
=> Path.Combine("todu", $"{sessionId}.json");
}
4.窗口界面关键代码(Windows Forms)
cs
csharp复制
public partial class MainForm : Form
{
private SessionManager _sessionManager = new SessionManager();
private TodoApiClient _apiClient = new TodoApiClient();
private BindingList<TodoItem> _currentTodos = new BindingList<TodoItem>();
public MainForm()
{
InitializeComponent();
_sessionManager.InitWorkspace();
lstSessions.DisplayMember = "Key";
lstSessions.ValueMember = "Value";
todoListBox.DataSource = _currentTodos;
todoListBox.DisplayMember = "Content";
}
// 新建会话按钮
private void btnNewSession_Click(object sender, EventArgs e)
{
var sessionId = _sessionManager.CreateNewSession();
lstSessions.Items.Add(new KeyValuePair<string, string>($"会话 {lstSessions.Items.Count+1}", sessionId));
}
// 发送提问按钮
private async void btnSend_Click(object sender, EventArgs e)
{
var todos = await _apiClient.GenerateTodosAsync(txtInput.Text);
_currentTodos.Clear();
foreach(var item in todos)
_currentTodos.Add(item);
_sessionManager.SaveCurrentTodos(_currentTodos.ToList());
}
// 切换会话选择
private void lstSessions_SelectedIndexChanged(object sender, EventArgs e)
{
if(lstSessions.SelectedItem is KeyValuePair<string, string> selected)
{
_sessionManager.SwitchSession(selected.Value);
_currentTodos = new BindingList<TodoItem>(_sessionManager.GetCurrentTodos());
todoListBox.DataSource = _currentTodos;
}
}
}
5.扩展功能建议
cs
csharp复制
// 增加会话元数据存储
public class SessionMetadata
{
public string SessionId { get; set; }
public string Title { get; set; }
public DateTime LastModified { get; set; }
}
// 在SessionManager中添加
public void SaveSessionMetadata(SessionMetadata meta)
{
var path = Path.Combine(_workspacePath, "_sessions.json");
var list = File.Exists(path) ?
JsonConvert.DeserializeObject<List<SessionMetadata>>(File.ReadAllText(path))
: new List<SessionMetadata>();
if(list.Any(m => m.SessionId == meta.SessionId))
list.RemoveAll(m => m.SessionId == meta.SessionId);
list.Add(meta);
File.WriteAllText(path, JsonConvert.SerializeObject(list));
}
TODO项状态管理扩展
cs
csharp复制
public class TodoItem
{
public Guid Id { get; set; }
public string Content { get; set; }
public bool IsCompleted { get; set; }
public DateTime Created { get; set; }
public DateTime? CompletedDate { get; set; }
}
// 在界面中添加状态切换
private void todoListBox_MouseDoubleClick(object sender, MouseEventArgs e)
{
if(todoListBox.SelectedItem is TodoItem item)
{
item.IsCompleted = !item.IsCompleted;
item.CompletedDate = item.IsCompleted ? DateTime.Now : null;
_sessionManager.SaveCurrentTodos(_currentTodos.ToList());
todoListBox.Refresh();
}
}