dsh-skill-hub 0.3.6 → 0.3.8

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.
Files changed (122) hide show
  1. package/README.md +40 -50
  2. package/README.zh.md +38 -48
  3. package/lib/client.js +2569 -1646
  4. package/lib/client.js.map +1 -1
  5. package/lib/index.js +988 -400
  6. package/lib/types/client/SkillHubSettingsCard.d.ts +1 -2
  7. package/lib/types/client/api.d.ts +15 -5
  8. package/lib/types/client/helpers.d.ts +10 -1
  9. package/lib/types/client/locales/common.d.ts +52 -0
  10. package/lib/types/client/locales/detail.d.ts +16 -0
  11. package/lib/types/client/locales/market.d.ts +73 -0
  12. package/lib/types/client/locales/settings.d.ts +41 -0
  13. package/lib/types/client/locales/skills.d.ts +65 -0
  14. package/lib/types/client/locales/sources.d.ts +35 -0
  15. package/lib/types/client/locales.d.ts +147 -111
  16. package/lib/types/client/panel/DisabledRow.d.ts +2 -0
  17. package/lib/types/client/panel/MarketSourceRow.d.ts +12 -0
  18. package/lib/types/client/panel/MarketView.d.ts +1 -0
  19. package/lib/types/client/panel/RepoScanCard.d.ts +10 -0
  20. package/lib/types/client/panel/SkillDetailView.d.ts +5 -1
  21. package/lib/types/client/panel/dialogs.d.ts +19 -0
  22. package/lib/types/client/panel/hooks/shared.d.ts +72 -0
  23. package/lib/types/client/panel/hooks/useCatalogFlow.d.ts +62 -0
  24. package/lib/types/client/panel/hooks/useGroupFlow.d.ts +41 -0
  25. package/lib/types/client/panel/hooks/useMarketFlow.d.ts +73 -0
  26. package/lib/types/client/panel/hooks/useMetaFlow.d.ts +18 -0
  27. package/lib/types/client/panel/hooks/useSourceFlow.d.ts +44 -0
  28. package/lib/types/client/panel/market-format.d.ts +6 -0
  29. package/lib/types/client/panel/useSkillHub.d.ts +54 -71
  30. package/lib/types/client/settings-card.d.ts +20 -17
  31. package/lib/types/client/settings-form.d.ts +6 -1
  32. package/lib/types/protocol/api.d.ts +38 -0
  33. package/lib/types/protocol/catalog.d.ts +155 -0
  34. package/lib/types/protocol/config.d.ts +113 -0
  35. package/lib/types/protocol/groups.d.ts +95 -0
  36. package/lib/types/protocol/market.d.ts +94 -0
  37. package/lib/types/protocol/repo.d.ts +107 -0
  38. package/lib/types/protocol/sources.d.ts +139 -0
  39. package/lib/types/protocol/stats.d.ts +46 -0
  40. package/lib/types/protocol.d.ts +13 -720
  41. package/lib/types/repo/github-client.d.ts +42 -0
  42. package/lib/types/repo.d.ts +9 -22
  43. package/lib/types/routes/catalog.d.ts +7 -0
  44. package/lib/types/routes/config.d.ts +7 -0
  45. package/lib/types/routes/groups.d.ts +7 -0
  46. package/lib/types/routes/helpers.d.ts +145 -0
  47. package/lib/types/routes/market.d.ts +8 -0
  48. package/lib/types/routes/repo-import.d.ts +7 -0
  49. package/lib/types/routes/route-state.d.ts +55 -0
  50. package/lib/types/routes/sources.d.ts +8 -0
  51. package/lib/types/routes.d.ts +5 -34
  52. package/lib/types/skillfs.d.ts +13 -0
  53. package/lib/types/stats.d.ts +3 -2
  54. package/lib/types/store/errors.d.ts +10 -0
  55. package/lib/types/store/migrate.d.ts +44 -0
  56. package/lib/types/store/paths.d.ts +32 -0
  57. package/lib/types/store/store.d.ts +133 -0
  58. package/lib/types/store.d.ts +7 -146
  59. package/package.json +30 -28
  60. package/src/client/SkillHubSettingsCard.tsx +17 -5
  61. package/src/client/api.ts +108 -184
  62. package/src/client/helpers.ts +50 -1
  63. package/src/client/locales/common.ts +102 -0
  64. package/src/client/locales/detail.ts +30 -0
  65. package/src/client/locales/market.ts +144 -0
  66. package/src/client/locales/settings.ts +80 -0
  67. package/src/client/locales/skills.ts +128 -0
  68. package/src/client/locales/sources.ts +68 -0
  69. package/src/client/locales.ts +26 -452
  70. package/src/client/panel/DisabledRow.tsx +22 -7
  71. package/src/client/panel/MarketSourceRow.tsx +108 -0
  72. package/src/client/panel/MarketView.tsx +12 -246
  73. package/src/client/panel/RepoScanCard.tsx +171 -0
  74. package/src/client/panel/ScenesView.tsx +1 -1
  75. package/src/client/panel/SkillDetailView.tsx +35 -11
  76. package/src/client/panel/SkillHubPanel.tsx +42 -4
  77. package/src/client/panel/SkillRow.tsx +5 -2
  78. package/src/client/panel/SourcesView.tsx +2 -17
  79. package/src/client/panel/dialogs.tsx +61 -0
  80. package/src/client/panel/hooks/shared.ts +81 -0
  81. package/src/client/panel/hooks/useCatalogFlow.ts +211 -0
  82. package/src/client/panel/hooks/useGroupFlow.ts +240 -0
  83. package/src/client/panel/hooks/useMarketFlow.ts +421 -0
  84. package/src/client/panel/hooks/useMetaFlow.ts +58 -0
  85. package/src/client/panel/hooks/useSourceFlow.ts +193 -0
  86. package/src/client/panel/market-format.ts +22 -0
  87. package/src/client/panel/panel.module.css +1 -8
  88. package/src/client/panel/useSkillHub.ts +142 -948
  89. package/src/client/settings-card.tsx +51 -42
  90. package/src/client/settings-form.ts +19 -5
  91. package/src/index.ts +14 -4
  92. package/src/protocol/api.ts +38 -0
  93. package/src/protocol/catalog.ts +168 -0
  94. package/src/protocol/config.ts +145 -0
  95. package/src/protocol/groups.ts +106 -0
  96. package/src/protocol/market.ts +100 -0
  97. package/src/protocol/repo.ts +104 -0
  98. package/src/protocol/sources.ts +146 -0
  99. package/src/protocol/stats.ts +42 -0
  100. package/src/protocol.ts +83 -775
  101. package/src/repo/github-client.ts +131 -0
  102. package/src/repo.test.ts +24 -1
  103. package/src/repo.ts +69 -147
  104. package/src/routes/catalog.ts +309 -0
  105. package/src/routes/config.ts +119 -0
  106. package/src/routes/groups.ts +133 -0
  107. package/src/routes/helpers.ts +489 -0
  108. package/src/routes/market.ts +255 -0
  109. package/src/routes/repo-import.ts +267 -0
  110. package/src/routes/route-state.ts +89 -0
  111. package/src/routes/sources.ts +318 -0
  112. package/src/routes.test.ts +42 -0
  113. package/src/routes.ts +21 -1528
  114. package/src/skillfs.ts +188 -3
  115. package/src/stats.test.ts +58 -3
  116. package/src/stats.ts +45 -16
  117. package/src/store/errors.ts +14 -0
  118. package/src/store/migrate.ts +272 -0
  119. package/src/store/paths.ts +43 -0
  120. package/src/store/store.ts +532 -0
  121. package/src/store.test.ts +18 -0
  122. package/src/store.ts +7 -737
