@ai-wendao/ant 0.3.11 → 0.3.12
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/MIGRATION.md +6 -6
- package/README.md +1 -1
- package/client.js +67 -35
- package/package.json +2 -1
package/MIGRATION.md
CHANGED
|
@@ -13,7 +13,7 @@
|
|
|
13
13
|
此方式适用于 DSH Desktop RC2 使用默认、启用 HMR 的 Desktop profile,且目标 ANT 版本已发布到 npm:
|
|
14
14
|
|
|
15
15
|
1. 打开 **插件 → ANT**,点击 **卸载** 并确认。
|
|
16
|
-
2. 回到插件列表,点击
|
|
16
|
+
2. 回到插件列表,点击 **添加插件**,输入目标版本的直接包名(正式发布后例如 `@ai-wendao/ant@0.3.12`),然后点击 **安装**。
|
|
17
17
|
3. 安装完成后启用 ANT,打开设置页,检查服务连接与获准模型。
|
|
18
18
|
|
|
19
19
|
RC2 的 Desktop 基础 profile 默认启用 HMR;官方管理器在该模式下会先卸载 Bundle,再用随 DSH 提供的包管理器移除依赖。包卸载本身不会调用 ANT 的“断开设备”操作,也不会清空 DSH 凭证存储。若 profile 禁用了 HMR,管理器会提示先停止 profile;此时改用下方 CLI 备用流程。真实成员 profile 的凭证保留仍需在目标 RC2 客户端上验收。
|
|
@@ -59,14 +59,14 @@ node packages/ant-bundle/tools/migrate-legacy.mjs migrate --apply
|
|
|
59
59
|
安装了系统 Node.js 的成员也可以从已发布 npm 包运行:
|
|
60
60
|
|
|
61
61
|
```sh
|
|
62
|
-
npm exec --yes --package @ai-wendao/ant@0.3.
|
|
63
|
-
npm exec --yes --package @ai-wendao/ant@0.3.
|
|
62
|
+
npm exec --yes --package @ai-wendao/ant@0.3.12 -- ant-migrate inspect
|
|
63
|
+
npm exec --yes --package @ai-wendao/ant@0.3.12 -- ant-migrate migrate
|
|
64
64
|
```
|
|
65
65
|
|
|
66
66
|
退出 DSH 后执行变更:
|
|
67
67
|
|
|
68
68
|
```sh
|
|
69
|
-
npm exec --yes --package @ai-wendao/ant@0.3.
|
|
69
|
+
npm exec --yes --package @ai-wendao/ant@0.3.12 -- ant-migrate migrate --apply
|
|
70
70
|
```
|
|
71
71
|
|
|
72
72
|
若 CLI 不在 PATH,可追加 `--dsh-cli "<Desktop CLI 完整路径>"`;若 DSH 使用自定义数据目录,可追加 `--dsh-home "<DSH_HOME 路径>"`。
|
|
@@ -76,8 +76,8 @@ npm exec --yes --package @ai-wendao/ant@0.3.11 -- ant-migrate migrate --apply
|
|
|
76
76
|
`migrate --apply` 会输出受限权限的备份目录,备份包含 profile 的 `package.json`、`pnpm-lock.yaml`、`pnpm-workspace.yaml`(若存在)及其 SHA-256 校验值,不包含密钥库。备份仅用于迁移状态核验和保留原始清单,不等于离线恢复包。确认 DSH 已退出后,通过同一工具调用:
|
|
77
77
|
|
|
78
78
|
```sh
|
|
79
|
-
npm exec --yes --package @ai-wendao/ant@0.3.
|
|
80
|
-
npm exec --yes --package @ai-wendao/ant@0.3.
|
|
79
|
+
npm exec --yes --package @ai-wendao/ant@0.3.12 -- ant-migrate rollback --backup "<备份目录>"
|
|
80
|
+
npm exec --yes --package @ai-wendao/ant@0.3.12 -- ant-migrate rollback --backup "<备份目录>" --apply
|
|
81
81
|
```
|
|
82
82
|
|
|
83
83
|
回退只在 scoped 包已安装、旧 alias 尚未移除的中间态工作;它会卸载 scoped 包并保留旧 alias。已完成迁移的 profile 不接受该回退,避免自动恢复已知有加载问题的 alias。若安装包时 npm registry 不可用,保持 DSH 关闭,稍后重新运行 `migrate --apply`。
|
package/README.md
CHANGED
|
@@ -6,7 +6,7 @@ ANT (AI-native Teams) connects a DeepSeek Harness Desktop profile to its team's
|
|
|
6
6
|
|
|
7
7
|
## 企业精选技能
|
|
8
8
|
|
|
9
|
-
团队管理员可在 ANT 管理台从 GitHub 目录、ZIP、TAR、TAR.GZ/TGZ 或单份 `SKILL.md` 导入技能,核对来源、文件和依赖后发布。已连接团队的成员在
|
|
9
|
+
团队管理员可在 ANT 管理台从 GitHub 目录、ZIP、TAR、TAR.GZ/TGZ 或单份 `SKILL.md` 导入技能,核对来源、文件和依赖后发布。已连接团队的成员在 DSH 的 ANT 插件设置页点击“打开技能中心”,进入独立目录页面浏览并安装。ANT Host 将固定版本的完整文件集放进 DSH 的用户技能目录;随后由 DSH 原生技能提供者发现和使用。
|
|
10
10
|
|
|
11
11
|
安装不会自动运行技能脚本或安装 Python、Node 等系统依赖。ANT 只更新或卸载自己管理且本机内容未被修改的技能目录;发现同名个人技能或本机改动时会停止覆盖。
|
|
12
12
|
|
package/client.js
CHANGED
|
@@ -9,6 +9,7 @@ window.__ModuleLoader__.load({
|
|
|
9
9
|
const DEVICE_ID_STORAGE_KEY = 'ant-team-device-id'
|
|
10
10
|
const ANT_BUNDLE_PACKAGE_NAME = '@ai-wendao/ant'
|
|
11
11
|
const ANT_API_PROTOCOL_VERSIONS = [1]
|
|
12
|
+
const fileCountFormat = new Intl.NumberFormat('zh-CN')
|
|
12
13
|
const panelStyle = {
|
|
13
14
|
display: 'grid', alignContent: 'start', gap: 14, padding: 18,
|
|
14
15
|
border: '0.5px solid var(--dsw-alias-border-l2)', borderRadius: 14,
|
|
@@ -60,7 +61,7 @@ window.__ModuleLoader__.load({
|
|
|
60
61
|
}
|
|
61
62
|
return false
|
|
62
63
|
}
|
|
63
|
-
const inject = ['slots', 'remote', 'remote.credentials', 'remote.settings', 'remote.pluginManager']
|
|
64
|
+
const inject = ['slots', 'layout', 'pluginNavigation', 'remote', 'remote.credentials', 'remote.settings', 'remote.pluginManager']
|
|
64
65
|
|
|
65
66
|
async function readLocalJsonResponse(response) {
|
|
66
67
|
const contentType = response.headers?.get?.('content-type') || ''
|
|
@@ -99,7 +100,7 @@ window.__ModuleLoader__.load({
|
|
|
99
100
|
return deviceId
|
|
100
101
|
}
|
|
101
102
|
|
|
102
|
-
function TeamServiceConfig({ remote }) {
|
|
103
|
+
function TeamServiceConfig({ remote, openSkillCenter }) {
|
|
103
104
|
const [serviceUrl, setServiceUrl] = useState(loadServiceUrl)
|
|
104
105
|
const [draft, setDraft] = useState(serviceUrl)
|
|
105
106
|
const [message, setMessage] = useState('')
|
|
@@ -141,21 +142,29 @@ window.__ModuleLoader__.load({
|
|
|
141
142
|
h('div', { style: { display: 'flex', flexWrap: 'wrap', alignItems: 'center', gap: 12 } },
|
|
142
143
|
message ? h('p', { role: 'status', style: mutedTextStyle }, message) : null,
|
|
143
144
|
link ? h('a', { href: link, target: '_blank', rel: 'noopener noreferrer', style: { color: 'var(--dsw-alias-link)', fontSize: 13 } }, '打开团队管理 ↗') : null)),
|
|
145
|
+
h('section', { style: { ...panelStyle, display: 'flex', flexWrap: 'wrap', alignItems: 'center', justifyContent: 'space-between' } },
|
|
146
|
+
h('div', null,
|
|
147
|
+
h('h3', { style: { margin: 0, fontSize: 16, fontWeight: 650 } }, '企业精选技能'),
|
|
148
|
+
h('p', { style: { ...mutedTextStyle, marginTop: 4 } }, '浏览团队审核发布的技能,在独立页面查看说明并安装到这台 DSH。')),
|
|
149
|
+
h('button', { type: 'button', onClick: openSkillCenter, style: primaryButtonStyle }, '打开技能中心 →')),
|
|
144
150
|
h(ModelSyncFooter, { remote, serviceUrl, onServiceUrlChange: setServiceUrl }))
|
|
145
151
|
}
|
|
146
152
|
|
|
147
|
-
function
|
|
153
|
+
function SkillCenterPage({ onBack }) {
|
|
148
154
|
const [skills, setSkills] = useState([])
|
|
149
155
|
const [loading, setLoading] = useState(false)
|
|
150
156
|
const [workingId, setWorkingId] = useState('')
|
|
151
157
|
const [message, setMessage] = useState('')
|
|
158
|
+
const [query, setQuery] = useState('')
|
|
159
|
+
const [filter, setFilter] = useState('all')
|
|
152
160
|
const refresh = async () => {
|
|
153
|
-
if (!connected) return
|
|
154
161
|
setLoading(true)
|
|
155
162
|
try {
|
|
156
163
|
const response = await fetch('/api/ant-teams/skills', { cache: 'no-store' })
|
|
157
164
|
const result = await readLocalJsonResponse(response)
|
|
158
|
-
if (!response.ok) throw new Error(
|
|
165
|
+
if (!response.ok) throw new Error(response.status === 401
|
|
166
|
+
? '请返回 ANT 插件设置,先验证工作邮箱并连接团队。'
|
|
167
|
+
: result.message || `读取技能失败(${response.status})。`)
|
|
159
168
|
if (!Array.isArray(result.skills)) throw new Error('企业技能目录格式无效。')
|
|
160
169
|
setSkills(result.skills)
|
|
161
170
|
setMessage(result.skills.length ? '' : '团队暂未发布精选技能。')
|
|
@@ -165,10 +174,7 @@ window.__ModuleLoader__.load({
|
|
|
165
174
|
}
|
|
166
175
|
finally { setLoading(false) }
|
|
167
176
|
}
|
|
168
|
-
useEffect(() => {
|
|
169
|
-
if (connected) void refresh()
|
|
170
|
-
else { setSkills([]); setMessage('') }
|
|
171
|
-
}, [connected])
|
|
177
|
+
useEffect(() => { void refresh() }, [])
|
|
172
178
|
const changeInstall = async (skill, remove = false) => {
|
|
173
179
|
const action = remove ? '卸载' : skill.local_status === 'update-available' ? '更新' : '安装'
|
|
174
180
|
const prompt = remove
|
|
@@ -189,31 +195,56 @@ window.__ModuleLoader__.load({
|
|
|
189
195
|
} catch (error) { setMessage(error instanceof Error ? error.message : `${action}失败。`) }
|
|
190
196
|
finally { setWorkingId('') }
|
|
191
197
|
}
|
|
192
|
-
|
|
193
|
-
|
|
198
|
+
const visible = skills.filter((skill) => {
|
|
199
|
+
const matchesFilter = filter === 'all' || skill.local_status === filter
|
|
200
|
+
const matchesQuery = !query.trim() || `${skill.title} ${skill.description} ${skill.dsh_name}`.toLowerCase().includes(query.trim().toLowerCase())
|
|
201
|
+
return matchesFilter && matchesQuery
|
|
202
|
+
})
|
|
203
|
+
const statusLabel = { installed: '已安装', 'update-available': '可更新', 'not-installed': '未安装', 'not-discovered': 'DSH 未发现', conflict: '本机冲突' }
|
|
204
|
+
return h('section', { 'aria-label': '企业精选技能', style: {
|
|
205
|
+
height: '100%', overflowY: 'auto', boxSizing: 'border-box',
|
|
206
|
+
padding: 'calc(var(--dsh-frame-top-clearance, 0px) + 20px) clamp(16px, 3vw, 36px) 48px',
|
|
207
|
+
} }, h('div', { style: { maxWidth: 1440, margin: '0 auto', display: 'grid', gap: 22 } },
|
|
208
|
+
h('button', { type: 'button', onClick: onBack, style: { ...secondaryButtonStyle, justifySelf: 'start' } }, '← 返回 ANT 插件设置'),
|
|
209
|
+
h('div', { style: { display: 'flex', flexWrap: 'wrap', alignItems: 'end', justifyContent: 'space-between', gap: 16 } },
|
|
194
210
|
h('div', null,
|
|
195
|
-
h('
|
|
196
|
-
h('p', { style: { ...mutedTextStyle, marginTop:
|
|
197
|
-
h('button', { type: 'button', disabled:
|
|
198
|
-
|
|
211
|
+
h('h1', { style: { margin: 0, fontSize: 28 } }, '企业精选技能'),
|
|
212
|
+
h('p', { style: { ...mutedTextStyle, marginTop: 6 } }, '团队管理员审核后发布;安装到这台 DSH 后,由 DSH 原生技能系统发现和使用。')),
|
|
213
|
+
h('button', { type: 'button', disabled: loading || Boolean(workingId), onClick: () => void refresh(), style: secondaryButtonStyle }, loading ? '读取中…' : '刷新目录')),
|
|
214
|
+
h('div', { style: { ...panelStyle, gap: 12 } },
|
|
215
|
+
h('input', { type: 'search', value: query, onChange: (event) => setQuery(event.target.value), placeholder: '搜索技能名称或说明', 'aria-label': '搜索企业精选技能', style: inputStyle }),
|
|
216
|
+
h('div', { style: { display: 'flex', flexWrap: 'wrap', alignItems: 'center', gap: 8 } },
|
|
217
|
+
...[['all', '全部'], ['not-installed', '可安装'], ['installed', '已安装'], ['update-available', '可更新']].map(([value, label]) =>
|
|
218
|
+
h('button', { key: value, type: 'button', onClick: () => setFilter(value), 'aria-pressed': filter === value,
|
|
219
|
+
style: { ...secondaryButtonStyle, minHeight: 34, padding: '6px 12px', backgroundColor: filter === value ? 'var(--dsw-alias-bg-layer-2)' : secondaryButtonStyle.backgroundColor } }, label)),
|
|
220
|
+
h('span', { style: { ...mutedTextStyle, marginLeft: 'auto' } }, `显示 ${visible.length} / ${skills.length} 个技能`))),
|
|
199
221
|
message ? h('p', { role: 'status', style: mutedTextStyle }, message) : null,
|
|
200
|
-
|
|
201
|
-
|
|
202
|
-
|
|
203
|
-
|
|
204
|
-
|
|
205
|
-
|
|
206
|
-
|
|
207
|
-
|
|
208
|
-
? h('
|
|
209
|
-
h('
|
|
210
|
-
h('
|
|
211
|
-
|
|
212
|
-
h('
|
|
213
|
-
|
|
214
|
-
|
|
215
|
-
|
|
216
|
-
|
|
222
|
+
visible.length ? h('div', { style: { display: 'grid', gridTemplateColumns: 'repeat(auto-fit, minmax(min(100%, 420px), 1fr))', gap: 16 } },
|
|
223
|
+
...visible.map((skill) => {
|
|
224
|
+
const description = skill.description || ''
|
|
225
|
+
return h('article', { key: skill.id, style: { ...panelStyle, gap: 13 } },
|
|
226
|
+
h('div', { style: { display: 'flex', flexWrap: 'wrap', justifyContent: 'space-between', alignItems: 'baseline', gap: 8 } },
|
|
227
|
+
h('h2', { style: { margin: 0, fontSize: 19 } }, skill.title),
|
|
228
|
+
h('span', { style: mutedTextStyle }, statusLabel[skill.local_status] || '状态未知')),
|
|
229
|
+
h('p', { style: mutedTextStyle }, description.length > 180 ? `${description.slice(0, 180)}…` : description),
|
|
230
|
+
description.length > 180 ? h('details', null,
|
|
231
|
+
h('summary', { style: { cursor: 'pointer', fontSize: 13 } }, '查看完整说明'),
|
|
232
|
+
h('p', { style: { ...mutedTextStyle, marginTop: 8, whiteSpace: 'pre-wrap' } }, description)) : null,
|
|
233
|
+
h('p', { style: mutedTextStyle }, `来源:${skill.source_kind === 'github' ? 'GitHub' : '管理员上传'} · 许可证:${skill.license} · ${fileCountFormat.format(skill.file_count)} 个文件`),
|
|
234
|
+
h('p', { style: mutedTextStyle }, `本机依赖:${skill.requirements}`),
|
|
235
|
+
skill.local_status === 'conflict'
|
|
236
|
+
? h('p', { role: 'status', style: mutedTextStyle }, '本机同名技能有未受 ANT 管理的内容、文件已被修改或备份损坏;请联系管理员处理。')
|
|
237
|
+
: skill.local_status === 'not-discovered'
|
|
238
|
+
? h('div', { style: { display: 'grid', gap: 10 } },
|
|
239
|
+
h('p', { role: 'status', style: mutedTextStyle }, '文件已在本机,但 DSH 技能服务没有发现它;请检查 DSH 技能目录配置。'),
|
|
240
|
+
h('button', { type: 'button', disabled: Boolean(workingId), onClick: () => void changeInstall(skill, true), style: { ...secondaryButtonStyle, justifySelf: 'start' } }, '卸载本机副本'))
|
|
241
|
+
: h('div', { style: { display: 'flex', flexWrap: 'wrap', gap: 8, marginTop: 'auto' } },
|
|
242
|
+
h('button', { type: 'button', disabled: Boolean(workingId) || skill.local_status === 'installed',
|
|
243
|
+
onClick: () => void changeInstall(skill), style: primaryButtonStyle },
|
|
244
|
+
skill.local_status === 'installed' ? '已安装' : skill.local_status === 'update-available' ? '更新技能' : '安装到这台 DSH'),
|
|
245
|
+
skill.local_status !== 'not-installed' ? h('button', { type: 'button', disabled: Boolean(workingId),
|
|
246
|
+
onClick: () => void changeInstall(skill, true), style: secondaryButtonStyle }, '卸载') : null))
|
|
247
|
+
})) : !loading && skills.length ? h('p', { style: mutedTextStyle }, '没有符合筛选条件的技能。') : null))
|
|
217
248
|
}
|
|
218
249
|
|
|
219
250
|
function ModelSyncFooter({ remote, serviceUrl, onServiceUrlChange }) {
|
|
@@ -654,8 +685,7 @@ window.__ModuleLoader__.load({
|
|
|
654
685
|
onChange: (event) => setCode(event.target.value.replace(/\D/gu, '').slice(0, 8)), style: inputStyle,
|
|
655
686
|
}),
|
|
656
687
|
h('button', { type: 'submit', disabled: busy || code.length !== 8, style: primaryButtonStyle }, busy ? '连接中…' : '验证并连接')) : null,
|
|
657
|
-
message ? h('p', { role: 'status', style: mutedTextStyle }, message) : null)
|
|
658
|
-
h(SkillCenter, { connected: credentialConfigured === true }))
|
|
688
|
+
message ? h('p', { role: 'status', style: mutedTextStyle }, message) : null))
|
|
659
689
|
|
|
660
690
|
}
|
|
661
691
|
|
|
@@ -665,13 +695,15 @@ window.__ModuleLoader__.load({
|
|
|
665
695
|
settings: ctx.remote.settings,
|
|
666
696
|
pluginManager: ctx.remote.pluginManager,
|
|
667
697
|
}
|
|
698
|
+
ctx.slots.inject('main', () => ctx.slots.register({ name: 'main', key: 'ant-skills' },
|
|
699
|
+
() => h(SkillCenterPage, { onBack: () => ctx.pluginNavigation.openBundle(ANT_BUNDLE_PACKAGE_NAME) })))
|
|
668
700
|
ctx.slots.inject('plugins.bundle.config', () => ctx.slots.register({
|
|
669
701
|
name: 'plugins.bundle.config',
|
|
670
702
|
key: ANT_BUNDLE_PACKAGE_NAME,
|
|
671
703
|
inject: () => ({ remote }),
|
|
672
704
|
}, ({ view, remote: injectedRemote }) => view === 'summary'
|
|
673
705
|
? h('p', null, 'ANT 团队服务入口。')
|
|
674
|
-
: h(TeamServiceConfig, { remote: injectedRemote })))
|
|
706
|
+
: h(TeamServiceConfig, { remote: injectedRemote, openSkillCenter: () => ctx.layout.selectPanel('ant-skills') })))
|
|
675
707
|
}
|
|
676
708
|
|
|
677
709
|
Object.assign(exports, { inject, apply })
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@ai-wendao/ant",
|
|
3
|
-
"version": "0.3.
|
|
3
|
+
"version": "0.3.12",
|
|
4
4
|
"description": "ANT (AI-native Teams) connects a DeepSeek Harness Desktop profile to team identity and approved models.",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"scripts": {
|
|
@@ -25,6 +25,7 @@
|
|
|
25
25
|
"platform": "web",
|
|
26
26
|
"inject": [
|
|
27
27
|
"@deepseek-ai/dsh-api-remotes",
|
|
28
|
+
"@deepseek-ai/dsh-client-ui-layout",
|
|
28
29
|
"@deepseek-ai/dsh-client-ui-plugin-manager"
|
|
29
30
|
]
|
|
30
31
|
}
|