关于 weaverse-content-api
用于通过经过身份验证的 REST API 读取和编辑 Weaverse 项目内容的技能,适合内容运营与自动化流程。涵盖即时写入、草稿审核、发布和定时变更,并强调版本控制与权限范围。
主要功能
- 01读取和编辑页面及主题设置
- 02管理多语言翻译
- 03批量修改页面内容
- 04保存草稿并审核发布
- 05定时发布或恢复版本
- 06创建、复制和管理项目
适用场景
- 01批量更新多个页面的文案
- 02将 AI 生成或翻译内容写入项目
- 03审核后发布或安排内容变更
- 04检查发布历史并恢复旧版本
MCP 相关
文档说明 API 可接受委托式 MCP OAuth 令牌,但此技能包本身不负责托管 MCP 服务或启用连接器。
安装
复制下面的命令,在终端中运行。
npx skills add https:/ / github.com/ weaverse/ shopify-hydrogen-skills --skill weaverse-content-api安装后在 Claude Code 中输入/weaverse-content-api确认已加载。
包含的文件
除 SKILL.md 外,安装时一起下载的参考资料和脚本。
references/endpoints.mdportable-text.mdscripts/weaverse_content_api.mjs详细介绍
Weaverse 内容 API
通过经过身份验证的 REST API,在 Studio 编辑器之外读取和编辑 Weaverse 内容(项目、页面、主题设置、翻译)。可用于批量编辑、AI/自动化内容工作流、草稿→发布流程,以及定时或版本化的内容变更。
- 基础 URL:
https://studio.weaverse.io/api/v1/content - 机器规范:
GET https://studio.weaverse.io/api/v1/content/openapi.json(OpenAPI 3.1,无需身份验证)——权威契约。请获取该规范以查看精确的字段级架构;本文档是工作流指南。 - 完整端点详情:
references/endpoints.md。富文本/Portable Text 详情:references/portable-text.md。 - 辅助脚本:
scripts/weaverse_content_api.mjs(零依赖,Node 18+)。
首先必须了解的一件事
并非所有写入操作都会立即上线。该 API 有三种写入模式:
- 实时编辑 —
PATCH .../pages/:type/*handle(条目数据)、PATCH .../theme-settings和翻译写入会立即生效并使缓存失效,通过api.weaverse.io上线——与 Studio 保存操作走的是同一条路径。 - 暂存写入 + 显式发布 — 页面草稿(
GET/PUT/DELETE .../page-drafts/:pageId)、全局版块草稿(op=save-draft/discard-draft)以及待发布版本替换(PUT /versions/{versionId},受 CAS 保护;拒绝草稿)不会自行更改线上内容。发布属于实时写入:POST /publish-versions/{versionId}(发布已保存的草稿)、POST /versions/{versionId}/publish-now(立即发布计划中的版本),或POST /versions/{versionId}/restore(立即覆盖线上内容——需确认的回滚)。POST /versions/{versionId}/schedule也并非无副作用:它会在publishAt自动提交线上变更,无需后续调用——因此,对已计划版本执行PUT替换也会在该时间上线。以上操作都需要content:publish(恢复操作还需要content:delete)。 - 项目生命周期 —
POST /projects,使用op=create|copy|delete|set-settings|purge-cache(作用域project:manage;删除还需要content:delete+confirm)。可以通过 API 创建项目——可以创建空白项目或以主题为基础的项目,也可以在后台复制本店自己的项目或公开演示商店项目。
因此,生命周期如下:
Create project → POST /projects (op=create) — or start from Weaverse Builder / demo store
Create initial pages → import a project JSON into Studio (generating-weaverse-project-json)
OR create pages one by one via POST /projects/:projectId/pages
Update content → live PATCH (item edits, theme settings) when immediacy is wanted
OR draft → review → publish / schedule when it must be gated
Fix a bad publish → restore a version (confirm-gated) or re-PATCH
适用场景
- 将 AI 生成或翻译的文案推送到现有线上项目
- 批量编辑多个页面/条目中的内容
- 读取当前页面内容/条目以进行差异比较或往返处理
- 向页面添加新的类型化条目(通过在新 ID 上使用带
type的PATCH),或重新链接children - 创建
CUSTOM页面或由资源支持的模板页面(POST /projects/:projectId/pages) - 将编辑暂存为草稿,然后立即发布、定时发布或丢弃
- 恢复先前的页面/主题版本,或查看发布历史
- 读取/写入页面的各语言翻译,或项目范围的翻译单元
- 创建/复制/删除项目,或更改项目名称/默认语言区域(
POST /projects生命周期操作) - 批量删除页面
- 将图片/视频上传到 Shopify,并在 Weaverse 条目中引用其 CDN URL
身份验证
除 openapi.json 外,每个端点都需要 bearer token:
Authorization: Bearer <WEAVERSE_API_KEY>
- 从 Weaverse Studio → Dashboard → Account/Settings → API Keys 获取商店密钥。将其存储在环境变量(
WEAVERSE_API_KEY)中;切勿将其硬编码,也不要在本地测试以外的场景中将其作为?apiKey=查询参数传递——查询参数会泄露到服务器/CDN 日志中。 - 商店密钥仅适用于一个商店。请求其他商店拥有的项目会失败(403/404——API 不会披露其他租户的信息)。
- 同一令牌也可授权 Shopify 代理(参见“将资源上传到 Shopify”)。
范围和令牌类型
bearerAuth 方案接受商店 API 密钥、带范围的 API 密钥、委派的 MCP OAuth 令牌,或(仅适用于翻译单元路由)绑定到项目的翻译 Agent 令牌。范围如下:
| 范围 | 授予权限 |
|---|---|
content:read | 读取项目、页面、主题设置、版本、草稿、翻译单元 |
content:write | 保存草稿和非破坏性编辑(条目、元数据、SEO、分配、语言、术语表)。无法调用明确的发布/计划/恢复/删除端点——但其实时编辑(PATCH .../pages/...、页面创建)会立即应用到店面 |
content:publish | 发布草稿、计划/重新计划/取消发布、恢复版本、发布全局版块 |
content:delete | 删除页面/全局版块/语言/静态键、撤销覆盖;删除项目时必须同时具有 project:manage |
project:manage | 创建/复制/删除项目、设置、变体、层级、备份、预览、主机名策略 |
translations:read / translations:write | 仅适用于翻译单元路由;无法访问一般内容 |
- 带范围的凭据缺少某个范围时,会返回
403 INSUFFICIENT_SCOPE,且不会写入任何内容。 - 旧版无范围密钥保留读取/写入/翻译的基础权限和所有范围机制引入前的端点,但不会隐式获得发布/删除/项目管理权限——其历史上的批量页面删除权限除外(在范围机制出现前签发的密钥仍可使用
DELETE .../pages)。请将此类密钥视为具有破坏性操作能力,并替换为带范围的密钥。 - 委派令牌(MCP OAuth)在写入时必须发送修订令牌:页面补丁请求需提供
expectedUpdatedAt,主题设置请求需提供expectedRevision;省略则返回428 PRECONDITION_REQUIRED。API 密钥可以省略这些参数,但仍建议默认发送。 - 带范围的密钥可以按任务严格限定权限(例如,为翻译 Agent 配置
content:read+translations:write),这样即使密钥泄露或脚本失控,也无法删除或发布内容。自动化任务应优先采用这种配置。
规范接受委派的 MCP OAuth 令牌,这只是关于身份验证的一项事实。托管 MCP 服务或列出 Claude/ChatGPT 连接器,是需要单独启用的功能,本技能包不会执行这些操作。
核心实时更新工作流
编辑前先阅读。 要更改现有内容,必须指定真实的项目条目 ID,因此请先读取页面——不能盲目打补丁。新增条目是唯一例外:它们使用全新的 ID 和一个 type,并且必须符合页面树结构(children 引用必须指向页面上已有的 ID,或在同一请求中创建的 ID)。
- 查找项目 —
GET /projects,按名称匹配并记下其id。 - 选择语言区域 —
GET /projects/:projectId/languages。记下isDefault: true的代码(例如en-us)。空的data: []是有效状态:项目没有配置语言,所有内容都在基础语言区域中——不要猜测或编造代码;显式使用locale=en-us读取时,会通过回退链访问基础页面。 - 读取页面 —
GET /projects/:projectId/pages/:type/*handle?locale=<code>。务必传入locale。解析时会依次回退到请求的语言区域 → 项目默认语言区域 →en-default,因此缺少语言区域仍可能成功,但返回其他语言区域的页面——随后编辑就会落到错误的页面上。默认的weaverse格式已经返回每个条目的id——补丁正需要这个 ID(只有读取portable-text时,?meta=true才有用)。保留响应中的updatedAt;它是补丁的乐观并发控制令牌。 - 构建补丁 — 对每个条目,只在
data中发送需要更改的字段(它会浅合并;嵌套对象会被整体替换)。每个条目都需要同时包含id和data——data不能省略,即使只重新关联拓扑结构也必须使用"data": {}。要创建新条目,请提供全新的id和type。包含与读取时相同的locale,并将读取结果中的updatedAt作为expectedUpdatedAt:{ "locale": "en-us", "expectedUpdatedAt": "2026-10-21T12:00:00.000Z", "items": [ { "id": "itm1", "data": { "heading": "New heading" } }, { "id": "itm-new", "type": "Hero", "data": { "heading": "Fresh section" }, "children": [{ "id": "itm1" }] } ] } - 应用补丁 —
PATCH /projects/:projectId/pages/:type/*handle(如果客户端或代理无法发送PATCH请求体,也接受 POST)。每个请求最多 100 个条目——较大的编辑请分批处理。添加"exact": true,以拒绝语言区域或句柄回退,并且只写入存储的(type, handle, locale)与请求目标完全一致的分配项(委托写入始终是精确匹配)。 - 检查响应 —
{ object: "page_update", requested, updated, created, notFound, failed, updatedIds, createdIds, notFoundIds, failedIds }。notFoundIds非空 = ID 不在解析出的页面上(页面或语言区域错误、ID 过期,或发送的新 ID 缺少type)——请用正确的语言区域重新读取,不要盲目重试。failedIds= 在请求中途检测到过期后,结果未能确认的条目——请重新读取并重新应用;不要假定它们已应用。
**过期拒绝:**如果页面在读取后发生变化(例如 Studio 中有并发保存),整个请求会在写入任何内容之前被拒绝,并返回 409 STALE_PAGE。请重新读取,并基于更新后的内容重新应用——绝不要重试相同的补丁。主题设置对 expectedRevision 也采用相同处理方式(409 STALE_PROJECT)。
成功的实时补丁会使缓存失效,并通过 api.weaverse.io 提供服务——与 Studio 保存所使用的路径相同。如果响应含糊不清(存在 failedIds,或发布/删除时出现 cacheDelivery: "degraded"),请重新读取资源以确认实际状态,然后再报告成功。
在一个请求中填充新建或空白页面
通过 POST /pages 创建的页面(或空白模板)只有一个根 main 条目。要从导入格式的 JSON 构建整个页面:
- 读取页面并获取根
main条目的 ID。 - 发送一个 PATCH(≤100 个条目),包含:根条目
{ "id": <rootId>, "data": {}, "children": [...] }(即使data为空也必须提供),以及作为新条目的每个 section/block,包含id、type、data、children。 - 预期结果:
updated: 1, created: N, notFound: 0。
每个页面都要使用全新的 ID(不要复用其他页面或先前测试渲染中的 ID)。通过这种方式发送的内容会跳过 Studio 的导入,因此不会应用 schema 预设——所有非默认值都必须包含在 data 中。
主题设置
PATCH /projects/:projectId/theme-settings,请求体为 { "theme": { ...changedKeys } },会浅合并顶层主题键(嵌套对象会整体替换——请先读取它们),仅写入项目自身的配置,并记录可还原的 ThemeVersion。将 GET 响应中的 revision 作为 expectedRevision 发送。主题键是全局的:产品卡片的键会为网站上的所有产品卡片重新设置样式。响应会返回完整合并后的主题和 updatedKeys。
页面元数据(名称、SEO)
GET/POST /projects/:projectId/page-settings/:pageId — op=rename(name/prefix)、op=rename-custom(name + handle、assignmentId)、op=set-seo(seo 对象)。此处可以写入 SEO;SEO 不属于页面内容 PATCH。
草稿 → 发布工作流
当编辑需要审核或审批,而不是立即上线时,请使用草稿。通过 pageId 定位——不会回退到 locale/handle,因此草稿绝不会应用到其他 assignment。
- 读取依据 —
GET /projects/:projectId/page-drafts/:pageId。如果存在草稿头,则返回当前草稿头;否则返回线上内容,同时返回保存时必须沿用的修订令牌:headVersionId、pageUpdatedAt、projectUpdatedAt。如果存在草稿头,页面和项目令牌是构建该草稿时依据的修订;线上内容一旦有更新,保存就会被拒绝。 - 保存草稿 — 使用完整项目列表(≤200 个项目,每项包含
id+ 可选的type/data/children;格式错误的图结构会返回 400)和 GET 原样返回的三个expected*令牌(包括原样传入的null)调用PUT .../page-drafts/:pageId。如果草稿头、线上页面或项目有更新,则会以409 STALE_PAGE拒绝保存——不会保存任何内容,请重新读取。绝不会触及线上内容。 - 发布 — 使用
{ "projectId", "pageId" }调用POST /publish-versions/:versionId(可选传入replaceScheduledVersionId,以原子方式替换已有的计划版本)。与 Studio 发布使用相同的提升和缓存扇出机制;需要content:publish权限。提交发布后若缓存失效操作失败,响应会报告cacheDelivery: "degraded"——内容已更改,交付已排队。 - 或丢弃 — 通过与草稿头进行精确 CAS,调用
DELETE .../page-drafts/:pageId。
全局区块
GET /projects/:projectId/global-sections 会列出区块及其使用情况。POST .../global-sections 会创建一个区块({ itemId, name })。对于每个区块:GET .../global-sections/:sectionId 会读取草稿头(不存在时为 null);POST .../global-sections/:sectionId 可执行 op=save-draft / discard-draft / publish-draft / rename / delete。save-draft/discard-draft 需要 content:write;publish-draft 需要 content:publish;delete 需要 content:delete + confirm="<sectionId>"。save-draft 需要完整项目列表和 expectedHeadVersionId CAS 令牌。
版本:历史记录、计划发布、恢复
- 列出 —
GET /projects/:projectId/versions?pageId=<id>(该页面的版本)、?kind=theme(主题版本)、?kind=retired-pages(已停用页面的版本,用于恢复),默认?kind=scheduled(当前计划发布,页面 + 主题)。 - 读取单个版本 —
GET /versions/:versionId?type=page|theme&projectId=<id>。 - 计划发布 —
POST /versions/:versionId/schedule{ projectId, type, publishAt }(页面版本还可提供replaceScheduledVersionId;主题版本会被拒绝并返回 400)。版本会在publishAt自动上线 — 无需再调用;应将计划发布视为批准上线变更。publishAt必须是未来时间;页面 / 项目已有计划版本时会返回409,且不会更改任何内容。 - 调整时间 / 取消 — 仅对计划发布中的版本使用
PATCH /versions/:versionId(重新安排时间)和DELETE /versions/:versionId(取消);不再处于计划发布状态的版本会返回409/ 404。 - 立即发布 —
POST /versions/:versionId/publish-now{ projectId, type }。 - 恢复 —
POST /versions/:versionId/restore{ projectId, type, confirm: "<versionId>" }。恢复会覆盖线上内容,因此需要同时具备content:publish和content:delete权限,并提供确认字符串。应将其视为经商家批准的回滚,而非常规编辑。遇到409(并发占用,未作任何更改)时,绝不要重放请求:重新读取版本和线上目标,并先就当前状态再次与商家确认。
翻译
有两种协议;两者都只写入 Translation 行 — 基础页面内容、条目和其他所有语言区域均保持不变;项目默认语言不能作为目标语言(它是其他语言进行翻译的源语言)。
- 按页面翻译 —
GET /projects/:projectId/page-translations/:pageId?locale=<code>会返回每个可翻译键及其source、当前translation,以及写回时必须重放的targetGeneration。对同一 URL 发送POST,并原样回传条目,仅修改translation(每次请求最多 250 条)。每个条目都会基于其对应的source和读取到的targetGeneration进行比较并设置 — 延迟的 Agent 绝不会覆盖商家更新后的源文本或其他写入者更新后的翻译;被拒绝的条目会出现在stale中,且不会写入。translation: ""会清除某个键(并与从未翻译过的状态区分开)。写入后,再次 GET 以读取结果。 - 项目级翻译单元 —
GET /projects/:projectId/translation-units?targetLocale=<code>(kind=text|image、status、游标分页)会列出存储的项目架构批准的所有单元 — 没有存储架构的组件或其他输入类型的字段不会列出,也不可写入。POST /projects/:projectId/translations/validate会运行所有检查,但不写入任何内容(试运行);POST .../translations/apply会在项目锁定期间以原子方式写入整批内容。任何过时的源 / 目标都会导致整批被拒绝(409 STALE_TRANSLATION),且不会写入任何内容;重试相同请求会收敛为无变化。这些路由也接受绑定到项目的翻译 Agent 令牌(仅限translations:read/translations:write)。
项目生命周期
使用 op 调用 POST /projects(权限范围 project:manage):
op | 正文 | 效果 |
|---|---|---|
create | name?、projectId?、config.themeName? | 创建空白项目或以主题为基础的项目 |
copy | sourceProjectId、name? | 在后台克隆(返回 202 + targetProjectId);源项目必须是本商店自有项目或公开的演示商店项目;通过列出目标项目的页面来确认完成 |
delete | projectId、confirm(= projectId) | 软删除,并在删除前备份;还需要 content:delete |
set-settings | projectId、expectedUpdatedAt、name?、defaultLocale? | 设置带修订版本校验的非机密设置 |
purge-cache | projectId | Studio 的“清除缓存” |
PATCH /projects/:projectId 会重命名项目(仅限 name,未知字段会返回 400)。创建、复制或删除前请先征求商家同意 — 这些操作会更改账户级状态,而不只是单个页面的内容。
Content API 无法执行的操作
- 将 Shopify 资源发布到销售渠道 — 代理令牌缺少
read_publications/write_publications权限。 - 通过 API 密钥设置市场设置 —
PATCH /projects/:projectId仅接受name。(层级结构 — 变体、父级链接/解除链接、页面覆盖 — 可通过专用的POST /projects/:projectId/hierarchy路由在project:manage权限下写入;破坏性操作需要确认;详见references/endpoints.md。)
页面寻址
页面通过页面类型 + handle 寻址:
INDEX, PRODUCT, ALL_PRODUCTS, COLLECTION, COLLECTION_LIST, PAGE, BLOG,
ARTICLE, CART, CUSTOMER, NOT_FOUND, PASSWORD, SEARCH, CUSTOM
- 单例(
INDEX、ALL_PRODUCTS、COLLECTION_LIST、CART、CUSTOMER、NOT_FOUND、PASSWORD、SEARCH)— 每个项目只有一个页面,省略 handle。 - CUSTOM — 通过其路径寻址(通配部分可包含斜杠,例如
blogs/news)。 - 模板化页面(
PRODUCT、COLLECTION、PAGE、BLOG、ARTICLE)— 将共享默认模板保留在空 handle 下,因此缺少 handle 时会被拒绝(不会静默编辑模板)。请传入真实的 handle。 - 真实 handle 并不保证存在针对单个资源的页面。 即使不存在针对单个资源的覆盖,在读取
…/pages/PRODUCT/<real-handle>时也会成功(200) — 解析器会回退到该类型的共享默认模板,返回的id标识该共享页面。随后执行 PATCH 会编辑该类型所有资源都会渲染的模板。PATCH 前请检查返回的id;如果更改仅针对一个资源,请先创建针对该资源的覆盖(POST /pages会克隆共享默认模板)。有意编辑共享模板也可以 — 请确认了解其影响。
Locale 始终重要。 读取/更新时,请始终传入真实的 locale 代码(来自 List languages)。在 list-pages 响应中,市场优先型项目的行的 locale 可能为 null(行按市场而非 locale 编号)— 不要将 null 原样传回;请传入真实代码,让解析器将其映射到市场(例如,locale=en-us 会解析到市场 us)。
完整的端点列表、查询参数和响应结构请参阅 references/endpoints.md。
将资源上传到 Shopify
Content API 本身没有上传端点。要将媒体添加到 Weaverse 项目,请先将其上传到 Shopify,然后引用返回的 CDN URL。
上传通过 Weaverse Shopify 代理进行,该代理接受相同的 Weaverse 令牌:
POST https://studio.weaverse.io/api/admin-graphql
Authorization: Bearer <WEAVERSE_API_KEY>
Content-Type: application/json
请求正文是标准的 Shopify Admin GraphQL 请求({ "query": "...", "variables": {...} })。上传遵循 Shopify 的标准两步流程:
stagedUploadsCreate→ 获取url+parameters(预签名目标)以及resourceUrl。- 使用返回的
parameters将文件字节上传到该暂存url(multipart POST,不通过代理)。 - 使用
originalSource: <resourceUrl>调用fileCreate→ Shopify 导入文件并返回永久 CDN 文件。 - 读取文件的
image.url/sources,并通过上述更新工作流将该 CDN URL 放入 Weaverse 项目data中。
builder 仓库中的参考实现:app/backend/admin/file.server.ts(generateStagedUploadLinks → stagedUploadsCreate,然后是 fileCreate)。如有疑问,请参照其中的 mutations 和字段选择。
或者,如果有已连接的 Shopify MCP,其图片上传 /
graphql_mutation工具也能完成相同工作,无需使用代理。使用已连接的工具即可。
辅助脚本的 upload 命令会执行全部四个步骤,并打印每个文件的 CDN URL、id 和大小。代理调用时请发送 User-Agent 标头 — 不带该标头的请求会被拒绝并返回 403。该代理是标准的 Admin GraphQL 端点,因此令牌允许的其他管理 mutations(例如用于导航菜单的 menuUpdate、fileDelete)也可以通过它执行。
辅助脚本
scripts/weaverse_content_api.mjs 封装了身份验证和常用调用。它会从环境变量中读取 WEAVERSE_API_KEY。
export WEAVERSE_API_KEY=...
node scripts/weaverse_content_api.mjs projects
node scripts/weaverse_content_api.mjs languages <projectId>
node scripts/weaverse_content_api.mjs theme <projectId>
node scripts/weaverse_content_api.mjs theme-update <projectId> <theme.json> # flat { "key": value }; the script wraps it in { theme } and replays the current revision as expectedRevision (409 STALE_PROJECT on a concurrent change)
node scripts/weaverse_content_api.mjs pages <projectId> [type]
node scripts/weaverse_content_api.mjs page <projectId> <type> [handle] [locale] # reads with ?locale
node scripts/weaverse_content_api.mjs create-page <projectId> <type> <handle> [name]
node scripts/weaverse_content_api.mjs update <projectId> <type> [handle] <patch.json> # omit handle for INDEX & other singletons
node scripts/weaverse_content_api.mjs delete <projectId> <type> <handle...>
node scripts/weaverse_content_api.mjs delete-ids <projectId> <pageId...> # projects without languages
node scripts/weaverse_content_api.mjs upload <file...> # → Shopify Files, prints CDN URLs
可使用它快速检查项目并应用补丁文件。对于该脚本未涵盖的内容——草稿、发布、版本、翻译、生命周期操作——请直接调用 REST 端点(参见 references/endpoints.md)或阅读 openapi.json。
危险信号
- 假设写入已上线——只有草稿保存(
PUT page-drafts、全局区段save-draft)和待发布版本的PUT /versions/{id}本身不会影响线上内容(被替换的已排期版本仍会在其publishAt时间上线)。在普通content:write权限下,线上条目的PATCH和POST /pages会立即更改店面;schedule会在publishAt自动上线;publish-versions/publish-now/restore会立即上线。 - 未经商家同意就创建、复制或删除项目——生命周期操作(
project:manage、删除操作 +content:delete+confirm)会更改账户级状态。op=copy会返回202,并在后台继续运行;通过列出目标项目的页面来查看是否完成。 - 随意恢复版本——
POST /versions/:id/restore会覆盖线上内容(需要content:publish+content:delete+confirm="<versionId>")。仅在商家批准回滚后执行。 - 原样重试
409 STALE_PAGE/STALE_PROJECT/STALE_TRANSLATION拒绝响应——资源已发生变化。重新读取,在较新的内容上重建编辑,然后再写入。page_update中的failedIds表示结果尚未确认——在确认之前,请重新读取这些条目。 - 委派的(MCP OAuth)令牌未提供
expectedUpdatedAt/expectedRevision——会收到428 PRECONDITION_REQUIRED。API 密钥可以省略这些字段;无论如何都发送它们是更安全的默认做法。 - 读取或更新页面时省略
locale——解析会按请求语言 → 默认语言 →en-default回退,因此请求可能会在不同语言的页面上成功,导致编辑看起来“丢失”(这与PAGE_NOT_FOUND不同)。务必传入 List languages 返回的真实代码;写入时使用"exact": true,可确保不会发生回退。 - 在 PATCH 中发送不带
type的新条目 ID——只有在提供type时才会创建未知 ID;否则这些 ID 会进入notFoundIds。children中的 ID 必须已存在于页面上,或在同一请求中创建。 - 未先读取 ID 就 PATCH 现有条目——必须指定真实的条目 ID。先读取页面(并使用正确的
locale);weaverse格式的读取已包含每个条目的id(无需?meta=true)。 - 发送不带
data的仅含children的条目——每个items条目都必须带有data对象;仅修改拓扑结构时也必须发送"data": {}(item.data must be an object)。 - 将 List languages 返回的
data: []视为错误(或猜测语言)——列表为空表示未配置语言(基础语言布局)。不要自行编造语言代码;显式传入en-us会通过回退链访问基础页面。 - 原样回传
locale: null——对于优先按市场区分的项目,list-pages 的行中locale可能为null。不要发送null;传入真实代码,让解析过程映射到对应市场。 - 普通编辑时添加
?meta=true——它只影响portable-text读取。对于weaverse格式的读取,它不会产生任何变化。 - 忽略响应中的
notFoundIds/stale——你的 ID 不在解析到的页面上,或源/目标已发生变化。使用正确的语言重新读取 / 重新运行 GET;不要重试相同的载荷。 - 单次更新发送超过 100 个条目(草稿保存为 200 个,翻译为 250 个,删除目标为 500 个)——请拆分请求。
- 编辑 handle 为空的模板化类型——这会按设计被拒绝。请传入真实的 handle。
- 硬编码令牌或使用
?apiKey=——请从环境变量中读取Authorization: Bearer;自动化应使用任务范围的密钥,而非完整的商店密钥。 - 替换整个
data对象——更新采用浅合并。只发送发生变化的字段;不要重新发送整个data,以免清除未读取的嵌套值。 - “上传”后在媒体字段中放入非 Shopify URL——请完成
fileCreate步骤,并使用返回的 Shopify CDN URL,而不是暂存/临时的resourceUrl。 - 批量删除时发送
locale: ""——会被拒绝("locale" cannot be an empty string)。对于未配置语言的项目,请通过pageIds删除(delete-ids)。 - PATCH 后立刻相信本地开发渲染结果——正在运行的 Hydrogen 开发服务器可能会保留之前渲染过的条目 ID 的缓存副本,因此页面仍显示旧数据。下结论认为 PATCH 未生效之前,请重启开发服务器(或在已部署的店面上验证)。
- 用已部署代码尚不支持的区段 PATCH 线上页面——在代码部署前,新的区段类型或设置在生产环境中会渲染异常。请先部署,或在部署前不久执行 PATCH 并说明情况。
- 更改全局主题键却不备份——执行
theme-update前,先从GET theme-settings保存当前值(其revision同时用作 CAS 令牌)。可在 Studio 中恢复 ThemeVersions,也可通过版本恢复功能恢复。 - 将 theme-update 文件包装在
{ "theme": … }中——脚本本身已添加包装,因此这样会写入一个多余的theme键,而不是你的设置。请检查响应中的updatedKeys。
相关技能
generating-weaverse-project-json— 创建导入 JSON,用于建立此 API 随后更新的结构。你在此处修改的项目 ID 来自该 JSON(或使用正确的locale读回的页面)。cloning-websites-to-weaverse/figma-to-weaverse— 生成传递给 JSON 生成器的版块规划。hydrogen-markets-localization— 此 API 的翻译路由所服务的端到端市场/本地化工作流。