specweave 2.2.1 ā 2.2.3
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-plugin/marketplace.json +2 -2
- package/CLAUDE.md +21 -36
- package/dist/src/cli/dispatcher.d.ts +1 -1
- package/dist/src/cli/dispatcher.js +1 -1
- package/dist/src/cli/helpers/init/instruction-file-merger.js +2 -2
- package/dist/src/cli/helpers/init/instruction-file-merger.js.map +1 -1
- package/dist/src/core/auto/completion-evaluator.d.ts +1 -1
- package/dist/src/core/auto/completion-evaluator.js +1 -1
- package/dist/src/core/fabric/security-judge.d.ts.map +1 -1
- package/dist/src/core/fabric/security-judge.js +37 -5
- package/dist/src/core/fabric/security-judge.js.map +1 -1
- package/dist/src/core/jev/browse.d.ts +2 -2
- package/dist/src/core/jev/browse.d.ts.map +1 -1
- package/dist/src/core/jev/browse.js +57 -11
- package/dist/src/core/jev/browse.js.map +1 -1
- package/dist/src/core/jev/client.d.ts.map +1 -1
- package/dist/src/core/jev/client.js +49 -20
- package/dist/src/core/jev/client.js.map +1 -1
- package/dist/src/core/jev/decide.d.ts.map +1 -1
- package/dist/src/core/jev/decide.js +12 -7
- package/dist/src/core/jev/decide.js.map +1 -1
- package/dist/src/core/llm/index.d.ts +1 -1
- package/dist/src/core/llm/index.js +1 -1
- package/dist/src/core/llm/model-capabilities.d.ts +79 -0
- package/dist/src/core/llm/model-capabilities.d.ts.map +1 -0
- package/dist/src/core/llm/model-capabilities.js +157 -0
- package/dist/src/core/llm/model-capabilities.js.map +1 -0
- package/dist/src/core/llm/provider-factory.js +1 -1
- package/dist/src/core/llm/providers/anthropic-provider.d.ts +1 -0
- package/dist/src/core/llm/providers/anthropic-provider.d.ts.map +1 -1
- package/dist/src/core/llm/providers/anthropic-provider.js +38 -11
- package/dist/src/core/llm/providers/anthropic-provider.js.map +1 -1
- package/dist/src/core/llm/providers/bedrock-provider.d.ts.map +1 -1
- package/dist/src/core/llm/providers/bedrock-provider.js +10 -5
- package/dist/src/core/llm/providers/bedrock-provider.js.map +1 -1
- package/dist/src/core/llm/providers/claude-code-provider.js +1 -1
- package/dist/src/core/llm/types.d.ts +20 -1
- package/dist/src/core/llm/types.d.ts.map +1 -1
- package/dist/src/core/llm/types.js.map +1 -1
- package/dist/src/core/session/handoff-secret-scrub.d.ts.map +1 -1
- package/dist/src/core/session/handoff-secret-scrub.js +2 -1
- package/dist/src/core/session/handoff-secret-scrub.js.map +1 -1
- package/dist/src/core/skill-gen/signal-collector.js +1 -1
- package/dist/src/core/skill-gen/signal-collector.js.map +1 -1
- package/dist/src/core/skill-gen/suggestion-engine.js +1 -1
- package/dist/src/core/skill-gen/suggestion-engine.js.map +1 -1
- package/dist/src/core/skill-gen/types.d.ts +1 -1
- package/dist/src/core/skill-gen/types.d.ts.map +1 -1
- package/dist/src/core/skill-refine/haiku-diff.d.ts +25 -2
- package/dist/src/core/skill-refine/haiku-diff.d.ts.map +1 -1
- package/dist/src/core/skill-refine/haiku-diff.js +18 -5
- package/dist/src/core/skill-refine/haiku-diff.js.map +1 -1
- package/dist/src/core/skills/skill-judge.d.ts +16 -17
- package/dist/src/core/skills/skill-judge.d.ts.map +1 -1
- package/dist/src/core/skills/skill-judge.js +39 -36
- package/dist/src/core/skills/skill-judge.js.map +1 -1
- package/dist/src/dashboard/server/data/cost-aggregator.d.ts.map +1 -1
- package/dist/src/dashboard/server/data/cost-aggregator.js +2 -0
- package/dist/src/dashboard/server/data/cost-aggregator.js.map +1 -1
- package/dist/src/utils/pricing-constants.d.ts +1 -1
- package/dist/src/utils/pricing-constants.d.ts.map +1 -1
- package/dist/src/utils/pricing-constants.js +3 -1
- package/dist/src/utils/pricing-constants.js.map +1 -1
- package/package.json +2 -2
- package/plugins/specweave/.claude-plugin/plugin.json +1 -1
- package/plugins/specweave/.lint/skill-lint.test.ts +104 -92
- package/plugins/specweave/skills/team/agents/_protocol.md +8 -52
- package/plugins/specweave/skills/team/agents/backend.md +2 -5
- package/plugins/specweave/skills/team/agents/brainstorm-advocate.md +4 -2
- package/plugins/specweave/skills/team/agents/brainstorm-critic.md +4 -2
- package/plugins/specweave/skills/team/agents/brainstorm-pragmatist.md +4 -2
- package/plugins/specweave/skills/team/agents/database.md +0 -2
- package/plugins/specweave/skills/team/agents/testing.md +0 -2
- package/dist/src/cli/helpers/init/ado-repo-cloning.d.ts +0 -32
- package/dist/src/cli/helpers/init/ado-repo-cloning.d.ts.map +0 -1
- package/dist/src/cli/helpers/init/ado-repo-cloning.js +0 -157
- package/dist/src/cli/helpers/init/ado-repo-cloning.js.map +0 -1
- package/dist/src/cli/helpers/init/api-docs-config.d.ts +0 -67
- package/dist/src/cli/helpers/init/api-docs-config.d.ts.map +0 -1
- package/dist/src/cli/helpers/init/api-docs-config.js +0 -426
- package/dist/src/cli/helpers/init/api-docs-config.js.map +0 -1
- package/dist/src/cli/helpers/init/bitbucket-repo-cloning.d.ts +0 -42
- package/dist/src/cli/helpers/init/bitbucket-repo-cloning.d.ts.map +0 -1
- package/dist/src/cli/helpers/init/bitbucket-repo-cloning.js +0 -261
- package/dist/src/cli/helpers/init/bitbucket-repo-cloning.js.map +0 -1
- package/dist/src/cli/helpers/init/brownfield-analysis.d.ts +0 -45
- package/dist/src/cli/helpers/init/brownfield-analysis.d.ts.map +0 -1
- package/dist/src/cli/helpers/init/brownfield-analysis.js +0 -431
- package/dist/src/cli/helpers/init/brownfield-analysis.js.map +0 -1
- package/dist/src/cli/helpers/init/claude-settings-lsp.d.ts +0 -55
- package/dist/src/cli/helpers/init/claude-settings-lsp.d.ts.map +0 -1
- package/dist/src/cli/helpers/init/claude-settings-lsp.js +0 -270
- package/dist/src/cli/helpers/init/claude-settings-lsp.js.map +0 -1
- package/dist/src/cli/helpers/init/multi-project-folders.d.ts +0 -15
- package/dist/src/cli/helpers/init/multi-project-folders.d.ts.map +0 -1
- package/dist/src/cli/helpers/init/multi-project-folders.js +0 -43
- package/dist/src/cli/helpers/init/multi-project-folders.js.map +0 -1
- package/dist/src/cli/helpers/init/plugin-install-flags.d.ts +0 -114
- package/dist/src/cli/helpers/init/plugin-install-flags.d.ts.map +0 -1
- package/dist/src/cli/helpers/init/plugin-install-flags.js +0 -202
- package/dist/src/cli/helpers/init/plugin-install-flags.js.map +0 -1
- package/dist/src/cli/helpers/init/prompt-flow.d.ts +0 -59
- package/dist/src/cli/helpers/init/prompt-flow.d.ts.map +0 -1
- package/dist/src/cli/helpers/init/prompt-flow.js +0 -127
- package/dist/src/cli/helpers/init/prompt-flow.js.map +0 -1
- package/dist/src/cli/helpers/init/testing-config.d.ts +0 -69
- package/dist/src/cli/helpers/init/testing-config.d.ts.map +0 -1
- package/dist/src/cli/helpers/init/testing-config.js +0 -433
- package/dist/src/cli/helpers/init/testing-config.js.map +0 -1
- package/dist/src/cli/helpers/init/umbrella-cloning.d.ts +0 -39
- package/dist/src/cli/helpers/init/umbrella-cloning.d.ts.map +0 -1
- package/dist/src/cli/helpers/init/umbrella-cloning.js +0 -121
- package/dist/src/cli/helpers/init/umbrella-cloning.js.map +0 -1
- package/plugins/specweave/.lint/skill-lint.ts +0 -51
|
@@ -1,100 +1,15 @@
|
|
|
1
1
|
/**
|
|
2
|
-
* Tests for
|
|
2
|
+
* Tests for scripts/lint-skills.mjs ā the one linter CI runs (.github/workflows/skill-lint.yml).
|
|
3
3
|
*
|
|
4
|
-
*
|
|
5
|
-
*
|
|
6
|
-
*
|
|
7
|
-
* -
|
|
4
|
+
* It keeps the shipped skill surface honest ā no `name:` frontmatter, no model/effort/context
|
|
5
|
+
* pins, short descriptions, every `specweave <cmd>` / `sw:<name>` reference resolvable ā and
|
|
6
|
+
* since 0669 it also owns the two checks that used to sit unused in `.lint/skill-lint.ts`:
|
|
7
|
+
* - retired 4.7 phrasing (ULTRATHINK, extended thinking, budget_tokens) is flagged
|
|
8
|
+
* - a SKILL.md declaring `allowed-tools` must also carry a `## Tool-Use Rationale` section
|
|
9
|
+
* (or a `tool-use-rationale:` frontmatter key)
|
|
8
10
|
*/
|
|
9
11
|
|
|
10
12
|
import { describe, it, expect } from 'vitest';
|
|
11
|
-
import { lintSkillFile } from './skill-lint.js';
|
|
12
|
-
|
|
13
|
-
describe('skill-lint tool-use-rationale enforcement', () => {
|
|
14
|
-
it('returns a lint error when SKILL.md has allowed-tools but no tool-use-rationale', async () => {
|
|
15
|
-
const content = `---
|
|
16
|
-
name: sw/test
|
|
17
|
-
allowed-tools: Read, Grep
|
|
18
|
-
---
|
|
19
|
-
|
|
20
|
-
# Test Skill
|
|
21
|
-
|
|
22
|
-
Body content without a rationale block.
|
|
23
|
-
`;
|
|
24
|
-
const result = await lintSkillFile('test/SKILL.md', content);
|
|
25
|
-
expect(result.errors.some((e) => /tool-use-rationale/i.test(e))).toBe(true);
|
|
26
|
-
});
|
|
27
|
-
|
|
28
|
-
it('returns no errors when both allowed-tools and tool-use-rationale are present', async () => {
|
|
29
|
-
const content = `---
|
|
30
|
-
name: sw/test
|
|
31
|
-
allowed-tools: Read, Grep
|
|
32
|
-
---
|
|
33
|
-
|
|
34
|
-
# Test Skill
|
|
35
|
-
|
|
36
|
-
## Tool-Use Rationale
|
|
37
|
-
|
|
38
|
-
- **Read**: Load spec.md context when AC IDs are referenced.
|
|
39
|
-
- **Grep**: Locate existing ACs to avoid duplication.
|
|
40
|
-
`;
|
|
41
|
-
const result = await lintSkillFile('test/SKILL.md', content);
|
|
42
|
-
expect(result.errors).toHaveLength(0);
|
|
43
|
-
});
|
|
44
|
-
|
|
45
|
-
it('accepts the frontmatter-style tool-use-rationale key', async () => {
|
|
46
|
-
const content = `---
|
|
47
|
-
name: sw/test
|
|
48
|
-
allowed-tools: Read, Grep
|
|
49
|
-
tool-use-rationale: |
|
|
50
|
-
Read loads context, Grep locates ACs.
|
|
51
|
-
---
|
|
52
|
-
|
|
53
|
-
# Body
|
|
54
|
-
`;
|
|
55
|
-
const result = await lintSkillFile('test/SKILL.md', content);
|
|
56
|
-
expect(result.errors).toHaveLength(0);
|
|
57
|
-
});
|
|
58
|
-
|
|
59
|
-
it('flags retired phrases regardless of rationale presence', async () => {
|
|
60
|
-
const content = `---
|
|
61
|
-
name: sw/test
|
|
62
|
-
---
|
|
63
|
-
|
|
64
|
-
ULTRATHINK BY DEFAULT ā think carefully and step-by-step.
|
|
65
|
-
`;
|
|
66
|
-
const result = await lintSkillFile('test/SKILL.md', content);
|
|
67
|
-
expect(result.errors.some((e) => /ULTRATHINK/i.test(e))).toBe(true);
|
|
68
|
-
});
|
|
69
|
-
|
|
70
|
-
it('flags thinking.budget_tokens retired phrase', async () => {
|
|
71
|
-
const content = `---
|
|
72
|
-
name: sw/test
|
|
73
|
-
---
|
|
74
|
-
|
|
75
|
-
Sets thinking.budget_tokens = 4096 during review.
|
|
76
|
-
`;
|
|
77
|
-
const result = await lintSkillFile('test/SKILL.md', content);
|
|
78
|
-
expect(result.errors.some((e) => /thinking\.budget_tokens/.test(e))).toBe(true);
|
|
79
|
-
});
|
|
80
|
-
|
|
81
|
-
it('returns no errors when a SKILL.md has no allowed-tools and no retired phrases', async () => {
|
|
82
|
-
const content = `---
|
|
83
|
-
name: sw/test
|
|
84
|
-
---
|
|
85
|
-
|
|
86
|
-
# Plain skill without tool declarations.
|
|
87
|
-
`;
|
|
88
|
-
const result = await lintSkillFile('test/SKILL.md', content);
|
|
89
|
-
expect(result.errors).toHaveLength(0);
|
|
90
|
-
});
|
|
91
|
-
});
|
|
92
|
-
|
|
93
|
-
/**
|
|
94
|
-
* Repo-surface lint (2.0): scripts/lint-skills.mjs is the guard that keeps the shipped
|
|
95
|
-
* skill surface honest ā no `name:` frontmatter, no model/effort/context pins, short
|
|
96
|
-
* descriptions, and every `specweave <cmd>` / `sw:<name>` reference resolvable.
|
|
97
|
-
*/
|
|
98
13
|
// @ts-expect-error ā zero-dep .mjs linter, no type declarations by design
|
|
99
14
|
import { lintContent, lintRepo, readRegisteredCommands, readShippedSkills } from '../../../scripts/lint-skills.mjs';
|
|
100
15
|
|
|
@@ -182,3 +97,100 @@ describe('lint-skills: shipped skill surface', () => {
|
|
|
182
97
|
expect(failures).toEqual([]);
|
|
183
98
|
});
|
|
184
99
|
});
|
|
100
|
+
|
|
101
|
+
describe('lint-skills: retired 4.7 phrasing', () => {
|
|
102
|
+
it('flags "ULTRATHINK BY DEFAULT"', () => {
|
|
103
|
+
const r = lintContent('skills/x/SKILL.md', body('description: short', '\n**ULTRATHINK BY DEFAULT** - validate.\n'), ctx);
|
|
104
|
+
expect(rules(r)).toEqual(['retired-phrase']);
|
|
105
|
+
expect(r.errors[0].message).toMatch(/ULTRATHINK BY DEFAULT/);
|
|
106
|
+
expect(r.errors[0].line).toBe(5);
|
|
107
|
+
});
|
|
108
|
+
|
|
109
|
+
it('flags a bare "Ultrathink" regardless of case', () => {
|
|
110
|
+
const r = lintContent('skills/x/SKILL.md', body('description: short', '\nUltrathink the plan first.\n'), ctx);
|
|
111
|
+
expect(r.errors[0].message).toMatch(/Retired phrase "ULTRATHINK"/);
|
|
112
|
+
});
|
|
113
|
+
|
|
114
|
+
it('reports one error, not two, when the longer phrase matches', () => {
|
|
115
|
+
const r = lintContent('skills/x/SKILL.md', body('description: short', '\nULTRATHINK BY DEFAULT\n'), ctx);
|
|
116
|
+
expect(r.errors).toHaveLength(1);
|
|
117
|
+
});
|
|
118
|
+
|
|
119
|
+
it('flags "[Extended thinking: ...]" ā the survivor a lowercase-only match missed', () => {
|
|
120
|
+
const r = lintContent(
|
|
121
|
+
'skills/x/SKILL.md',
|
|
122
|
+
body('description: short', '\n[Extended thinking: this workflow enforces test-first development.]\n'),
|
|
123
|
+
ctx,
|
|
124
|
+
);
|
|
125
|
+
expect(r.errors[0].message).toMatch(/extended thinking/);
|
|
126
|
+
});
|
|
127
|
+
|
|
128
|
+
it('flags thinking.budget_tokens and spawn-agents-anyway', () => {
|
|
129
|
+
const r = lintContent(
|
|
130
|
+
'skills/x/SKILL.md',
|
|
131
|
+
body('description: short', '\nSets thinking.budget_tokens = 4096.\nEven for small work ā spawn agents anyway.\n'),
|
|
132
|
+
ctx,
|
|
133
|
+
);
|
|
134
|
+
expect(rules(r)).toEqual(['retired-phrase', 'retired-phrase']);
|
|
135
|
+
});
|
|
136
|
+
|
|
137
|
+
it('does not flag a phrase quoted inside a fenced code block', () => {
|
|
138
|
+
const r = lintContent(
|
|
139
|
+
'skills/x/SKILL.md',
|
|
140
|
+
body('description: short', '\n```\nULTRATHINK BY DEFAULT - the old wording\n```\n'),
|
|
141
|
+
ctx,
|
|
142
|
+
);
|
|
143
|
+
expect(r.errors).toHaveLength(0);
|
|
144
|
+
});
|
|
145
|
+
|
|
146
|
+
it('does not flag a line that documents the retirement itself', () => {
|
|
147
|
+
const r = lintContent(
|
|
148
|
+
'skills/x/SKILL.md',
|
|
149
|
+
body('description: short', '\nRetired phrases: ULTRATHINK BY DEFAULT, extended thinking, budget_tokens:.\n'),
|
|
150
|
+
ctx,
|
|
151
|
+
);
|
|
152
|
+
expect(r.errors).toHaveLength(0);
|
|
153
|
+
});
|
|
154
|
+
|
|
155
|
+
it('checks non-skill files too (agents, reference, PLUGIN.md)', () => {
|
|
156
|
+
const r = lintContent('plugins/specweave/agents/x.md', 'Use extended thinking here.\n', {
|
|
157
|
+
...ctx,
|
|
158
|
+
isSkillFile: false,
|
|
159
|
+
});
|
|
160
|
+
expect(rules(r)).toEqual(['retired-phrase']);
|
|
161
|
+
});
|
|
162
|
+
});
|
|
163
|
+
|
|
164
|
+
describe('lint-skills: tool-use-rationale enforcement', () => {
|
|
165
|
+
it('returns a lint error when SKILL.md has allowed-tools but no tool-use-rationale', () => {
|
|
166
|
+
const r = lintContent('skills/x/SKILL.md', body('description: short\nallowed-tools: Read, Grep'), ctx);
|
|
167
|
+
expect(rules(r)).toEqual(['tool-use-rationale']);
|
|
168
|
+
expect(r.errors[0].line).toBe(3);
|
|
169
|
+
});
|
|
170
|
+
|
|
171
|
+
it('returns no errors when both allowed-tools and a rationale section are present', () => {
|
|
172
|
+
const r = lintContent(
|
|
173
|
+
'skills/x/SKILL.md',
|
|
174
|
+
body(
|
|
175
|
+
'description: short\nallowed-tools: Read, Grep',
|
|
176
|
+
'\n## Tool-Use Rationale\n\n- **Read**: load spec.md context.\n- **Grep**: locate existing ACs.\n',
|
|
177
|
+
),
|
|
178
|
+
ctx,
|
|
179
|
+
);
|
|
180
|
+
expect(r.errors).toHaveLength(0);
|
|
181
|
+
});
|
|
182
|
+
|
|
183
|
+
it('accepts the frontmatter-style tool-use-rationale key', () => {
|
|
184
|
+
const r = lintContent(
|
|
185
|
+
'skills/x/SKILL.md',
|
|
186
|
+
body('description: short\nallowed-tools: Read, Grep\ntool-use-rationale: Read loads context, Grep locates ACs.'),
|
|
187
|
+
ctx,
|
|
188
|
+
);
|
|
189
|
+
expect(r.errors).toHaveLength(0);
|
|
190
|
+
});
|
|
191
|
+
|
|
192
|
+
it('says nothing about rationale when the skill declares no tools', () => {
|
|
193
|
+
const r = lintContent('skills/x/SKILL.md', body('description: short'), ctx);
|
|
194
|
+
expect(r.errors).toHaveLength(0);
|
|
195
|
+
});
|
|
196
|
+
});
|
|
@@ -22,8 +22,9 @@ SendMessage({ type: "message", recipient: "team-lead",
|
|
|
22
22
|
summary: "[Domain] plan ready ā proceeding to implementation" })
|
|
23
23
|
```
|
|
24
24
|
|
|
25
|
-
**STATUS** ā
|
|
26
|
-
|
|
25
|
+
**STATUS** ā send when a task completes, and before anything that will keep you
|
|
26
|
+
silent for minutes. The lead watches the ledger (`specweave task list`), not your
|
|
27
|
+
output, so a STATUS is what tells it a silent stretch is work rather than a stall.
|
|
27
28
|
|
|
28
29
|
```
|
|
29
30
|
SendMessage({ type: "message", recipient: "team-lead",
|
|
@@ -80,53 +81,8 @@ Approve only if you have no unsaved state. Approving terminates your process.
|
|
|
80
81
|
## Rules (apply to every agent)
|
|
81
82
|
|
|
82
83
|
- Do NOT run `sw:done` or `sw:review` ā the lead closes the increment centrally
|
|
83
|
-
-
|
|
84
|
-
-
|
|
85
|
-
-
|
|
86
|
-
-
|
|
87
|
-
-
|
|
88
|
-
- Create `.specweave/increments/` in YOUR assigned repo, NOT in the umbrella project root
|
|
89
|
-
- **Workflow Mode** (below) is OPT-IN and default-off ā only borrow a `Workflow()` for a ā„~25 same-shape independent-task batch, exactly once, and only if `quality.workflows.agentBorrow.enabled` is true
|
|
90
|
-
|
|
91
|
-
## Workflow Mode (OPT-IN ā large homogeneous batch only)
|
|
92
|
-
|
|
93
|
-
You normally implement tasks sequentially. **IF AND ONLY IF** your assigned task list is a **large homogeneous batch** ā **ā„~25 tasks of the same shape with no cross-task dependencies** (e.g. apply the same rename/migration/edit to N files, port N similar tests, audit N modules) ā you MAY call `Workflow()` **EXACTLY ONCE** to fan them out.
|
|
94
|
-
|
|
95
|
-
**Gate (ALL must hold, else implement sequentially):**
|
|
96
|
-
- `quality.workflows.enabled === true` AND `quality.workflows.agentBorrow.enabled === true` in `.specweave/config.json` (both default **off** ā if absent/false, do NOT use Workflow).
|
|
97
|
-
- ā„~25 same-shape, independent tasks (`quality.workflows.batchShapeThreshold`, default 25).
|
|
98
|
-
- Projected concurrency ⤠`quality.workflows.maxSubagentsPerWorkflow` (ā¤16) and projected tokens ⤠`quality.workflows.perRunTokenBudget`.
|
|
99
|
-
|
|
100
|
-
**Nesting law (HARD):** You were spawned by team-lead via the `Task` tool, so you ARE allowed ONE `Workflow()` call. The subagents your Workflow spawns are **leaves** ā they CANNOT call `Workflow()` (it throws). One borrow, one level down. Never nest.
|
|
101
|
-
|
|
102
|
-
**Heartbeat-before-Workflow (MANDATORY ā prevents false-kill):** A background Workflow makes you silent for minutes. BEFORE the call, emit a STATUS that declares the delegation so team-lead extends its stuck-detection window (see SKILL.md §8b Workflow-Aware Stuck Detection):
|
|
103
|
-
|
|
104
|
-
```
|
|
105
|
-
SendMessage({ type: "message", recipient: "team-lead",
|
|
106
|
-
content: "STATUS: T-{N}/{total} ā DELEGATING {batchCount} tasks to background Workflow (workflow_id={id}). Expect silence until WORKFLOW_DONE.",
|
|
107
|
-
summary: "[Domain] entering Workflow Mode ā {batchCount} tasks" })
|
|
108
|
-
```
|
|
109
|
-
On completion emit `STATUS: WORKFLOW_DONE ā {done}/{batchCount} ok, {failed} failed. Resuming T-{M}.` then resume normal heartbeats.
|
|
110
|
-
|
|
111
|
-
**Template** (one call; results stay in script vars, NOT your context). Inject SpecWeave context (spec/AC refs, file paths) into every agent prompt ā Workflow is domain-blind:
|
|
112
|
-
|
|
113
|
-
```js
|
|
114
|
-
export const meta = {
|
|
115
|
-
name: "batch-fanout",
|
|
116
|
-
description: "Fan out a homogeneous batch of same-shape tasks",
|
|
117
|
-
phases: [{ title: "batch" }],
|
|
118
|
-
};
|
|
119
|
-
const items = [/* the >=25 same-shape task descriptors: { target, acRef, file } */];
|
|
120
|
-
const results = await parallel(
|
|
121
|
-
items.map((it) => () => agent(
|
|
122
|
-
`Apply <the same transform> to ${it.target}. Spec: ${it.acRef}. Write ONLY ${it.file}.`,
|
|
123
|
-
{ label: it.target, phase: "batch", isolation: "worktree" }
|
|
124
|
-
))
|
|
125
|
-
);
|
|
126
|
-
log(`batch complete: ${results.filter(Boolean).length}/${items.length}`);
|
|
127
|
-
return results;
|
|
128
|
-
```
|
|
129
|
-
|
|
130
|
-
**Budget guard:** Keep projected tokens under `quality.workflows.perRunTokenBudget`. If your batch would exceed it, split into fewer items or fall back to sequential ā do NOT raise the cap yourself.
|
|
131
|
-
|
|
132
|
-
**If the gate fails for any reason ā implement the tasks sequentially as usual.** Workflow Mode is an optimization, never a requirement.
|
|
84
|
+
- Write only to your assigned file patterns (listed in the domain template below)
|
|
85
|
+
- Read any file for context
|
|
86
|
+
- Do not wait for a team-lead response to PLAN_READY ā proceed immediately
|
|
87
|
+
- All repository operations use the `repositories/{ORG}/` directory structure
|
|
88
|
+
- Create `.specweave/increments/` in your assigned repo, not in the umbrella project root
|
|
@@ -27,13 +27,10 @@ WORKFLOW:
|
|
|
27
27
|
6. Create plan.md and tasks.md
|
|
28
28
|
7. Send PLAN_READY (shared protocol) ā do NOT wait for approval
|
|
29
29
|
8. Deliverables: API endpoints, services, middleware, OpenAPI spec
|
|
30
|
-
9.
|
|
31
|
-
10.
|
|
32
|
-
11. Send COMPLETION with backend-specific fields
|
|
30
|
+
9. `npm test` ā do NOT signal COMPLETION until green
|
|
31
|
+
10. Send COMPLETION with backend-specific fields
|
|
33
32
|
|
|
34
33
|
DOMAIN RULES:
|
|
35
34
|
- Every new API endpoint needs request/response validation
|
|
36
35
|
- Error handling follows project conventions
|
|
37
36
|
- All services must have unit tests
|
|
38
|
-
- Workflow Mode: for >=~25 independent same-shape endpoints/DTOs,
|
|
39
|
-
you MAY borrow a Workflow() ONCE (see _protocol.md; gated on quality.workflows.agentBorrow.enabled)
|
|
@@ -40,8 +40,10 @@ YOUR ANALYSIS MUST INCLUDE:
|
|
|
40
40
|
### Migration Path
|
|
41
41
|
If this requires changing existing code, outline the migration strategy.
|
|
42
42
|
|
|
43
|
-
PROGRESS UPDATES
|
|
44
|
-
|
|
43
|
+
PROGRESS UPDATES:
|
|
44
|
+
Your plain text output is not visible to team-lead, so send a heartbeat as you
|
|
45
|
+
finish each APPROACH step ā a silent stretch is otherwise indistinguishable
|
|
46
|
+
from a stalled agent:
|
|
45
47
|
SendMessage({
|
|
46
48
|
to: "team-lead",
|
|
47
49
|
message: "STATUS: [Step N/4] [what you just finished]. Proceeding to [next step].",
|
|
@@ -49,8 +49,10 @@ YOUR ANALYSIS MUST INCLUDE:
|
|
|
49
49
|
### Red Lines
|
|
50
50
|
Absolute dealbreakers ā conditions under which an approach should be rejected outright.
|
|
51
51
|
|
|
52
|
-
PROGRESS UPDATES
|
|
53
|
-
|
|
52
|
+
PROGRESS UPDATES:
|
|
53
|
+
Your plain text output is not visible to team-lead, so send a heartbeat as you
|
|
54
|
+
finish each APPROACH step ā a silent stretch is otherwise indistinguishable
|
|
55
|
+
from a stalled agent:
|
|
54
56
|
SendMessage({
|
|
55
57
|
to: "team-lead",
|
|
56
58
|
message: "STATUS: [Step N/4] [what you just finished]. Proceeding to [next step].",
|
|
@@ -57,8 +57,10 @@ YOUR ANALYSIS MUST INCLUDE:
|
|
|
57
57
|
Features or aspects that seem important but aren't worth the effort right now.
|
|
58
58
|
YAGNI candidates.
|
|
59
59
|
|
|
60
|
-
PROGRESS UPDATES
|
|
61
|
-
|
|
60
|
+
PROGRESS UPDATES:
|
|
61
|
+
Your plain text output is not visible to team-lead, so send a heartbeat as you
|
|
62
|
+
finish each APPROACH step ā a silent stretch is otherwise indistinguishable
|
|
63
|
+
from a stalled agent:
|
|
62
64
|
SendMessage({
|
|
63
65
|
to: "team-lead",
|
|
64
66
|
message: "STATUS: [Step N/4] [what you just finished]. Proceeding to [next step].",
|
|
@@ -30,5 +30,3 @@ DOMAIN RULES:
|
|
|
30
30
|
- Always create migrations (never modify schema without a migration)
|
|
31
31
|
- Seed data must be idempotent
|
|
32
32
|
- Schema changes should be backward-compatible when possible
|
|
33
|
-
- Workflow Mode: for a bulk migration touching >=~25 independent tables/files,
|
|
34
|
-
you MAY borrow a Workflow() ONCE (see _protocol.md; gated on quality.workflows.agentBorrow.enabled)
|
|
@@ -33,5 +33,3 @@ DOMAIN RULES:
|
|
|
33
33
|
- Tests must cover all ACs from spec.md
|
|
34
34
|
- Follow existing test patterns and utilities
|
|
35
35
|
- E2E tests include a11y checks when applicable
|
|
36
|
-
- Workflow Mode: if you must generate/port >=~25 independent same-shape test files,
|
|
37
|
-
you MAY borrow a Workflow() ONCE (see _protocol.md; gated on quality.workflows.agentBorrow.enabled)
|
|
@@ -1,32 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* ADO Repository Cloning
|
|
3
|
-
*
|
|
4
|
-
* Handles fetching and cloning Azure DevOps repositories during init.
|
|
5
|
-
* Cloning runs in background (non-blocking) via job manager.
|
|
6
|
-
*
|
|
7
|
-
* @module cli/helpers/init/ado-repo-cloning
|
|
8
|
-
*/
|
|
9
|
-
import { type ClonePatternResult } from '../selection-strategy.js';
|
|
10
|
-
/**
|
|
11
|
-
* ADO project selection (from repository-setup.ts)
|
|
12
|
-
*/
|
|
13
|
-
export interface AdoProjectSelection {
|
|
14
|
-
org: string;
|
|
15
|
-
pat: string;
|
|
16
|
-
projects: string[];
|
|
17
|
-
}
|
|
18
|
-
/**
|
|
19
|
-
* Trigger ADO repository cloning during init
|
|
20
|
-
*
|
|
21
|
-
* This function:
|
|
22
|
-
* 1. Fetches repository list from each selected ADO project
|
|
23
|
-
* 2. Filters repositories by clone pattern (glob/regex)
|
|
24
|
-
* 3. Creates a background job for cloning
|
|
25
|
-
* 4. Starts cloning asynchronously (non-blocking)
|
|
26
|
-
*
|
|
27
|
-
* @param projectPath - Target directory for cloning
|
|
28
|
-
* @param adoProjectSelection - ADO org, PAT, and selected projects
|
|
29
|
-
* @param clonePattern - Clone pattern configuration
|
|
30
|
-
*/
|
|
31
|
-
export declare function triggerAdoRepoCloning(projectPath: string, adoProjectSelection: AdoProjectSelection, clonePattern: ClonePatternResult): Promise<string | undefined>;
|
|
32
|
-
//# sourceMappingURL=ado-repo-cloning.d.ts.map
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"ado-repo-cloning.d.ts","sourceRoot":"","sources":["../../../../../src/cli/helpers/init/ado-repo-cloning.ts"],"names":[],"mappings":"AAAA;;;;;;;GAOG;AAIH,OAAO,EAA+B,KAAK,kBAAkB,EAAE,MAAM,0BAA0B,CAAC;AAGhG;;GAEG;AACH,MAAM,WAAW,mBAAmB;IAClC,GAAG,EAAE,MAAM,CAAC;IACZ,GAAG,EAAE,MAAM,CAAC;IACZ,QAAQ,EAAE,MAAM,EAAE,CAAC;CACpB;AAuDD;;;;;;;;;;;;GAYG;AACH,wBAAsB,qBAAqB,CACzC,WAAW,EAAE,MAAM,EACnB,mBAAmB,EAAE,mBAAmB,EACxC,YAAY,EAAE,kBAAkB,GAC/B,OAAO,CAAC,MAAM,GAAG,SAAS,CAAC,CA0G7B"}
|
|
@@ -1,157 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* ADO Repository Cloning
|
|
3
|
-
*
|
|
4
|
-
* Handles fetching and cloning Azure DevOps repositories during init.
|
|
5
|
-
* Cloning runs in background (non-blocking) via job manager.
|
|
6
|
-
*
|
|
7
|
-
* @module cli/helpers/init/ado-repo-cloning
|
|
8
|
-
*/
|
|
9
|
-
import chalk from 'chalk';
|
|
10
|
-
import { AzureDevOpsProvider } from '../../../core/repo-structure/providers/azure-devops-provider.js';
|
|
11
|
-
import { filterRepositoriesByPattern } from '../selection-strategy.js';
|
|
12
|
-
import { launchCloneJob } from '../../../core/background/job-launcher.js';
|
|
13
|
-
/**
|
|
14
|
-
* Sanitize ADO project name for use as filesystem folder name
|
|
15
|
-
*
|
|
16
|
-
* ADO project names can contain:
|
|
17
|
-
* - Spaces: "My Enterprise Project"
|
|
18
|
-
* - Special characters that are invalid in paths
|
|
19
|
-
*
|
|
20
|
-
* This function creates a filesystem-safe folder name while preserving readability.
|
|
21
|
-
*/
|
|
22
|
-
function sanitizeProjectNameForPath(projectName) {
|
|
23
|
-
return projectName
|
|
24
|
-
.toLowerCase()
|
|
25
|
-
.replace(/\s+/g, '-') // Spaces ā hyphens
|
|
26
|
-
.replace(/[<>:"|?*\\\/]/g, '') // Remove filesystem-invalid chars
|
|
27
|
-
.replace(/&/g, '-and-') // & ā -and-
|
|
28
|
-
.replace(/-+/g, '-') // Collapse multiple hyphens
|
|
29
|
-
.replace(/^-|-$/g, ''); // Trim leading/trailing hyphens
|
|
30
|
-
}
|
|
31
|
-
/**
|
|
32
|
-
* Build proper ADO clone URL with PAT authentication
|
|
33
|
-
*
|
|
34
|
-
* ADO clone URL format: https://{PAT}@dev.azure.com/{org}/{project}/_git/{repo}
|
|
35
|
-
*
|
|
36
|
-
* The remoteUrl from ADO API may come in different formats:
|
|
37
|
-
* - https://dev.azure.com/org/project/_git/repo
|
|
38
|
-
* - https://org@dev.azure.com/org/project/_git/repo (with org as placeholder)
|
|
39
|
-
*
|
|
40
|
-
* We need to construct a proper URL with PAT authentication.
|
|
41
|
-
* IMPORTANT: URL-encode org, project, and repo names to handle spaces and special characters.
|
|
42
|
-
*/
|
|
43
|
-
function buildAdoCloneUrl(org, project, repoName, pat) {
|
|
44
|
-
// Build clean URL with PAT authentication
|
|
45
|
-
// Format: https://{PAT}@dev.azure.com/{org}/{project}/_git/{repo}
|
|
46
|
-
// URL-encode path segments to handle spaces (e.g., "My Enterprise Project")
|
|
47
|
-
const encodedOrg = encodeURIComponent(org);
|
|
48
|
-
const encodedProject = encodeURIComponent(project);
|
|
49
|
-
const encodedRepo = encodeURIComponent(repoName);
|
|
50
|
-
return `https://${pat}@dev.azure.com/${encodedOrg}/${encodedProject}/_git/${encodedRepo}`;
|
|
51
|
-
}
|
|
52
|
-
/**
|
|
53
|
-
* Trigger ADO repository cloning during init
|
|
54
|
-
*
|
|
55
|
-
* This function:
|
|
56
|
-
* 1. Fetches repository list from each selected ADO project
|
|
57
|
-
* 2. Filters repositories by clone pattern (glob/regex)
|
|
58
|
-
* 3. Creates a background job for cloning
|
|
59
|
-
* 4. Starts cloning asynchronously (non-blocking)
|
|
60
|
-
*
|
|
61
|
-
* @param projectPath - Target directory for cloning
|
|
62
|
-
* @param adoProjectSelection - ADO org, PAT, and selected projects
|
|
63
|
-
* @param clonePattern - Clone pattern configuration
|
|
64
|
-
*/
|
|
65
|
-
export async function triggerAdoRepoCloning(projectPath, adoProjectSelection, clonePattern) {
|
|
66
|
-
// Skip if user chose to skip cloning
|
|
67
|
-
if (clonePattern.strategy === 'skip') {
|
|
68
|
-
console.log(chalk.gray('\n Skipping repository cloning (can configure later with sw:ado-clone-repos)\n'));
|
|
69
|
-
return undefined;
|
|
70
|
-
}
|
|
71
|
-
const { org, pat, projects } = adoProjectSelection;
|
|
72
|
-
if (!projects || projects.length === 0) {
|
|
73
|
-
console.log(chalk.yellow('\n No ADO projects selected for cloning.\n'));
|
|
74
|
-
return;
|
|
75
|
-
}
|
|
76
|
-
if (!pat) {
|
|
77
|
-
console.log(chalk.yellow('\n No PAT provided. Cannot clone repositories.\n'));
|
|
78
|
-
return;
|
|
79
|
-
}
|
|
80
|
-
console.log(chalk.blue('\nš¦ Fetching ADO Repositories\n'));
|
|
81
|
-
const provider = new AzureDevOpsProvider();
|
|
82
|
-
const allRepos = [];
|
|
83
|
-
// Fetch repositories from each selected project
|
|
84
|
-
for (const project of projects) {
|
|
85
|
-
try {
|
|
86
|
-
console.log(chalk.gray(` Fetching from ${org}/${project}...`));
|
|
87
|
-
const repos = await provider.listRepositories(org, project, pat);
|
|
88
|
-
const reposWithProject = repos.map(r => ({ ...r, project }));
|
|
89
|
-
allRepos.push(...reposWithProject);
|
|
90
|
-
console.log(chalk.green(` ā Found ${repos.length} repositories in ${project}`));
|
|
91
|
-
}
|
|
92
|
-
catch (error) {
|
|
93
|
-
const errorMsg = error instanceof Error ? error.message : String(error);
|
|
94
|
-
console.log(chalk.yellow(` ā ļø Failed to fetch from ${project}: ${errorMsg}`));
|
|
95
|
-
}
|
|
96
|
-
}
|
|
97
|
-
if (allRepos.length === 0) {
|
|
98
|
-
console.log(chalk.yellow('\n No repositories found in selected projects.\n'));
|
|
99
|
-
return;
|
|
100
|
-
}
|
|
101
|
-
// Filter by pattern
|
|
102
|
-
const filteredRepos = filterRepositoriesByPattern(allRepos, clonePattern);
|
|
103
|
-
if (filteredRepos.length === 0) {
|
|
104
|
-
const patternDesc = clonePattern.pattern ? ` matching "${clonePattern.pattern}"` : '';
|
|
105
|
-
console.log(chalk.yellow(`\n No repositories${patternDesc} to clone.\n`));
|
|
106
|
-
return;
|
|
107
|
-
}
|
|
108
|
-
// Group repos by project for display
|
|
109
|
-
const projectGroups = new Map();
|
|
110
|
-
for (const repo of filteredRepos) {
|
|
111
|
-
const group = projectGroups.get(repo.project) || [];
|
|
112
|
-
group.push(repo);
|
|
113
|
-
projectGroups.set(repo.project, group);
|
|
114
|
-
}
|
|
115
|
-
console.log(chalk.blue(`\nš Starting background clone for ${filteredRepos.length} repositories...\n`));
|
|
116
|
-
// Show project structure
|
|
117
|
-
for (const [project, repos] of projectGroups) {
|
|
118
|
-
const sanitizedName = sanitizeProjectNameForPath(project);
|
|
119
|
-
console.log(chalk.gray(` š ${sanitizedName}/ (${repos.length} repos from "${project}")`));
|
|
120
|
-
}
|
|
121
|
-
console.log('');
|
|
122
|
-
// Prepare repositories with clone URLs (organized by org folder)
|
|
123
|
-
// v1.0.21: Clone into repositories/{org}/repo-name/ structure
|
|
124
|
-
// This keeps all cloned repos organized and separate from the main project
|
|
125
|
-
// NOTE: ADO org replaces the old project-based structure for consistency across providers
|
|
126
|
-
const reposWithUrls = filteredRepos.map(r => {
|
|
127
|
-
return {
|
|
128
|
-
owner: `${org}/${r.project}`,
|
|
129
|
-
name: r.name,
|
|
130
|
-
path: `repositories/${org}/${r.name}`, // Clone into repositories/{org}/{repo}
|
|
131
|
-
cloneUrl: buildAdoCloneUrl(org, r.project, r.name, pat)
|
|
132
|
-
};
|
|
133
|
-
});
|
|
134
|
-
// Launch background clone job (truly async - spawns detached process)
|
|
135
|
-
const result = await launchCloneJob({
|
|
136
|
-
projectPath,
|
|
137
|
-
repositories: reposWithUrls
|
|
138
|
-
});
|
|
139
|
-
// Show progress info (skip if all repos were already cloned)
|
|
140
|
-
if (!result.skippedPreFlight) {
|
|
141
|
-
console.log(chalk.gray(` Repositories will be cloned to: ${projectPath}/repositories/${org}/`));
|
|
142
|
-
console.log(chalk.gray(` Job ID: ${result.job.id}`));
|
|
143
|
-
if (result.isBackground) {
|
|
144
|
-
console.log(chalk.green(` ā Clone job started in background (PID: ${result.pid})`));
|
|
145
|
-
console.log(chalk.cyan('\n Check progress: sw:jobs'));
|
|
146
|
-
console.log(chalk.cyan(` Kill if needed: sw:jobs --kill ${result.job.id}`));
|
|
147
|
-
console.log(chalk.gray('\n Init will continue - cloning runs independently.\n'));
|
|
148
|
-
}
|
|
149
|
-
else {
|
|
150
|
-
console.log(chalk.yellow(' ā ļø Running in foreground (clone worker not found)'));
|
|
151
|
-
console.log(chalk.gray(' Init will block until cloning completes.\n'));
|
|
152
|
-
}
|
|
153
|
-
}
|
|
154
|
-
// Return job ID for dependency tracking
|
|
155
|
-
return result.job.id;
|
|
156
|
-
}
|
|
157
|
-
//# sourceMappingURL=ado-repo-cloning.js.map
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"ado-repo-cloning.js","sourceRoot":"","sources":["../../../../../src/cli/helpers/init/ado-repo-cloning.ts"],"names":[],"mappings":"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"}
|
|
@@ -1,67 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* API Documentation configuration prompts
|
|
3
|
-
* Handles OpenAPI and Postman collection settings for API projects
|
|
4
|
-
*
|
|
5
|
-
* @module api-docs-config
|
|
6
|
-
* @since v1.0.58
|
|
7
|
-
*/
|
|
8
|
-
import type { SupportedLanguage } from '../../../core/i18n/types.js';
|
|
9
|
-
import { WIZARD_BACK } from './wizard-navigation.js';
|
|
10
|
-
/**
|
|
11
|
-
* API Documentation configuration
|
|
12
|
-
*/
|
|
13
|
-
export interface ApiDocsConfig {
|
|
14
|
-
/** Enable API documentation features */
|
|
15
|
-
enabled: boolean;
|
|
16
|
-
/** OpenAPI spec location */
|
|
17
|
-
openApiPath: string;
|
|
18
|
-
/** Auto-generate OpenAPI from code decorators */
|
|
19
|
-
autoGenerateOpenApi: boolean;
|
|
20
|
-
/** Generate Postman collection from OpenAPI */
|
|
21
|
-
generatePostman: boolean;
|
|
22
|
-
/** Postman collection output path */
|
|
23
|
-
postmanPath: string;
|
|
24
|
-
/** When to regenerate API docs */
|
|
25
|
-
generateOn: 'on-increment-done' | 'on-api-change' | 'manual';
|
|
26
|
-
/** API file patterns to watch */
|
|
27
|
-
watchPatterns: string[];
|
|
28
|
-
/** Base URL for the API */
|
|
29
|
-
baseUrl: string;
|
|
30
|
-
}
|
|
31
|
-
/**
|
|
32
|
-
* Detected API framework
|
|
33
|
-
*/
|
|
34
|
-
export interface DetectedApiFramework {
|
|
35
|
-
name: string;
|
|
36
|
-
openApiSupport: 'built-in' | 'plugin' | 'manual';
|
|
37
|
-
setupInstructions: string;
|
|
38
|
-
}
|
|
39
|
-
/**
|
|
40
|
-
* Detect API framework from project files
|
|
41
|
-
*/
|
|
42
|
-
export declare function detectApiFramework(targetDir: string): DetectedApiFramework | null;
|
|
43
|
-
/**
|
|
44
|
-
* Result of API docs configuration
|
|
45
|
-
*/
|
|
46
|
-
export interface ApiDocsConfigResult {
|
|
47
|
-
config: ApiDocsConfig | null;
|
|
48
|
-
/** Signal to go back to previous step */
|
|
49
|
-
goBack?: typeof WIZARD_BACK;
|
|
50
|
-
}
|
|
51
|
-
/**
|
|
52
|
-
* Prompt user for API documentation configuration
|
|
53
|
-
*
|
|
54
|
-
* @param targetDir - Project directory
|
|
55
|
-
* @param language - Language for translations
|
|
56
|
-
* @returns API docs configuration or null if skipped
|
|
57
|
-
*/
|
|
58
|
-
export declare function promptApiDocsConfig(targetDir: string, language?: SupportedLanguage): Promise<ApiDocsConfigResult>;
|
|
59
|
-
/**
|
|
60
|
-
* Update config.json with API docs configuration
|
|
61
|
-
*
|
|
62
|
-
* @param targetDir - Project directory
|
|
63
|
-
* @param config - API docs configuration
|
|
64
|
-
* @param language - Language for translations
|
|
65
|
-
*/
|
|
66
|
-
export declare function updateConfigWithApiDocs(targetDir: string, config: ApiDocsConfig, language?: SupportedLanguage): void;
|
|
67
|
-
//# sourceMappingURL=api-docs-config.d.ts.map
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"api-docs-config.d.ts","sourceRoot":"","sources":["../../../../../src/cli/helpers/init/api-docs-config.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AAMH,OAAO,KAAK,EAAE,iBAAiB,EAAE,MAAM,6BAA6B,CAAC;AACrE,OAAO,EAAE,WAAW,EAAyC,MAAM,wBAAwB,CAAC;AAE5F;;GAEG;AACH,MAAM,WAAW,aAAa;IAC5B,wCAAwC;IACxC,OAAO,EAAE,OAAO,CAAC;IAEjB,4BAA4B;IAC5B,WAAW,EAAE,MAAM,CAAC;IAEpB,iDAAiD;IACjD,mBAAmB,EAAE,OAAO,CAAC;IAE7B,+CAA+C;IAC/C,eAAe,EAAE,OAAO,CAAC;IAEzB,qCAAqC;IACrC,WAAW,EAAE,MAAM,CAAC;IAEpB,kCAAkC;IAClC,UAAU,EAAE,mBAAmB,GAAG,eAAe,GAAG,QAAQ,CAAC;IAE7D,iCAAiC;IACjC,aAAa,EAAE,MAAM,EAAE,CAAC;IAExB,2BAA2B;IAC3B,OAAO,EAAE,MAAM,CAAC;CACjB;AAED;;GAEG;AACH,MAAM,WAAW,oBAAoB;IACnC,IAAI,EAAE,MAAM,CAAC;IACb,cAAc,EAAE,UAAU,GAAG,QAAQ,GAAG,QAAQ,CAAC;IACjD,iBAAiB,EAAE,MAAM,CAAC;CAC3B;AA0KD;;GAEG;AACH,wBAAgB,kBAAkB,CAAC,SAAS,EAAE,MAAM,GAAG,oBAAoB,GAAG,IAAI,CAyIjF;AAED;;GAEG;AACH,MAAM,WAAW,mBAAmB;IAClC,MAAM,EAAE,aAAa,GAAG,IAAI,CAAC;IAC7B,yCAAyC;IACzC,MAAM,CAAC,EAAE,OAAO,WAAW,CAAC;CAC7B;AAED;;;;;;GAMG;AACH,wBAAsB,mBAAmB,CACvC,SAAS,EAAE,MAAM,EACjB,QAAQ,GAAE,iBAAwB,GACjC,OAAO,CAAC,mBAAmB,CAAC,CA2G9B;AAED;;;;;;GAMG;AACH,wBAAgB,uBAAuB,CACrC,SAAS,EAAE,MAAM,EACjB,MAAM,EAAE,aAAa,EACrB,QAAQ,GAAE,iBAAwB,GACjC,IAAI,CAWN"}
|