@@ -0,0 +1,73 @@
1
+ /**
2
+ * useMarketFlow — 市场域:市场源增删、仓库扫描、分支/版本选择、导入任务
3
+ * (轮询+取消)、更新检查、星标统计、版本同步、全部更新。目录/分组/来源
4
+ * 的刷新与来源检查经聚合根传入,不直接碰其他域的 state。
5
+ */
6
+ import type { RepoImportProgressResponse, SourceCheckResult } from '../../../protocol.ts';
7
+ import type { SkillHubApi } from '../../api.ts';
8
+ import type { FlowNotices, MarketState, RepoDiscoverState } from './shared.ts';
9
+ import type { BranchChoiceState, MarketSyncDialogState, VersionChoiceState } from '../dialogs.tsx';
10
+ export declare function useMarketFlow(api: SkillHubApi, shared: FlowNotices,
11
+ /** 目录重载(导入/同步后刷新列表,目录域提供)。 */
12
+ reloadCatalog: () => Promise<void>,
13
+ /** 分组重载(导入后刷新,分组域提供)。 */
14
+ reloadGroups: () => Promise<void>,
15
+ /** 来源重载(导入/同步后刷新,来源域提供)。 */
16
+ reloadSources: () => Promise<void>,
17
+ /** 来源更新检查(全部更新后重查,来源域提供)。 */
18
+ checkSources: (repo?: string) => Promise<void>,
19
+ /** 各来源的上游检查结果(全部更新遍历它,来源域提供)。 */
20
+ sourceCheck: Readonly<Record<string, SourceCheckResult>>): {
21
+ marketState: MarketState;
22
+ marketCheck: Readonly<Record<string, {
23
+ repo: string;
24
+ ref?: string;
25
+ latestTag?: string;
26
+ updateAvailable: boolean;
27
+ commitSha: string;
28
+ throttled?: boolean;
29
+ error?: string;
30
+ }>>;
31
+ branchChoice: BranchChoiceState | null;
32
+ branchBusy: boolean;
33
+ marketSyncDialog: MarketSyncDialogState | null;
34
+ syncingMarket: string | null;
35
+ syncBusy: boolean;
36
+ newSourceName: string;
37
+ repoDiscoverState: RepoDiscoverState;
38
+ scanningRepo: string | null;
39
+ repoSelected: ReadonlySet<string>;
40
+ repoImporting: boolean;
41
+ repoResult: RepoImportProgressResponse | null;
42
+ importJobId: string | null;
43
+ marketStats: Readonly<Record<string, {
44
+ stars: number;
45
+ downloads: number;
46
+ }>>;
47
+ versionDialog: VersionChoiceState | null;
48
+ versionBusy: boolean;
49
+ updateAllDialog: boolean;
50
+ setBranchChoice: import("react").Dispatch<import("react").SetStateAction<BranchChoiceState | null>>;
51
+ setMarketSyncDialog: import("react").Dispatch<import("react").SetStateAction<MarketSyncDialogState | null>>;
52
+ setNewSourceName: import("react").Dispatch<import("react").SetStateAction<string>>;
53
+ setRepoSelected: import("react").Dispatch<import("react").SetStateAction<ReadonlySet<string>>>;
54
+ setUpdateAllDialog: import("react").Dispatch<import("react").SetStateAction<boolean>>;
55
+ setVersionDialog: import("react").Dispatch<import("react").SetStateAction<VersionChoiceState | null>>;
56
+ loadMarket: () => Promise<void>;
57
+ addSource: (input: string) => Promise<void>;
58
+ addMarketSource: () => Promise<void>;
59
+ removeMarketSource: (repo: string) => Promise<void>;
60
+ scanRepo: (input: string) => Promise<void>;
61
+ confirmBranchChoice: () => Promise<void>;
62
+ openVersionDialog: (repo: string) => Promise<void>;
63
+ confirmVersionDialog: () => Promise<void>;
64
+ toggleRepoSelected: (path: string, checked: boolean) => void;
65
+ importRepo: () => Promise<void>;
66
+ cancelImport: () => Promise<void>;
67
+ clearScan: () => void;
68
+ checkMarket: () => Promise<void>;
69
+ loadMarketStats: () => Promise<void>;
70
+ syncMarketSource: (repo: string) => Promise<void>;
71
+ confirmMarketSync: () => Promise<void>;
72
+ updateAll: () => Promise<void>;
73
+ };
@@ -0,0 +1,18 @@
1
+ /**
2
+ * useMetaFlow — 自身更新检查 + 调用统计 + 配置:只依赖 api,
3
+ * 不碰其他域。补捞 effect 自包含(uses.size + loadUses)。
4
+ */
5
+ import type { HubConfig } from '../../../protocol.ts';
6
+ import type { SkillHubApi } from '../../api.ts';
7
+ import { type UpdateState } from './shared.ts';
8
+ export declare function useMetaFlow(api: SkillHubApi): {
9
+ updateState: UpdateState;
10
+ checkUpdate: () => Promise<void>;
11
+ uses: ReadonlyMap<string, {
12
+ count: number;
13
+ lastUsed?: number;
14
+ }>;
15
+ loadUses: () => Promise<void>;
16
+ hubConfig: HubConfig | null;
17
+ loadConfig: () => Promise<void>;
18
+ };
@@ -0,0 +1,44 @@
1
+ /**
2
+ * useSourceFlow — 来源域:来源列表/更新检查/同步确认/跟进删除/回收站恢复/
3
+ * 清空回收站,以及单个技能/整组的删除确认流。目录与分组的刷新经聚合根
4
+ * 传入的 reload 回调,不直接碰其他域的 state。
5
+ */
6
+ import type { SourceCheckResult, SourcesResponse } from '../../../protocol.ts';
7
+ import type { SkillHubApi } from '../../api.ts';
8
+ import type { FlowNotices } from './shared.ts';
9
+ import type { ConfirmDialogState } from '../dialogs.tsx';
10
+ export declare function useSourceFlow(api: SkillHubApi, shared: FlowNotices,
11
+ /** 目录重载(技能增删后刷新列表,目录域提供)。 */
12
+ reloadCatalog: () => Promise<void>,
13
+ /** 分组重载(来源/成员变化后刷新,分组域提供)。 */
14
+ reloadGroups: () => Promise<void>): {
15
+ sourcesState: SourcesResponse | null;
16
+ sourceCheck: Readonly<Record<string, SourceCheckResult>>;
17
+ checkingSource: string | null;
18
+ syncingSource: string | null;
19
+ confirmDialog: ConfirmDialogState | null;
20
+ deleteSkillDialog: string | null;
21
+ deleteGroupDialog: {
22
+ name: string;
23
+ skillNames: string[];
24
+ } | null;
25
+ confirmClearTrash: boolean;
26
+ setConfirmDialog: import("react").Dispatch<import("react").SetStateAction<ConfirmDialogState | null>>;
27
+ setDeleteSkillDialog: import("react").Dispatch<import("react").SetStateAction<string | null>>;
28
+ setDeleteGroupDialog: import("react").Dispatch<import("react").SetStateAction<{
29
+ name: string;
30
+ skillNames: string[];
31
+ } | null>>;
32
+ setConfirmClearTrash: import("react").Dispatch<import("react").SetStateAction<boolean>>;
33
+ loadSources: () => Promise<void>;
34
+ checkSources: (repo?: string) => Promise<void>;
35
+ requestSync: (repo: string, skills: string[]) => void;
36
+ requestDelete: (repo: string, skills: string[]) => void;
37
+ runConfirmed: () => Promise<void>;
38
+ restoreTrash: (name: string) => Promise<void>;
39
+ clearTrash: () => Promise<void>;
40
+ requestDeleteSkill: (name: string) => void;
41
+ runDeleteSkill: () => Promise<void>;
42
+ requestDeleteGroup: (name: string, skillNames: string[]) => void;
43
+ runDeleteGroup: () => Promise<void>;
44
+ };
@@ -0,0 +1,6 @@
1
+ /** Market tab number formatting (stars/downloads/bytes/speed). Pure, no deps. */
2
+ /** Compact count for stars/downloads (1234 → 1.2k). */
3
+ export declare function formatCount(n: number): string;
4
+ /** Compact byte size for repo preview rows. */
5
+ export declare function formatBytes(bytes: number): string;
6
+ export declare function formatSpeed(bps?: number): string;
@@ -1,68 +1,36 @@
1
1
  /**
2
- * useSkillHub — the panel's state owner. Everything the skill hub panel
3
- * knows (catalog, groups, sources, market, dialogs, drafts) plus every
4
- * async flow lives here; the panel itself only renders. All hooks run
5
- * unconditionally at the top, so the panel may early-return for the detail
6
- * and tag-editor views without violating the rules of hooks.
2
+ * useSkillHub — 面板的状态聚合根:只持有跨域共享的通知状态与纯视图状态,
3
+ * 各域状态与动作分散在 ./hooks/*,这里按依赖顺序组装(meta → 目录 →
4
+ * 分组 → 来源 → 市场),轮询与派生组装在此。返回形状与拆分前完全一致,
5
+ * 所有视图无需改动。All hooks run unconditionally at the top, so the panel
6
+ * may early-return for the detail and tag-editor views without violating
7
+ * the rules of hooks.
7
8
  */
