feat(halo): 添加图片自动上传功能
- 新增图片处理工具模块 `src/utils/image.ts`,包含图片引用提取、绝对路径解析和路径替换功能 - 新增图片上传服务 `src/service/image-uploader.ts`,支持调用 Halo 媒体 API 上传图片并实现缓存机制 - 在设置界面添加图片上传开关和上传路径配置项 - 更新发布流程,在提交到 Halo 前自动检测并上传本地图片,替换为远程 URL - 添加英文、简体中文和繁体中文的国际化文案 - 更新插件版本至 1.1.1 并完善相关配置文件
This commit is contained in:
@@ -0,0 +1,141 @@
|
||||
# obsidian-halo 插件功能增强计划
|
||||
|
||||
## 当前功能分析
|
||||
|
||||
当前插件已实现:
|
||||
- ✅ 发布文档到 Halo
|
||||
- ✅ 从 Halo 拉取文档
|
||||
- ✅ 更新已发布文章内容
|
||||
- ✅ 多站点管理
|
||||
- ✅ Frontmatter 元数据同步(标题、摘要、分类、标签、封面)
|
||||
|
||||
---
|
||||
|
||||
## 功能增强方向
|
||||
|
||||
### 1. 图片/附件上传(TODO 清单已标注)
|
||||
**优先级:高 | 难度:中**
|
||||
|
||||
- [ ] 自动检测并上传笔记中的图片到 Halo 媒体库
|
||||
- [ ] 支持粘贴截图自动上传
|
||||
- [ ] 转换本地图片路径为 Halo URL
|
||||
- [ ] 附件管理(支持其他文件类型)
|
||||
|
||||
### 2. 批量操作功能
|
||||
**优先级:高 | 难度:中**
|
||||
|
||||
- [ ] 批量发布:选择多个笔记一次性发布
|
||||
- [ ] 批量同步:检测所有已发布笔记的更新状态
|
||||
- [ ] 批量管理:统一管理 Halo 上的文章列表
|
||||
|
||||
### 3. 双向同步增强
|
||||
**优先级:高 | 难度:高**
|
||||
|
||||
- [ ] 差异检测:比较本地和 Halo 版本的修改时间
|
||||
- [ ] 选择性同步:仅同步本地/仅同步 Halo/完全合并
|
||||
- [ ] 冲突解决:处理两边同时修改的情况
|
||||
- [ ] 同步历史:记录每次同步的详情
|
||||
|
||||
### 4. 高级发布选项
|
||||
**优先级:中 | 难度:中**
|
||||
|
||||
- [ ] 自定义 Slug 格式(支持模板变量:`{{title}}`, `{{date}}`)
|
||||
- [ ] 发布时间调度(定时发布)
|
||||
- [ ] SEO 元数据设置(meta description、keywords)
|
||||
- [ ] 文章属性控制(评论开关、置顶、优先级、可见性)
|
||||
|
||||
### 5. 内容预览
|
||||
**优先级:中 | 难度:中**
|
||||
|
||||
- [ ] 发布前预览 Halo 渲染效果
|
||||
- [ ] 预览不同主题下的样式
|
||||
- [ ] 实时预览面板
|
||||
|
||||
### 6. 状态管理和日志
|
||||
**优先级:中 | 难度:中**
|
||||
|
||||
- [ ] 插件面板:显示所有同步状态
|
||||
- [ ] 同步历史记录
|
||||
- [ ] 错误日志和告警
|
||||
- [ ] 同步状态图标(同步中、已同步、有冲突)
|
||||
|
||||
### 7. 搜索和过滤
|
||||
**优先级:低 | 难度:中**
|
||||
|
||||
- [ ] 按分类/标签筛选 Halo 文章列表
|
||||
- [ ] 搜索已发布文章
|
||||
- [ ] 高级筛选条件(日期范围、发布状态)
|
||||
|
||||
### 8. 模板支持
|
||||
**优先级:低 | 难度:中**
|
||||
|
||||
- [ ] 发布模板:预定义 frontmatter 结构
|
||||
- [ ] 快捷键自定义默认值
|
||||
- [ ] 模板变量支持
|
||||
|
||||
### 9. 命令面板增强
|
||||
**优先级:低 | 难度:低**
|
||||
|
||||
- [ ] 键盘快捷键支持
|
||||
- [ ] 快速切换站点
|
||||
- [ ] 快捷操作菜单
|
||||
|
||||
### 10. 用户界面优化
|
||||
**优先级:低 | 难度:中**
|
||||
|
||||
- [ ] 进度条显示
|
||||
- [ ] 更详细的错误提示
|
||||
- [ ] 通知中心整合
|
||||
- [ ] 右键菜单支持
|
||||
|
||||
---
|
||||
|
||||
## 推荐优先级(建议优先实现)
|
||||
|
||||
1. **图片/附件上传** - 核心功能缺失,影响使用体验
|
||||
2. **批量操作** - 提升工作效率
|
||||
3. **高级发布选项** - 增加灵活性
|
||||
4. **状态管理和日志** - 问题排查和监控
|
||||
5. **双向同步增强** - 高级用户需求
|
||||
|
||||
---
|
||||
|
||||
## 技术实现要点
|
||||
|
||||
### 图片上传实现思路
|
||||
```typescript
|
||||
// 1. 解析 Markdown 中的图片引用
|
||||
// 2. 上传到 Halo 媒体库获取 URL
|
||||
// 3. 替换本地路径为远程 URL
|
||||
|
||||
// Halo 媒体上传 API 端点
|
||||
POST /apis/api.console.halo.run/v1alpha1/attachments/upload
|
||||
```
|
||||
|
||||
### 批量操作实现思路
|
||||
```typescript
|
||||
// 1. 创建批量选择界面
|
||||
// 2. 批量处理队列
|
||||
// 3. 进度显示和错误处理
|
||||
```
|
||||
|
||||
### 同步检测实现思路
|
||||
```typescript
|
||||
// 1. 保存本地最后同步时间戳
|
||||
// 2. 对比 Halo 文章的更新时间
|
||||
// 3. 标记需要更新的文章
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 开发建议
|
||||
|
||||
1. **模块化开发**:新增功能独立成模块
|
||||
2. **配置化**:新功能支持在设置中开关
|
||||
3. **国际化**:所有文案支持 i18n
|
||||
4. **错误处理**:完善异常捕获和用户提示
|
||||
5. **测试**:添加单元测试和集成测试
|
||||
|
||||
---
|
||||
|
||||
请确认需要实现哪些功能,我将制定详细的技术方案。
|
||||
@@ -0,0 +1,37 @@
|
||||
# 图片上传功能检查清单
|
||||
|
||||
## 代码实现检查
|
||||
|
||||
- [ ] `src/utils/image.ts` 文件创建完成
|
||||
- [ ] `extractImageReferences()` 函数正确实现
|
||||
- [ ] `getAbsolutePath()` 函数正确实现
|
||||
- [ ] `replaceImagePaths()` 函数正确实现
|
||||
- [ ] `src/service/image-uploader.ts` 文件创建完成
|
||||
- [ ] `uploadImage()` 方法正确调用 Halo API
|
||||
- [ ] `uploadImages()` 方法正确实现批量上传
|
||||
- [ ] 图片缓存机制正确实现
|
||||
|
||||
## 设置界面检查
|
||||
|
||||
- [ ] 设置界面包含图片上传开关
|
||||
- [ ] 设置界面包含上传路径配置
|
||||
- [ ] 设置数据正确保存和加载
|
||||
|
||||
## 集成检查
|
||||
|
||||
- [ ] 发布流程正确调用图片上传
|
||||
- [ ] 图片路径正确替换为远程 URL
|
||||
- [ ] 上传失败时正确处理错误
|
||||
|
||||
## 国际化检查
|
||||
|
||||
- [ ] 英文文案添加完成
|
||||
- [ ] 简体中文文案添加完成
|
||||
- [ ] 繁体中文文案添加完成
|
||||
|
||||
## 测试检查
|
||||
|
||||
- [ ] 编译通过无错误
|
||||
- [ ] 插件文件正确复制到 Obsidian 插件目录
|
||||
- [ ] 基本功能测试通过
|
||||
- [ ] 图片上传测试通过
|
||||
@@ -0,0 +1,107 @@
|
||||
# 图片上传功能规格说明
|
||||
|
||||
## Why
|
||||
当前 obsidian-halo 插件无法将本地图片上传到 Halo 媒体库,导致发布的文章中的图片无法正常显示。这是一个核心功能缺失,直接影响使用体验。
|
||||
|
||||
## What Changes
|
||||
- 新增图片检测模块:解析 Markdown 中的本地图片引用
|
||||
- 新增图片上传服务:调用 Halo 媒体 API 上传图片
|
||||
- 新增图片路径替换:自动将本地路径替换为 Halo 远程 URL
|
||||
- 新增设置选项:允许用户开关自动上传功能
|
||||
|
||||
## Impact
|
||||
- 影响规格:
|
||||
- 发布功能:发布时自动处理图片
|
||||
- 设置功能:新增图片上传相关配置
|
||||
- 影响代码:
|
||||
- 新增 `src/utils/image.ts`:图片处理工具函数
|
||||
- 新增 `src/service/image-uploader.ts`:图片上传服务
|
||||
- 修改 `src/service/index.ts`:集成图片上传到发布流程
|
||||
- 修改 `src/settings.ts`:添加图片上传设置项
|
||||
- 修改 `src/i18n/locales/*.json`:添加国际化文案
|
||||
|
||||
## ADDED Requirements
|
||||
|
||||
### Requirement: 图片自动上传
|
||||
系统 SHALL 在发布文档时自动检测并上传本地图片到 Halo 媒体库。
|
||||
|
||||
#### Scenario: 检测到本地图片
|
||||
- **WHEN** 用户执行发布命令且文档中包含本地图片(如 `assets/image.png`)
|
||||
- **THEN** 系统自动上传图片到 Halo 并将文档中的路径替换为远程 URL
|
||||
|
||||
#### Scenario: 图片已上传过
|
||||
- **WHEN** 系统检测到相同图片(基于文件路径和修改时间)
|
||||
- **THEN** 直接使用已上传的 URL,不重复上传
|
||||
|
||||
#### Scenario: 上传失败
|
||||
- **WHEN** 图片上传过程中发生错误
|
||||
- **THEN** 系统记录错误并继续处理其他图片,已失败的图片保持原路径
|
||||
|
||||
### Requirement: 图片路径识别
|
||||
系统 SHALL 支持识别以下格式的图片引用:
|
||||
- `` - 普通 Markdown 图片语法
|
||||
- `` - 相对路径
|
||||
- `` - 绝对路径(Vault 根目录)
|
||||
- `` - Base64 内联图片(可选支持)
|
||||
|
||||
### Requirement: 上传配置选项
|
||||
系统 SHALL 提供以下配置选项:
|
||||
- 开关:是否启用自动图片上传
|
||||
- 媒体库路径:上传到 Halo 的哪个媒体目录
|
||||
- 保留原图:是否保留本地路径作为备选
|
||||
|
||||
## MODIFIED Requirements
|
||||
|
||||
### Requirement: 发布流程
|
||||
原发布流程:
|
||||
1. 读取文档内容
|
||||
2. 解析 frontmatter
|
||||
3. 提交到 Halo API
|
||||
|
||||
修改后的发布流程:
|
||||
1. 读取文档内容
|
||||
2. 解析 frontmatter
|
||||
3. **检测并上传本地图片**
|
||||
4. **替换图片路径为远程 URL**
|
||||
5. 提交到 Halo API
|
||||
|
||||
## REMOVED Requirements
|
||||
|
||||
无
|
||||
|
||||
---
|
||||
|
||||
## 技术实现细节
|
||||
|
||||
### Halo 媒体上传 API
|
||||
|
||||
```
|
||||
POST /apis/api.console.halo.run/v1alpha1/attachments/upload
|
||||
Content-Type: multipart/form-data
|
||||
|
||||
请求体:
|
||||
- file: 二进制文件数据
|
||||
- groupName: 媒体分组名称(可选)
|
||||
|
||||
响应:
|
||||
{
|
||||
"name": "uuid-filename.png",
|
||||
"url": "/upload/2024/01/abc.png",
|
||||
"type": "IMAGE",
|
||||
"size": 12345
|
||||
}
|
||||
```
|
||||
|
||||
### 图片检测正则
|
||||
```typescript
|
||||
const imageRegex = /!\[([^\]]*)\]\(([^)]+)\)/g;
|
||||
```
|
||||
|
||||
### 配置项
|
||||
```typescript
|
||||
interface ImageUploadSettings {
|
||||
enabled: boolean; // 是否启用
|
||||
uploadPath: string; // 上传路径(空表示根目录)
|
||||
preserveOriginal: boolean; // 保留原路径
|
||||
}
|
||||
```
|
||||
@@ -0,0 +1,58 @@
|
||||
# 图片上传功能任务清单
|
||||
|
||||
## 任务列表
|
||||
|
||||
- [x] 任务 1:创建图片处理工具模块 `src/utils/image.ts`
|
||||
- [ ] 子任务 1.1:实现 `extractImageReferences()` 函数,检测 Markdown 中的图片引用
|
||||
- [ ] 子任务 1.2:实现 `getAbsolutePath()` 函数,将相对路径转为绝对路径
|
||||
- [ ] 子任务 1.3:实现 `replaceImagePaths()` 函数,替换图片路径
|
||||
|
||||
- [x] 任务 2:创建图片上传服务 `src/service/image-uploader.ts`
|
||||
- [ ] 子任务 2.1:实现 `uploadImage()` 方法,调用 Halo 媒体 API 上传单个图片
|
||||
- [ ] 子任务 2.2:实现 `uploadImages()` 方法,批量上传图片并返回映射表
|
||||
- [ ] 子任务 2.3:实现缓存机制,记录已上传图片的 URL
|
||||
|
||||
- [x] 任务 3:更新设置界面 `src/settings.ts`
|
||||
- [x] 子任务 3.1:在设置界面添加图片上传开关
|
||||
- [x] 子任务 3.2:添加上传路径配置项
|
||||
- [x] 子任务 3.3:更新设置数据结构
|
||||
|
||||
- [x] 任务 5:添加国际化文案 `src/i18n/locales/*.json`
|
||||
- [x] 子任务 5.1:添加英文文案
|
||||
- [x] 子任务 5.2:添加简体中文文案
|
||||
- [x] 子任务 5.3:添加繁体中文文案
|
||||
|
||||
- [x] 任务 4:集成图片上传到发布流程 `src/service/index.ts`
|
||||
- [x] 子任务 4.1:在 `publishPost()` 方法中调用图片上传
|
||||
- [x] 子任务 4.2:处理上传后的路径替换
|
||||
- [x] 子任务 4.3:添加错误处理和用户提示
|
||||
|
||||
- [ ] 任务 5:添加国际化文案 `src/i18n/locales/*.json`
|
||||
- [ ] 子任务 5.1:添加英文文案
|
||||
- [ ] 子任务 5.2:添加简体中文文案
|
||||
- [ ] 子任务 5.3:添加繁体中文文案
|
||||
|
||||
- [ ] 任务 6:编译和测试
|
||||
- [ ] 子任务 6.1:运行 `pnpm build` 确保编译通过
|
||||
- [ ] 子任务 6.2:复制编译产物到插件目录
|
||||
- [ ] 子任务 6.3:手动测试图片上传功能
|
||||
|
||||
---
|
||||
|
||||
## 任务依赖关系
|
||||
|
||||
- [任务 1] 和 [任务 2] 可并行开发
|
||||
- [任务 3] 可在 [任务 2] 完成后开始
|
||||
- [任务 4] 依赖 [任务 1] 和 [任务 2] 完成
|
||||
- [任务 5] 可与其他任务并行进行
|
||||
- [任务 6] 需要所有其他任务完成后执行
|
||||
|
||||
---
|
||||
|
||||
## 实现顺序建议
|
||||
|
||||
1. 先完成 [任务 1] 和 [任务 2](核心功能)
|
||||
2. 再完成 [任务 3](配置界面)
|
||||
3. 然后完成 [任务 4](集成)
|
||||
4. [任务 5] 和 [任务 3] 可同时进行
|
||||
5. 最后 [任务 6](测试)
|
||||
Reference in New Issue
Block a user