@simplysm/sd-claude 13.0.55 → 13.0.57
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/claude/{rules → refs}/sd-code-conventions.md +6 -0
- package/claude/refs/sd-orm.md +17 -0
- package/claude/refs/sd-service.md +5 -0
- package/claude/refs/sd-simplysm-docs.md +52 -0
- package/claude/refs/sd-solid.md +49 -0
- package/claude/rules/sd-refs-linker.md +18 -0
- package/claude/skills/sd-check/SKILL.md +22 -166
- package/claude/skills/sd-check/run-checks.mjs +10 -79
- package/claude/skills/sd-plan/SKILL.md +7 -4
- package/claude/skills/sd-worktree/sd-worktree.mjs +12 -5
- package/package.json +1 -1
- package/claude/rules/sd-simplysm-docs.md +0 -52
- /package/claude/{rules → refs}/sd-directories.md +0 -0
- /package/claude/{rules/sd-workflow-rules.md → refs/sd-workflow.md} +0 -0
|
@@ -8,6 +8,7 @@
|
|
|
8
8
|
## Prototype Extensions
|
|
9
9
|
|
|
10
10
|
Importing `@simplysm/core-common` adds extension methods to Array, Map, Set:
|
|
11
|
+
|
|
11
12
|
- `Array`: `single()`, `filterExists()`, `groupBy()`, `orderBy()`, etc.
|
|
12
13
|
- `Map`: `getOrCreate()`, `update()`
|
|
13
14
|
- `Set`: `adds()`, `toggle()`
|
|
@@ -28,6 +29,11 @@ function readFileSync() { ... } // Sync version
|
|
|
28
29
|
async function readFileAsync() { ... } // Async suffix prohibited
|
|
29
30
|
```
|
|
30
31
|
|
|
32
|
+
## File Naming
|
|
33
|
+
|
|
34
|
+
- Auxiliary files (`types.ts`, `utils.ts`, etc.) must be prefixed with the main file name (e.g., `CrudSheet.types.ts`)
|
|
35
|
+
- File names must be self-identifying without relying on the parent directory
|
|
36
|
+
|
|
31
37
|
## JSDoc Convention
|
|
32
38
|
|
|
33
39
|
- Not enforced — omit when code is self-explanatory
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
# ORM Guidelines
|
|
2
|
+
|
|
3
|
+
## Table Definition
|
|
4
|
+
```typescript
|
|
5
|
+
const User = Table("User")
|
|
6
|
+
.database("mydb")
|
|
7
|
+
.columns((c) => ({ id: c.bigint().autoIncrement(), name: c.varchar(100) }))
|
|
8
|
+
.primaryKey("id");
|
|
9
|
+
```
|
|
10
|
+
|
|
11
|
+
## SQL Injection Prevention
|
|
12
|
+
ORM uses string escaping (not parameter binding). **Always validate user input before ORM queries.**
|
|
13
|
+
```typescript
|
|
14
|
+
const userId = Number(req.query.id);
|
|
15
|
+
if (Number.isNaN(userId)) throw new Error("Invalid ID");
|
|
16
|
+
await db.user().where((u) => [expr.eq(u.id, userId)]).result();
|
|
17
|
+
```
|
|
@@ -0,0 +1,52 @@
|
|
|
1
|
+
# @simplysm Package Documentation
|
|
2
|
+
|
|
3
|
+
When you need API details, usage examples, or component props for `@simplysm/*` packages,
|
|
4
|
+
read the package's README.md from node_modules.
|
|
5
|
+
|
|
6
|
+
## How to use
|
|
7
|
+
|
|
8
|
+
Read the package README directly:
|
|
9
|
+
|
|
10
|
+
```
|
|
11
|
+
node_modules/@simplysm/{package-name}/README.md
|
|
12
|
+
```
|
|
13
|
+
|
|
14
|
+
If not found (pnpm hoisting), try:
|
|
15
|
+
|
|
16
|
+
```
|
|
17
|
+
packages/*/node_modules/@simplysm/{package-name}/README.md
|
|
18
|
+
```
|
|
19
|
+
|
|
20
|
+
## When to use
|
|
21
|
+
|
|
22
|
+
**MANDATORY**: Read the relevant README BEFORE any of the following:
|
|
23
|
+
|
|
24
|
+
- Writing new code that uses `@simplysm/*` APIs
|
|
25
|
+
- Fixing type errors or bugs in code that uses `@simplysm/*` APIs
|
|
26
|
+
- Making assumptions about type mappings (e.g., DB column types → TypeScript types)
|
|
27
|
+
- Refactoring or migrating code that depends on `@simplysm/*` packages
|
|
28
|
+
|
|
29
|
+
Do NOT guess API behavior or type mappings — always verify from the README first.
|
|
30
|
+
|
|
31
|
+
## Available Packages
|
|
32
|
+
|
|
33
|
+
| Package | Description |
|
|
34
|
+
| ------------------------------ | --------------------------------------------------------------- |
|
|
35
|
+
| `core-common` | Common utilities, custom types (DateTime, DateOnly, Time, Uuid) |
|
|
36
|
+
| `core-browser` | Browser-specific extensions |
|
|
37
|
+
| `core-node` | Node.js utilities (filesystem, workers) |
|
|
38
|
+
| `orm-common` | ORM query builder, table schema definitions |
|
|
39
|
+
| `orm-node` | DB connectors (MySQL, MSSQL, PostgreSQL) |
|
|
40
|
+
| `service-common` | Service protocol, type definitions |
|
|
41
|
+
| `service-client` | WebSocket client |
|
|
42
|
+
| `service-server` | Fastify-based HTTP/WebSocket server |
|
|
43
|
+
| `solid` | SolidJS UI components + Tailwind CSS |
|
|
44
|
+
| `excel` | Excel (.xlsx) read/write |
|
|
45
|
+
| `storage` | FTP/SFTP client |
|
|
46
|
+
| `sd-cli` | Build, lint, typecheck CLI tool |
|
|
47
|
+
| `claude` | Claude Code skills/agents (auto-installs via postinstall) |
|
|
48
|
+
| `eslint-plugin` | Custom ESLint rules |
|
|
49
|
+
| `capacitor-plugin-auto-update` | Auto update |
|
|
50
|
+
| `capacitor-plugin-broadcast` | Broadcast |
|
|
51
|
+
| `capacitor-plugin-file-system` | File system |
|
|
52
|
+
| `capacitor-plugin-usb-storage` | USB storage |
|
|
@@ -0,0 +1,49 @@
|
|
|
1
|
+
# SolidJS Guidelines
|
|
2
|
+
|
|
3
|
+
**SolidJS is NOT React!**
|
|
4
|
+
|
|
5
|
+
## Core Concepts
|
|
6
|
+
- Component functions run **once** at mount (not on every state change)
|
|
7
|
+
- Fine-grained reactivity: unchanged signals don't re-evaluate expressions
|
|
8
|
+
- `createMemo`: only for expensive computations used in multiple places
|
|
9
|
+
- **Props destructuring prohibited** → use `props.xxx`
|
|
10
|
+
- Conditionals: `<Show>`, Lists: `<For>`
|
|
11
|
+
- No SSR → browser APIs usable directly
|
|
12
|
+
- Responsive: Mobile UI below 520px
|
|
13
|
+
- Chrome 84+ target
|
|
14
|
+
- CSS NOT transpiled → no `aspect-ratio`, `inset`, `:is()`, `:where()`
|
|
15
|
+
|
|
16
|
+
## Props Design
|
|
17
|
+
- Props that don't need parameters must accept plain values (`editable={perms().edit}`), not wrapped in functions (`editable={() => perms().edit}`) — use function props only when parameters are needed (callbacks)
|
|
18
|
+
|
|
19
|
+
## Implementation Rules
|
|
20
|
+
- Prefer signals/stores over Provider/Context
|
|
21
|
+
- Check existing patterns before introducing abstractions
|
|
22
|
+
- Before modifying components: always Read the file to check existing props/patterns
|
|
23
|
+
|
|
24
|
+
## Hook Naming
|
|
25
|
+
- `create*`: Reactive hooks wrapping SolidJS primitives
|
|
26
|
+
- `use*`: Hooks depending on Provider Context
|
|
27
|
+
- Others: no hook prefix
|
|
28
|
+
|
|
29
|
+
## Compound Components
|
|
30
|
+
All sub-components via dot notation only (`Parent.Child`).
|
|
31
|
+
- Define `interface ParentComponent { Child: typeof ChildComponent }`
|
|
32
|
+
- Assign `Parent.Child = ChildComponent;`
|
|
33
|
+
- Don't export sub-components separately (export parent only)
|
|
34
|
+
- UI elements → compound sub-components, non-rendering config (state, behavior, callbacks) → props
|
|
35
|
+
|
|
36
|
+
## Tailwind CSS
|
|
37
|
+
- `darkMode: "class"`, `aspectRatio` plugin disabled (Chrome 84)
|
|
38
|
+
- Semantic colors: `primary`(blue), `info`(sky), `success`(green), `warning`(amber), `danger`(red), `base`(zinc) → never use `zinc-*` directly
|
|
39
|
+
- Heights: `field`, `field-sm`, `field-lg`
|
|
40
|
+
- z-index: `sidebar`(100), `sidebar-backdrop`(99), `dropdown`(1000)
|
|
41
|
+
- Default `rem`, use `em` for text-relative sizing (e.g., Icon)
|
|
42
|
+
- Use `clsx()` with semantic grouping + `twMerge()` for conflict resolution
|
|
43
|
+
- Before modifying styles: Read existing class patterns of the same component
|
|
44
|
+
|
|
45
|
+
## Application View Naming (`client-*`)
|
|
46
|
+
- `~Sheet` — List view based on DataSheet (e.g., `UserSheet`)
|
|
47
|
+
- `~Detail` — Single record detail/edit view (e.g., `MyInfoDetail`)
|
|
48
|
+
- `~View` — Everything else (e.g., `LoginView`, `MainView`)
|
|
49
|
+
- Directory: `src/views/` (usable as standalone page, embedded component, or modal)
|
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
# Reference Guide
|
|
2
|
+
|
|
3
|
+
Before starting work, **Read** the relevant reference files from `.claude/refs/`.
|
|
4
|
+
|
|
5
|
+
| When | Read this file |
|
|
6
|
+
|------|---------------|
|
|
7
|
+
| Writing or modifying code | `.claude/refs/sd-code-conventions.md` |
|
|
8
|
+
| Working with `.cache/` or Playwright screenshots | `.claude/refs/sd-directories.md` |
|
|
9
|
+
| Using `@simplysm/*` package APIs | `.claude/refs/sd-simplysm-docs.md` |
|
|
10
|
+
| Debugging, problem-solving, or planning approach | `.claude/refs/sd-workflow.md` |
|
|
11
|
+
| SolidJS / @simplysm/solid / Tailwind 작업 시 | `.claude/refs/sd-solid.md` |
|
|
12
|
+
| @simplysm/orm-* 사용 시 (`@^13`) | `.claude/refs/sd-orm.md` |
|
|
13
|
+
| @simplysm/service-* 사용 시 (`@^13`) | `.claude/refs/sd-service.md` |
|
|
14
|
+
|
|
15
|
+
**Rules:**
|
|
16
|
+
- Read the reference BEFORE starting the related work (not after)
|
|
17
|
+
- You may read multiple references if the task spans multiple areas
|
|
18
|
+
- If unsure whether a reference applies, read it — the cost of reading is low
|
|
@@ -1,184 +1,40 @@
|
|
|
1
1
|
---
|
|
2
2
|
name: sd-check
|
|
3
3
|
description: Use when verifying code quality via typecheck, lint, and tests - before deployment, PR creation, after code changes, or when type errors, lint violations, or test failures are suspected. Applies to whole project or specific paths.
|
|
4
|
-
allowed-tools: Bash(
|
|
4
|
+
allowed-tools: Bash(pnpm check), Bash(pnpm typecheck), Bash(pnpm lint --fix), Bash(pnpm vitest)
|
|
5
5
|
---
|
|
6
6
|
|
|
7
7
|
# sd-check
|
|
8
8
|
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
## Overview
|
|
12
|
-
|
|
13
|
-
**This skill provides EXACT STEPS you MUST follow - it is NOT a command to invoke.**
|
|
14
|
-
|
|
15
|
-
**Foundational Principle:** Violating the letter of these steps is violating the spirit of verification.
|
|
16
|
-
|
|
17
|
-
When the user asks to verify code, YOU will manually execute **EXACTLY THESE 3 STEPS** (no more, no less):
|
|
18
|
-
|
|
19
|
-
**Step 1:** Run the unified check script (single background command)
|
|
20
|
-
**Step 2:** Collect results, fix errors in priority order
|
|
21
|
-
**Step 3:** Re-verify (go back to Step 1) until all pass
|
|
22
|
-
|
|
23
|
-
**Core principle:** Always re-run ALL checks after any fix - changes can cascade.
|
|
24
|
-
|
|
25
|
-
**CRITICAL:**
|
|
26
|
-
- This skill verifies ONLY typecheck, lint, and test
|
|
27
|
-
- **NO BUILD. NO DEV SERVER. NO TEAMS. NO TASK LISTS.**
|
|
28
|
-
- Do NOT create your own "better" workflow - follow these 3 steps EXACTLY
|
|
9
|
+
Run `pnpm check`, fix errors, repeat until clean.
|
|
29
10
|
|
|
30
11
|
## Usage
|
|
31
12
|
|
|
32
|
-
- `/sd-check` — verify entire project
|
|
33
|
-
- `/sd-check packages/core-common` — verify specific path only
|
|
34
|
-
|
|
35
|
-
**Default:** If no path argument provided, verify entire project.
|
|
36
|
-
|
|
37
|
-
## Quick Reference
|
|
38
|
-
|
|
39
|
-
| Check | Purpose |
|
|
40
|
-
|-------|---------|
|
|
41
|
-
| Typecheck | Type errors |
|
|
42
|
-
| Lint | Code quality (with auto-fix) |
|
|
43
|
-
| Test | Functionality |
|
|
44
|
-
|
|
45
|
-
**All 3 run in PARALLEL** inside the unified script (single command).
|
|
46
|
-
|
|
47
|
-
## Workflow
|
|
48
|
-
|
|
49
|
-
### Step 1: Run Unified Check Script
|
|
50
|
-
|
|
51
|
-
Launch the single check command in background:
|
|
52
|
-
|
|
53
|
-
```
|
|
54
|
-
Bash tool:
|
|
55
|
-
command: "node .claude/skills/sd-check/run-checks.mjs [path]"
|
|
56
|
-
description: "Run typecheck + lint + test"
|
|
57
|
-
timeout: 600000
|
|
58
|
-
```
|
|
59
|
-
|
|
60
|
-
Replace `[path]` with user's argument, or OMIT if no argument (defaults to full project).
|
|
61
|
-
|
|
62
|
-
**Output format:**
|
|
63
13
|
```
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
====== LINT: FAIL → .tmp/sd-check/lint.log ======
|
|
67
|
-
|
|
68
|
-
====== TEST: PASS (47 tests) ======
|
|
69
|
-
|
|
70
|
-
====== SUMMARY: 1/3 FAILED (lint) ======
|
|
14
|
+
pnpm check [path] [--type typecheck|lint|test]
|
|
71
15
|
```
|
|
72
16
|
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
-
|
|
77
|
-
-
|
|
78
|
-
-
|
|
17
|
+
| Example | Effect |
|
|
18
|
+
|---------|--------|
|
|
19
|
+
| `/sd-check` | Full project, all checks |
|
|
20
|
+
| `/sd-check packages/core-common` | Specific path, all checks |
|
|
21
|
+
| `/sd-check test` | Tests only, full project |
|
|
22
|
+
| `/sd-check packages/core-common lint` | Specific path + type |
|
|
79
23
|
|
|
80
|
-
|
|
24
|
+
Multiple types: `--type typecheck,lint`. No path = full project. No type = all checks.
|
|
81
25
|
|
|
82
|
-
|
|
83
|
-
- Typecheck errors may cause lint/test errors (cascade)
|
|
84
|
-
|
|
85
|
-
2. **Read log files** (`.tmp/sd-check/{name}.log`) to see full error output, then **read failing source files** to identify root cause
|
|
86
|
-
|
|
87
|
-
3. **Fix with Edit:**
|
|
88
|
-
- **Typecheck:** Fix type issues
|
|
89
|
-
- **Lint:** Fix code quality (most auto-fixed by `--fix`)
|
|
90
|
-
- **Test:**
|
|
91
|
-
- Run `git diff` to check intentional changes
|
|
92
|
-
- If changes not reflected in tests: Update test
|
|
93
|
-
- If source bug: Fix source
|
|
94
|
-
- **If root cause unclear OR 2-3 fix attempts failed:** Recommend `/sd-debug`
|
|
95
|
-
|
|
96
|
-
4. **Proceed to Step 3**
|
|
97
|
-
|
|
98
|
-
### Step 3: Re-verify (Loop Until All Pass)
|
|
99
|
-
|
|
100
|
-
**CRITICAL:** After ANY fix, re-run ALL 3 checks.
|
|
101
|
-
|
|
102
|
-
Go back to Step 1 and run the unified script again.
|
|
103
|
-
|
|
104
|
-
**Do NOT assume:** "I only fixed typecheck → skip lint/test". Fixes cascade.
|
|
105
|
-
|
|
106
|
-
Repeat Steps 1-3 until all 3 checks pass.
|
|
107
|
-
|
|
108
|
-
## Common Mistakes
|
|
109
|
-
|
|
110
|
-
### Fixing before reading full output
|
|
111
|
-
**Wrong:** See first error in output → fix immediately
|
|
112
|
-
**Right:** Read full SUMMARY → collect all errors → fix in priority order → re-verify
|
|
113
|
-
|
|
114
|
-
### Skipping re-verification after fixes
|
|
115
|
-
**Wrong:** Fix typecheck → assume lint/test still pass
|
|
116
|
-
**Right:** ALWAYS re-run the script after any fix
|
|
117
|
-
|
|
118
|
-
### Using agents instead of background Bash
|
|
119
|
-
**Wrong:** Launch haiku/sonnet/opus agents via Task tool to run the script
|
|
120
|
-
**Right:** Use `Bash` with `run_in_background: true` (no model overhead)
|
|
121
|
-
|
|
122
|
-
### Including build/dev steps
|
|
123
|
-
**Wrong:** Run `pnpm build` or `pnpm dev` as part of verification
|
|
124
|
-
**Right:** sd-check is ONLY typecheck, lint, test (no build, no dev)
|
|
125
|
-
|
|
126
|
-
### Asking user for path
|
|
127
|
-
**Wrong:** No path provided → ask "which package?"
|
|
128
|
-
**Right:** No path → verify entire project (omit path in command)
|
|
129
|
-
|
|
130
|
-
### Infinite fix loop
|
|
131
|
-
**Wrong:** Keep trying same fix when tests fail repeatedly
|
|
132
|
-
**Right:** After 2-3 failed attempts → recommend `/sd-debug`
|
|
133
|
-
|
|
134
|
-
### Claiming success without fresh evidence
|
|
135
|
-
**Wrong:** "All checks should pass now" or "Great, that fixes it!"
|
|
136
|
-
**Right:** Run script → read output → cite results (e.g., "0 errors, 47 tests passed") → THEN claim
|
|
137
|
-
|
|
138
|
-
## Red Flags - STOP and Follow Workflow
|
|
139
|
-
|
|
140
|
-
If you find yourself doing ANY of these, you're violating the skill:
|
|
141
|
-
|
|
142
|
-
- Including build or dev server in verification
|
|
143
|
-
- Using Task/agent instead of background Bash
|
|
144
|
-
- Not re-verifying after every fix
|
|
145
|
-
- Asking user for path when none provided
|
|
146
|
-
- Continuing past 2-3 failed fix attempts without recommending `/sd-debug`
|
|
147
|
-
- Expressing satisfaction ("Great!", "Perfect!", "Done!") before all 3 checks pass
|
|
148
|
-
- Using vague language: "should work", "probably passes", "seems fine"
|
|
149
|
-
- Claiming completion based on a previous run, not the current one
|
|
150
|
-
|
|
151
|
-
**All of these violate the skill's core principles. Go back to Step 1 and follow the workflow exactly.**
|
|
152
|
-
|
|
153
|
-
## Completion Criteria
|
|
154
|
-
|
|
155
|
-
**Complete when:**
|
|
156
|
-
- All 3 checks (typecheck, lint, test) pass without errors **in the most recent run**
|
|
157
|
-
- Report with evidence: "All checks passed" + cite actual output (e.g., "0 errors", "47 tests passed")
|
|
158
|
-
|
|
159
|
-
**Fresh evidence required:**
|
|
160
|
-
- "Passes" = you ran it THIS iteration and saw it pass in the output
|
|
161
|
-
- Previous run results are NOT evidence for current state
|
|
162
|
-
- Confidence is NOT evidence — run the check
|
|
26
|
+
## Workflow
|
|
163
27
|
|
|
164
|
-
**
|
|
165
|
-
|
|
166
|
-
|
|
167
|
-
-
|
|
168
|
-
-
|
|
28
|
+
1. **Run** `pnpm check [path] [--type type]` (timeout: 600000)
|
|
29
|
+
2. **All passed?** Report with actual output numbers → done
|
|
30
|
+
3. **Errors?** Fix in priority order: typecheck → lint → test (fixes cascade)
|
|
31
|
+
- Test failures: run `git diff` to decide — update test or fix source
|
|
32
|
+
- Stuck after 2-3 attempts → recommend `/sd-debug`
|
|
33
|
+
4. **Go to 1** — always re-run ALL checks after any fix
|
|
169
34
|
|
|
170
|
-
##
|
|
35
|
+
## Rules
|
|
171
36
|
|
|
172
|
-
|
|
173
|
-
|
|
174
|
-
|
|
175
|
-
|
|
176
|
-
| "Agents can analyze output better" | Background Bash is sufficient - analysis happens in main context |
|
|
177
|
-
| "I only fixed lint, typecheck still passes" | Always re-verify ALL - fixes can cascade |
|
|
178
|
-
| "Build is part of verification" | Build is deployment, not verification - NEVER include it |
|
|
179
|
-
| "Let me ask which path to check" | Default to full project - explicit behavior |
|
|
180
|
-
| "I'll try one more fix approach" | After 2-3 attempts → recommend /sd-debug |
|
|
181
|
-
| "Tests are independent of types" | Type fixes affect tests - always re-run ALL |
|
|
182
|
-
| "I'm confident it passes" | Confidence is not evidence — run the check |
|
|
183
|
-
| "It should work now" | "Should" = no evidence — run the check |
|
|
184
|
-
| "I already verified earlier" | Earlier is not now — re-run after every change |
|
|
37
|
+
- **Always re-run ALL checks** after any fix — never assume other checks still pass
|
|
38
|
+
- **Report with evidence** — cite actual numbers (e.g., "0 errors, 47 tests passed"), not "should work"
|
|
39
|
+
- **No build, no dev server** — typecheck + lint + test only
|
|
40
|
+
- **Run Bash directly** — no Task/agent/team overhead
|
|
@@ -1,9 +1,8 @@
|
|
|
1
|
-
import { readFileSync, existsSync
|
|
1
|
+
import { readFileSync, existsSync } from "fs";
|
|
2
2
|
import { resolve } from "path";
|
|
3
3
|
import { spawn } from "child_process";
|
|
4
4
|
|
|
5
5
|
const root = resolve(import.meta.dirname, "../../..");
|
|
6
|
-
const pathArg = process.argv[2];
|
|
7
6
|
|
|
8
7
|
// ══════════════════════════════════════════
|
|
9
8
|
// Phase 1: Environment Pre-check
|
|
@@ -20,11 +19,8 @@ if (!existsSync(pkgPath)) {
|
|
|
20
19
|
if (Number.isNaN(major) || major < 13) {
|
|
21
20
|
errors.push(`This skill requires simplysm v13+. Current: ${pkg.version}`);
|
|
22
21
|
}
|
|
23
|
-
if (!pkg.scripts?.
|
|
24
|
-
errors.push("'
|
|
25
|
-
}
|
|
26
|
-
if (!pkg.scripts?.lint) {
|
|
27
|
-
errors.push("'lint' script not defined in package.json");
|
|
22
|
+
if (!pkg.scripts?.check) {
|
|
23
|
+
errors.push("'check' script not defined in package.json");
|
|
28
24
|
}
|
|
29
25
|
}
|
|
30
26
|
|
|
@@ -44,80 +40,15 @@ if (errors.length > 0) {
|
|
|
44
40
|
process.exit(1);
|
|
45
41
|
}
|
|
46
42
|
|
|
47
|
-
|
|
48
|
-
// Phase 2: Run 3 checks in parallel
|
|
49
|
-
// ══════════════════════════════════════════
|
|
50
|
-
|
|
51
|
-
const logDir = resolve(root, ".tmp/sd-check");
|
|
52
|
-
|
|
53
|
-
function runCommand(name, cmd, args) {
|
|
54
|
-
return new Promise((res) => {
|
|
55
|
-
const child = spawn(cmd, args, { cwd: root, shell: true, stdio: "pipe" });
|
|
56
|
-
const chunks = [];
|
|
57
|
-
|
|
58
|
-
child.stdout.on("data", (d) => chunks.push(d));
|
|
59
|
-
child.stderr.on("data", (d) => chunks.push(d));
|
|
60
|
-
|
|
61
|
-
child.on("close", (code) => {
|
|
62
|
-
const output = Buffer.concat(chunks).toString("utf8");
|
|
63
|
-
res({ name, code, output });
|
|
64
|
-
});
|
|
65
|
-
|
|
66
|
-
child.on("error", (err) => {
|
|
67
|
-
res({ name, code: 1, output: err.message });
|
|
68
|
-
});
|
|
69
|
-
});
|
|
70
|
-
}
|
|
71
|
-
|
|
72
|
-
function extractTestCount(output) {
|
|
73
|
-
const match =
|
|
74
|
-
output.match(/(\d+)\s+tests?\s+passed/i) ??
|
|
75
|
-
output.match(/Tests\s+(\d+)\s+passed/i) ??
|
|
76
|
-
output.match(/(\d+)\s+pass/i);
|
|
77
|
-
return match ? match[1] : null;
|
|
78
|
-
}
|
|
79
|
-
|
|
80
|
-
const checks = [
|
|
81
|
-
{ name: "TYPECHECK", cmd: "pnpm", args: pathArg ? ["typecheck", pathArg] : ["typecheck"] },
|
|
82
|
-
{ name: "LINT", cmd: "pnpm", args: pathArg ? ["lint", "--fix", pathArg] : ["lint", "--fix"] },
|
|
83
|
-
{ name: "TEST", cmd: "pnpm", args: pathArg ? ["vitest", pathArg, "--run"] : ["vitest", "--run"] },
|
|
84
|
-
];
|
|
85
|
-
|
|
86
|
-
const results = await Promise.all(checks.map((c) => runCommand(c.name, c.cmd, c.args)));
|
|
43
|
+
console.log("ENV-CHECK OK");
|
|
87
44
|
|
|
88
45
|
// ══════════════════════════════════════════
|
|
89
|
-
//
|
|
46
|
+
// Phase 2: Delegate to pnpm check
|
|
90
47
|
// ══════════════════════════════════════════
|
|
91
48
|
|
|
92
|
-
const
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
for (const r of results) {
|
|
96
|
-
const passed = r.code === 0;
|
|
97
|
-
let label = passed ? "PASS" : "FAIL";
|
|
98
|
-
|
|
99
|
-
if (passed && r.name === "TEST") {
|
|
100
|
-
const count = extractTestCount(r.output);
|
|
101
|
-
if (count) label = `PASS (${count} tests)`;
|
|
102
|
-
}
|
|
103
|
-
|
|
104
|
-
if (passed) {
|
|
105
|
-
console.log(`\n${"=".repeat(6)} ${r.name}: ${label} ${"=".repeat(6)}`);
|
|
106
|
-
} else {
|
|
107
|
-
const logFile = resolve(logDir, `${r.name.toLowerCase()}.log`);
|
|
108
|
-
writeFileSync(logFile, r.output, "utf8");
|
|
109
|
-
console.log(`\n${"=".repeat(6)} ${r.name}: ${label} → ${logFile} ${"=".repeat(6)}`);
|
|
110
|
-
failed.push(r.name.toLowerCase());
|
|
111
|
-
}
|
|
112
|
-
}
|
|
113
|
-
|
|
114
|
-
console.log();
|
|
115
|
-
if (failed.length === 0) {
|
|
116
|
-
console.log(`${"=".repeat(6)} SUMMARY: ALL PASSED ${"=".repeat(6)}`);
|
|
117
|
-
} else {
|
|
118
|
-
console.log(
|
|
119
|
-
`${"=".repeat(6)} SUMMARY: ${failed.length}/3 FAILED (${failed.join(", ")}) ${"=".repeat(6)}`,
|
|
120
|
-
);
|
|
121
|
-
}
|
|
49
|
+
const args = ["check", ...process.argv.slice(2)];
|
|
50
|
+
const child = spawn("pnpm", args, { cwd: root, shell: true, stdio: "inherit" });
|
|
122
51
|
|
|
123
|
-
|
|
52
|
+
child.on("close", (code) => {
|
|
53
|
+
process.exit(code ?? 1);
|
|
54
|
+
});
|
|
@@ -19,10 +19,13 @@ Turn a design doc into a step-by-step implementation plan through codebase explo
|
|
|
19
19
|
- Ask questions one at a time as they arise during planning, with your recommendation
|
|
20
20
|
- Don't batch questions upfront — real questions emerge while deep in the details
|
|
21
21
|
|
|
22
|
-
**Ask about
|
|
23
|
-
-
|
|
24
|
-
-
|
|
25
|
-
-
|
|
22
|
+
**Ask about anything you're not 100% confident about.** Examples:
|
|
23
|
+
- Dependency choices (add library vs implement directly)
|
|
24
|
+
- Conflicts with existing codebase patterns
|
|
25
|
+
- Implementation choices the design didn't specify
|
|
26
|
+
- Ambiguous behavior or edge cases
|
|
27
|
+
- Migration concerns (breaking changes, compatibility)
|
|
28
|
+
- If in doubt, ask. The cost of asking is low; the cost of a wrong assumption is high.
|
|
26
29
|
|
|
27
30
|
**Don't ask — just decide:**
|
|
28
31
|
- Internal details covered by project conventions (file naming, export patterns)
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
2
|
import { execSync } from "node:child_process";
|
|
3
|
-
import { existsSync } from "node:fs";
|
|
4
|
-
import { resolve } from "node:path";
|
|
3
|
+
import { existsSync, rmSync } from "node:fs";
|
|
4
|
+
import { resolve, sep } from "node:path";
|
|
5
5
|
|
|
6
6
|
const [cmd, ...args] = process.argv.slice(2);
|
|
7
7
|
|
|
@@ -21,8 +21,8 @@ const mainWorktree = getOutput("git worktree list --porcelain")
|
|
|
21
21
|
function detectWorktreeName() {
|
|
22
22
|
const cwd = process.cwd();
|
|
23
23
|
const worktreesDir = resolve(mainWorktree, ".worktrees");
|
|
24
|
-
if (cwd.startsWith(worktreesDir +
|
|
25
|
-
return cwd.slice(worktreesDir.length + 1).split(
|
|
24
|
+
if (cwd.startsWith(worktreesDir + sep)) {
|
|
25
|
+
return cwd.slice(worktreesDir.length + 1).split(sep)[0];
|
|
26
26
|
}
|
|
27
27
|
return undefined;
|
|
28
28
|
}
|
|
@@ -118,7 +118,14 @@ switch (cmd) {
|
|
|
118
118
|
}
|
|
119
119
|
if (existsSync(worktreePath)) {
|
|
120
120
|
console.log(`Removing worktree: .worktrees/${name}`);
|
|
121
|
-
|
|
121
|
+
try {
|
|
122
|
+
run(`git worktree remove --force "${worktreePath}"`, { cwd: mainWorktree });
|
|
123
|
+
} catch {
|
|
124
|
+
// node_modules 등으로 git worktree remove 실패 시 수동 정리
|
|
125
|
+
console.log("git worktree remove failed, cleaning up manually...");
|
|
126
|
+
rmSync(worktreePath, { recursive: true, force: true });
|
|
127
|
+
run("git worktree prune", { cwd: mainWorktree });
|
|
128
|
+
}
|
|
122
129
|
}
|
|
123
130
|
console.log(`Deleting branch: ${name}`);
|
|
124
131
|
run(`git branch -d "${name}"`, { cwd: mainWorktree });
|
package/package.json
CHANGED
|
@@ -1,52 +0,0 @@
|
|
|
1
|
-
# @simplysm Package Documentation
|
|
2
|
-
|
|
3
|
-
When you need API details, usage examples, or component props for `@simplysm/*` packages,
|
|
4
|
-
read the package's README.md from node_modules.
|
|
5
|
-
|
|
6
|
-
## How to use
|
|
7
|
-
|
|
8
|
-
Read the package README directly:
|
|
9
|
-
|
|
10
|
-
```
|
|
11
|
-
node_modules/@simplysm/{package-name}/README.md
|
|
12
|
-
```
|
|
13
|
-
|
|
14
|
-
If not found (pnpm hoisting), try:
|
|
15
|
-
|
|
16
|
-
```
|
|
17
|
-
packages/*/node_modules/@simplysm/{package-name}/README.md
|
|
18
|
-
```
|
|
19
|
-
|
|
20
|
-
## When to use
|
|
21
|
-
|
|
22
|
-
**MANDATORY**: Read the relevant README BEFORE any of the following:
|
|
23
|
-
|
|
24
|
-
- Writing new code that uses `@simplysm/*` APIs
|
|
25
|
-
- Fixing type errors or bugs in code that uses `@simplysm/*` APIs
|
|
26
|
-
- Making assumptions about type mappings (e.g., DB column types → TypeScript types)
|
|
27
|
-
- Refactoring or migrating code that depends on `@simplysm/*` packages
|
|
28
|
-
|
|
29
|
-
Do NOT guess API behavior or type mappings — always verify from the README first.
|
|
30
|
-
|
|
31
|
-
## Available Packages
|
|
32
|
-
|
|
33
|
-
| Package | Description |
|
|
34
|
-
|---------|-------------|
|
|
35
|
-
| `core-common` | Common utilities, custom types (DateTime, DateOnly, Time, Uuid) |
|
|
36
|
-
| `core-browser` | Browser-specific extensions |
|
|
37
|
-
| `core-node` | Node.js utilities (filesystem, workers) |
|
|
38
|
-
| `orm-common` | ORM query builder, table schema definitions |
|
|
39
|
-
| `orm-node` | DB connectors (MySQL, MSSQL, PostgreSQL) |
|
|
40
|
-
| `service-common` | Service protocol, type definitions |
|
|
41
|
-
| `service-client` | WebSocket client |
|
|
42
|
-
| `service-server` | Fastify-based HTTP/WebSocket server |
|
|
43
|
-
| `solid` | SolidJS UI components + Tailwind CSS |
|
|
44
|
-
| `excel` | Excel (.xlsx) read/write |
|
|
45
|
-
| `storage` | FTP/SFTP client |
|
|
46
|
-
| `sd-cli` | Build, lint, typecheck CLI tool |
|
|
47
|
-
| `claude` | Claude Code skills/agents (auto-installs via postinstall) |
|
|
48
|
-
| `eslint-plugin` | Custom ESLint rules |
|
|
49
|
-
| `capacitor-plugin-auto-update` | Auto update |
|
|
50
|
-
| `capacitor-plugin-broadcast` | Broadcast |
|
|
51
|
-
| `capacitor-plugin-file-system` | File system |
|
|
52
|
-
| `capacitor-plugin-usb-storage` | USB storage |
|
|
File without changes
|
|
File without changes
|