8
- import { type FormEvent } from 'react';
9
- import type { CatalogResponse, CatalogSkill, DisabledSkill, GroupsResponse, HubConfig, MarketSourceRecord, RepoDiscoverResponse, RepoImportProgressResponse, SkillDetail, SkillTag, SourceCheckResult, SourcesResponse, UpdateCheckResponse, WritableRoot } from '../../protocol.ts';
10
9
  import type { SkillHubApi } from '../api.ts';
11
- import { type SortKey, type GroupSwitchState } from '../grouping.ts';
12
- import type { BranchChoiceState, ConfirmDialogState, ConflictDialogState, MarketSyncDialogState } from './dialogs.tsx';
13
- /** One-shot self-update check state. */
14
- type UpdateState = {
15
- status: 'idle';
16
- } | {
17
- status: 'checking';
18
- } | {
19
- status: 'ready';
20
- data: UpdateCheckResponse;
21
- } | {
22
- status: 'error';
23
- message: string;
24
- };
25
- /** Repo scanner/import state (drives the market source preview). */
26
- type RepoDiscoverState = {
27
- status: 'idle';
28
- } | {
29
- status: 'scanning';
30
- } | {
31
- status: 'ready';
32
- data: RepoDiscoverResponse;
33
- } | {
34
- status: 'error';
35
- message: string;
36
- };
37
- /** Market sources list state. */
38
- type MarketState = {
39
- status: 'loading' | 'ready' | 'error';
40
- repos: MarketSourceRecord[];
41
- };
42
10
  /** The hook's result: the panel's complete state + action surface. */
