dijk-skills 1.0.4 → 1.0.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.
package/README.md
CHANGED
|
@@ -15,27 +15,41 @@ npm install -g dijk-skills
|
|
|
15
15
|
npx dijk-skills install [options]
|
|
16
16
|
```
|
|
17
17
|
|
|
18
|
+
### CLI Alias
|
|
19
|
+
|
|
20
|
+
After `npm i -g dijk-skills`, both `dijk-skills` and the short alias `dijk` work: `dijk install`, `dijk -- openspec init`. Without a global install, use `npx -p dijk-skills dijk -- openspec init`, or plain `npx dijk-skills ...`.
|
|
21
|
+
|
|
22
|
+
> Caveat: bare `npx dijk` does NOT resolve to this package — npx would look for an unrelated npm package named `dijk`. Always use `-p dijk-skills` or a global/local install.
|
|
23
|
+
|
|
18
24
|
### Options
|
|
19
25
|
|
|
20
26
|
| Option | Description | Default |
|
|
21
27
|
|--------|-------------|---------|
|
|
22
|
-
| `--modules <list>` | Comma-separated module names | `
|
|
28
|
+
| `--modules <list>` | Comma-separated module names | `all` |
|
|
23
29
|
| `--dir <path>` | Target installation directory | `~/.agents` |
|
|
24
30
|
|
|
25
31
|
### Modules
|
|
26
32
|
|
|
27
|
-
| Module |
|
|
28
|
-
|
|
29
|
-
| `common` | caveman
|
|
30
|
-
| `
|
|
31
|
-
| `
|
|
32
|
-
| `
|
|
33
|
+
| Module | Skill | Description |
|
|
34
|
+
|--------|-------|-------------|
|
|
35
|
+
| `common` | caveman | 超压缩交流模式,在保持技术准确性的同时大幅节省输出 token(分 lite/full/ultra 档) |
|
|
36
|
+
| `common` | grilling | 对计划、决策或想法进行不留情面的连环追问,压力测试你的思路 |
|
|
37
|
+
| `common` | humanizer-zh | 去除文本中的 AI 生成痕迹,使其更自然、更像人类书写 |
|
|
38
|
+
| `common` | i-have-adhd | 面向 ADHD 读者塑造输出:下一步行动置顶、多步任务编号、复述状态、抑制离题、给出时间预估 |
|
|
39
|
+
| `writing` | grill-my-proposal | 把方案往死里问——三阶段递进追问(宏观结构→逐章深挖→交叉验证),动手前压力测试方案 |
|
|
40
|
+
| `writing` | last30days | 研究任意话题近 30 天的真实讨论,覆盖 Reddit、X、YouTube、TikTok、Hacker News、Polymarket、GitHub 与全网 |
|
|
41
|
+
| `writing` | vibe-code-insight | 对软件项目做深度系统分析,产出 `design.md`(系统设计)与 `trend.md`(生态与趋势洞察) |
|
|
42
|
+
| `writing` | vibe-opinion-insight | Human 驱动的 AI Agent 技术洞察框架——Agent 是启发工具,Human 赋予意义并承担责任 |
|
|
43
|
+
| `tools` | handoff | 将当前会话压缩为交接文档,供另一个 agent 接续工作 |
|
|
44
|
+
| `tools` | mcp-builder | 构建高质量 MCP 服务器的指南,支持 Python(FastMCP)与 Node/TypeScript(MCP SDK) |
|
|
45
|
+
| `tools` | skill-creator | 创建、编辑、评测与优化 skill,含触发准确率的基准测试 |
|
|
46
|
+
| `coding` | *(reserved)* | 空——保留给未来的 skill |
|
|
33
47
|
|
|
34
48
|
> Installing any module automatically includes `common`.
|
|
35
49
|
|
|
36
50
|
### Examples
|
|
37
51
|
|
|
38
|
-
Install
|
|
52
|
+
Install all skills to default location:
|
|
39
53
|
```bash
|
|
40
54
|
npx dijk-skills install
|
|
41
55
|
```
|
|
@@ -50,6 +64,26 @@ Custom target directory:
|
|
|
50
64
|
npx dijk-skills install --modules coding --dir ~/my-agents
|
|
51
65
|
```
|
|
52
66
|
|
|
67
|
+
## OpenSpec Bootstrap
|
|
68
|
+
|
|
69
|
+
Bootstrap OpenSpec (`@fission-ai/openspec`) into a project for spec-driven development. Run it inside your project directory.
|
|
70
|
+
|
|
71
|
+
```bash
|
|
72
|
+
npx dijk-skills -- openspec init # bootstrap the current project
|
|
73
|
+
npx dijk-skills -- openspec <args...> # any other openspec command (pure passthrough)
|
|
74
|
+
dijk -- openspec init # same, via the short alias
|
|
75
|
+
```
|
|
76
|
+
|
|
77
|
+
- Passthrough — forwards to `@fission-ai/openspec@latest` via npx, exit codes propagated
|
|
78
|
+
- On `init` only: drops the customizable config template (`coding/openspec/config.yaml`) into `./openspec/` first (never overwrites an existing config) and defaults `--tools opencode --no-animation` unless you pass your own
|
|
79
|
+
- Idempotent — re-run anytime to refresh CLI-owned files
|
|
80
|
+
|
|
81
|
+
Default target is `opencode` (`.opencode/skills/openspec-*/` + `/opsx-*` commands). For the vendor-neutral shared target, pass `--tools agents` explicitly: writes `.agents/skills/openspec-*/` only (no `/opsx-*` command files; in opencode the skills are then invoked by name, e.g. `/openspec-propose`).
|
|
82
|
+
|
|
83
|
+
**Prerequisites:** Node >= 20.19, network access for npx.
|
|
84
|
+
|
|
85
|
+
**Customization:** edit the project's `openspec/config.yaml` (keys: `schema`, `context`, `rules`, `operations`), or edit the repo template (`coding/openspec/config.yaml`) to change defaults for future bootstraps.
|
|
86
|
+
|
|
53
87
|
## Installed Structure
|
|
54
88
|
|
|
55
89
|
Skills are installed to `{dir}/skills/{skill-name}/`:
|
package/bin/dijk-skills.js
CHANGED
|
@@ -2,42 +2,59 @@
|
|
|
2
2
|
|
|
3
3
|
import { parseArgs } from 'node:util';
|
|
4
4
|
import { install } from '../lib/installer.js';
|
|
5
|
+
import { runOpenspec } from '../lib/openspec.js';
|
|
5
6
|
import { dirname, resolve } from 'node:path';
|
|
6
7
|
import { fileURLToPath } from 'node:url';
|
|
7
8
|
|
|
8
9
|
const __dirname = dirname(fileURLToPath(import.meta.url));
|
|
9
10
|
const packageRoot = resolve(__dirname, '..');
|
|
10
11
|
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
12
|
+
// Everything after the first `--` (npx may consume it), or all of argv
|
|
13
|
+
const argv = process.argv.slice(2);
|
|
14
|
+
const sepIdx = argv.indexOf('--');
|
|
15
|
+
const effective = sepIdx !== -1 ? argv.slice(sepIdx + 1) : argv;
|
|
16
|
+
|
|
17
|
+
if (effective[0] === 'openspec') {
|
|
18
|
+
// Passthrough to the OpenSpec CLI; lib owns exitCode + init output
|
|
19
|
+
await runOpenspec({ packageRoot, args: effective.slice(1), cwd: process.cwd() });
|
|
20
|
+
} else {
|
|
21
|
+
const { values, positionals } = parseArgs({
|
|
22
|
+
args: effective,
|
|
23
|
+
allowPositionals: true,
|
|
24
|
+
options: {
|
|
25
|
+
modules: {
|
|
26
|
+
type: 'string',
|
|
27
|
+
default: 'all'
|
|
28
|
+
},
|
|
29
|
+
dir: {
|
|
30
|
+
type: 'string',
|
|
31
|
+
default: '~/.agents'
|
|
32
|
+
},
|
|
33
|
+
help: {
|
|
34
|
+
type: 'boolean',
|
|
35
|
+
short: 'h'
|
|
36
|
+
}
|
|
25
37
|
}
|
|
26
|
-
}
|
|
27
|
-
});
|
|
38
|
+
});
|
|
28
39
|
|
|
29
|
-
const command = positionals[0];
|
|
40
|
+
const command = positionals[0];
|
|
30
41
|
|
|
31
|
-
if (values.help || !command) {
|
|
32
|
-
|
|
42
|
+
if (values.help || !command) {
|
|
43
|
+
console.log(`Usage: npx dijk-skills <command> [options]
|
|
44
|
+
(short alias: dijk — after \`npm i -g dijk-skills\`, or \`npx -p dijk-skills dijk ...\`)
|
|
33
45
|
|
|
34
46
|
Commands:
|
|
35
|
-
install
|
|
47
|
+
install Install skills to target directory
|
|
48
|
+
openspec <args...> Run the OpenSpec CLI (passthrough via npx). Put it after
|
|
49
|
+
\`--\` to be npx-safe: npx dijk-skills -- openspec init
|
|
50
|
+
On \`init\`: drops the customizable coding/openspec/config.yaml
|
|
51
|
+
template into ./openspec/ (never overwrites an existing
|
|
52
|
+
config) and defaults --tools opencode --no-animation.
|
|
36
53
|
|
|
37
54
|
Options:
|
|
38
55
|
--modules <list> Comma-separated module names or "all"
|
|
39
56
|
Values: coding,common,tools,writing,all
|
|
40
|
-
Default:
|
|
57
|
+
Default: all
|
|
41
58
|
--dir <path> Target installation directory
|
|
42
59
|
Default: ~/.agents
|
|
43
60
|
-h, --help Show this help message
|
|
@@ -47,32 +64,40 @@ Examples:
|
|
|
47
64
|
npx dijk-skills install --modules all
|
|
48
65
|
npx dijk-skills install --modules writing,tools
|
|
49
66
|
npx dijk-skills install --modules coding --dir ~/custom/path
|
|
67
|
+
npx dijk-skills -- openspec init
|
|
68
|
+
npx dijk-skills -- openspec update
|
|
69
|
+
npx dijk-skills -- openspec status
|
|
50
70
|
`);
|
|
51
|
-
|
|
52
|
-
}
|
|
71
|
+
process.exit(0);
|
|
72
|
+
}
|
|
53
73
|
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
}
|
|
74
|
+
function expandTilde(path) {
|
|
75
|
+
return path.startsWith('~')
|
|
76
|
+
? path.replace('~', process.env.HOME || process.env.USERPROFILE || '')
|
|
77
|
+
: path;
|
|
78
|
+
}
|
|
59
79
|
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
80
|
+
if (command !== 'install') {
|
|
81
|
+
console.error(`Unknown command: ${command}`);
|
|
82
|
+
console.error('Available commands: install, openspec');
|
|
83
|
+
process.exit(1);
|
|
84
|
+
}
|
|
63
85
|
|
|
64
|
-
const
|
|
65
|
-
|
|
66
|
-
|
|
86
|
+
const modules = values.modules === 'all'
|
|
87
|
+
? ['coding', 'common', 'tools', 'writing']
|
|
88
|
+
: values.modules.split(',').map(m => m.trim()).filter(Boolean);
|
|
67
89
|
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
}
|
|
76
|
-
|
|
77
|
-
|
|
90
|
+
const targetDir = expandTilde(values.dir);
|
|
91
|
+
|
|
92
|
+
try {
|
|
93
|
+
await install({
|
|
94
|
+
packageRoot,
|
|
95
|
+
modules,
|
|
96
|
+
targetDir: resolve(targetDir)
|
|
97
|
+
});
|
|
98
|
+
console.log('\n✓ Installation complete');
|
|
99
|
+
} catch (err) {
|
|
100
|
+
console.error('Installation failed:', err.message);
|
|
101
|
+
process.exit(1);
|
|
102
|
+
}
|
|
78
103
|
}
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
schema: spec-driven
|
|
2
|
+
|
|
3
|
+
rules:
|
|
4
|
+
proposal:
|
|
5
|
+
- 保持简洁,不描述实现方式;
|
|
6
|
+
- 背景:必须,包括变更背景、目标、动机;
|
|
7
|
+
- 术语表:必须,表格,包括 [中文-英文-解释];
|
|
8
|
+
- 用户故事:必须,子章节,每一章包括 [> 叙事性描述]、[- 用户故事描述] 和 [**验收标准**];
|
|
9
|
+
- 功能清单:必须,子章节,每一章包括 [> 描述]、[- 规格]、[**使用方式** (如界面操作/后台接口等)]、[影响];
|
|
10
|
+
- 每一个功能对应一个 spec 文件;
|
|
11
|
+
- 修改 proposal 之后必须确保 proposal 其他章节以及 specs 和 design 同步满足;
|
|
12
|
+
|
|
13
|
+
specs:
|
|
14
|
+
- 保持简洁,不描述实现细节;
|
|
15
|
+
- 功能需求(FR):必须,包括ID、描述、1~N个用户场景(GIVEN/WHEN/THEN格式);
|
|
16
|
+
- 非功能需求(NFR):必须,包括ID、描述,范围包括可靠性、可用性、资源占用、性能、安全、容错、可观测等方面
|
|
17
|
+
|
|
18
|
+
design:
|
|
19
|
+
- 保持简洁;
|
|
20
|
+
- 上下文:必须,包括上游系统、下游系统、外部接口清单;
|
|
21
|
+
- 总体架构:必须,包括架构约束、各模块的逻辑架构和依赖关系、技术选型及理由;
|
|
22
|
+
- 必须包含设计决策记录(ADR),记录关键取舍及备选方案(为什么 X 而不是 Y);
|
|
23
|
+
- 必须考虑非功能性需求的应对方案;
|
|
24
|
+
- 必须识别技术风险,并列出已知限制和后续演进方向;
|
|
25
|
+
|
|
26
|
+
tasks:
|
|
27
|
+
- 每个 task 须包含:用例编号、用例名称、前置条件、步骤、预期结果、验证方法;
|
|
28
|
+
- 必须关联 FR-ID 和 NFR-ID,确保可追溯;
|
|
29
|
+
- 必须包含单元测试(覆盖率 ≥ 80%)、集成测试、冒烟测试(如有);
|
|
30
|
+
- 必须包含验收测试(与 specs 中的用户场景对应)、人工测试指导(如有)、构建与部署验证、数据准备方法、文档交付等;
|
|
31
|
+
- 缺陷必须分级(致命/重/一般/建议),并明确发布影响;
|
|
32
|
+
|
package/lib/openspec.js
ADDED
|
@@ -0,0 +1,83 @@
|
|
|
1
|
+
import { spawnSync } from 'node:child_process';
|
|
2
|
+
import { copyFile, mkdir } from 'node:fs/promises';
|
|
3
|
+
import { existsSync } from 'node:fs';
|
|
4
|
+
import { join } from 'node:path';
|
|
5
|
+
|
|
6
|
+
/**
|
|
7
|
+
* Drop the user-owned OpenSpec config template into <cwd>/openspec/.
|
|
8
|
+
* Never overwrites an existing config.yaml / config.yml.
|
|
9
|
+
*/
|
|
10
|
+
async function ensureConfigTemplate(cwd, packageRoot) {
|
|
11
|
+
await mkdir(join(cwd, 'openspec'), { recursive: true });
|
|
12
|
+
|
|
13
|
+
// Config is user-owned: only drop the template if no config exists yet
|
|
14
|
+
const configYaml = join(cwd, 'openspec', 'config.yaml');
|
|
15
|
+
const configYml = join(cwd, 'openspec', 'config.yml');
|
|
16
|
+
|
|
17
|
+
if (!existsSync(configYaml) && !existsSync(configYml)) {
|
|
18
|
+
await copyFile(join(packageRoot, 'coding', 'openspec', 'config.yaml'), configYaml);
|
|
19
|
+
console.log('✓ wrote openspec/config.yaml (template — customize freely)');
|
|
20
|
+
} else {
|
|
21
|
+
const existing = existsSync(configYaml) ? 'config.yaml' : 'config.yml';
|
|
22
|
+
console.log(`· openspec/${existing} exists — keeping it (never overwritten)`);
|
|
23
|
+
}
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
/**
|
|
27
|
+
* Run the OpenSpec CLI (@fission-ai/openspec) via npx, forwarding args
|
|
28
|
+
* verbatim. On `init`: drops the config template first (never overwriting
|
|
29
|
+
* an existing config) and adds default flags `--tools opencode
|
|
30
|
+
* --no-animation` when the user didn't supply their own. Child exit codes
|
|
31
|
+
* propagate; this never throws.
|
|
32
|
+
*/
|
|
33
|
+
export async function runOpenspec({ packageRoot, args, cwd = process.cwd() }) {
|
|
34
|
+
const isInit = args[0] === 'init';
|
|
35
|
+
|
|
36
|
+
if (isInit) {
|
|
37
|
+
// OpenSpec requires Node >= 20.19.0 — warn, but do not abort
|
|
38
|
+
const [major, minor] = process.versions.node.split('.').map(Number);
|
|
39
|
+
if (major < 20 || (major === 20 && minor < 19)) {
|
|
40
|
+
console.log(`⚠ OpenSpec requires Node >= 20.19.0 (current: ${process.versions.node}) — continuing anyway`);
|
|
41
|
+
}
|
|
42
|
+
|
|
43
|
+
console.log(`Target project: ${cwd}`);
|
|
44
|
+
|
|
45
|
+
await ensureConfigTemplate(cwd, packageRoot);
|
|
46
|
+
|
|
47
|
+
// Default flags, appended only when the user didn't supply their own
|
|
48
|
+
// (--tools also matches the equals form `--tools=<list>`)
|
|
49
|
+
const hasTools = args.some(a => a === '--tools' || a.startsWith('--tools='));
|
|
50
|
+
if (!hasTools) {
|
|
51
|
+
args = [...args, '--tools', 'opencode'];
|
|
52
|
+
}
|
|
53
|
+
if (!args.includes('--no-animation')) {
|
|
54
|
+
args = [...args, '--no-animation'];
|
|
55
|
+
}
|
|
56
|
+
}
|
|
57
|
+
|
|
58
|
+
const result = spawnSync('npx', ['-y', '@fission-ai/openspec@latest', ...args], {
|
|
59
|
+
cwd,
|
|
60
|
+
stdio: 'inherit',
|
|
61
|
+
shell: process.platform === 'win32'
|
|
62
|
+
});
|
|
63
|
+
|
|
64
|
+
if (result.error) {
|
|
65
|
+
console.error(`Failed to run openspec via npx: ${result.error.message}`);
|
|
66
|
+
process.exitCode = 1;
|
|
67
|
+
return;
|
|
68
|
+
}
|
|
69
|
+
|
|
70
|
+
if (result.status !== 0) {
|
|
71
|
+
process.exitCode = result.status ?? 1;
|
|
72
|
+
return;
|
|
73
|
+
}
|
|
74
|
+
|
|
75
|
+
if (isInit) {
|
|
76
|
+
console.log(`✓ OpenSpec bootstrap complete
|
|
77
|
+
- Project config: openspec/config.yaml (yours — openspec never overwrites it)
|
|
78
|
+
- Agent skills: .opencode/skills/openspec-*/
|
|
79
|
+
- Slash commands: .opencode/commands/opsx-*.md (/opsx-propose, /opsx-apply, ...)
|
|
80
|
+
- Vendor-neutral alternative: re-run with --tools agents for shared .agents/skills (skills only, no commands)
|
|
81
|
+
- Re-run anytime to refresh CLI-owned files; upgrade later with: npx @fission-ai/openspec@latest update`);
|
|
82
|
+
}
|
|
83
|
+
}
|
package/package.json
CHANGED
|
@@ -1,10 +1,11 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "dijk-skills",
|
|
3
|
-
"version": "1.0.
|
|
3
|
+
"version": "1.0.8",
|
|
4
4
|
"description": "CLI installer for Dijk skills collection",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"bin": {
|
|
7
|
-
"dijk-skills": "./bin/dijk-skills.js"
|
|
7
|
+
"dijk-skills": "./bin/dijk-skills.js",
|
|
8
|
+
"dijk": "./bin/dijk-skills.js"
|
|
8
9
|
},
|
|
9
10
|
"files": [
|
|
10
11
|
"bin/",
|
|
File without changes
|
|
File without changes
|