API:商店
Halo HTTP API 商店接口:浏览和搜索商店、查看详情,安装和卸载数字人与技能,管理商店来源与更新。
浏览和搜索商店、查看条目详情,安装和卸载数字人与技能,从本地 .dhpkg 文件安装,并管理商店来源与更新。发布到商店请在 Halo 中操作,见 发布到商店。
所有路径都相对于你的 Halo 地址,每个请求都要带上访问密码。示例中的 $HALO_URL 和 $HALO_TOKEN 按快速上手设置;地址、鉴权和错误约定见 HTTP API 概览。
| 操作 | 端点 |
|---|---|
| 设置从商店安装的数字人如何处理版本升级 (数字人) | POST /api/apps/:appId/upgrade-strategy |
| 预览技能标题会安装成的斜杠命令名 | GET /api/skills/command-name |
| 获取条目的 SKILL.md 或 README 文档 | GET /api/store/app-document |
| 列出商店条目(旧接口,不分页;建议用 POST /api/store/query) | GET /api/store/apps |
| 按 slug 获取一个商店条目的完整详情 | GET /api/store/apps/:slug |
| 按 slug 从商店安装(slug 写在路径中) | POST /api/store/apps/:slug/install |
| 查询本版本支持哪些商店功能(发布、评审、安装数) | GET /api/store/capabilities |
| 获取浏览和发布用的商店分类 | GET /api/store/category-taxonomy |
| 获取商店首页的精选内容 | GET /api/store/discover-page |
| 忽略一个可用更新,不再提示 | POST /api/store/ignore-version |
| 从本地 .dhpkg 文件安装数字人 | POST /api/store/import-dhpkg |
| 按 slug 从商店安装 | POST /api/store/install |
| 列出已登录作者自己发布的应用 | GET /api/store/my-publications |
| 查找某个商店 slug 对应的已安装应用 | POST /api/store/publish/find-app |
| 预览发布应用时会得到的 slug 和版本 | POST /api/store/publish/preview |
| 分页搜索商店条目(主要的浏览接口) | POST /api/store/query |
| 强制重新下载完整的商店索引 | POST /api/store/refresh |
| 列出已配置的商店来源 | GET /api/store/registries |
| 添加商店来源 | POST /api/store/registries |
| 移除一个商店来源 | DELETE /api/store/registries/:registryId |
| 修改商店来源的适配器配置(例如 API Key) | PATCH /api/store/registries/:registryId/adapter-config |
| 启用或停用一个商店来源 | POST /api/store/registries/:registryId/toggle |
| 按条件快速检查商店索引是否有更新 | POST /api/store/revalidate |
| 下架作者自己发布的一个应用 | POST /api/store/unpublish |
| 列出已安装应用的可用更新 | GET /api/store/updates |
| 为已安装的应用应用可用更新 | POST /api/store/updates/:appId/apply |
| 立即重新检查所有已安装应用的更新 | POST /api/store/updates/check-now |
预览技能标题会安装成的斜杠命令名
GET /api/skills/command-name 助手可调用
- Query: ?name=. A missing name returns an empty string, not a 400. Pure string transform — it does not check whether that name is already taken.
查询参数:name
响应
{success:true,data:string} // e.g. "My Skill" -> "my-skill"示例
curl -s "$HALO_URL/api/skills/command-name" \
-H "Authorization: Bearer $HALO_TOKEN"获取条目的 SKILL.md 或 README 文档
GET /api/store/app-document 助手可调用
- slug is a query param (?slug=...), not a path segment — scoped slugs like "owner/repo" contain "/". content is null when the source has no document.
查询参数:slug
响应
{success:true,data:{content:string|null}}示例
curl -s "$HALO_URL/api/store/app-document" \
-H "Authorization: Bearer $HALO_TOKEN"列出商店条目(旧接口,不分页;建议用 POST /api/store/query)
GET /api/store/apps 助手可调用
- Query params: search, locale, category, type, tags (comma-separated).
查询参数:category、locale、search、tags、type
响应
{success:true,data:[{slug,name,version,author,description,type,category,tags,...}]}示例
curl -s "$HALO_URL/api/store/apps" \
-H "Authorization: Bearer $HALO_TOKEN"按 slug 获取一个商店条目的完整详情
GET /api/store/apps/:slug 助手可调用
路径参数
| 名称 | 说明 |
|---|---|
slug | 商店条目的标识(slug),来自 GET /api/store/apps。 |
响应
{success:true,data:{entry:{slug,name,version,...},spec:<AppSpec>,registryId}} or {success:false,error}示例
curl -s "$HALO_URL/api/store/apps/<slug>" \
-H "Authorization: Bearer $HALO_TOKEN"按 slug 从商店安装(slug 写在路径中)
POST /api/store/apps/:slug/install 可撤销 助手可调用
- Always send
spaceId. It is used exactly as sent: leave it out and the item installs for every workspace; name another workspace and it installs there. Both answersuccess: true, and the response does not say where it went. - Send
"spaceId": nullonly for a deliberate global install of a skill or MCP app. Optional field:userConfig(object). - Same as
POST /api/store/installwith the slug in the path, including the 403MCP_COMMAND_BLOCKEDcase.
路径参数
| 名称 | 说明 |
|---|---|
slug | 商店条目的标识(slug),来自 GET /api/store/apps。 |
请求体
{
"spaceId": "<spaceId>"
}响应
{success:true,data:{appId}} or {success:false,error,code?}示例
curl -sX POST "$HALO_URL/api/store/apps/<slug>/install" \
-H "Authorization: Bearer $HALO_TOKEN" \
-H "Content-Type: application/json" \
-d '{"spaceId":"<spaceId>"}'查询本版本支持哪些商店功能(发布、评审、安装数)
GET /api/store/capabilities 助手可调用
- Reports which Store features this build supports. Publishing happens in the Halo app, not through this API.
响应
{success:true,data:{catalog:true,installs:boolean,publish:boolean,reviewWorkflow:boolean,identity:"none"|string}}示例
curl -s "$HALO_URL/api/store/capabilities" \
-H "Authorization: Bearer $HALO_TOKEN"获取浏览和发布用的商店分类
GET /api/store/category-taxonomy 助手可调用
- Categories are keyed per app type (skill/automation/mcp/extension) with "default" as the fallback list for types without their own entry.
响应
{success:true,data:{default:[{id,label|labelKey,icon?}],<appType>?:[...]}}示例
curl -s "$HALO_URL/api/store/category-taxonomy" \
-H "Authorization: Bearer $HALO_TOKEN"获取商店首页的精选内容
GET /api/store/discover-page 助手可调用
- Query params: locale?, pageSize?. Falls back to a single paginated catalog node when no curated layout is configured.
查询参数:locale、pageSize
响应
{success:true,data:{version,nodes:[{type,title?,subtitle?,entries?:[RegistryEntry],collections?,hasMore?}]}}示例
curl -s "$HALO_URL/api/store/discover-page" \
-H "Authorization: Bearer $HALO_TOKEN"忽略一个可用更新,不再提示
POST /api/store/ignore-version 可撤销 助手可调用
- Only hides that one version; a newer update still surfaces normally.
请求体
{
"appId": "<appId — a uuid from GET /api/apps>",
"version": "1.2.0"
}响应
{success:true,data:null}示例
curl -sX POST "$HALO_URL/api/store/ignore-version" \
-H "Authorization: Bearer $HALO_TOKEN" \
-H "Content-Type: application/json" \
-d '{"appId":"<appId — a uuid from GET /api/apps>","version":"1.2.0"}'从本地 .dhpkg 文件安装数字人
POST /api/store/import-dhpkg 可撤销 助手可调用
- Installs and activates the package's Digital Human; it then runs on its own schedule. Undo with
DELETE /api/apps/:appId. - Unlike installing in the Halo app or through its assistant, this does not fetch the package's required skills or undo a half-finished install. Check
GET /api/apps/:appIdafterwards; an activation that fails after the install still answerssuccess: true. filePathis a path on the computer running Halo.spaceIdis used exactly as sent: left out means an install for every workspace, another workspace installs there, and neither is reported back.
请求体
{
"filePath": "/absolute/path/to/app.dhpkg",
"spaceId": "<spaceId>"
}响应
{success:true,data:{appId}}错误
- 400 when
filePathis missing.
示例
curl -sX POST "$HALO_URL/api/store/import-dhpkg" \
-H "Authorization: Bearer $HALO_TOKEN" \
-H "Content-Type: application/json" \
-d '{"filePath":"/absolute/path/to/app.dhpkg","spaceId":"<spaceId>"}'按 slug 从商店安装
POST /api/store/install 可撤销 助手可调用
- Always send
spaceId. It is used exactly as sent: leave it out and the item installs for every workspace; name another workspace and it installs there. Both answersuccess: true, and the response does not say where it went. - Send
"spaceId": nullonly for a deliberate global install of a skill or MCP app. Optional field:userConfig(object). - Same operation as
POST /api/store/apps/:slug/install, with the slug in the body.
请求体
{
"slug": "author/app-id",
"spaceId": "<spaceId>"
}响应
{success:true,data:{appId}} or {success:false,error,code?}错误
- 400 = missing slug.
- 403 with
code: "MCP_COMMAND_BLOCKED"when the item is an MCP server this build's policy blocks.
示例
curl -sX POST "$HALO_URL/api/store/install" \
-H "Authorization: Bearer $HALO_TOKEN" \
-H "Content-Type: application/json" \
-d '{"slug":"author/app-id","spaceId":"<spaceId>"}'列出已登录作者自己发布的应用
GET /api/store/my-publications 助手可调用
- Fails when no creator identity is signed in — this build may not support publishing at all (check
GET /api/store/capabilitiesfirst).
响应
{success:true,data:[{slug,name?,displayName?,type?,version,status:"listed"|"hidden"|"rejected",takedownBy?,rejectReason?,submittedAt?,channel?,installs?}]}示例
curl -s "$HALO_URL/api/store/my-publications" \
-H "Authorization: Bearer $HALO_TOKEN"查找某个商店 slug 对应的已安装应用
POST /api/store/publish/find-app 助手可调用
- Optional fields: type, author. appId is null when no locally installed app uniquely matches.
请求体
{
"slug": "author/app-id"
}响应
{success:true,data:{appId: string|null}}示例
curl -sX POST "$HALO_URL/api/store/publish/find-app" \
-H "Authorization: Bearer $HALO_TOKEN" \
-H "Content-Type: application/json" \
-d '{"slug":"author/app-id"}'预览发布应用时会得到的 slug 和版本
POST /api/store/publish/preview 助手可调用
- Optional fields: author, name (override the store name before deriving the slug). storeVersion is null when the slug has never been published.
请求体
{
"appId": "<appId — a uuid from GET /api/apps>"
}响应
{success:true,data:{slug,localVersion,storeVersion:string|null}}示例
curl -sX POST "$HALO_URL/api/store/publish/preview" \
-H "Authorization: Bearer $HALO_TOKEN" \
-H "Content-Type: application/json" \
-d '{"appId":"<appId — a uuid from GET /api/apps>"}'分页搜索商店条目(主要的浏览接口)
POST /api/store/query 助手可调用
- All fields optional: search, type, category, page, pageSize, locale.
请求体
{
"search": "weather",
"page": 1,
"pageSize": 20
}响应
{success:true,data:{items:[{slug,name,version,author,description,type,category,tags,...}],total?,hasMore,groups?:[{type,count,hasMore}],sources:[{registryId,status,error?}]}}示例
curl -sX POST "$HALO_URL/api/store/query" \
-H "Authorization: Bearer $HALO_TOKEN" \
-H "Content-Type: application/json" \
-d '{"search":"weather","page":1,"pageSize":20}'强制重新下载完整的商店索引
POST /api/store/refresh 助手可调用
- Heavier than
POST /api/store/revalidate— use revalidate for a cheap freshness check.
响应
{success:true,data:undefined}示例
curl -sX POST "$HALO_URL/api/store/refresh" \
-H "Authorization: Bearer $HALO_TOKEN"列出已配置的商店来源
GET /api/store/registries 助手可调用
adapterConfigis returned as stored and can hold an API key in plain text. Treat the response like a secret.
响应
{success:true,data:[{id,name,url,enabled,isDefault?,sourceType?,adapterConfig?}]}示例
curl -s "$HALO_URL/api/store/registries" \
-H "Authorization: Bearer $HALO_TOKEN"添加商店来源
POST /api/store/registries 助手可调用
- Optional fields:
sourceType(string) andadapterConfig(object, adapter-specific, for example an API key). The response returnsadapterConfigas stored. urlmust be http(s) and must not point to a loopback, private or link-local host. Fails if a source with the same URL already exists.
请求体
{
"name": "My Registry",
"url": "https://example.com/registry"
}响应
{success:true,data:{id,name,url,enabled,isDefault:false,sourceType?,adapterConfig?}} | {success:false,error}示例
curl -sX POST "$HALO_URL/api/store/registries" \
-H "Authorization: Bearer $HALO_TOKEN" \
-H "Content-Type: application/json" \
-d '{"name":"My Registry","url":"https://example.com/registry"}'移除一个商店来源
DELETE /api/store/registries/:registryId 可撤销 助手可调用
- Fails with an error (not thrown) when the target is the built-in/default registry — those cannot be removed. Can be added back with
POST /api/store/registries.
路径参数
| 名称 | 说明 |
|---|---|
registryId | 商店来源 ID,来自 GET /api/store/registries。 |
响应
{success:true,data:undefined} or {success:false,error}示例
curl -sX DELETE "$HALO_URL/api/store/registries/<registryId>" \
-H "Authorization: Bearer $HALO_TOKEN"修改商店来源的适配器配置(例如 API Key)
PATCH /api/store/registries/:registryId/adapter-config 可撤销 助手可调用
- Body is a flat JSON object of adapter-specific fields — exact keys depend on the registry's sourceType.
- Write-only: the response never echoes the config back, so this is safe for setting credentials. 400 if the body is missing or not a plain object.
路径参数
| 名称 | 说明 |
|---|---|
registryId | 商店来源 ID,来自 GET /api/store/registries。 |
请求体
{
"apiKey": "sk-..."
}响应
{success:true,data:undefined}示例
curl -sX PATCH "$HALO_URL/api/store/registries/<registryId>/adapter-config" \
-H "Authorization: Bearer $HALO_TOKEN" \
-H "Content-Type: application/json" \
-d '{"apiKey":"sk-..."}'启用或停用一个商店来源
POST /api/store/registries/:registryId/toggle 可撤销 助手可调用
路径参数
| 名称 | 说明 |
|---|---|
registryId | 商店来源 ID,来自 GET /api/store/registries。 |
请求体
{
"enabled": true
}响应
{success:true,data:undefined}错误
- 400 if enabled is missing or not a boolean.
示例
curl -sX POST "$HALO_URL/api/store/registries/<registryId>/toggle" \
-H "Authorization: Bearer $HALO_TOKEN" \
-H "Content-Type: application/json" \
-d '{"enabled":true}'按条件快速检查商店索引是否有更新
POST /api/store/revalidate 助手可调用
- changed:false means the index did not move (a 304-equivalent); the browse list does not need refetching.
响应
{success:true,data:{changed:boolean}}示例
curl -sX POST "$HALO_URL/api/store/revalidate" \
-H "Authorization: Bearer $HALO_TOKEN"下架作者自己发布的一个应用
POST /api/store/unpublish 可撤销 助手可调用
- Can be republished later; already-installed/downloaded copies elsewhere are not affected either way.
请求体
{
"slug": "author/app-id"
}响应
{success:true,data:null}示例
curl -sX POST "$HALO_URL/api/store/unpublish" \
-H "Authorization: Bearer $HALO_TOKEN" \
-H "Content-Type: application/json" \
-d '{"slug":"author/app-id"}'列出已安装应用的可用更新
GET /api/store/updates 助手可调用
响应
{success:true,data:[{appId,currentVersion,latestVersion,entry,strategy,severity}]}示例
curl -s "$HALO_URL/api/store/updates" \
-H "Authorization: Bearer $HALO_TOKEN"为已安装的应用应用可用更新
POST /api/store/updates/:appId/apply 可撤销 助手可调用
- mode is optional: "patch_minor"|"major"|"force", defaults to "force". No built-in downgrade path — reinstalling the old version is the way back.
- A digital human keeps the user's version of every field that differs from the author's new version (prompt, run schedule, name, ...); kept lists those fields, empty when the update applied in full. editsKnown false means there was no earlier author version to compare with, so every difference was kept. The user can switch kept fields to the author's version in the app.
路径参数
| 名称 | 说明 |
|---|---|
appId | 数字人 ID,来自 GET /api/apps。 |
请求体
{
"mode": "force"
}响应
{success:true,data:{appId,from,to,severity,kept,editsKnown}} or {success:false,error}示例
curl -sX POST "$HALO_URL/api/store/updates/<appId>/apply" \
-H "Authorization: Bearer $HALO_TOKEN" \
-H "Content-Type: application/json" \
-d '{"mode":"force"}'立即重新检查所有已安装应用的更新
POST /api/store/updates/check-now 可撤销 助手可调用
- Apps set to auto-update silently apply any patch/minor update found — this is not just a read.
响应
{success:true,data:[{appId,currentVersion,latestVersion,entry,strategy,severity}]}示例
curl -sX POST "$HALO_URL/api/store/updates/check-now" \
-H "Authorization: Bearer $HALO_TOKEN"