Skip to content

文件夹

文件夹用于在控制台中整理您上传的文件。默认情况下文件夹仅是元数据 — 文件保留各自的 CID,并不会在 IPFS 上被移动 — 但您也可以为文件夹生成快照,将其具象化为一个真实的 UnixFS 目录,并获得整个文件夹的单一 CID。

何时需要为文件夹生成快照

文件夹快照是一个单一的 IPFS 目录 CID,其中包含文件夹内的所有文件,并可按名称寻址。有了它,您可以:

  • 通过一个 URL 分享整个文件夹:https://ipfs.ninja/ipfs/{dirCid}/
  • 直接解析 https://ipfs.ninja/ipfs/{dirCid}/photo.jpg(或任何其他网关)
  • 将 CID 放入 ENS contenthash 中以托管静态网站
  • 将其用作 NFT 合集的基础 CID,使每个 token 引用 ipfs://{dirCid}/<id>.json
  • 在其他任何地方固定该目录 — 全世界的每个 IPFS 网关都知道如何解析 UnixFS 目录 CID

快照是内容寻址的:相同的文件夹内容始终会产生相同的 CID。对未做更改的文件夹重新生成快照会返回与之前相同的 CID。添加/删除/重命名文件会产生新的 CID;只要您不删除其文件,之前的 CID 仍会保持固定状态并可被解析。

创建文件夹

POST /folders

参数类型必填描述
namestring显示名称。
parentFolderIdstring | null用于嵌套文件夹的父文件夹 ID。若为根级别文件夹则省略此参数。

示例

bash
curl -X POST https://api.ipfs.ninja/folders \
  -H "X-Api-Key: bws_your_api_key_here" \
  -H "Content-Type: application/json" \
  -d '{ "name": "My NFT collection" }'

返回:

json
{
  "folderId": "1f8e2c3a-…",
  "name": "My NFT collection",
  "parentFolderId": null,
  "createdAt": 1746360000000
}

新创建的文件夹没有快照。一旦您调用 POST /folders/{id}/snapshot(见下文),latestSnapshot 字段就会出现在该文件夹上,并在后续的 GET /folders 响应中显示。

列出文件夹

GET /folders

返回您账户中的每个文件夹,包括根级别和嵌套的文件夹,并附带各自的最新快照 CID(如果有)。

json
[
  {
    "folderId": "1f8e2c3a-…",
    "name": "My NFT collection",
    "parentFolderId": null,
    "createdAt": 1746360000000,
    "fileCount": 42,
    "latestSnapshot": {
      "cid": "QmRZx5…",
      "takenAt": 1746421000000,
      "fileCount": 42
    }
  }
]

fileCount 反映文件夹的当前内容;latestSnapshot.fileCount 反映上次生成快照时的内容。如果两者不一致,快照 CID 仍然可以解析,但已经过期 — 重新生成快照即可刷新。

将文件移动到文件夹中

PUT /files/{cid}/move

参数类型必填描述
folderIdstring | null目标文件夹 ID,或使用 null 将文件移动到根目录。
bash
curl -X PUT https://api.ipfs.ninja/files/Qm.../move \
  -H "X-Api-Key: bws_your_api_key_here" \
  -H "Content-Type: application/json" \
  -d '{ "folderId": "1f8e2c3a-…" }'

为文件夹生成快照(获取 UnixFS 目录 CID)

POST /folders/{folderId}/snapshot

在 IPFS 集群上将该文件夹具象化为一个真实的 UnixFS 目录,并固定生成的结果。为整个文件夹返回一个 CID。子项名称来自各个文件的 fileName;重复的名称会被自动去重处理。

不需要请求正文;路径参数即可标识文件夹。

示例

bash
curl -X POST https://api.ipfs.ninja/folders/1f8e2c3a-.../snapshot \
  -H "X-Api-Key: bws_your_api_key_here"

返回:

json
{
  "ok": true,
  "folderId": "1f8e2c3a-…",
  "cid": "QmRZx5VgFHDsG7ECvaKkZBS4ydmkdAkDyaKyF71RYvh8",
  "fileCount": 42,
  "sizeBytes": 8421376,
  "takenAt": 1746421000000,
  "ipfsUrl": "https://ipfs.ninja/ipfs/QmRZx5.../"
}

该 CID 也会持久化保存在文件夹记录中,因此后续的 GET /folders 调用会将其作为 latestSnapshot.cid 返回,无需再次生成快照。

解析快照

一旦快照被固定,目录 CID 就可以通过任何 IPFS 网关解析。最简单的 URL 格式如下:

https://ipfs.ninja/ipfs/{dirCid}/         → directory listing
https://ipfs.ninja/ipfs/{dirCid}/photo.jpg → that one file

集群会进行递归固定,因此子项同样可以被解析 — 即使您之后从账户中删除了原始文件,快照中的副本仍会保留,因为它是通过目录递归产生的一个独立固定。

重新生成快照

对未更改的文件夹重新生成快照会返回相同的 CID — 目录 CID 是内容寻址的,因此相同的内容始终会产生相同的哈希值,并且集群的固定调用会识别出重复项,在其一端不做任何实际操作。

