AppendNote 以追加模式写入一条记忆 file: 目标文件名(相对于 memoryPath) title: 记忆标题,为空时使用当前时间 content: 记忆内容正文
(ctx context.Context, file, title, content string)
| 100 | // title: 记忆标题,为空时使用当前时间 |
| 101 | // content: 记忆内容正文 |
| 102 | func (m *Manager) AppendNote(ctx context.Context, file, title, content string) (string, error) { |
| 103 | if file == "" { |
| 104 | return "", errors.New("memory.AppendNote: file cannot be empty") |
| 105 | } |
| 106 | if strings.TrimSpace(content) == "" { |
| 107 | return "", errors.New("memory.AppendNote: content cannot be empty") |
| 108 | } |
| 109 | |
| 110 | path := m.resolvePath(file) |
| 111 | |
| 112 | // 尝试读取现有内容,不存在时视为空 |
| 113 | existing, err := m.backend.Read(ctx, path, 0, 0) |
| 114 | if err != nil && !strings.Contains(strings.ToLower(err.Error()), "not found") { |
| 115 | // 兼容不同 Backend 的错误信息,只在确定不是 "not found" 时返回错误 |
| 116 | return "", fmt.Errorf("memory.AppendNote: read existing content failed: %w", err) |
| 117 | } |
| 118 | |
| 119 | noteTitle := strings.TrimSpace(title) |
| 120 | if noteTitle == "" { |
| 121 | noteTitle = time.Now().Format("2006-01-02 15:04:05") |
| 122 | } |
| 123 | |
| 124 | section := fmt.Sprintf("## %s\n\n%s\n", noteTitle, strings.TrimSpace(content)) |
| 125 | |
| 126 | var newContent string |
| 127 | if strings.TrimSpace(existing) == "" { |
| 128 | newContent = section |
| 129 | } else { |
| 130 | if !strings.HasSuffix(existing, "\n") { |
| 131 | existing += "\n" |
| 132 | } |
| 133 | newContent = existing + "\n" + section |
| 134 | } |
| 135 | |
| 136 | if _, err := m.backend.Write(ctx, path, newContent); err != nil { |
| 137 | return "", fmt.Errorf("memory.AppendNote: write content failed: %w", err) |
| 138 | } |
| 139 | |
| 140 | return path, nil |
| 141 | } |
| 142 | |
| 143 | // OverwriteWithNote 使用单个 Note 覆盖整个记忆文件 |
| 144 | // 与 AppendNote 不同,该方法会丢弃原有内容,仅保留新的标题与正文 |
no test coverage detected