文件存储 API
管理项目文件的上传、下载、删除和预览,支持文件夹管理和存储限制查询。
基础路径
/storage/:projectId注意:存储 API 的基础路径是
/storage,与其他项目 API 的/projects前缀不同。
认证方式
所有端点均需要 JWT Bearer Token 或 API Key 认证(combinedAuth 中间件)。
权限说明
- 读取操作(GET):需要项目访问权限(项目所属团队成员)
- 写入操作(POST / DELETE / PATCH):额外检查写入权限(
write/admin,或团队成员默认读写权限)
端点列表
1. 获取文件列表
GET /storage/:projectId/files获取项目的文件列表,支持按文件夹过滤。
Path 参数
| 参数 | 类型 | 必填 | 说明 |
|---|---|---|---|
projectId | string | 是 | 项目 ID |
Query 参数
| 参数 | 类型 | 必填 | 说明 |
|---|---|---|---|
folderKey | string | 否 | 文件夹 key。不传=全部文件,空字符串=根目录文件,有值=指定文件夹内的文件 |
响应 200
json
{
"files": [
{
"id": "uuid",
"file_name": "photo.jpg",
"mime_type": "image/jpeg",
"size": 1024000,
"folder_key": "",
"created_at": "2026-01-01T00:00:00Z"
}
]
}错误码
| 状态码 | 说明 |
|---|---|
| 401 | 未认证 |
| 404 | 项目不存在或无权访问 |
| 500 | 获取文件列表失败 |
2. 上传文件
POST /storage/:projectId/upload上传文件到项目存储。支持文件类型校验、大小限制检查和知识库工作流触发。
Path 参数
| 参数 | 类型 | 必填 | 说明 |
|---|---|---|---|
projectId | string | 是 | 项目 ID |
Body 参数(multipart/form-data)
| 参数 | 类型 | 必填 | 说明 |
|---|---|---|---|
file | File | 是 | 上传的文件 |
folderKey | string | 否 | 目标文件夹 key(仅允许字母数字下划线连字符) |
knowledgeBaseTag | string | 否 | 知识库标签(触发自动向量化) |
source | string | 否 | 来源标识 |
sourceRef | string | 否 | 来源引用 |
fileType | string | 否 | 文件类型约束:image / audio / pdf / csv |
文件类型限制(当指定 fileType 时)
| fileType | 最大大小 | 允许的 MIME 类型 |
|---|---|---|
image | 10 MB | image/* |
audio | 50 MB | audio/* |
pdf | 20 MB | application/pdf |
csv | 10 MB | text/csv、application/vnd.ms-excel 或 .csv 后缀 |
未指定 fileType 时,按订阅计划的文件大小限制检查。
知识库自动向量化:当同时提供 knowledgeBaseTag 且文件 MIME 类型受支持时(文本、图片、视频、PDF、Word),自动触发知识库工作流。
响应 200
json
{
"id": "uuid",
"path": "projects/xxx/files/photo.jpg",
"file_name": "photo.jpg",
"mime_type": "image/jpeg",
"size": 1024000
}错误码
| 状态码 | 说明 |
|---|---|
| 400 | 未提供文件、文件大小超限、文件类型不匹配、folderKey 格式无效或 fileType 不支持 |
| 401 | 未认证 |
| 403 | 无写入权限 |
| 404 | 项目不存在或无权访问 |
| 500 | 上传失败 |
3. 移动文件到根目录
PATCH /storage/:projectId/files/move-to-root将指定文件夹下的文件移到根目录。
Path 参数
| 参数 | 类型 | 必填 | 说明 |
|---|---|---|---|
projectId | string | 是 | 项目 ID |
Body 参数(JSON)
| 参数 | 类型 | 必填 | 说明 |
|---|---|---|---|
folderKeys | string[] | 是 | 要移动文件的文件夹 key 数组(非空) |
响应 200
json
{
"success": true,
"movedCount": 5
}错误码
| 状态码 | 说明 |
|---|---|
| 400 | folderKeys 为空数组 |
| 401 | 未认证 |
| 403 | 无写入权限 |
| 404 | 项目不存在或无权访问 |
| 500 | 移动文件失败 |
4. 删除文件
DELETE /storage/:projectId/files/:fileId删除指定文件。
Path 参数
| 参数 | 类型 | 必填 | 说明 |
|---|---|---|---|
projectId | string | 是 | 项目 ID |
fileId | string | 是 | 文件 ID |
响应 200
json
{
"success": true
}错误码
| 状态码 | 说明 |
|---|---|
| 401 | 未认证 |
| 403 | 无写入权限 |
| 404 | 项目不存在或无权访问 |
| 500 | 删除失败 |
5. 获取签名下载 URL
GET /storage/:projectId/files/:fileId/signed-url获取文件的签名下载 URL(临时有效)。
Path 参数
| 参数 | 类型 | 必填 | 说明 |
|---|---|---|---|
projectId | string | 是 | 项目 ID |
fileId | string | 是 | 文件 ID |
响应 200
json
{
"url": "https://storage.example.com/signed/..."
}错误码
| 状态码 | 说明 |
|---|---|
| 401 | 未认证 |
| 404 | 项目不存在或无权访问 |
| 500 | 获取下载链接失败 |
6. 获取预览 URL
GET /storage/:projectId/files/:fileId/preview-url获取文件的预览 URL。优先返回缩略图 URL,如果没有缩略图则返回原图签名 URL。
Path 参数
| 参数 | 类型 | 必填 | 说明 |
|---|---|---|---|
projectId | string | 是 | 项目 ID |
fileId | string | 是 | 文件 ID |
响应 200
json
{
"url": "https://storage.example.com/preview/...",
"isThumbnail": true
}错误码
| 状态码 | 说明 |
|---|---|
| 401 | 未认证 |
| 404 | 项目不存在或无权访问 |
| 500 | 获取预览链接失败 |
7. 获取存储限制信息
GET /storage/:projectId/limits获取项目的存储限制信息(基于订阅计划)。
Path 参数
| 参数 | 类型 | 必填 | 说明 |
|---|---|---|---|
projectId | string | 是 | 项目 ID |
响应 200
json
{
"maxFileSize": 52428800,
"usedStorage": 10485760,
"maxStorage": 1073741824
}错误码
| 状态码 | 说明 |
|---|---|
| 401 | 未认证 |
| 404 | 项目不存在或无权访问 |
| 500 | 获取存储限制失败 |
8. 创建文件夹
POST /storage/:projectId/folders创建文件夹占位符。实际文件夹数据由前端通过 projectStore 更新 storageFolder 管理,此端点返回生成的 key。
Path 参数
| 参数 | 类型 | 必填 | 说明 |
|---|---|---|---|
projectId | string | 是 | 项目 ID |
Body 参数(JSON)
| 参数 | 类型 | 必填 | 说明 |
|---|---|---|---|
name | string | 是 | 文件夹名称 |
parentKey | string | 否 | 父文件夹 key |
响应 200
json
{
"key": "folder-1709123456-abc123",
"label": "文件夹名称"
}错误码
| 状态码 | 说明 |
|---|---|
| 400 | 文件夹名称为空 |
| 401 | 未认证 |
| 403 | 无写入权限 |
| 404 | 项目不存在或无权访问 |
| 500 | 创建文件夹失败 |
源码
- 路由:
apps/backend/src/routes/storage.ts - 服务:
apps/backend/src/services/storage/ - 参考文档:文件存储指南