注意:即使结果是相同的 CID,快照这条路径本身也并非没有成本。每次调用都会从 IPFS 读回每个文件的字节内容,并将其作为 multipart 数据重新上传到集群的 /add 端点 — 目录包装(wrap-with-directory)正是在这一步完成的。对于典型的文件夹(≤100 个小文件),这仍然可以在几秒内完成;对于非常大的文件夹,建议仅在内容确实发生变化时才调用快照。

在添加或删除文件后调用快照会产生不同的 CID;只要您不删除其底层文件,之前的 CID 会继续可解析。

限制

  • 文件夹必须至少包含一个文件。空文件夹会返回 400 — folder is empty
  • 文件名字符会在 Kubo 接受的 multipart 上传中进行 URL 编码;如果您的文件名中包含空格或非 ASCII 字符,网关 URL 可能需要进行百分号编码。
  • 快照会按每个唯一 CID 计入您计划的固定总数一次 — 文件区块会被去重,因此快照大多只是在您已固定的文件之上增加一个很小的目录节点。

更新文件夹

PUT /folders/{folderId}

参数类型必填描述
namestring新的显示名称。
parentFolderIdstring | null重新指定文件夹的父级。使用 null 将其移动到根目录。

删除文件夹

DELETE /folders/{folderId}

删除该文件夹,并递归级联删除其中包含的每个文件和子文件夹。此操作受到与单个文件删除相同的共享 CID 安全保护 — 如果其他用户仍在固定您上传的某个 CID,您的取消固定操作不会将其从他们那里移除。

json
{
  "deleted": true,
  "filesDeleted": 42,
  "foldersDeleted": 3
}

为文件夹 / bucket 配置 S3 CORS

通过 S3 兼容 API 暴露的文件夹会作为 bucket。如果您是从浏览器 JavaScript 中调用该 API,就需要在 bucket 上设置 CORS 规则,以便浏览器的预检请求(preflight)能够通过。有两个等效的入口会持久化到同一个存储:

  • PUT /folders/{folderId}/cors — 此 REST 端点,通过 JWT 认证(供 Dashboard 使用)
  • S3 子资源 PUT /{bucket}?cors — 通过 SigV4 认证(供 AWS SDK 使用,参见 s3-compatibility.md

如果尚未被认领,该端点上的 PUT 操作还会将该文件夹的名称认领为一个全局唯一的 bucket

PUT /folders/{folderId}/cors

为文件夹的 S3 bucket 设置 CORS 规则。每个 bucket 最多 5 条规则,总计 64 KB。

参数类型必填描述
rulesCorsRule[]AWS 格式的 CORS 规则数组(见下文)。不能为空。
bucketNamestring显式指定的 S3 bucket 名称。默认为文件夹的显示名称。如果所需名称已在全局范围内被认领,请在此处传入备选名称。

每个 CorsRule

字段类型必填描述
AllowedOriginsstring[]允许发送请求的源。支持通配符(https://*.myapp.com)。使用 * 表示允许任何源。
AllowedMethodsstring[]一个或多个 GETHEADPUTPOSTDELETE
AllowedHeadersstring[]浏览器可能在请求中包含的 header。默认值:无。使用 ["*"] 以允许所有 header(推荐用于会发送 Authorizationx-amz-* 等 header 的 AWS SDK v3)。
ExposeHeadersstring[]使浏览器 JavaScript 可读取的响应 header。如果您的应用需要返回的 CID,请包含 ETagx-amz-meta-cid
MaxAgeSecondsnumber浏览器缓存预检请求结果的时长。0-86400。默认值 3600。
IDstring该规则的自由文本标签。

请求示例

bash
curl -X PUT https://api.ipfs.ninja/folders/17f6dfd8-519c-4d0e-8f3a-5988a1d34ef2/cors \
  -H "Authorization: Bearer $COGNITO_JWT" \
  -H "Content-Type: application/json" \
  -d '{
    "rules": [{
      "AllowedOrigins": ["https://myapp.com", "http://localhost:3000"],
      "AllowedMethods": ["GET", "HEAD", "PUT", "POST", "DELETE"],
      "AllowedHeaders": ["*"],
      "ExposeHeaders": ["ETag", "x-amz-meta-cid", "x-amz-request-id"],
      "MaxAgeSeconds": 3600
    }]
  }'

响应 200 OK

json
{ "success": true, "rules": [ { "AllowedOrigins": ["https://myapp.com", "http://localhost:3000"], "AllowedMethods": ["GET", "HEAD", "PUT", "POST", "DELETE"], "AllowedHeaders": ["*"], "ExposeHeaders": ["ETag", "x-amz-meta-cid", "x-amz-request-id"], "MaxAgeSeconds": 3600 } ] }

GET /folders/{folderId}/cors

返回当前的 CORS 规则以及 bucket 名称(如果已被认领)。

json
{
  "rules": [  ],
  "bucketName": "my-project"
}

DELETE /folders/{folderId}/cors

删除所有 CORS 规则。在设置新规则之前,针对该 bucket 的浏览器预检请求将始终失败(fail closed)。

Dashboard 替代方式

在 Files 页面中,每个文件夹的操作菜单都有一个 S3 CORS 选项,可打开一个基于表单的编辑器。它与此 REST 端点以及通过 S3 API 调用的 PutBucketCors 共享相同的底层存储。