@rpamis/comet 0.1.0 → 0.1.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/LICENSE +21 -21
- package/README.md +184 -49
- package/assets/manifest.json +13 -13
- package/assets/skills/comet/SKILL.md +12 -0
- package/assets/skills/comet/scripts/comet-guard.sh +147 -0
- package/assets/skills/comet-archive/SKILL.md +1 -0
- package/assets/skills/comet-build/SKILL.md +1 -0
- package/assets/skills/comet-design/SKILL.md +1 -0
- package/assets/skills/comet-hotfix/SKILL.md +1 -0
- package/assets/skills/comet-open/SKILL.md +1 -0
- package/assets/skills/comet-tweak/SKILL.md +118 -117
- package/assets/skills/comet-verify/SKILL.md +1 -0
- package/bin/comet.js +3 -3
- package/package.json +50 -50
- package/scripts/postinstall.js +44 -44
package/LICENSE
CHANGED
|
@@ -1,21 +1,21 @@
|
|
|
1
|
-
MIT License
|
|
2
|
-
|
|
3
|
-
Copyright (c) 2026 rpamis
|
|
4
|
-
|
|
5
|
-
Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
6
|
-
of this software and associated documentation files (the "Software"), to deal
|
|
7
|
-
in the Software without restriction, including without limitation the rights
|
|
8
|
-
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
9
|
-
copies of the Software, and to permit persons to whom the Software is
|
|
10
|
-
furnished to do so, subject to the following conditions:
|
|
11
|
-
|
|
12
|
-
The above copyright notice and this permission notice shall be included in all
|
|
13
|
-
copies or substantial portions of the Software.
|
|
14
|
-
|
|
15
|
-
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
16
|
-
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
17
|
-
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
18
|
-
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
19
|
-
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
20
|
-
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
|
21
|
-
SOFTWARE.
|
|
1
|
+
MIT License
|
|
2
|
+
|
|
3
|
+
Copyright (c) 2026 rpamis
|
|
4
|
+
|
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
6
|
+
of this software and associated documentation files (the "Software"), to deal
|
|
7
|
+
in the Software without restriction, including without limitation the rights
|
|
8
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
9
|
+
copies of the Software, and to permit persons to whom the Software is
|
|
10
|
+
furnished to do so, subject to the following conditions:
|
|
11
|
+
|
|
12
|
+
The above copyright notice and this permission notice shall be included in all
|
|
13
|
+
copies or substantial portions of the Software.
|
|
14
|
+
|
|
15
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
16
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
17
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
18
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
19
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
20
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
|
21
|
+
SOFTWARE.
|
package/README.md
CHANGED
|
@@ -1,49 +1,184 @@
|
|
|
1
|
-
# @rpamis/comet
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
|
41
|
-
|
|
42
|
-
|
|
|
43
|
-
|
|
|
44
|
-
|
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
1
|
+
# @rpamis/comet
|
|
2
|
+
|
|
3
|
+
```
|
|
4
|
+
██████╗ ██████╗ ███╗ ███╗███████╗████████╗
|
|
5
|
+
██╔════╝██╔═══██╗████╗ ████║██╔════╝╚══██╔══╝
|
|
6
|
+
██║ ██║ ██║██╔████╔██║█████╗ ██║
|
|
7
|
+
██║ ██║ ██║██║╚██╔╝██║██╔══╝ ██║
|
|
8
|
+
╚██████╗╚██████╔╝██║ ╚═╝ ██║███████╗ ██║
|
|
9
|
+
╚═════╝ ╚═════╝ ╚═╝ ╚═╝╚══════╝ ╚═╝
|
|
10
|
+
```
|
|
11
|
+
|
|
12
|
+
**OpenSpec + Superpowers dual-star development workflow** — one command from idea to archive.
|
|
13
|
+
|
|
14
|
+
OpenSpec handles **WHAT** (outlines, proposals, spec lifecycle, archiving). Superpowers handles **HOW** (technical design, planning, execution, wrap-up). Comet chains both into a five-phase automated pipeline.
|
|
15
|
+
|
|
16
|
+
## Install
|
|
17
|
+
|
|
18
|
+
```bash
|
|
19
|
+
npm install -g @rpamis/comet
|
|
20
|
+
```
|
|
21
|
+
|
|
22
|
+
## Quick Start
|
|
23
|
+
|
|
24
|
+
```bash
|
|
25
|
+
cd your-project
|
|
26
|
+
comet init
|
|
27
|
+
```
|
|
28
|
+
|
|
29
|
+
`comet init` will:
|
|
30
|
+
|
|
31
|
+
1. Prompt you to select AI platforms (auto-detects existing configs)
|
|
32
|
+
2. Choose install scope: project-level (current directory) or global (home directory)
|
|
33
|
+
3. Install [OpenSpec](https://github.com/Fission-AI/OpenSpec) skills
|
|
34
|
+
4. Install [Superpowers](https://github.com/obra/superpowers) skills
|
|
35
|
+
5. Deploy Comet skills to selected platforms
|
|
36
|
+
6. Create `docs/superpowers/specs/` and `docs/superpowers/plans/` working directories
|
|
37
|
+
|
|
38
|
+
## Commands
|
|
39
|
+
|
|
40
|
+
| Command | Description |
|
|
41
|
+
|---------|-------------|
|
|
42
|
+
| `comet init [path]` | Initialize Comet workflow |
|
|
43
|
+
| `comet --help` | Show help |
|
|
44
|
+
| `comet --version` | Show version |
|
|
45
|
+
|
|
46
|
+
### init Options
|
|
47
|
+
|
|
48
|
+
| Option | Description |
|
|
49
|
+
|--------|-------------|
|
|
50
|
+
| `--yes` | Non-interactive mode, auto-select detected platforms |
|
|
51
|
+
| `--skip-existing` | Skip already installed components |
|
|
52
|
+
| `--overwrite` | Overwrite already installed components |
|
|
53
|
+
|
|
54
|
+
## Supported Platforms
|
|
55
|
+
|
|
56
|
+
`comet init` supports 28 AI coding platforms:
|
|
57
|
+
|
|
58
|
+
| Platform | Skills Dir | Platform | Skills Dir |
|
|
59
|
+
|----------|-----------|----------|-----------|
|
|
60
|
+
| Claude Code | `.claude/` | Cursor | `.cursor/` |
|
|
61
|
+
| Codex | `.codex/` | OpenCode | `.opencode/` |
|
|
62
|
+
| Windsurf | `.windsurf/` | Cline | `.cline/` |
|
|
63
|
+
| RooCode | `.roo/` | Continue | `.continue/` |
|
|
64
|
+
| GitHub Copilot | `.github/` | Gemini CLI | `.gemini/` |
|
|
65
|
+
| Amazon Q Developer | `.amazonq/` | Qwen Code | `.qwen/` |
|
|
66
|
+
| Kilo Code | `.kilocode/` | Auggie | `.augment/` |
|
|
67
|
+
| Kiro | `.kiro/` | Lingma | `.lingma/` |
|
|
68
|
+
| Junie | `.junie/` | CodeBuddy | `.codebuddy/` |
|
|
69
|
+
| CoStrict | `.cospec/` | Crush | `.crush/` |
|
|
70
|
+
| Factory Droid | `.factory/` | iFlow | `.iflow/` |
|
|
71
|
+
| Pi | `.pi/` | Qoder | `.qoder/` |
|
|
72
|
+
| Antigravity | `.agent/` | Bob Shell | `.bob/` |
|
|
73
|
+
| ForgeCode | `.forge/` | Trae | `.trae/` |
|
|
74
|
+
|
|
75
|
+
## Skills
|
|
76
|
+
|
|
77
|
+
After `comet init`, three groups of skills are installed to the selected platform's `skills/` directory:
|
|
78
|
+
|
|
79
|
+
### Comet Skills
|
|
80
|
+
|
|
81
|
+
| Skill | Description |
|
|
82
|
+
|-------|-------------|
|
|
83
|
+
| `/comet` | Main entry — auto-detects phase and dispatches to sub-commands |
|
|
84
|
+
| `/comet-open` | Phase 1: Open a change (proposal, design, task breakdown) |
|
|
85
|
+
| `/comet-design` | Phase 2: Deep design (brainstorming, Design Doc) |
|
|
86
|
+
| `/comet-build` | Phase 3: Plan and build (implementation plan, code commits) |
|
|
87
|
+
| `/comet-verify` | Phase 4: Verify and finish (testing, verification report) |
|
|
88
|
+
| `/comet-archive` | Phase 5: Archive (delta spec sync, status annotation) |
|
|
89
|
+
| `/comet-hotfix` | Preset: Quick bug fix (skips brainstorming) |
|
|
90
|
+
| `/comet-tweak` | Preset: Small change (skips brainstorming and full plan) |
|
|
91
|
+
|
|
92
|
+
### OpenSpec Skills
|
|
93
|
+
|
|
94
|
+
Spec lifecycle management: propose, explore, sync, verify, archive, and more.
|
|
95
|
+
|
|
96
|
+
### Superpowers Skills
|
|
97
|
+
|
|
98
|
+
Development methodology: brainstorming, TDD, subagent-driven development, code review, plan writing, and more.
|
|
99
|
+
|
|
100
|
+
## Workflow
|
|
101
|
+
|
|
102
|
+
```
|
|
103
|
+
/comet
|
|
104
|
+
↓ auto-detect
|
|
105
|
+
/comet-open ——→ /comet-design ——→ /comet-build ——→ /comet-verify ——→ /comet-archive
|
|
106
|
+
(OpenSpec) (Superpowers) (Superpowers) (Both) (OpenSpec)
|
|
107
|
+
|
|
108
|
+
/comet-hotfix (preset path, skips brainstorming)
|
|
109
|
+
open ——→ build ——→ verify ——→ archive
|
|
110
|
+
|
|
111
|
+
/comet-tweak (preset path, skips brainstorming and full plan)
|
|
112
|
+
open ——→ lightweight build ——→ light verify ——→ archive
|
|
113
|
+
```
|
|
114
|
+
|
|
115
|
+
### Five Phases
|
|
116
|
+
|
|
117
|
+
| Phase | Command | Owner | Artifacts |
|
|
118
|
+
|-------|---------|-------|-----------|
|
|
119
|
+
| 1. Open | `/comet-open` | OpenSpec | proposal.md, design.md, tasks.md |
|
|
120
|
+
| 2. Deep Design | `/comet-design` | Superpowers | Design Doc, delta spec |
|
|
121
|
+
| 3. Plan & Build | `/comet-build` | Superpowers | Implementation plan, code commits |
|
|
122
|
+
| 4. Verify & Finish | `/comet-verify` | Both | Verification report, branch handling |
|
|
123
|
+
| 5. Archive | `/comet-archive` | OpenSpec | delta→main spec sync, archive |
|
|
124
|
+
|
|
125
|
+
### Core Principles
|
|
126
|
+
|
|
127
|
+
- **Brainstorming is non-skippable** — every change must go through deep design (except hotfix/tweak)
|
|
128
|
+
- **Delta specs are living documents** — freely editable during Phase 3, synced at archive
|
|
129
|
+
- **Keep tasks.md in sync** — check off each task as completed
|
|
130
|
+
- **Commit frequently** — one commit per task, message reflects design intent
|
|
131
|
+
- **Verify before archive** — `/comet-verify` must pass before `/comet-archive`
|
|
132
|
+
|
|
133
|
+
## Project Structure
|
|
134
|
+
|
|
135
|
+
```
|
|
136
|
+
your-project/
|
|
137
|
+
├── .claude/skills/ # Platform skills dir (Comet + OpenSpec + Superpowers)
|
|
138
|
+
│ ├── comet/SKILL.md
|
|
139
|
+
│ ├── comet-*/SKILL.md
|
|
140
|
+
│ ├── openspec-*/SKILL.md
|
|
141
|
+
│ └── brainstorming/SKILL.md
|
|
142
|
+
├── openspec/ # OpenSpec — WHAT
|
|
143
|
+
│ ├── config.yaml
|
|
144
|
+
│ └── changes/
|
|
145
|
+
│ └── <name>/
|
|
146
|
+
│ ├── .openspec.yaml
|
|
147
|
+
│ ├── proposal.md
|
|
148
|
+
│ ├── design.md
|
|
149
|
+
│ ├── specs/<capability>/spec.md
|
|
150
|
+
│ └── tasks.md
|
|
151
|
+
└── docs/superpowers/ # Superpowers — HOW
|
|
152
|
+
├── specs/ # Design documents
|
|
153
|
+
└── plans/ # Implementation plans
|
|
154
|
+
```
|
|
155
|
+
|
|
156
|
+
## Development
|
|
157
|
+
|
|
158
|
+
```bash
|
|
159
|
+
# Clone
|
|
160
|
+
git clone https://github.com/benym/comet.git
|
|
161
|
+
cd comet
|
|
162
|
+
|
|
163
|
+
# Install dependencies
|
|
164
|
+
pnpm install
|
|
165
|
+
|
|
166
|
+
# Dev mode (watch)
|
|
167
|
+
pnpm dev
|
|
168
|
+
|
|
169
|
+
# Build
|
|
170
|
+
pnpm build
|
|
171
|
+
|
|
172
|
+
# Test
|
|
173
|
+
pnpm test
|
|
174
|
+
```
|
|
175
|
+
|
|
176
|
+
## Security
|
|
177
|
+
|
|
178
|
+
- Pre-publish scan for API keys, secrets, tokens, and private keys
|
|
179
|
+
- `.npmignore` prevents source code and config files from entering the npm package
|
|
180
|
+
- `.gitignore` covers secrets, credentials, IDE configs, and more
|
|
181
|
+
|
|
182
|
+
## License
|
|
183
|
+
|
|
184
|
+
MIT
|
package/assets/manifest.json
CHANGED
|
@@ -1,13 +1,13 @@
|
|
|
1
|
-
{
|
|
2
|
-
"version": "0.1.0",
|
|
3
|
-
"skills": [
|
|
4
|
-
"comet/SKILL.md",
|
|
5
|
-
"comet-open/SKILL.md",
|
|
6
|
-
"comet-design/SKILL.md",
|
|
7
|
-
"comet-build/SKILL.md",
|
|
8
|
-
"comet-verify/SKILL.md",
|
|
9
|
-
"comet-archive/SKILL.md",
|
|
10
|
-
"comet-hotfix/SKILL.md",
|
|
11
|
-
"comet-tweak/SKILL.md"
|
|
12
|
-
]
|
|
13
|
-
}
|
|
1
|
+
{
|
|
2
|
+
"version": "0.1.0",
|
|
3
|
+
"skills": [
|
|
4
|
+
"comet/SKILL.md",
|
|
5
|
+
"comet-open/SKILL.md",
|
|
6
|
+
"comet-design/SKILL.md",
|
|
7
|
+
"comet-build/SKILL.md",
|
|
8
|
+
"comet-verify/SKILL.md",
|
|
9
|
+
"comet-archive/SKILL.md",
|
|
10
|
+
"comet-hotfix/SKILL.md",
|
|
11
|
+
"comet-tweak/SKILL.md"
|
|
12
|
+
]
|
|
13
|
+
}
|
|
@@ -158,6 +158,18 @@ comet:
|
|
|
158
158
|
|
|
159
159
|
## 快速参考
|
|
160
160
|
|
|
161
|
+
### 脚本定位
|
|
162
|
+
|
|
163
|
+
Comet 阶段守卫脚本 `comet-guard.sh` 随 skill 包分发,位于 `comet/scripts/` 目录。
|
|
164
|
+
**不硬编码平台路径**,运行时通过以下命令自定位:
|
|
165
|
+
|
|
166
|
+
```bash
|
|
167
|
+
COMET_GUARD=$(find . -path '*/comet/scripts/comet-guard.sh' -type f -print -quit)
|
|
168
|
+
bash "$COMET_GUARD" <change-name> <phase>
|
|
169
|
+
```
|
|
170
|
+
|
|
171
|
+
后续文档中 `bash $COMET_GUARD <change> <phase>` 均指此命令。加载 comet 后,agent 应在 shell 环境中缓存 `COMET_GUARD` 路径,避免重复 `find`。
|
|
172
|
+
|
|
161
173
|
### 文件结构
|
|
162
174
|
|
|
163
175
|
```
|
|
@@ -0,0 +1,147 @@
|
|
|
1
|
+
#!/bin/bash
|
|
2
|
+
# Comet Phase Guard — validates exit conditions before phase transitions
|
|
3
|
+
# Usage: comet-guard.sh <change-name> <from-phase>
|
|
4
|
+
# Phases: open, design, build, verify, archive
|
|
5
|
+
# Exit 0 = all checks pass, exit 1 = blocked (reasons printed to stderr)
|
|
6
|
+
|
|
7
|
+
set -euo pipefail
|
|
8
|
+
|
|
9
|
+
CHANGE="$1"
|
|
10
|
+
PHASE="$2"
|
|
11
|
+
CHANGE_DIR="openspec/changes/$CHANGE"
|
|
12
|
+
|
|
13
|
+
red() { echo -e "\033[31m$1\033[0m" >&2; }
|
|
14
|
+
green() { echo -e "\033[32m$1\033[0m" >&2; }
|
|
15
|
+
warn() { echo -e "\033[33m$1\033[0m" >&2; }
|
|
16
|
+
|
|
17
|
+
BLOCK=0
|
|
18
|
+
check() {
|
|
19
|
+
local desc="$1"
|
|
20
|
+
shift
|
|
21
|
+
if "$@" 2>/dev/null; then
|
|
22
|
+
green " [PASS] $desc"
|
|
23
|
+
else
|
|
24
|
+
red " [FAIL] $desc"
|
|
25
|
+
BLOCK=1
|
|
26
|
+
fi
|
|
27
|
+
}
|
|
28
|
+
|
|
29
|
+
# --- Helper functions ---
|
|
30
|
+
|
|
31
|
+
tasks_all_done() {
|
|
32
|
+
local tasks="$CHANGE_DIR/tasks.md"
|
|
33
|
+
[ -f "$tasks" ] || return 1
|
|
34
|
+
grep -q '\- \[x\]' "$tasks" || return 1
|
|
35
|
+
! grep -q '\- \[ \]' "$tasks"
|
|
36
|
+
}
|
|
37
|
+
|
|
38
|
+
tasks_has_any() {
|
|
39
|
+
local tasks="$CHANGE_DIR/tasks.md"
|
|
40
|
+
[ -f "$tasks" ] && grep -q '\- \[' "$tasks"
|
|
41
|
+
}
|
|
42
|
+
|
|
43
|
+
yaml_has_field() {
|
|
44
|
+
local field="$1"
|
|
45
|
+
local yaml="$CHANGE_DIR/.openspec.yaml"
|
|
46
|
+
[ -f "$yaml" ] && grep -q "^${field}:" "$yaml"
|
|
47
|
+
}
|
|
48
|
+
|
|
49
|
+
yaml_field_value() {
|
|
50
|
+
local field="$1"
|
|
51
|
+
local yaml="$CHANGE_DIR/.openspec.yaml"
|
|
52
|
+
if [ -f "$yaml" ]; then
|
|
53
|
+
# Escape dots for literal match (YAML field names contain dots)
|
|
54
|
+
local escaped
|
|
55
|
+
escaped=$(echo "$field" | sed 's/\./\\./g')
|
|
56
|
+
grep "^${escaped}:" "$yaml" | sed "s/^${escaped}: *//" | tr -d '"' | tr -d "'"
|
|
57
|
+
fi
|
|
58
|
+
}
|
|
59
|
+
|
|
60
|
+
file_nonempty() {
|
|
61
|
+
[ -f "$1" ] && [ -s "$1" ]
|
|
62
|
+
}
|
|
63
|
+
|
|
64
|
+
maven_compiles() {
|
|
65
|
+
mvn compile -q 2>/dev/null
|
|
66
|
+
}
|
|
67
|
+
|
|
68
|
+
verify_result_is_pass() {
|
|
69
|
+
local result
|
|
70
|
+
result=$(yaml_field_value "comet.verify_result" 2>/dev/null || true)
|
|
71
|
+
[ "$result" = "pass" ]
|
|
72
|
+
}
|
|
73
|
+
|
|
74
|
+
# --- Phase-specific checks ---
|
|
75
|
+
|
|
76
|
+
guard_open() {
|
|
77
|
+
echo "=== Guard: open → design ===" >&2
|
|
78
|
+
|
|
79
|
+
check "proposal.md exists and non-empty" file_nonempty "$CHANGE_DIR/proposal.md"
|
|
80
|
+
check "design.md exists and non-empty" file_nonempty "$CHANGE_DIR/design.md"
|
|
81
|
+
check "tasks.md exists and non-empty" file_nonempty "$CHANGE_DIR/tasks.md"
|
|
82
|
+
check "tasks.md has at least one task" tasks_has_any
|
|
83
|
+
}
|
|
84
|
+
|
|
85
|
+
guard_design() {
|
|
86
|
+
echo "=== Guard: design → build ===" >&2
|
|
87
|
+
|
|
88
|
+
local design_doc
|
|
89
|
+
design_doc=$(yaml_field_value "comet.design_doc" 2>/dev/null || true)
|
|
90
|
+
|
|
91
|
+
check "proposal.md exists" file_nonempty "$CHANGE_DIR/proposal.md"
|
|
92
|
+
check "tasks.md exists" file_nonempty "$CHANGE_DIR/tasks.md"
|
|
93
|
+
|
|
94
|
+
if [ -n "$design_doc" ] && [ "$design_doc" != "null" ]; then
|
|
95
|
+
check "Design Doc ($design_doc) exists" file_nonempty "$design_doc"
|
|
96
|
+
else
|
|
97
|
+
warn " [WARN] No design_doc recorded in .openspec.yaml"
|
|
98
|
+
fi
|
|
99
|
+
}
|
|
100
|
+
|
|
101
|
+
guard_build() {
|
|
102
|
+
echo "=== Guard: build → verify ===" >&2
|
|
103
|
+
|
|
104
|
+
check "tasks.md all tasks checked" tasks_all_done
|
|
105
|
+
check "proposal.md exists" file_nonempty "$CHANGE_DIR/proposal.md"
|
|
106
|
+
check "Maven compile passes" maven_compiles
|
|
107
|
+
}
|
|
108
|
+
|
|
109
|
+
guard_verify() {
|
|
110
|
+
echo "=== Guard: verify → archive ===" >&2
|
|
111
|
+
|
|
112
|
+
check "verify_result is pass" verify_result_is_pass
|
|
113
|
+
check "tasks.md all tasks checked" tasks_all_done
|
|
114
|
+
check "Maven compile passes" maven_compiles
|
|
115
|
+
}
|
|
116
|
+
|
|
117
|
+
guard_archive() {
|
|
118
|
+
echo "=== Guard: archive completeness ===" >&2
|
|
119
|
+
|
|
120
|
+
check "proposal.md exists" file_nonempty "$CHANGE_DIR/proposal.md"
|
|
121
|
+
check "tasks.md all tasks checked" tasks_all_done
|
|
122
|
+
}
|
|
123
|
+
|
|
124
|
+
# --- Main ---
|
|
125
|
+
|
|
126
|
+
case "$PHASE" in
|
|
127
|
+
open) guard_open ;;
|
|
128
|
+
design) guard_design ;;
|
|
129
|
+
build) guard_build ;;
|
|
130
|
+
verify) guard_verify ;;
|
|
131
|
+
archive) guard_archive ;;
|
|
132
|
+
*)
|
|
133
|
+
red "Unknown phase: $PHASE"
|
|
134
|
+
echo "Valid phases: open, design, build, verify, archive" >&2
|
|
135
|
+
exit 1
|
|
136
|
+
;;
|
|
137
|
+
esac
|
|
138
|
+
|
|
139
|
+
if [ "$BLOCK" -eq 1 ]; then
|
|
140
|
+
echo "" >&2
|
|
141
|
+
red "BLOCKED — fix failing checks before proceeding to next phase"
|
|
142
|
+
exit 1
|
|
143
|
+
else
|
|
144
|
+
echo "" >&2
|
|
145
|
+
green "ALL CHECKS PASSED — ready for next phase"
|
|
146
|
+
exit 0
|
|
147
|
+
fi
|
|
@@ -93,6 +93,7 @@ brainstorming → delta spec → 实施(增量修改)→ 验证 → 主 spec
|
|
|
93
93
|
- 关联 design doc 已标注归档状态
|
|
94
94
|
- 关联 plan 已标注归档状态
|
|
95
95
|
- `.openspec.yaml` 中 `comet.archived` 已记录为 `true`
|
|
96
|
+
- **阶段守卫**:运行 `bash $COMET_GUARD <change-name> archive`,全部 PASS 后确认归档完整
|
|
96
97
|
|
|
97
98
|
归档完成后,在归档目录的 `.openspec.yaml` 中合并更新:
|
|
98
99
|
|
|
@@ -1,117 +1,118 @@
|
|
|
1
|
-
---
|
|
2
|
-
name: comet-tweak
|
|
3
|
-
description: "Comet 预设路径:非 bug 的小改动(tweak)。跳过 brainstorming 和完整 plan,直接 open → lightweight build → light verify → archive。适用于文案、配置、文档或 prompt 的局部优化。"
|
|
4
|
-
---
|
|
5
|
-
|
|
6
|
-
# Comet 预设路径:Tweak
|
|
7
|
-
|
|
8
|
-
Tweak 是 Comet 五阶段能力的预设工作流,不是独立的平行流程。它复用 open、build、verify、archive 能力,仅跳过 brainstorming 和完整 plan。
|
|
9
|
-
|
|
10
|
-
适用于非 bug 的小范围变更,例如文案调整、配置调整、文档或 prompt 的局部优化。
|
|
11
|
-
|
|
12
|
-
**适用条件**(必须全部满足):
|
|
13
|
-
1. 不新增 capability
|
|
14
|
-
2. 不改变架构
|
|
15
|
-
3. 不涉及接口变化
|
|
16
|
-
4. 通常不超过 3 个 tasks、5 个文件
|
|
17
|
-
|
|
18
|
-
**不适用**:如变更过程中发现需要 capability、架构或接口调整,应升级为完整 `/comet` 流程。
|
|
19
|
-
|
|
20
|
-
---
|
|
21
|
-
|
|
22
|
-
## 流程(preset workflow,4 阶段)
|
|
23
|
-
|
|
24
|
-
执行链路:open → lightweight build → light verify → archive。Tweak 为每个阶段提供默认决策:精简开启、轻量构建、轻量验证、验证通过后归档。
|
|
25
|
-
|
|
26
|
-
### 1. 快速开启(preset open)
|
|
27
|
-
|
|
28
|
-
复用 Comet open 能力创建 change,但使用 tweak 默认值:不执行 `openspec-explore` 长探索,直接进入精简 change 创建。
|
|
29
|
-
|
|
30
|
-
**立即执行:** 使用 Skill 工具加载 `openspec-new-change` 技能。禁止跳过此步骤。
|
|
31
|
-
|
|
32
|
-
技能加载后,按其指引创建精简版产物:
|
|
33
|
-
- `proposal.md` — 变更动机 + 目标 + 范围
|
|
34
|
-
- `design.md` — 简短实现说明(无需方案对比)
|
|
35
|
-
- `tasks.md` — 不超过 3 个任务
|
|
36
|
-
- **无需 delta spec**(除非变更改变了已有 spec 的验收场景;一旦需要 delta spec,升级为完整 `/comet`)
|
|
37
|
-
|
|
38
|
-
在 `openspec/changes/<name>/.openspec.yaml` 中写入或合并 tweak 状态:
|
|
39
|
-
|
|
40
|
-
```yaml
|
|
41
|
-
comet:
|
|
42
|
-
workflow: tweak
|
|
43
|
-
phase: build
|
|
44
|
-
design_doc: null
|
|
45
|
-
plan: null
|
|
46
|
-
build_mode: direct
|
|
47
|
-
verify_mode: light
|
|
48
|
-
verify_result: pending
|
|
49
|
-
verified_at: null
|
|
50
|
-
archived: false
|
|
51
|
-
```
|
|
52
|
-
|
|
53
|
-
### 2. 轻量构建(preset build)
|
|
54
|
-
|
|
55
|
-
使用 tweak 默认值:`build_mode: direct`。跳过 `superpowers:brainstorming` 和 `superpowers:writing-plans`。
|
|
56
|
-
|
|
57
|
-
**立即执行:** 按 tasks.md 逐个执行任务:
|
|
58
|
-
|
|
59
|
-
1. 读取 `openspec/changes/<name>/tasks.md`,获取未完成任务列表
|
|
60
|
-
2. 对每个未完成任务:
|
|
61
|
-
- 根据任务描述修改目标文件
|
|
62
|
-
- 运行 `mvn spotless:apply` 格式化
|
|
63
|
-
- 运行相关测试确认通过
|
|
64
|
-
- 将 tasks.md 中对应 `- [ ]` 勾选为 `- [x]`
|
|
65
|
-
- 提交代码,commit message 格式:`tweak: <简述变更>`
|
|
66
|
-
3. 全部任务完成后进入验证
|
|
67
|
-
|
|
68
|
-
### 3. 轻量验证(preset verify)
|
|
69
|
-
|
|
70
|
-
复用 `/comet-verify`。Tweak 必须保持轻量验证条件:≤ 3 tasks、≤ 5 files、无 delta spec、无新 capability。
|
|
71
|
-
|
|
72
|
-
**立即执行:** 使用 Skill 工具加载 `comet-verify` 技能。禁止跳过此步骤。
|
|
73
|
-
|
|
74
|
-
如规模评估进入完整验证路径,停止 tweak,升级为完整 `/comet`。
|
|
75
|
-
|
|
76
|
-
验证通过后,按 `/comet-verify` 的规则将 `comet.verify_result` 记录为 `pass`,归档前不得跳过该状态。
|
|
77
|
-
|
|
78
|
-
### 4. 归档(preset archive)
|
|
79
|
-
|
|
80
|
-
复用 `/comet-archive`。归档前必须满足 `comet.verify_result: pass`。
|
|
81
|
-
|
|
82
|
-
**立即执行:** 使用 Skill 工具加载 `comet-archive` 技能进行归档。禁止跳过此步骤。
|
|
83
|
-
|
|
84
|
-
---
|
|
85
|
-
|
|
86
|
-
## 连续执行模式
|
|
87
|
-
|
|
88
|
-
<IMPORTANT>
|
|
89
|
-
Tweak 流程为 **一次性连续执行**。调用 `/comet-tweak` 后,agent 必须自动走完全部 4 个阶段,中间不停顿等待用户输入(除非遇到升级条件需要用户确认)。
|
|
90
|
-
|
|
91
|
-
执行顺序:快速开启 → 轻量构建 → 轻量验证 → 归档 → 完成
|
|
92
|
-
|
|
93
|
-
每个阶段完成后立即进入下一阶段,无需用户再次输入。阶段内部仍必须按上文要求调用对应 Comet/OpenSpec/Superpowers skill。
|
|
94
|
-
</IMPORTANT>
|
|
95
|
-
|
|
96
|
-
---
|
|
97
|
-
|
|
98
|
-
## 升级条件
|
|
99
|
-
|
|
100
|
-
执行过程中出现以下情况时,停止 tweak 流程,升级为完整 `/comet`:
|
|
101
|
-
|
|
102
|
-
1. 需要新增 capability
|
|
103
|
-
2. 需要架构调整
|
|
104
|
-
3. 需要接口变化
|
|
105
|
-
4. 影响范围扩大到 > 5 个文件
|
|
106
|
-
5. 任务数超过 3 个
|
|
107
|
-
6. 需要 delta spec
|
|
108
|
-
|
|
109
|
-
升级方式:在当前 change 基础上补充 Design Doc(执行 `/comet-design`),后续正常走完整流程。
|
|
110
|
-
|
|
111
|
-
---
|
|
112
|
-
|
|
113
|
-
## 退出条件
|
|
114
|
-
|
|
115
|
-
- 小改动已完成,测试通过
|
|
116
|
-
- change 已归档
|
|
117
|
-
- 未新增 capability、架构调整或接口变化
|
|
1
|
+
---
|
|
2
|
+
name: comet-tweak
|
|
3
|
+
description: "Comet 预设路径:非 bug 的小改动(tweak)。跳过 brainstorming 和完整 plan,直接 open → lightweight build → light verify → archive。适用于文案、配置、文档或 prompt 的局部优化。"
|
|
4
|
+
---
|
|
5
|
+
|
|
6
|
+
# Comet 预设路径:Tweak
|
|
7
|
+
|
|
8
|
+
Tweak 是 Comet 五阶段能力的预设工作流,不是独立的平行流程。它复用 open、build、verify、archive 能力,仅跳过 brainstorming 和完整 plan。
|
|
9
|
+
|
|
10
|
+
适用于非 bug 的小范围变更,例如文案调整、配置调整、文档或 prompt 的局部优化。
|
|
11
|
+
|
|
12
|
+
**适用条件**(必须全部满足):
|
|
13
|
+
1. 不新增 capability
|
|
14
|
+
2. 不改变架构
|
|
15
|
+
3. 不涉及接口变化
|
|
16
|
+
4. 通常不超过 3 个 tasks、5 个文件
|
|
17
|
+
|
|
18
|
+
**不适用**:如变更过程中发现需要 capability、架构或接口调整,应升级为完整 `/comet` 流程。
|
|
19
|
+
|
|
20
|
+
---
|
|
21
|
+
|
|
22
|
+
## 流程(preset workflow,4 阶段)
|
|
23
|
+
|
|
24
|
+
执行链路:open → lightweight build → light verify → archive。Tweak 为每个阶段提供默认决策:精简开启、轻量构建、轻量验证、验证通过后归档。
|
|
25
|
+
|
|
26
|
+
### 1. 快速开启(preset open)
|
|
27
|
+
|
|
28
|
+
复用 Comet open 能力创建 change,但使用 tweak 默认值:不执行 `openspec-explore` 长探索,直接进入精简 change 创建。
|
|
29
|
+
|
|
30
|
+
**立即执行:** 使用 Skill 工具加载 `openspec-new-change` 技能。禁止跳过此步骤。
|
|
31
|
+
|
|
32
|
+
技能加载后,按其指引创建精简版产物:
|
|
33
|
+
- `proposal.md` — 变更动机 + 目标 + 范围
|
|
34
|
+
- `design.md` — 简短实现说明(无需方案对比)
|
|
35
|
+
- `tasks.md` — 不超过 3 个任务
|
|
36
|
+
- **无需 delta spec**(除非变更改变了已有 spec 的验收场景;一旦需要 delta spec,升级为完整 `/comet`)
|
|
37
|
+
|
|
38
|
+
在 `openspec/changes/<name>/.openspec.yaml` 中写入或合并 tweak 状态:
|
|
39
|
+
|
|
40
|
+
```yaml
|
|
41
|
+
comet:
|
|
42
|
+
workflow: tweak
|
|
43
|
+
phase: build
|
|
44
|
+
design_doc: null
|
|
45
|
+
plan: null
|
|
46
|
+
build_mode: direct
|
|
47
|
+
verify_mode: light
|
|
48
|
+
verify_result: pending
|
|
49
|
+
verified_at: null
|
|
50
|
+
archived: false
|
|
51
|
+
```
|
|
52
|
+
|
|
53
|
+
### 2. 轻量构建(preset build)
|
|
54
|
+
|
|
55
|
+
使用 tweak 默认值:`build_mode: direct`。跳过 `superpowers:brainstorming` 和 `superpowers:writing-plans`。
|
|
56
|
+
|
|
57
|
+
**立即执行:** 按 tasks.md 逐个执行任务:
|
|
58
|
+
|
|
59
|
+
1. 读取 `openspec/changes/<name>/tasks.md`,获取未完成任务列表
|
|
60
|
+
2. 对每个未完成任务:
|
|
61
|
+
- 根据任务描述修改目标文件
|
|
62
|
+
- 运行 `mvn spotless:apply` 格式化
|
|
63
|
+
- 运行相关测试确认通过
|
|
64
|
+
- 将 tasks.md 中对应 `- [ ]` 勾选为 `- [x]`
|
|
65
|
+
- 提交代码,commit message 格式:`tweak: <简述变更>`
|
|
66
|
+
3. 全部任务完成后进入验证
|
|
67
|
+
|
|
68
|
+
### 3. 轻量验证(preset verify)
|
|
69
|
+
|
|
70
|
+
复用 `/comet-verify`。Tweak 必须保持轻量验证条件:≤ 3 tasks、≤ 5 files、无 delta spec、无新 capability。
|
|
71
|
+
|
|
72
|
+
**立即执行:** 使用 Skill 工具加载 `comet-verify` 技能。禁止跳过此步骤。
|
|
73
|
+
|
|
74
|
+
如规模评估进入完整验证路径,停止 tweak,升级为完整 `/comet`。
|
|
75
|
+
|
|
76
|
+
验证通过后,按 `/comet-verify` 的规则将 `comet.verify_result` 记录为 `pass`,归档前不得跳过该状态。
|
|
77
|
+
|
|
78
|
+
### 4. 归档(preset archive)
|
|
79
|
+
|
|
80
|
+
复用 `/comet-archive`。归档前必须满足 `comet.verify_result: pass`。
|
|
81
|
+
|
|
82
|
+
**立即执行:** 使用 Skill 工具加载 `comet-archive` 技能进行归档。禁止跳过此步骤。
|
|
83
|
+
|
|
84
|
+
---
|
|
85
|
+
|
|
86
|
+
## 连续执行模式
|
|
87
|
+
|
|
88
|
+
<IMPORTANT>
|
|
89
|
+
Tweak 流程为 **一次性连续执行**。调用 `/comet-tweak` 后,agent 必须自动走完全部 4 个阶段,中间不停顿等待用户输入(除非遇到升级条件需要用户确认)。
|
|
90
|
+
|
|
91
|
+
执行顺序:快速开启 → 轻量构建 → 轻量验证 → 归档 → 完成
|
|
92
|
+
|
|
93
|
+
每个阶段完成后立即进入下一阶段,无需用户再次输入。阶段内部仍必须按上文要求调用对应 Comet/OpenSpec/Superpowers skill。
|
|
94
|
+
</IMPORTANT>
|
|
95
|
+
|
|
96
|
+
---
|
|
97
|
+
|
|
98
|
+
## 升级条件
|
|
99
|
+
|
|
100
|
+
执行过程中出现以下情况时,停止 tweak 流程,升级为完整 `/comet`:
|
|
101
|
+
|
|
102
|
+
1. 需要新增 capability
|
|
103
|
+
2. 需要架构调整
|
|
104
|
+
3. 需要接口变化
|
|
105
|
+
4. 影响范围扩大到 > 5 个文件
|
|
106
|
+
5. 任务数超过 3 个
|
|
107
|
+
6. 需要 delta spec
|
|
108
|
+
|
|
109
|
+
升级方式:在当前 change 基础上补充 Design Doc(执行 `/comet-design`),后续正常走完整流程。
|
|
110
|
+
|
|
111
|
+
---
|
|
112
|
+
|
|
113
|
+
## 退出条件
|
|
114
|
+
|
|
115
|
+
- 小改动已完成,测试通过
|
|
116
|
+
- change 已归档
|
|
117
|
+
- 未新增 capability、架构调整或接口变化
|
|
118
|
+
- **阶段守卫**:build → verify 前运行 `bash $COMET_GUARD <change-name> build`,verify → archive 前运行 `bash $COMET_GUARD <change-name> verify`
|
package/bin/comet.js
CHANGED
|
@@ -1,3 +1,3 @@
|
|
|
1
|
-
#!/usr/bin/env node
|
|
2
|
-
|
|
3
|
-
import '../dist/cli/index.js';
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
|
|
3
|
+
import '../dist/cli/index.js';
|
package/package.json
CHANGED
|
@@ -1,50 +1,50 @@
|
|
|
1
|
-
{
|
|
2
|
-
"name": "@rpamis/comet",
|
|
3
|
-
"version": "0.1.
|
|
4
|
-
"description": "OpenSpec + Superpowers dual-star development workflow",
|
|
5
|
-
"keywords": [
|
|
6
|
-
"comet",
|
|
7
|
-
"openspec",
|
|
8
|
-
"superpowers",
|
|
9
|
-
"skills",
|
|
10
|
-
"workflow"
|
|
11
|
-
],
|
|
12
|
-
"license": "MIT",
|
|
13
|
-
"author": "benym",
|
|
14
|
-
"type": "module",
|
|
15
|
-
"publishConfig": {
|
|
16
|
-
"access": "public"
|
|
17
|
-
},
|
|
18
|
-
"bin": {
|
|
19
|
-
"comet": "./bin/comet.js"
|
|
20
|
-
},
|
|
21
|
-
"files": [
|
|
22
|
-
"dist",
|
|
23
|
-
"bin",
|
|
24
|
-
"assets",
|
|
25
|
-
"scripts/postinstall.js",
|
|
26
|
-
"!dist/**/*.test.js",
|
|
27
|
-
"!dist/**/__tests__"
|
|
28
|
-
],
|
|
29
|
-
"scripts": {
|
|
30
|
-
"build": "node build.js",
|
|
31
|
-
"dev": "tsc --watch",
|
|
32
|
-
"test": "vitest run",
|
|
33
|
-
"test:watch": "vitest",
|
|
34
|
-
"prepare": "pnpm run build",
|
|
35
|
-
"prepublishOnly": "pnpm run build",
|
|
36
|
-
"postinstall": "node scripts/postinstall.js"
|
|
37
|
-
},
|
|
38
|
-
"engines": {
|
|
39
|
-
"node": ">=18"
|
|
40
|
-
},
|
|
41
|
-
"devDependencies": {
|
|
42
|
-
"@types/node": "^24.2.0",
|
|
43
|
-
"typescript": "^5.9.3",
|
|
44
|
-
"vitest": "^3.2.4"
|
|
45
|
-
},
|
|
46
|
-
"dependencies": {
|
|
47
|
-
"@inquirer/prompts": "^8.4.3",
|
|
48
|
-
"commander": "^14.0.0"
|
|
49
|
-
}
|
|
50
|
-
}
|
|
1
|
+
{
|
|
2
|
+
"name": "@rpamis/comet",
|
|
3
|
+
"version": "0.1.2",
|
|
4
|
+
"description": "OpenSpec + Superpowers dual-star development workflow",
|
|
5
|
+
"keywords": [
|
|
6
|
+
"comet",
|
|
7
|
+
"openspec",
|
|
8
|
+
"superpowers",
|
|
9
|
+
"skills",
|
|
10
|
+
"workflow"
|
|
11
|
+
],
|
|
12
|
+
"license": "MIT",
|
|
13
|
+
"author": "benym",
|
|
14
|
+
"type": "module",
|
|
15
|
+
"publishConfig": {
|
|
16
|
+
"access": "public"
|
|
17
|
+
},
|
|
18
|
+
"bin": {
|
|
19
|
+
"comet": "./bin/comet.js"
|
|
20
|
+
},
|
|
21
|
+
"files": [
|
|
22
|
+
"dist",
|
|
23
|
+
"bin",
|
|
24
|
+
"assets",
|
|
25
|
+
"scripts/postinstall.js",
|
|
26
|
+
"!dist/**/*.test.js",
|
|
27
|
+
"!dist/**/__tests__"
|
|
28
|
+
],
|
|
29
|
+
"scripts": {
|
|
30
|
+
"build": "node build.js",
|
|
31
|
+
"dev": "tsc --watch",
|
|
32
|
+
"test": "vitest run",
|
|
33
|
+
"test:watch": "vitest",
|
|
34
|
+
"prepare": "pnpm run build",
|
|
35
|
+
"prepublishOnly": "node scripts/prepublish-check.js && pnpm run build",
|
|
36
|
+
"postinstall": "node scripts/postinstall.js"
|
|
37
|
+
},
|
|
38
|
+
"engines": {
|
|
39
|
+
"node": ">=18"
|
|
40
|
+
},
|
|
41
|
+
"devDependencies": {
|
|
42
|
+
"@types/node": "^24.2.0",
|
|
43
|
+
"typescript": "^5.9.3",
|
|
44
|
+
"vitest": "^3.2.4"
|
|
45
|
+
},
|
|
46
|
+
"dependencies": {
|
|
47
|
+
"@inquirer/prompts": "^8.4.3",
|
|
48
|
+
"commander": "^14.0.0"
|
|
49
|
+
}
|
|
50
|
+
}
|
package/scripts/postinstall.js
CHANGED
|
@@ -1,44 +1,44 @@
|
|
|
1
|
-
#!/usr/bin/env node
|
|
2
|
-
|
|
3
|
-
/**
|
|
4
|
-
* Postinstall script that hints about comet init.
|
|
5
|
-
*
|
|
6
|
-
* The tip is suppressed when:
|
|
7
|
-
* - CI=true environment variable is set
|
|
8
|
-
* - COMET_NO_HINTS=1 environment variable is set
|
|
9
|
-
* - dist/ directory doesn't exist (dev setup scenario)
|
|
10
|
-
*/
|
|
11
|
-
|
|
12
|
-
import { promises as fs } from 'fs';
|
|
13
|
-
import path from 'path';
|
|
14
|
-
import { fileURLToPath } from 'url';
|
|
15
|
-
|
|
16
|
-
const __filename = fileURLToPath(import.meta.url);
|
|
17
|
-
const __dirname = path.dirname(__filename);
|
|
18
|
-
|
|
19
|
-
function shouldSkip() {
|
|
20
|
-
if (process.env.CI === 'true' || process.env.CI === '1') return true;
|
|
21
|
-
if (process.env.COMET_NO_HINTS === '1') return true;
|
|
22
|
-
return false;
|
|
23
|
-
}
|
|
24
|
-
|
|
25
|
-
async function distExists() {
|
|
26
|
-
try {
|
|
27
|
-
const stat = await fs.stat(path.join(__dirname, '..', 'dist'));
|
|
28
|
-
return stat.isDirectory();
|
|
29
|
-
} catch {
|
|
30
|
-
return false;
|
|
31
|
-
}
|
|
32
|
-
}
|
|
33
|
-
|
|
34
|
-
async function main() {
|
|
35
|
-
try {
|
|
36
|
-
if (shouldSkip()) return;
|
|
37
|
-
if (!(await distExists())) return;
|
|
38
|
-
console.log(`\nTip: Run 'comet init' to set up Comet workflow in your project`);
|
|
39
|
-
} catch {
|
|
40
|
-
// Never break npm install
|
|
41
|
-
}
|
|
42
|
-
}
|
|
43
|
-
|
|
44
|
-
main().catch(() => process.exit(0));
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
|
|
3
|
+
/**
|
|
4
|
+
* Postinstall script that hints about comet init.
|
|
5
|
+
*
|
|
6
|
+
* The tip is suppressed when:
|
|
7
|
+
* - CI=true environment variable is set
|
|
8
|
+
* - COMET_NO_HINTS=1 environment variable is set
|
|
9
|
+
* - dist/ directory doesn't exist (dev setup scenario)
|
|
10
|
+
*/
|
|
11
|
+
|
|
12
|
+
import { promises as fs } from 'fs';
|
|
13
|
+
import path from 'path';
|
|
14
|
+
import { fileURLToPath } from 'url';
|
|
15
|
+
|
|
16
|
+
const __filename = fileURLToPath(import.meta.url);
|
|
17
|
+
const __dirname = path.dirname(__filename);
|
|
18
|
+
|
|
19
|
+
function shouldSkip() {
|
|
20
|
+
if (process.env.CI === 'true' || process.env.CI === '1') return true;
|
|
21
|
+
if (process.env.COMET_NO_HINTS === '1') return true;
|
|
22
|
+
return false;
|
|
23
|
+
}
|
|
24
|
+
|
|
25
|
+
async function distExists() {
|
|
26
|
+
try {
|
|
27
|
+
const stat = await fs.stat(path.join(__dirname, '..', 'dist'));
|
|
28
|
+
return stat.isDirectory();
|
|
29
|
+
} catch {
|
|
30
|
+
return false;
|
|
31
|
+
}
|
|
32
|
+
}
|
|
33
|
+
|
|
34
|
+
async function main() {
|
|
35
|
+
try {
|
|
36
|
+
if (shouldSkip()) return;
|
|
37
|
+
if (!(await distExists())) return;
|
|
38
|
+
console.log(`\nTip: Run 'comet init' to set up Comet workflow in your project`);
|
|
39
|
+
} catch {
|
|
40
|
+
// Never break npm install
|
|
41
|
+
}
|
|
42
|
+
}
|
|
43
|
+
|
|
44
|
+
main().catch(() => process.exit(0));
|