@constraint/cli 0.3.1 → 0.3.2

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/README.md CHANGED
@@ -70,6 +70,7 @@ constraint setup --agent codex --dry-run
70
70
  ```bash
71
71
  constraint skills list
72
72
  constraint skills list --search research
73
+ constraint skills domains
73
74
  constraint skills inspect account-research
74
75
  constraint skills inspect account-research --files
75
76
  ```
@@ -129,9 +130,14 @@ constraint skills update --all --global
129
130
  Create or edit a standard Agent Skill folder locally, then upload it:
130
131
 
131
132
  ```bash
133
+ constraint skills domains
132
134
  constraint skills upload ./account-research --domain sales_pipeline
133
135
  ```
134
136
 
137
+ `constraint skills domains --json` returns the exact domain slugs where the
138
+ authenticated user can upload skills. Agents should discover the destination
139
+ first and pass one returned `slug` to `--domain`.
140
+
135
141
  The folder must contain a root `SKILL.md` with `name` and `description` YAML
136
142
  frontmatter. Pass the owning domain with `--domain`; if it is omitted in an
137
143
  interactive terminal, the CLI asks which permitted domain owns the skill.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@constraint/cli",
3
- "version": "0.3.1",
3
+ "version": "0.3.2",
4
4
  "description": "Install, publish, and report Agent Skills with Constraint",
5
5
  "type": "module",
6
6
  "bin": {
package/src/cli.js CHANGED
@@ -23,13 +23,14 @@ import {
23
23
  configuredAgents,
24
24
  installSkill,
25
25
  installedSkills,
26
+ manageableDomainRecords,
26
27
  manageableDomains,
27
28
  readTranscript,
28
29
  updateAll,
29
30
  uploadSkill,
30
31
  } from './skills.js';
31
32
 
32
- const VERSION = '0.3.1';
33
+ const VERSION = '0.3.2';
33
34
 
34
35
  const HELP = `Constraint Skills CLI
35
36
 
@@ -39,6 +40,7 @@ Usage:
39
40
  constraint doctor [--agent codex|claude-code]...
40
41
  constraint skills list [--search <text>]
41
42
  constraint skills list --installed [--project|--global] [--agent <agent>]...
43
+ constraint skills domains
42
44
  constraint skills inspect <skill> [--version <version>] [--files]
43
45
  constraint skills install <skill> [--version <version>] [--agent <agent>]...
44
46
  [--project|--global] [--copy] [--yes]
@@ -131,6 +133,39 @@ function printSkillList(items, options, out) {
131
133
  else out.line(`${presentation.title}\n${presentation.message}`);
132
134
  }
133
135
 
136
+ export function domainListPresentation(domains) {
137
+ if (domains.length === 0) {
138
+ return {
139
+ title: 'No upload domains',
140
+ message: 'You do not have permission to upload skills to any domain.',
141
+ };
142
+ }
143
+ return {
144
+ title: `${domains.length} skill upload domain${domains.length === 1 ? '' : 's'}`,
145
+ message: domains.map((domain) => [
146
+ `${domain.name} (${domain.slug})`,
147
+ domain.description || 'No description.',
148
+ ].join('\n')).join('\n\n'),
149
+ };
150
+ }
151
+
152
+ async function listSkillDomains(args, config, out) {
153
+ rejectUnknown(args);
154
+ if (args.length) throw new Error('skills domains does not accept positional arguments');
155
+ const domains = (await manageableDomainRecords(config)).map(({ slug, name, description }) => ({
156
+ slug,
157
+ name,
158
+ description,
159
+ }));
160
+ if (out.json) {
161
+ out.data(domains);
162
+ return;
163
+ }
164
+ const presentation = domainListPresentation(domains);
165
+ if (interactive(out)) note(presentation.message, presentation.title);
166
+ else out.line(`${presentation.title}\n${presentation.message}`);
167
+ }
168
+
134
169
  function takeScope(args) {
135
170
  const project = takeFlag(args, '--project');
136
171
  const global = takeFlag(args, '--global');
@@ -441,12 +476,13 @@ async function runCommand(args, config, out) {
441
476
  async function skillsCommand(args, config, out) {
442
477
  const command = args.shift();
443
478
  if (command === 'list') return listSkills(args, config, out);
479
+ if (command === 'domains') return listSkillDomains(args, config, out);
444
480
  if (command === 'inspect') return inspectSkill(args, config, out);
445
481
  if (command === 'install') return installCommand(args, config, out);
446
482
  if (command === 'update') return updateCommand(args, config, out);
447
483
  if (command === 'upload') return uploadCommand(args, config, out);
448
484
  if (command === 'run') return runCommand(args, config, out);
449
- throw new Error('Expected skills list, inspect, install, update, upload, or run.');
485
+ throw new Error('Expected skills list, domains, inspect, install, update, upload, or run.');
450
486
  }
451
487
 
452
488
  export async function main(argv) {
package/src/skills.js CHANGED
@@ -66,10 +66,12 @@ export async function uploadSkill(config, localPath, domain) {
66
66
  }
67
67
 
68
68
  export async function manageableDomains(config) {
69
+ return (await manageableDomainRecords(config)).map((domain) => domain.slug);
70
+ }
71
+
72
+ export async function manageableDomainRecords(config) {
69
73
  const domains = await apiRequest(config, '/domains');
70
- return domains
71
- .filter((domain) => domain.permissions.includes('domain:skill_manage'))
72
- .map((domain) => domain.slug);
74
+ return domains.filter((domain) => domain.permissions.includes('domain:skill_manage'));
73
75
  }
74
76
 
75
77
  export async function configuredAgents() {