43
11
  export type SkillHubState = ReturnType<typeof useSkillHub>;
44
12
  export declare function useSkillHub(api: SkillHubApi): {
45
- catalog: CatalogResponse | null;
13
+ catalog: import("../../protocol.ts").CatalogResponse | null;
46
14
  loading: boolean;
47
15
  loadError: string | null;
48
16
  successBanner: string | null;
49
- updateState: UpdateState;
50
- repoDiscoverState: RepoDiscoverState;
17
+ updateState: import("./hooks/shared.ts").UpdateState;
18
+ repoDiscoverState: import("./hooks/shared.ts").RepoDiscoverState;
51
19
  scanningRepo: string | null;
52
20
  repoSelected: ReadonlySet<string>;
53
21
  repoImporting: boolean;
54
- repoResult: RepoImportProgressResponse | null;
22
+ repoResult: import("../../protocol.ts").RepoImportProgressResponse | null;
55
23
  importJobId: string | null;
56
24
  search: string;
57
25
  workspace: string;
58
- detail: SkillDetail | null;
26
+ detail: import("../../protocol.ts").SkillDetail | null;
59
27
  detailLoading: boolean;
60
28
  busyNames: ReadonlySet<string>;
61
29
  batchBusy: boolean;
62
30
  showForm: boolean;
63
31
  formName: string;
64
32
  formDesc: string;
65
- formRoot: WritableRoot;
33
+ formRoot: import("../../protocol.ts").WritableRoot;
66
34
  formBusy: boolean;
67
35
  formMessage: {
68
36
  kind: "error" | "success";
@@ -72,12 +40,13 @@ export declare function useSkillHub(api: SkillHubApi): {
72
40
  count: number;
73
41
  lastUsed?: number;
74
42
  }>;
75
- hubConfig: HubConfig | null;
43
+ hubConfig: import("../../protocol.ts").HubConfig | null;
76
44
  tab: "sources" | "scenes" | "market";
77
45
  skillView: "flat" | "groups";
78
46
  sourceFilter: string;
79
- sortKey: SortKey;
80
- marketState: MarketState;
47
+ invocationFilter: "user" | "model" | "all";
48
+ sortKey: import("../grouping.ts").SortKey;
49
+ marketState: import("./hooks/shared.ts").MarketState;
81
50
  marketCheck: Readonly<Record<string, {
82
51
  repo: string;
83
52
  ref?: string;
@@ -87,19 +56,23 @@ export declare function useSkillHub(api: SkillHubApi): {
87
56
  throttled?: boolean;
88
57
  error?: string;
89
58
  }>>;
90
- branchChoice: BranchChoiceState | null;
59
+ marketStats: Readonly<Record<string, {
60
+ stars: number;
61
+ downloads: number;
62
+ }>>;
63
+ branchChoice: import("./dialogs.tsx").BranchChoiceState | null;
91
64
  branchBusy: boolean;
92
- marketSyncDialog: MarketSyncDialogState | null;
65
+ marketSyncDialog: import("./dialogs.tsx").MarketSyncDialogState | null;
93
66
  syncingMarket: string | null;
94
67
  syncBusy: boolean;
95
68
  newSourceName: string;
96
- groupsState: GroupsResponse | null;
97
- sourcesState: SourcesResponse | null;
98
- sourceCheck: Readonly<Record<string, SourceCheckResult>>;
69
+ groupsState: import("../../protocol.ts").GroupsResponse | null;
70
+ sourcesState: import("../../protocol.ts").SourcesResponse | null;
71
+ sourceCheck: Readonly<Record<string, import("../../protocol.ts").SourceCheckResult>>;
99
72
  checkingSource: string | null;
100
73
  syncingSource: string | null;
101
- conflictDialog: ConflictDialogState | null;
102
- confirmDialog: ConfirmDialogState | null;
74
+ conflictDialog: import("./dialogs.tsx").ConflictDialogState | null;
75
+ confirmDialog: import("./dialogs.tsx").ConfirmDialogState | null;
103
76
  deleteSkillDialog: string | null;
104
77
  deleteGroupDialog: {
105
78
  name: string;
@@ -107,7 +80,7 @@ export declare function useSkillHub(api: SkillHubApi): {
107
80
  } | null;
108
81
  confirmClearTrash: boolean;
109
82
  updateAllDialog: boolean;
110
- editingTag: SkillTag | null;
83
+ editingTag: import("../../protocol.ts").SkillTag | null;
111
84
  editName: string;
112
85
  membersDraft: ReadonlySet<string>;
113
86
  newTagName: string;
@@ -117,22 +90,25 @@ export declare function useSkillHub(api: SkillHubApi): {
117
90
  subdividedProjects: ReadonlySet<string>;
118
91
  showLegend: boolean;
119
92
  editMode: boolean;
93
+ versionDialog: import("./dialogs.tsx").VersionChoiceState | null;
94
+ versionBusy: boolean;
120
95
  actionNames: Set<string>;
121
96
  viewNames: Set<string>;
122
97
  normalized: string;
123
98
  origins: Record<string, string>;
124
99
  sourceOptions: string[];
125
- filtered: CatalogSkill[];
126
- sorted: CatalogSkill[];
100
+ filtered: import("../../protocol.ts").CatalogSkill[];
101
+ sorted: import("../../protocol.ts").CatalogSkill[];
102
+ shortenedCount: number;
127
103
  setLoadError: import("react").Dispatch<import("react").SetStateAction<string | null>>;
128
104
  setSuccessBanner: import("react").Dispatch<import("react").SetStateAction<string | null>>;
129
105
  setSearch: import("react").Dispatch<import("react").SetStateAction<string>>;
130
106
  setWorkspace: import("react").Dispatch<import("react").SetStateAction<string>>;
131
- setDetail: import("react").Dispatch<import("react").SetStateAction<SkillDetail | null>>;
107
+ setDetail: import("react").Dispatch<import("react").SetStateAction<import("../../protocol.ts").SkillDetail | null>>;
132
108
  setShowForm: import("react").Dispatch<import("react").SetStateAction<boolean>>;
133
109
  setFormName: import("react").Dispatch<import("react").SetStateAction<string>>;
134
110
  setFormDesc: import("react").Dispatch<import("react").SetStateAction<string>>;
135
- setFormRoot: import("react").Dispatch<import("react").SetStateAction<WritableRoot>>;
111
+ setFormRoot: import("react").Dispatch<import("react").SetStateAction<import("../../protocol.ts").WritableRoot>>;
136
112
  setFormMessage: import("react").Dispatch<import("react").SetStateAction<{
137
113
  kind: "error" | "success";
138
114
  text: string;
@@ -141,12 +117,13 @@ export declare function useSkillHub(api: SkillHubApi): {
141
117
  setTab: import("react").Dispatch<import("react").SetStateAction<"sources" | "scenes" | "market">>;
142
118
  setSkillView: import("react").Dispatch<import("react").SetStateAction<"flat" | "groups">>;
143
119
  setSourceFilter: import("react").Dispatch<import("react").SetStateAction<string>>;
144
- setSortKey: import("react").Dispatch<import("react").SetStateAction<SortKey>>;
145
- setBranchChoice: import("react").Dispatch<import("react").SetStateAction<BranchChoiceState | null>>;
146
- setMarketSyncDialog: import("react").Dispatch<import("react").SetStateAction<MarketSyncDialogState | null>>;
120
+ setInvocationFilter: import("react").Dispatch<import("react").SetStateAction<"user" | "model" | "all">>;
121
+ setSortKey: import("react").Dispatch<import("react").SetStateAction<import("../grouping.ts").SortKey>>;
122
+ setBranchChoice: import("react").Dispatch<import("react").SetStateAction<import("./dialogs.tsx").BranchChoiceState | null>>;
123
+ setMarketSyncDialog: import("react").Dispatch<import("react").SetStateAction<import("./dialogs.tsx").MarketSyncDialogState | null>>;
147
124
  setNewSourceName: import("react").Dispatch<import("react").SetStateAction<string>>;
148
- setConflictDialog: import("react").Dispatch<import("react").SetStateAction<ConflictDialogState | null>>;
149
- setConfirmDialog: import("react").Dispatch<import("react").SetStateAction<ConfirmDialogState | null>>;
125
+ setConflictDialog: import("react").Dispatch<import("react").SetStateAction<import("./dialogs.tsx").ConflictDialogState | null>>;
126
+ setConfirmDialog: import("react").Dispatch<import("react").SetStateAction<import("./dialogs.tsx").ConfirmDialogState | null>>;
150
127
  setDeleteSkillDialog: import("react").Dispatch<import("react").SetStateAction<string | null>>;
151
128
  setDeleteGroupDialog: import("react").Dispatch<import("react").SetStateAction<{
152
129
  name: string;
@@ -154,22 +131,23 @@ export declare function useSkillHub(api: SkillHubApi): {
154
131
  } | null>>;
155
132
  setConfirmClearTrash: import("react").Dispatch<import("react").SetStateAction<boolean>>;
156
133
  setUpdateAllDialog: import("react").Dispatch<import("react").SetStateAction<boolean>>;
157
- setEditingTag: import("react").Dispatch<import("react").SetStateAction<SkillTag | null>>;
134
+ setEditingTag: import("react").Dispatch<import("react").SetStateAction<import("../../protocol.ts").SkillTag | null>>;
158
135
  setEditName: import("react").Dispatch<import("react").SetStateAction<string>>;
159
136
  setMembersDraft: import("react").Dispatch<import("react").SetStateAction<ReadonlySet<string>>>;
160
137
  setNewTagName: import("react").Dispatch<import("react").SetStateAction<string>>;
161
138
  setEditSearch: import("react").Dispatch<import("react").SetStateAction<string>>;
162
139
  setShowLegend: import("react").Dispatch<import("react").SetStateAction<boolean>>;
163
140
  setEditMode: import("react").Dispatch<import("react").SetStateAction<boolean>>;
141
+ setVersionDialog: import("react").Dispatch<import("react").SetStateAction<import("./dialogs.tsx").VersionChoiceState | null>>;
164
142
  toggleGroupCollapse: (key: string) => void;
165
143
  toggleSubdivide: (key: string) => void;
166
144
  checkUpdate: () => Promise<void>;
167
145
  loadMarket: () => Promise<void>;
168
146
  openDetail: (name: string) => Promise<void>;
169
- toggle: (skill: CatalogSkill, enabled: boolean) => Promise<void>;
170
- enableDisabled: (record: DisabledSkill) => Promise<void>;
147
+ toggle: (skill: import("../../protocol.ts").CatalogSkill, enabled: boolean) => Promise<void>;
148
+ enableDisabled: (record: import("../../protocol.ts").DisabledSkill) => Promise<void>;
171
149
  batchToggleNames: (names: string[], enabled: boolean) => Promise<void>;
172
- toggleGroup: (key: string, name: string, view: GroupSwitchState) => void;
150
+ toggleGroup: (key: string, name: string, view: import("../grouping.ts").GroupSwitchState) => void;
173
151
  resolveConflict: (closeAll: boolean) => Promise<void>;
174
152
  runConfirmed: () => Promise<void>;
175
153
  checkSources: (repo?: string) => Promise<void>;
@@ -177,11 +155,16 @@ export declare function useSkillHub(api: SkillHubApi): {
177
155
  requestDelete: (repo: string, skills: string[]) => void;
178
156
  restoreTrash: (name: string) => Promise<void>;
179
157
  clearTrash: () => Promise<void>;
158
+ fixingPaths: ReadonlySet<string>;
159
+ fixDiagnostic: (path: string) => Promise<void>;
160
+ clearListFilters: () => void;
161
+ openVersionDialog: (repo: string) => Promise<void>;
162
+ confirmVersionDialog: () => Promise<void>;
180
163
  requestDeleteSkill: (name: string) => void;
181
164
  runDeleteSkill: () => Promise<void>;
182
165
  requestDeleteGroup: (name: string, skillNames: string[]) => void;
183
166
  runDeleteGroup: () => Promise<void>;
184
- createTag: (event: FormEvent) => Promise<void>;
167
+ createTag: (event: import("react").FormEvent) => Promise<void>;
185
168
  deleteTag: (id: string) => Promise<void>;
186
169
  saveTag: (id: string, name: string, memberNames: string[] | null) => Promise<void>;
187
170
  reorderTags: (orderedIds: string[]) => Promise<void>;
@@ -197,9 +180,9 @@ export declare function useSkillHub(api: SkillHubApi): {
197
180
  cancelImport: () => Promise<void>;
198
181
  clearScan: () => void;
199
182
  checkMarket: () => Promise<void>;
183
+ loadMarketStats: () => Promise<void>;
200
184
  syncMarketSource: (repo: string) => Promise<void>;
201
185
  confirmMarketSync: () => Promise<void>;
202
186
  updateAll: () => Promise<void>;
203
- create: (event: FormEvent) => Promise<void>;
187
+ create: (event: import("react").FormEvent) => Promise<void>;
204
188
  };
205
- export {};
@@ -30,23 +30,6 @@ export interface PluginSettingsCardProps {
30
30
  * @returns the card, or nothing while the namespace is still loading.
31
31
  */
32
32
  export declare function PluginSettingsCard(props: PluginSettingsCardProps): ReactElement | null;
33
- /** One staged boolean field: 继承 / 开 / 关. */
34
- export interface BooleanFieldProps {
35
- id: string;
36
- label: string;
37
- hint: string;
38
- inheritLabel: string;
39
- onLabel: string;
40
- offLabel: string;
41
- overriddenLabel: string;
42
- resetLabel: string;
43
- disabled: boolean;
44
- text: string;
45
- overridden: boolean;
46
- onEdit: (text: string) => void;
47
- onReset: () => void;
48
- }
49
- export declare function BooleanField(props: BooleanFieldProps): ReactElement;
50
33
  /**
51
34
  * A compact sliding switch for the card's master enable/disable control.
52
35
  * An empty text value means the field inherits its default; the switch still
@@ -82,6 +65,26 @@ export interface ColorFieldProps {
82
65
  onReset: () => void;
83
66
  }
84
67
  export declare function ColorField(props: ColorFieldProps): ReactElement;
68
+ /**
69
+ * One staged secret field: a password input that never echoes the stored
70
+ * value. Shows a "set" state via the overridden badge; Reset unsets it.
71
+ */
72
+ export interface SecretFieldProps {
73
+ id: string;
74
+ label: string;
75
+ hint: string;
76
+ /** Placeholder shown while empty (never the stored token). */
77
+ placeholder: string;
78
+ overriddenLabel: string;
79
+ resetLabel: string;
80
+ disabled: boolean;
81
+ text: string;
82
+ overridden: boolean;
83
+ invalid?: boolean;
84
+ onEdit: (text: string) => void;
85
+ onReset: () => void;
86
+ }
87
+ export declare function SecretField(props: SecretFieldProps): ReactElement;
85
88
  /** One staged numeric field: a numeric draft text input with inherit/reset semantics. */
86
89
  export interface NumberFieldProps {
87
90
  id: string;
@@ -23,6 +23,12 @@ export interface FieldSpec {
23
23
  export declare function booleanField(field: string): FieldSpec;
24
24
  /** A #rrggbb color field, edited through hex draft text. */
25
25
  export declare function colorField(field: string): FieldSpec;
26
+ /**
27
+ * A secret field (API token): the stored value is never echoed back into the
28
+ * draft (format always yields ''), so typing is always a fresh set and Reset
29
+ * always unsets. An empty draft stages nothing.
30
+ */
31
+ export declare function secretField(field: string): FieldSpec;
26
32
  /**
27
33
  * A numeric field with range clamping. Integer by default: a fractional draft
28
34
  * is truncated so "5.5 分钟" cannot sneak past an integer-only schema.
@@ -98,7 +104,6 @@ export declare class CardForm {
98
104
  private specOf;
99
105
  private sectionValue;
100
106
  private baseValue;
101
- private userLayer;
102
107
  private stored;
103
108
  private publish;
104
109
  }
@@ -0,0 +1,38 @@
1
+ /** Browser-facing base paths of the skill-hub API family. */
2
+ export declare const SKILL_HUB_API: {
3
+ readonly catalog: "/api/skill-hub/catalog";
4
+ readonly skill: "/api/skill-hub/skill";
5
+ readonly skillDelete: "/api/skill-hub/skill/delete";
6
+ readonly toggle: "/api/skill-hub/toggle";
7
+ readonly toggleBatch: "/api/skill-hub/toggle-batch";
8
+ readonly create: "/api/skill-hub/create";
9
+ readonly stats: "/api/skill-hub/stats";
10
+ readonly config: "/api/skill-hub/config";
11
+ readonly market: "/api/skill-hub/market";
12
+ readonly marketSource: "/api/skill-hub/market/source";
13
+ readonly marketSourceDelete: "/api/skill-hub/market/source/delete";
14
+ readonly marketSourceRef: "/api/skill-hub/market/source/ref";
15
+ readonly marketCheck: "/api/skill-hub/market/check";
16
+ readonly marketSync: "/api/skill-hub/market/source/sync";
17
+ readonly repo: "/api/skill-hub/repo";
18
+ readonly repoImport: "/api/skill-hub/repo/import";
19
+ readonly repoImportProgress: "/api/skill-hub/repo/import/progress";
20
+ readonly repoImportCancel: "/api/skill-hub/repo/import/cancel";
21
+ readonly update: "/api/skill-hub/update";
22
+ readonly groups: "/api/skill-hub/groups";
23
+ readonly tag: "/api/skill-hub/tag";
24
+ readonly tagDelete: "/api/skill-hub/tag/delete";
25
+ readonly tagMembers: "/api/skill-hub/tag/members";
26
+ readonly tagReorder: "/api/skill-hub/tag/reorder";
27
+ readonly collectionReorder: "/api/skill-hub/collections/reorder";
28
+ readonly sourceGroupReorder: "/api/skill-hub/source-groups/reorder";
29
+ readonly sources: "/api/skill-hub/sources";
30
+ readonly sourceCheck: "/api/skill-hub/sources/check";
31
+ readonly sourceSync: "/api/skill-hub/sources/sync";
32
+ readonly sourceDelete: "/api/skill-hub/sources/delete";
33
+ readonly sourceRestore: "/api/skill-hub/sources/restore";
34
+ readonly sourceTrashClear: "/api/skill-hub/sources/trash/clear";
35
+ readonly diagnosticFix: "/api/skill-hub/diagnostic/fix";
36
+ readonly marketSourceVersions: "/api/skill-hub/market/source/versions";
37
+ readonly marketStats: "/api/skill-hub/market/stats";
38
+ };
@@ -0,0 +1,155 @@
1
+ /** User-level roots the hub may write to (matches dsh-skill-filesystem ranks 400/500). */
2
+ export type WritableRoot = 'user-dsh' | 'user-agents';
3
+ /** Invocation policy resolved by the registry, re-spelled for the wire. */
4
+ export interface HubInvocation {
5
+ /** Whether model-facing catalogs may load this skill. */
6
+ modelInvocable: boolean;
7
+ /** Whether human-facing command catalogs may load this skill. */
8
+ userInvocable: boolean;
9
+ }
10
+ /** One enabled skill row in the catalog. */
11
+ export interface CatalogSkill {
12
+ name: string;
13
+ description: string;
14
+ whenToUse?: string;
15
+ invocation: HubInvocation;
16
+ provider: string;
17
+ /** Whether the hub may toggle this skill (user-level filesystem skills only). */
18
+ writable: boolean;
19
+ /** 技能来源标识(user-dsh/user-agents/project-dsh/project-agents/...)。 */
20
+ source: string;
21
+ /** SKILL.md creation time (epoch ms); used for "added" sorting. Absent when unknown. */
22
+ addedAt?: number;
23
+ /** SKILL.md last-modified time (epoch ms); used for "updated" display. Absent when unknown. */
24
+ updatedAt?: number;
25
+ /** 项目技能的所属工作区路径(仅 project-dsh/project-agents 来源携带)。 */
26
+ workspace?: string;
27
+ /** 工作区显示标题(来自 workspace.json;无则回退为路径)。 */
28
+ workspaceTitle?: string;
29
+ /** UI metadata from agents/openai.yaml (mirrors codex SkillInterface). */
30
+ displayName?: string;
31
+ shortDescription?: string;
32
+ brandColor?: string;
33
+ iconSmall?: string;
34
+ iconLarge?: string;
35
+ defaultPrompt?: string;
36
+ }
37
+ /** One disabled skill tracked by the hub sidecar (SKILL.md renamed away). */
38
+ export interface DisabledSkill {
39
+ name: string;
40
+ description: string;
41
+ /** Absolute path of the renamed file (SKILL.md.disabled / <name>.md.disabled). */
42
+ path: string;
43
+ root: WritableRoot;
44
+ disabledAt: number;
45
+ }
46
+ /** One discovery diagnostic: a file the filesystem provider skips, with the reason. */
47
+ export interface DiagnosticEntry {
48
+ path: string;
49
+ root: string;
50
+ reason: string;
51
+ /** Whether this diagnostic can be auto-fixed (e.g. unquoted colon). */
52
+ fixable?: boolean;
53
+ }
54
+ /** POST /api/skill-hub/diagnostic/fix — repair a fixable diagnostic in place. */
55
+ export interface DiagnosticFixRequest {
56
+ path: string;
57
+ }
58
+ export interface DiagnosticFixResponse {
59
+ ok: true;
60
+ path: string;
61
+ }
62
+ /** GET /api/skill-hub/catalog */
63
+ export interface CatalogResponse {
64
+ ok: true;
65
+ /** 已安装插件自身的版本号(package.json version),面板标题旁显示。 */
66
+ pluginVersion: string;
67
+ /** Whether discovery completed within a stable catalog revision. */
68
+ complete: boolean;
69
+ /** Sorted winning summaries of every enabled skill (all roots + providers). */
70
+ skills: CatalogSkill[];
71
+ /** Skills the hub has toggled off (kept outside provider discovery). */
72
+ disabled: DisabledSkill[];
73
+ /** Files in the writable roots the provider ignores, with reasons. */
74
+ diagnostics: DiagnosticEntry[];
75
+ /** Skill names that appeared in multiple roots (first wins, others hidden). Mirrors codex name_counts. */
76
+ duplicateNames?: string[];
77
+ }
78
+ /** GET /api/skill-hub/skill */
79
+ export interface SkillDetail {
80
+ name: string;
81
+ description: string;
82
+ whenToUse?: string;
83
+ invocation: HubInvocation;
84
+ provider: string;
85
+ /** Absolute file path when the skill came from disk. */
86
+ path?: string;
87
+ /** SKILL.md creation time (epoch ms); absent when the file is unreadable. */
88
+ addedAt?: number;
89
+ /** SKILL.md last-modified time (epoch ms); absent when the file is unreadable. */
90
+ updatedAt?: number;
91
+ /** Markdown instruction body. */
92
+ content: string;
93
+ displayName?: string;
94
+ shortDescription?: string;
95
+ brandColor?: string;
96
+ iconSmall?: string;
97
+ iconLarge?: string;
98
+ defaultPrompt?: string;
99
+ }
100
+ export interface SkillDetailResponse {
101
+ ok: true;
102
+ skill: SkillDetail;
103
+ }
104
+ /** POST /api/skill-hub/skill/delete — 把单个技能移入回收站(可恢复)。 */
105
+ export interface SkillDeleteRequest {
106
+ name: string;
107
+ }
108
+ /** POST /api/skill-hub/skill/delete */
109
+ export interface SkillDeleteResponse {
110
+ ok: true;
111
+ name: string;
112
+ /** 移入回收站后的路径(目录或文件)。 */
113
+ path: string;
114
+ }
115
+ /** POST /api/skill-hub/toggle */
116
+ export interface ToggleRequest {
117
+ /** Kebab-case skill name. */
118
+ name: string;
119
+ /** true re-enables a hub-disabled skill; false disables an enabled one. */
120
+ enabled: boolean;
121
+ }
122
+ export interface ToggleResponse {
123
+ ok: true;
124
+ /** Fresh catalog after the mutation (the filesystem provider may lag a beat). */
125
+ catalog: CatalogResponse;
126
+ }
127
+ /** POST /api/skill-hub/toggle-batch — one group of skills, one write. */
128
+ export interface ToggleBatchRequest {
129
+ names: string[];
130
+ enabled: boolean;
131
+ }
132
+ /** POST /api/skill-hub/toggle-batch */
133
+ export interface ToggleBatchResponse {
134
+ ok: true;
135
+ catalog: CatalogResponse;
136
+ /** Per-name failures (unknown/read-only skills); empty means all landed. */
137
+ failures: Array<{
138
+ name: string;
139
+ error: string;
140
+ }>;
141
+ }
142
+ /** POST /api/skill-hub/create */
143
+ export interface CreateRequest {
144
+ /** Kebab-case skill name (validated with the official isSkillName grammar). */
145
+ name: string;
146
+ /** Optional one-line routing description for the frontmatter. */
147
+ description?: string;
148
+ /** Target user root; defaults to user-dsh (~/.dsh/skills). */
149
+ root?: WritableRoot;
150
+ }
151
+ export interface CreateResponse {
152
+ ok: true;
153
+ path: string;
154
+ root: WritableRoot;
155
+ }