specpulse 1.0.5__py3-none-any.whl → 1.1.0__py3-none-any.whl

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.
Files changed (43) hide show
  1. specpulse/__init__.py +1 -1
  2. specpulse/cli/main.py +60 -93
  3. specpulse/core/specpulse.py +1110 -1099
  4. specpulse/resources/commands/claude/sp-continue.md +203 -0
  5. specpulse/resources/commands/claude/{plan.md → sp-plan.md} +53 -38
  6. specpulse/resources/commands/claude/sp-pulse.md +142 -0
  7. specpulse/resources/commands/claude/{spec.md → sp-spec.md} +36 -23
  8. specpulse/resources/commands/claude/sp-status.md +170 -0
  9. specpulse/resources/commands/claude/{task.md → sp-task.md} +68 -48
  10. specpulse/resources/commands/gemini/sp-continue.toml +56 -0
  11. specpulse/resources/commands/gemini/sp-plan.toml +68 -0
  12. specpulse/resources/commands/gemini/{pulse.toml → sp-pulse.toml} +12 -6
  13. specpulse/resources/commands/gemini/sp-spec.toml +54 -0
  14. specpulse/resources/commands/gemini/sp-status.toml +61 -0
  15. specpulse/resources/commands/gemini/sp-task.toml +79 -0
  16. specpulse/resources/memory/constitution.md +5 -5
  17. specpulse/resources/memory/context.md +12 -1
  18. specpulse/resources/scripts/{pulse-init.py → sp-pulse-init.py} +6 -6
  19. specpulse/resources/scripts/{pulse-init.sh → sp-pulse-init.sh} +95 -95
  20. specpulse/resources/scripts/{pulse-plan.py → sp-pulse-plan.py} +32 -7
  21. specpulse/resources/scripts/{pulse-plan.sh → sp-pulse-plan.sh} +136 -126
  22. specpulse/resources/scripts/{pulse-spec.py → sp-pulse-spec.py} +26 -6
  23. specpulse/resources/scripts/{pulse-spec.sh → sp-pulse-spec.sh} +126 -103
  24. specpulse/resources/scripts/{pulse-task.py → sp-pulse-task.py} +42 -6
  25. specpulse/resources/scripts/{pulse-task.sh → sp-pulse-task.sh} +32 -16
  26. specpulse/resources/templates/plan.md +206 -206
  27. specpulse/resources/templates/spec.md +125 -125
  28. specpulse/resources/templates/task.md +164 -163
  29. {specpulse-1.0.5.dist-info → specpulse-1.1.0.dist-info}/METADATA +36 -45
  30. specpulse-1.1.0.dist-info/RECORD +41 -0
  31. specpulse/resources/commands/claude/pulse.md +0 -91
  32. specpulse/resources/commands/gemini/plan.toml +0 -59
  33. specpulse/resources/commands/gemini/spec.toml +0 -45
  34. specpulse/resources/commands/gemini/task.toml +0 -69
  35. specpulse/resources/scripts/pulse-init.ps1 +0 -186
  36. specpulse/resources/scripts/pulse-plan.ps1 +0 -251
  37. specpulse/resources/scripts/pulse-spec.ps1 +0 -185
  38. specpulse/resources/scripts/pulse-task.ps1 +0 -263
  39. specpulse-1.0.5.dist-info/RECORD +0 -41
  40. {specpulse-1.0.5.dist-info → specpulse-1.1.0.dist-info}/WHEEL +0 -0
  41. {specpulse-1.0.5.dist-info → specpulse-1.1.0.dist-info}/entry_points.txt +0 -0
  42. {specpulse-1.0.5.dist-info → specpulse-1.1.0.dist-info}/licenses/LICENSE +0 -0
  43. {specpulse-1.0.5.dist-info → specpulse-1.1.0.dist-info}/top_level.txt +0 -0
@@ -1,1100 +1,1111 @@
1
- """
2
- SpecPulse Core Implementation
3
- """
4
-
5
- from pathlib import Path
6
- from datetime import datetime
7
- from typing import Dict, List, Optional
8
- import yaml
9
- import json
10
- import os
11
-
12
-
13
-
14
- class SpecPulse:
15
- """Core SpecPulse functionality"""
16
-
17
- def __init__(self, project_path: Optional[Path] = None):
18
- self.project_path = project_path or Path.cwd()
19
- self.config = self._load_config()
20
- # Get resource directory path
21
- self.resources_dir = Path(__file__).parent.parent / "resources"
22
-
23
- def _load_config(self) -> Dict:
24
- """Load project configuration"""
25
- config_path = self.project_path / ".specpulse" / "config.yaml"
26
- if config_path.exists():
27
- with open(config_path, 'r') as f:
28
- return yaml.safe_load(f)
29
- return {}
30
-
31
- def get_spec_template(self) -> str:
32
- """Get specification template from file"""
33
- template_path = self.resources_dir / "templates" / "spec.md"
34
- if template_path.exists():
35
- with open(template_path, 'r', encoding='utf-8') as f:
36
- return f.read()
37
- # Fallback to embedded template if file not found
38
- return """<!-- SpecPulse Specification Template v1.0 -->
39
- <!-- AI Instructions: Fill this template based on user description -->
40
-
41
- # Specification: [FEATURE_NAME]
42
-
43
- ## Metadata
44
- - **ID**: SPEC-[XXX]
45
- - **Created**: [DATE]
46
- - **Author**: [USER]
47
- - **AI Assistant**: [CLAUDE|GEMINI]
48
- - **Version**: 1.0.0
49
-
50
- ## Executive Summary
51
- [One paragraph description of what this feature does and why it's needed]
52
-
53
- ## Problem Statement
54
- [Detailed description of the problem being solved]
55
-
56
- ## Proposed Solution
57
- [High-level approach to solving the problem]
58
-
59
- ## Detailed Requirements
60
-
61
- ### Functional Requirements
62
- <!-- AI: Generate numbered list of specific, testable requirements -->
63
-
64
- FR-001: [Requirement]
65
- - Acceptance: [How to verify this requirement is met]
66
- - Priority: [MUST|SHOULD|COULD]
67
-
68
- ### Non-Functional Requirements
69
-
70
- #### Performance
71
- - Response Time: [Target]
72
- - Throughput: [Target]
73
- - Resource Usage: [Limits]
74
-
75
- #### Security
76
- - Authentication: [Method]
77
- - Authorization: [Model]
78
- - Data Protection: [Requirements]
79
-
80
- #### Scalability
81
- - User Load: [Target]
82
- - Data Volume: [Target]
83
- - Geographic Distribution: [Requirements]
84
-
85
- ## User Stories
86
-
87
- <!-- AI: Generate user stories in standard format -->
88
-
89
- ### Story 1: [Title]
90
- **As a** [user type]
91
- **I want** [action/feature]
92
- **So that** [benefit/value]
93
-
94
- **Acceptance Criteria:**
95
- - [ ] [Criterion 1]
96
- - [ ] [Criterion 2]
97
- - [ ] [Criterion 3]
98
-
99
- ## Technical Constraints
100
- <!-- List any technical limitations or requirements -->
101
-
102
- ## Dependencies
103
- <!-- External services, libraries, or other features required -->
104
-
105
- ## Risks and Mitigations
106
- <!-- Identify potential risks and how to address them -->
107
-
108
- ## Open Questions
109
- <!-- Mark with [NEEDS CLARIFICATION] for items requiring user input -->
110
-
111
- ## Appendix
112
- <!-- Additional diagrams, mockups, or references -->
113
- """
114
-
115
- def get_plan_template(self) -> str:
116
- """Get implementation plan template from file"""
117
- template_path = self.resources_dir / "templates" / "plan.md"
118
- if template_path.exists():
119
- with open(template_path, 'r', encoding='utf-8') as f:
120
- return f.read()
121
- # Fallback to embedded template if file not found
122
- return """<!-- SpecPulse Implementation Plan Template v1.0 -->
123
- <!-- AI Instructions: Generate plan from specification -->
124
-
125
- # Implementation Plan: [FEATURE_NAME]
126
-
127
- ## Specification Reference
128
- - **Spec ID**: SPEC-[XXX]
129
- - **Generated**: [DATE]
130
- - **Optimization Focus**: [PERFORMANCE|SECURITY|SIMPLICITY|COST]
131
-
132
- ## Architecture Overview
133
- ```mermaid
134
- <!-- AI: Generate architecture diagram -->
135
- ```
136
-
137
- ## Technology Stack
138
-
139
- ### Core Technologies
140
- - **Language**: [Choice with rationale]
141
- - **Framework**: [Choice with rationale]
142
- - **Database**: [Choice with rationale]
143
- - **Cache**: [Choice with rationale]
144
-
145
- ### Supporting Tools
146
- - **Testing**: [Framework choice]
147
- - **CI/CD**: [Platform choice]
148
- - **Monitoring**: [Solution choice]
149
-
150
- ## Implementation Phases
151
-
152
- ### Phase 0: Setup and Prerequisites
153
- **Duration**: [Estimate]
154
- **Tasks**:
155
- 1. Environment setup
156
- 2. Repository initialization
157
- 3. Dependency installation
158
- 4. Configuration
159
-
160
- ### Phase 1: Data Layer
161
- **Duration**: [Estimate]
162
- **Deliverables**:
163
- - Database schema
164
- - Migration scripts
165
- - Data models
166
- - Repository pattern implementation
167
-
168
- **Tasks**:
169
- 1. Design database schema
170
- 2. Create migration scripts
171
- 3. Implement data models
172
- 4. Create repository interfaces
173
- 5. Write data layer tests
174
-
175
- ### Phase 2: Business Logic
176
- **Duration**: [Estimate]
177
- **Deliverables**:
178
- - Service layer
179
- - Business rules implementation
180
- - Validation logic
181
-
182
- **Tasks**:
183
- 1. Implement service interfaces
184
- 2. Create business logic modules
185
- 3. Add validation rules
186
- 4. Implement error handling
187
- 5. Write unit tests
188
-
189
- ### Phase 3: API Layer
190
- **Duration**: [Estimate]
191
- **Deliverables**:
192
- - REST/GraphQL endpoints
193
- - API documentation
194
- - Authentication/Authorization
195
-
196
- **Tasks**:
197
- 1. Design API contracts
198
- 2. Implement endpoints
199
- 3. Add authentication
200
- 4. Create API documentation
201
- 5. Write integration tests
202
-
203
- ### Phase 4: Testing and Optimization
204
- **Duration**: [Estimate]
205
- **Deliverables**:
206
- - Complete test suite
207
- - Performance optimization
208
- - Security hardening
209
-
210
- **Tasks**:
211
- 1. Complete test coverage
212
- 2. Performance testing
213
- 3. Security audit
214
- 4. Load testing
215
- 5. Documentation
216
-
217
- ## File Structure
218
- ```
219
- [feature-name]/
220
- ├── src/
221
- │ ├── models/
222
- │ ├── services/
223
- │ ├── controllers/
224
- │ └── utils/
225
- ├── tests/
226
- │ ├── unit/
227
- │ ├── integration/
228
- │ └── e2e/
229
- ├── docs/
230
- └── config/
231
- ```
232
-
233
- ## API Contracts
234
-
235
- ### Endpoint: [ENDPOINT_NAME]
236
- ```yaml
237
- method: POST
238
- path: /api/v1/[resource]
239
- request:
240
- headers:
241
- Content-Type: application/json
242
- Authorization: Bearer {token}
243
- body:
244
- field1: string
245
- field2: number
246
- response:
247
- 200:
248
- success: true
249
- data: object
250
- 400:
251
- error: string
252
- ```
253
-
254
- ## Data Models
255
-
256
- ### Entity: [ENTITY_NAME]
257
- ```yaml
258
- fields:
259
- id: uuid
260
- created_at: timestamp
261
- updated_at: timestamp
262
- [field_name]: [type]
263
- relations:
264
- [relation_name]: [type]
265
- indexes:
266
- - [field_name]
267
- ```
268
-
269
- ## Testing Strategy
270
-
271
- ### Unit Tests
272
- - Coverage Target: 80%
273
- - Framework: [Choice]
274
- - Mock Strategy: [Approach]
275
-
276
- ### Integration Tests
277
- - API Contract Tests
278
- - Database Integration Tests
279
- - External Service Tests
280
-
281
- ### E2E Tests
282
- - Critical User Journeys
283
- - Performance Benchmarks
284
- - Security Scenarios
285
-
286
- ## Constitution Compliance
287
-
288
- ### Principle Validation
289
- - [ ] Single Responsibility: Each component has one purpose
290
- - [ ] Test-First: Tests written before implementation
291
- - [ ] Documentation: All code is documented
292
- - [ ] Security: Security considered by design
293
- - [ ] Performance: Meets performance targets
294
-
295
- ## Risk Assessment
296
-
297
- ### Technical Risks
298
- | Risk | Probability | Impact | Mitigation |
299
- |------|------------|--------|------------|
300
- | [Risk] | [H/M/L] | [H/M/L] | [Strategy] |
301
-
302
- ### Timeline Risks
303
- | Risk | Probability | Impact | Mitigation |
304
- |------|------------|--------|------------|
305
- | [Risk] | [H/M/L] | [H/M/L] | [Strategy] |
306
-
307
- ## Success Criteria
308
- - [ ] All functional requirements implemented
309
- - [ ] Test coverage > 80%
310
- - [ ] Performance targets met
311
- - [ ] Security audit passed
312
- - [ ] Documentation complete
313
- """
314
-
315
- def get_task_template(self) -> str:
316
- """Get task list template from file"""
317
- template_path = self.resources_dir / "templates" / "task.md"
318
- if template_path.exists():
319
- with open(template_path, 'r', encoding='utf-8') as f:
320
- return f.read()
321
- # Fallback to embedded template if file not found
322
- return """<!-- SpecPulse Task List Template v1.0 -->
323
- <!-- AI Instructions: Generate from implementation plan -->
324
-
325
- # Task List: [FEATURE_NAME]
326
-
327
- ## Metadata
328
- - **Plan Reference**: [PLAN_ID]
329
- - **Total Tasks**: [COUNT]
330
- - **Estimated Duration**: [TOTAL_HOURS]
331
- - **Parallel Groups**: [COUNT]
332
-
333
- ## Task Organization
334
-
335
- ### 🔄 Parallel Group A
336
- *These tasks can be executed simultaneously*
337
-
338
- #### TASK-001: [Task Name]
339
- - **Type**: [setup|development|testing|documentation]
340
- - **Priority**: [HIGH|MEDIUM|LOW]
341
- - **Estimate**: [hours]
342
- - **Dependencies**: None
343
- - **Description**: [What needs to be done]
344
- - **Acceptance**: [How to verify completion]
345
- - **Assignable**: [role/skill required]
346
-
347
- #### TASK-002: [Task Name]
348
- [Same structure as above]
349
-
350
- ### 📝 Sequential Tasks
351
- *These tasks must be completed in order*
352
-
353
- #### TASK-003: [Task Name]
354
- - **Dependencies**: TASK-001
355
- [Rest of structure]
356
-
357
- ### 🎯 Critical Path
358
- *Tasks that directly impact timeline*
359
-
360
- 1. TASK-001 → TASK-003 → TASK-007
361
- 2. Estimated critical path duration: [hours]
362
-
363
- ## Task Details
364
-
365
- ### Development Tasks
366
- - [ ] TASK-XXX: Implement [component]
367
- - [ ] TASK-XXX: Create [feature]
368
- - [ ] TASK-XXX: Integrate [service]
369
-
370
- ### Testing Tasks
371
- - [ ] TASK-XXX: Write unit tests for [component]
372
- - [ ] TASK-XXX: Create integration tests
373
- - [ ] TASK-XXX: Perform security testing
374
-
375
- ### Documentation Tasks
376
- - [ ] TASK-XXX: Document API endpoints
377
- - [ ] TASK-XXX: Create user guide
378
- - [ ] TASK-XXX: Update README
379
-
380
- ## Execution Schedule
381
-
382
- ### Day 1-2
383
- - Morning: TASK-001, TASK-002 (parallel)
384
- - Afternoon: TASK-003
385
-
386
- ### Day 3-4
387
- - Morning: TASK-004
388
- - Afternoon: TASK-005, TASK-006
389
-
390
- ## Progress Tracking
391
- ```yaml
392
- status:
393
- total: [count]
394
- completed: 0
395
- in_progress: 0
396
- blocked: 0
397
-
398
- metrics:
399
- velocity: [tasks/day]
400
- estimated_completion: [date]
401
- blockers: []
402
- ```
403
- """
404
-
405
- def get_constitution_template(self) -> str:
406
- """Get constitution template from file"""
407
- template_path = self.resources_dir / "memory" / "constitution.md"
408
- if template_path.exists():
409
- with open(template_path, 'r', encoding='utf-8') as f:
410
- return f.read()
411
- # Fallback to embedded template if file not found
412
- return """# Project Constitution
413
-
414
- ## Immutable Principles
415
-
416
- ### Principle 1: Simplicity First
417
- Every solution must start with the simplest approach that could work.
418
- Complexity is added only when proven necessary.
419
-
420
- ### Principle 2: Test-Driven Development
421
- No production code without tests.
422
- Tests are written first, implementation follows.
423
-
424
- ### Principle 3: Single Responsibility
425
- Each module, function, and component does one thing well.
426
- If you need "and" to describe it, split it.
427
-
428
- ### Principle 4: Documentation as Code
429
- Documentation lives with code.
430
- If it's not documented, it doesn't exist.
431
-
432
- ### Principle 5: Security by Design
433
- Security is not an afterthought.
434
- Every feature considers security implications from the start.
435
-
436
- ## Technical Standards
437
-
438
- ### Code Style
439
- - Python: PEP 8 with type hints
440
- - JavaScript: StandardJS
441
- - Go: Official Go formatting
442
-
443
- ### Testing Requirements
444
- - Minimum 80% code coverage
445
- - All API endpoints must have contract tests
446
- - Critical paths require E2E tests
447
-
448
- ### Performance Targets
449
- - API response time: < 200ms (p95)
450
- - Page load time: < 2 seconds
451
- - Database queries: < 50ms
452
-
453
- ### Security Requirements
454
- - All data encrypted in transit (TLS 1.3+)
455
- - Sensitive data encrypted at rest
456
- - Authentication: OAuth 2.0 / JWT
457
- - Authorization: RBAC with least privilege
458
-
459
- ## Architecture Rules
460
-
461
- ### Service Boundaries
462
- - Services communicate only through defined APIs
463
- - No shared databases between services
464
- - Each service owns its data
465
-
466
- ### Data Management
467
- - Single source of truth for each data type
468
- - Event sourcing for audit requirements
469
- - CQRS where read/write patterns differ
470
-
471
- ### Error Handling
472
- - All errors are handled explicitly
473
- - User-facing errors are helpful and actionable
474
- - System errors are logged with context
475
-
476
- ## Amendment Process
477
-
478
- Changes to this constitution require:
479
- 1. Documented rationale
480
- 2. Team consensus
481
- 3. Gradual migration plan
482
- 4. Update to all affected documentation
483
- """
484
-
485
- def get_context_template(self) -> str:
486
- """Get context template from file"""
487
- template_path = self.resources_dir / "memory" / "context.md"
488
- if template_path.exists():
489
- with open(template_path, 'r', encoding='utf-8') as f:
490
- return f.read()
491
- # Fallback to embedded template if file not found
492
- return """# Project Context
493
-
494
- ## Current State
495
- Last Updated: [AI updates this automatically]
496
-
497
- ### Active Features
498
- 1. **[feature-name]** (SPEC-XXX)
499
- - Status: [Phase]
500
- - Branch: [branch-name]
501
- - Blockers: [None|List]
502
-
503
- ### Recent Decisions
504
- - [Decision with rationale]
505
-
506
- ### Known Issues
507
- - [Issue description]
508
-
509
- ## Team Preferences
510
-
511
- ### Technology Choices
512
- - **Preferred Stack**: [Stack]
513
- - **Testing**: [Framework]
514
- - **CI/CD**: [Platform]
515
- - **Deployment**: [Method]
516
-
517
- ### Coding Patterns
518
- - [Pattern preference]
519
-
520
- ## Project Glossary
521
-
522
- ### Domain Terms
523
- - **[Term]**: [Definition]
524
-
525
- ### Technical Terms
526
- - **[Term]**: [Definition]
527
- """
528
-
529
- def get_decisions_template(self) -> str:
530
- """Get architectural decisions template from file"""
531
- template_path = self.resources_dir / "memory" / "decisions.md"
532
- if template_path.exists():
533
- with open(template_path, 'r', encoding='utf-8') as f:
534
- return f.read()
535
- # Fallback to embedded template if file not found
536
- return """# Architectural Decisions
537
-
538
- ## Decision Log
539
-
540
- ### ADR-001: [Title]
541
- **Date**: [DATE]
542
- **Status**: [PROPOSED|ACCEPTED|DEPRECATED]
543
- **Context**: [Why this decision was needed]
544
- **Decision**: [What was decided]
545
- **Consequences**: [What happens as a result]
546
- **Alternatives Considered**: [Other options that were evaluated]
547
-
548
- ---
549
-
550
- ### ADR-002: [Title]
551
- [Same structure as above]
552
- """
553
-
554
- def get_setup_script(self) -> str:
555
- """Get pulse-init script for feature initialization from file"""
556
- script_path = self.resources_dir / "scripts" / "pulse-init.sh"
557
- if script_path.exists():
558
- with open(script_path, 'r', encoding='utf-8') as f:
559
- return f.read()
560
- # Fallback to embedded script if file not found
561
- return """#!/bin/bash
562
- # SpecPulse Feature Initialization Script
563
-
564
- set -e
565
-
566
- # Get feature name from argument
567
- FEATURE_NAME="$1"
568
- if [ -z "$FEATURE_NAME" ]; then
569
- echo "Error: Feature name required"
570
- exit 1
571
- fi
572
-
573
- # Clean feature name (replace spaces with hyphens, lowercase)
574
- CLEAN_NAME=$(echo "$FEATURE_NAME" | tr '[:upper:]' '[:lower:]' | tr ' ' '-' | tr '_' '-')
575
-
576
- # Get next feature number
577
- if [ -d "specs" ]; then
578
- FEATURE_NUM=$(find specs -maxdepth 1 -type d -name "[0-9][0-9][0-9]-*" | wc -l)
579
- FEATURE_NUM=$((FEATURE_NUM + 1))
580
- else
581
- FEATURE_NUM=1
582
- fi
583
-
584
- # Format with leading zeros
585
- FEATURE_ID=$(printf "%03d" $FEATURE_NUM)
586
- BRANCH_NAME="${FEATURE_ID}-${CLEAN_NAME}"
587
-
588
- # Create directories
589
- mkdir -p "specs/${BRANCH_NAME}"
590
- mkdir -p "plans/${BRANCH_NAME}"
591
- mkdir -p "tasks/${BRANCH_NAME}"
592
-
593
- # Create feature branch if git is available
594
- if command -v git &> /dev/null && [ -d ".git" ]; then
595
- git checkout -b "$BRANCH_NAME" 2>/dev/null || git checkout "$BRANCH_NAME"
596
- fi
597
-
598
- # Output JSON result
599
- echo "{"
600
- echo " \\"branch_name\\": \\"$BRANCH_NAME\\","
601
- echo " \\"feature_id\\": \\"$FEATURE_ID\\","
602
- echo " \\"spec_dir\\": \\"specs/$BRANCH_NAME\\","
603
- echo " \\"plan_dir\\": \\"plans/$BRANCH_NAME\\","
604
- echo " \\"task_dir\\": \\"tasks/$BRANCH_NAME\\""
605
- echo "}"
606
- """
607
-
608
- def get_spec_script(self) -> str:
609
- """Get pulse-spec script for getting current feature context from file"""
610
- script_path = self.resources_dir / "scripts" / "pulse-spec.sh"
611
- if script_path.exists():
612
- with open(script_path, 'r', encoding='utf-8') as f:
613
- return f.read()
614
- # Fallback to embedded script if file not found
615
- return """#!/bin/bash
616
- # SpecPulse Spec Context Script
617
-
618
- # Check for --current flag
619
- if [ "$1" == "--current" ]; then
620
- # Find the current feature branch
621
- if command -v git &> /dev/null && [ -d ".git" ]; then
622
- BRANCH=$(git branch --show-current)
623
- if [[ "$BRANCH" =~ ^[0-9]{3}-.* ]]; then
624
- FEATURE_DIR="specs/$BRANCH"
625
- if [ -d "$FEATURE_DIR" ]; then
626
- echo "{"
627
- echo " \\"branch\\": \\"$BRANCH\\","
628
- echo " \\"spec_file\\": \\"$FEATURE_DIR/spec.md\\","
629
- echo " \\"spec_dir\\": \\"$FEATURE_DIR\\""
630
- echo "}"
631
- exit 0
632
- fi
633
- fi
634
- fi
635
-
636
- # Fallback: find latest spec directory
637
- LATEST=$(find specs -maxdepth 1 -type d -name "[0-9][0-9][0-9]-*" | sort -r | head -1)
638
- if [ -n "$LATEST" ]; then
639
- echo "{"
640
- echo " \\"branch\\": \\"$(basename $LATEST)\\","
641
- echo " \\"spec_file\\": \\"$LATEST/spec.md\\","
642
- echo " \\"spec_dir\\": \\"$LATEST\\""
643
- echo "}"
644
- else
645
- echo "{\\"error\\": \\"No active feature found\\"}"
646
- exit 1
647
- fi
648
- fi
649
- """
650
-
651
- def get_plan_script(self) -> str:
652
- """Get pulse-plan script for plan context from file"""
653
- script_path = self.resources_dir / "scripts" / "pulse-plan.sh"
654
- if script_path.exists():
655
- with open(script_path, 'r', encoding='utf-8') as f:
656
- return f.read()
657
- # Fallback to embedded script if file not found
658
- return """#!/bin/bash
659
- # SpecPulse Plan Context Script
660
-
661
- # Check for --current flag
662
- if [ "$1" == "--current" ]; then
663
- # Find the current feature branch
664
- if command -v git &> /dev/null && [ -d ".git" ]; then
665
- BRANCH=$(git branch --show-current)
666
- if [[ "$BRANCH" =~ ^[0-9]{3}-.* ]]; then
667
- SPEC_DIR="specs/$BRANCH"
668
- PLAN_DIR="plans/$BRANCH"
669
- if [ -d "$SPEC_DIR" ]; then
670
- echo "{"
671
- echo " \\"branch\\": \\"$BRANCH\\","
672
- echo " \\"spec_file\\": \\"$SPEC_DIR/spec.md\\","
673
- echo " \\"plan_file\\": \\"$PLAN_DIR/plan.md\\","
674
- echo " \\"plan_dir\\": \\"$PLAN_DIR\\""
675
- echo "}"
676
- exit 0
677
- fi
678
- fi
679
- fi
680
-
681
- # Fallback: find latest directories
682
- LATEST=$(find specs -maxdepth 1 -type d -name "[0-9][0-9][0-9]-*" | sort -r | head -1)
683
- if [ -n "$LATEST" ]; then
684
- BRANCH=$(basename "$LATEST")
685
- echo "{"
686
- echo " \\"branch\\": \\"$BRANCH\\","
687
- echo " \\"spec_file\\": \\"specs/$BRANCH/spec.md\\","
688
- echo " \\"plan_file\\": \\"plans/$BRANCH/plan.md\\","
689
- echo " \\"plan_dir\\": \\"plans/$BRANCH\\""
690
- echo "}"
691
- else
692
- echo "{\\"error\\": \\"No active feature found\\"}"
693
- exit 1
694
- fi
695
- fi
696
- """
697
-
698
- def get_task_script(self) -> str:
699
- """Get pulse-task script for task context from file"""
700
- script_path = self.resources_dir / "scripts" / "pulse-task.sh"
701
- if script_path.exists():
702
- with open(script_path, 'r', encoding='utf-8') as f:
703
- return f.read()
704
- # Fallback to embedded script if file not found
705
- return """#!/bin/bash
706
- # SpecPulse Task Context Script
707
-
708
- # Check for --current flag
709
- if [ "$1" == "--current" ]; then
710
- # Find the current feature branch
711
- if command -v git &> /dev/null && [ -d ".git" ]; then
712
- BRANCH=$(git branch --show-current)
713
- if [[ "$BRANCH" =~ ^[0-9]{3}-.* ]]; then
714
- SPEC_DIR="specs/$BRANCH"
715
- PLAN_DIR="plans/$BRANCH"
716
- TASK_DIR="tasks/$BRANCH"
717
- if [ -d "$SPEC_DIR" ]; then
718
- echo "{"
719
- echo " \\"branch\\": \\"$BRANCH\\","
720
- echo " \\"spec_file\\": \\"$SPEC_DIR/spec.md\\","
721
- echo " \\"plan_file\\": \\"$PLAN_DIR/plan.md\\","
722
- echo " \\"task_file\\": \\"$TASK_DIR/tasks.md\\","
723
- echo " \\"task_dir\\": \\"$TASK_DIR\\""
724
- echo "}"
725
- exit 0
726
- fi
727
- fi
728
- fi
729
-
730
- # Fallback: find latest directories
731
- LATEST=$(find specs -maxdepth 1 -type d -name "[0-9][0-9][0-9]-*" | sort -r | head -1)
732
- if [ -n "$LATEST" ]; then
733
- BRANCH=$(basename "$LATEST")
734
- echo "{"
735
- echo " \\"branch\\": \\"$BRANCH\\","
736
- echo " \\"spec_file\\": \\"specs/$BRANCH/spec.md\\","
737
- echo " \\"plan_file\\": \\"plans/$BRANCH/plan.md\\","
738
- echo " \\"task_file\\": \\"tasks/$BRANCH/tasks.md\\","
739
- echo " \\"task_dir\\": \\"tasks/$BRANCH\\""
740
- echo "}"
741
- else
742
- echo "{\\"error\\": \\"No active feature found\\"}"
743
- exit 1
744
- fi
745
- fi
746
- """
747
-
748
- def get_validate_script(self) -> str:
749
- """Get validation script"""
750
- return """#!/bin/bash
751
- # SpecPulse Validation Script
752
-
753
- validate_spec() {
754
- local spec_file=$1
755
- local errors=0
756
-
757
- echo "Validating: $spec_file"
758
-
759
- # Check required sections
760
- if ! grep -q "## Requirements" $spec_file; then
761
- echo " ❌ Missing Requirements section"
762
- ((errors++))
763
- fi
764
-
765
- if ! grep -q "## User Stories" $spec_file; then
766
- echo " ❌ Missing User Stories section"
767
- ((errors++))
768
- fi
769
-
770
- if ! grep -q "## Acceptance Criteria" $spec_file; then
771
- echo " ❌ Missing Acceptance Criteria section"
772
- ((errors++))
773
- fi
774
-
775
- # Check for clarification markers
776
- if grep -q "\\[NEEDS CLARIFICATION\\]" $spec_file; then
777
- echo " ⚠️ Contains items needing clarification"
778
- fi
779
-
780
- if [ $errors -eq 0 ]; then
781
- echo " Specification valid"
782
- return 0
783
- else
784
- echo " ❌ Specification has $errors errors"
785
- return 1
786
- fi
787
- }
788
-
789
- # Main
790
- if [ "$1" == "spec" ]; then
791
- validate_spec $2
792
- elif [ "$1" == "all" ]; then
793
- for spec in specs/*/spec.md; do
794
- validate_spec $spec
795
- done
796
- fi
797
- """
798
-
799
- def get_generate_script(self) -> str:
800
- """Get generation script"""
801
- return """#!/bin/bash
802
- # SpecPulse Generation Script
803
-
804
- generate_from_template() {
805
- local template=$1
806
- local output=$2
807
- local feature_name=$3
808
-
809
- # Replace placeholders
810
- sed "s/\\[FEATURE_NAME\\]/$feature_name/g" $template > $output
811
- sed -i "s/\\[DATE\\]/$(date +%Y-%m-%d)/g" $output
812
- sed -i "s/\\[XXX\\]/$(printf '%03d' $RANDOM)/g" $output
813
-
814
- echo "Generated: $output"
815
- }
816
-
817
- # Main
818
- if [ "$1" == "spec" ]; then
819
- generate_from_template templates/spec.md $2 $3
820
- elif [ "$1" == "plan" ]; then
821
- generate_from_template templates/plan.md $2 $3
822
- elif [ "$1" == "task" ]; then
823
- generate_from_template templates/task.md $2 $3
824
- fi
825
- """
826
-
827
- def get_claude_instructions(self) -> str:
828
- """Get Claude instructions"""
829
- return """# SpecPulse Commands for Claude
830
-
831
- You have access to SpecPulse commands for specification-driven development.
832
-
833
- ## Available Commands
834
-
835
- ### /pulse init <feature-name>
836
- Initializes a new feature with proper structure.
837
- - Creates feature branch
838
- - Sets up specification directory
839
- - Loads templates
840
- - Updates context
841
-
842
- ### /spec create <description>
843
- Creates a detailed specification from description.
844
- - Use the template in templates/spec.md
845
- - Mark uncertainties with [NEEDS CLARIFICATION]
846
- - Ensure all sections are complete
847
- - Validate against constitution
848
-
849
- ### /plan generate
850
- Generates implementation plan from current specification.
851
- - Read the active specification
852
- - Create detailed phases
853
- - Include technology decisions
854
- - Add time estimates
855
-
856
- ### /task breakdown
857
- Creates task list from implementation plan.
858
- - Identify dependencies
859
- - Mark parallel tasks with [P]
860
- - Add time estimates
861
- - Create critical path
862
-
863
- ### /validate <component>
864
- Validates specifications, plans, or project.
865
- - Check completeness
866
- - Verify consistency
867
- - Ensure constitution compliance
868
-
869
- ## Workflow
870
-
871
- 1. User requests feature → Use `/pulse init`
872
- 2. User describes requirements → Use `/spec create`
873
- 3. Specification complete → Use `/plan generate`
874
- 4. Plan approved → Use `/task breakdown`
875
- 5. Before implementation Use `/validate all`
876
-
877
- ## Constitution Rules
878
-
879
- Always enforce these principles:
880
- 1. Simplicity first
881
- 2. Test-driven development
882
- 3. Single responsibility
883
- 4. Documentation as code
884
- 5. Security by design
885
-
886
- ## Context Management
887
-
888
- - Read `memory/context.md` for project state
889
- - Update context after major decisions
890
- - Check `memory/constitution.md` for principles
891
- - Reference previous specs for consistency
892
-
893
- ## Templates
894
-
895
- Always use templates from `templates/` directory:
896
- - `spec.md` for specifications
897
- - `plan.md` for implementation plans
898
- - `task.md` for task lists
899
-
900
- ## Best Practices
901
-
902
- 1. Always validate before moving to next phase
903
- 2. Keep specifications testable and measurable
904
- 3. Update context.md with decisions
905
- 4. Create atomic, focused commits
906
- 5. Document rationale for technology choices
907
- """
908
-
909
- # Claude command getters
910
- def get_claude_pulse_command(self) -> str:
911
- """Get Claude pulse command"""
912
- command_path = self.resources_dir / "commands" / "claude" / "pulse.md"
913
- if command_path.exists():
914
- with open(command_path, 'r', encoding='utf-8') as f:
915
- return f.read()
916
- return "# /pulse command not found"
917
-
918
- def get_claude_spec_command(self) -> str:
919
- """Get Claude spec command"""
920
- command_path = self.resources_dir / "commands" / "claude" / "spec.md"
921
- if command_path.exists():
922
- with open(command_path, 'r', encoding='utf-8') as f:
923
- return f.read()
924
- return "# /spec command not found"
925
-
926
- def get_claude_plan_command(self) -> str:
927
- """Get Claude plan command"""
928
- command_path = self.resources_dir / "commands" / "claude" / "plan.md"
929
- if command_path.exists():
930
- with open(command_path, 'r', encoding='utf-8') as f:
931
- return f.read()
932
- return "# /plan command not found"
933
-
934
- def get_claude_task_command(self) -> str:
935
- """Get Claude task command"""
936
- command_path = self.resources_dir / "commands" / "claude" / "task.md"
937
- if command_path.exists():
938
- with open(command_path, 'r', encoding='utf-8') as f:
939
- return f.read()
940
- return "# /task command not found"
941
-
942
- # Gemini command getters
943
- def get_gemini_pulse_command(self) -> str:
944
- """Get Gemini pulse command"""
945
- command_path = self.resources_dir / "commands" / "gemini" / "pulse.toml"
946
- if command_path.exists():
947
- with open(command_path, 'r', encoding='utf-8') as f:
948
- return f.read()
949
- return "# Gemini pulse command not found"
950
-
951
- def get_gemini_spec_command(self) -> str:
952
- """Get Gemini spec command"""
953
- command_path = self.resources_dir / "commands" / "gemini" / "spec.toml"
954
- if command_path.exists():
955
- with open(command_path, 'r', encoding='utf-8') as f:
956
- return f.read()
957
- return "# Gemini spec command not found"
958
-
959
- def get_gemini_plan_command(self) -> str:
960
- """Get Gemini plan command"""
961
- command_path = self.resources_dir / "commands" / "gemini" / "plan.toml"
962
- if command_path.exists():
963
- with open(command_path, 'r', encoding='utf-8') as f:
964
- return f.read()
965
- return "# Gemini plan command not found"
966
-
967
- def get_gemini_task_command(self) -> str:
968
- """Get Gemini task command"""
969
- command_path = self.resources_dir / "commands" / "gemini" / "task.toml"
970
- if command_path.exists():
971
- with open(command_path, 'r', encoding='utf-8') as f:
972
- return f.read()
973
- return "# Gemini task command not found"
974
-
975
- def get_gemini_instructions(self) -> str:
976
- """Get Gemini instructions"""
977
- return """# SpecPulse Commands for Gemini CLI
978
-
979
- This project uses SpecPulse for specification-driven development.
980
-
981
- ## Command Reference
982
-
983
- ### Initialization
984
- ```
985
- /pulse init <feature-name>
986
- ```
987
- Creates new feature structure and branch.
988
-
989
- ### Specification Creation
990
- ```
991
- /spec create <description>
992
- ```
993
- Generates detailed specification from natural language.
994
-
995
- Required sections:
996
- - Requirements (functional and non-functional)
997
- - User stories with acceptance criteria
998
- - Technical constraints
999
- - Dependencies
1000
- - Risks and mitigations
1001
-
1002
- ### Plan Generation
1003
- ```
1004
- /plan generate [--optimize <focus>]
1005
- ```
1006
- Creates implementation plan from specification.
1007
-
1008
- Optimization options:
1009
- - performance: Speed and efficiency focus
1010
- - security: Security-first approach
1011
- - simplicity: Maintainable solution
1012
- - cost: Resource optimization
1013
-
1014
- ### Task Breakdown
1015
- ```
1016
- /task breakdown [--parallel]
1017
- ```
1018
- Generates actionable task list.
1019
-
1020
- Features:
1021
- - Dependency detection
1022
- - Parallel task identification
1023
- - Time estimation
1024
- - Critical path analysis
1025
-
1026
- ### Validation
1027
- ```
1028
- /validate [all|spec|plan|constitution]
1029
- ```
1030
- Validates project components.
1031
-
1032
- ## Templates Location
1033
-
1034
- Use templates from `templates/` directory:
1035
- - Specification: templates/spec.md
1036
- - Implementation: templates/plan.md
1037
- - Tasks: templates/task.md
1038
-
1039
- ## Memory System
1040
-
1041
- Project memory in `memory/` directory:
1042
- - constitution.md: Immutable principles
1043
- - context.md: Current project state
1044
- - decisions.md: Architectural decisions
1045
-
1046
- ## Workflow Process
1047
-
1048
- 1. **Initialize Feature**
1049
- - Run: `/pulse init feature-name`
1050
- - Creates branch and structure
1051
-
1052
- 2. **Create Specification**
1053
- - Run: `/spec create "description"`
1054
- - Fill template completely
1055
- - Mark unclear items: [NEEDS CLARIFICATION]
1056
-
1057
- 3. **Generate Plan**
1058
- - Run: `/plan generate`
1059
- - Choose optimization focus
1060
- - Review technology choices
1061
-
1062
- 4. **Create Tasks**
1063
- - Run: `/task breakdown`
1064
- - Review dependencies
1065
- - Check time estimates
1066
-
1067
- 5. **Validate**
1068
- - Run: `/validate all`
1069
- - Fix any issues
1070
- - Proceed to implementation
1071
-
1072
- ## Constitution Principles
1073
-
1074
- Enforce these rules:
1075
- 1. Start simple, add complexity only when needed
1076
- 2. Write tests before code
1077
- 3. One responsibility per component
1078
- 4. Document everything
1079
- 5. Consider security from start
1080
-
1081
- ## Project Structure
1082
-
1083
- ```
1084
- project/
1085
- ├── specs/ # Specifications
1086
- ├── plans/ # Implementation plans
1087
- ├── tasks/ # Task lists
1088
- ├── memory/ # Project memory
1089
- ├── scripts/ # Automation
1090
- └── templates/ # Templates
1091
- ```
1092
-
1093
- ## Important Notes
1094
-
1095
- - Always update context.md after decisions
1096
- - Validate specifications before planning
1097
- - Use [P] marker for parallel tasks
1098
- - Keep commits atomic and focused
1099
- - Reference constitution for all decisions
1
+ """
2
+ SpecPulse Core Implementation
3
+ """
4
+
5
+ from pathlib import Path
6
+ from datetime import datetime
7
+ from typing import Dict, List, Optional
8
+ import yaml
9
+ import json
10
+ import os
11
+
12
+
13
+
14
+ class SpecPulse:
15
+ """Core SpecPulse functionality"""
16
+
17
+ def __init__(self, project_path: Optional[Path] = None):
18
+ self.project_path = project_path or Path.cwd()
19
+ self.config = self._load_config()
20
+ # Get resource directory path using package data
21
+ try:
22
+ # Use modern importlib.resources (Python 3.9+)
23
+ from importlib import resources
24
+ self.resources_dir = Path(resources.files('specpulse').joinpath('resources'))
25
+ except:
26
+ try:
27
+ # Fallback to pkg_resources for older Python versions
28
+ import pkg_resources
29
+ self.resources_dir = Path(pkg_resources.resource_filename('specpulse', 'resources'))
30
+ except:
31
+ # Final fallback to development path
32
+ self.resources_dir = Path(__file__).parent.parent / "resources"
33
+
34
+ def _load_config(self) -> Dict:
35
+ """Load project configuration"""
36
+ config_path = self.project_path / ".specpulse" / "config.yaml"
37
+ if config_path.exists():
38
+ with open(config_path, 'r') as f:
39
+ return yaml.safe_load(f)
40
+ return {}
41
+
42
+ def get_spec_template(self) -> str:
43
+ """Get specification template from file"""
44
+ template_path = self.resources_dir / "templates" / "spec-001.md"
45
+ if template_path.exists():
46
+ with open(template_path, 'r', encoding='utf-8') as f:
47
+ return f.read()
48
+ # Fallback to embedded template if file not found
49
+ return """<!-- SpecPulse Specification Template v1.0 -->
50
+ <!-- AI Instructions: Fill this template based on user description -->
51
+
52
+ # Specification: [FEATURE_NAME]
53
+
54
+ ## Metadata
55
+ - **ID**: SPEC-[XXX]
56
+ - **Created**: [DATE]
57
+ - **Author**: [USER]
58
+ - **AI Assistant**: [CLAUDE|GEMINI]
59
+ - **Version**: 1.0.0
60
+
61
+ ## Executive Summary
62
+ [One paragraph description of what this feature does and why it's needed]
63
+
64
+ ## Problem Statement
65
+ [Detailed description of the problem being solved]
66
+
67
+ ## Proposed Solution
68
+ [High-level approach to solving the problem]
69
+
70
+ ## Detailed Requirements
71
+
72
+ ### Functional Requirements
73
+ <!-- AI: Generate numbered list of specific, testable requirements -->
74
+
75
+ FR-001: [Requirement]
76
+ - Acceptance: [How to verify this requirement is met]
77
+ - Priority: [MUST|SHOULD|COULD]
78
+
79
+ ### Non-Functional Requirements
80
+
81
+ #### Performance
82
+ - Response Time: [Target]
83
+ - Throughput: [Target]
84
+ - Resource Usage: [Limits]
85
+
86
+ #### Security
87
+ - Authentication: [Method]
88
+ - Authorization: [Model]
89
+ - Data Protection: [Requirements]
90
+
91
+ #### Scalability
92
+ - User Load: [Target]
93
+ - Data Volume: [Target]
94
+ - Geographic Distribution: [Requirements]
95
+
96
+ ## User Stories
97
+
98
+ <!-- AI: Generate user stories in standard format -->
99
+
100
+ ### Story 1: [Title]
101
+ **As a** [user type]
102
+ **I want** [action/feature]
103
+ **So that** [benefit/value]
104
+
105
+ **Acceptance Criteria:**
106
+ - [ ] [Criterion 1]
107
+ - [ ] [Criterion 2]
108
+ - [ ] [Criterion 3]
109
+
110
+ ## Technical Constraints
111
+ <!-- List any technical limitations or requirements -->
112
+
113
+ ## Dependencies
114
+ <!-- External services, libraries, or other features required -->
115
+
116
+ ## Risks and Mitigations
117
+ <!-- Identify potential risks and how to address them -->
118
+
119
+ ## Open Questions
120
+ <!-- Mark with [NEEDS CLARIFICATION] for items requiring user input -->
121
+
122
+ ## Appendix
123
+ <!-- Additional diagrams, mockups, or references -->
124
+ """
125
+
126
+ def get_plan_template(self) -> str:
127
+ """Get implementation plan template from file"""
128
+ template_path = self.resources_dir / "templates" / "plan-001.md"
129
+ if template_path.exists():
130
+ with open(template_path, 'r', encoding='utf-8') as f:
131
+ return f.read()
132
+ # Fallback to embedded template if file not found
133
+ return """<!-- SpecPulse Implementation Plan Template v1.0 -->
134
+ <!-- AI Instructions: Generate plan from specification -->
135
+
136
+ # Implementation Plan: [FEATURE_NAME]
137
+
138
+ ## Specification Reference
139
+ - **Spec ID**: SPEC-[XXX]
140
+ - **Generated**: [DATE]
141
+ - **Optimization Focus**: [PERFORMANCE|SECURITY|SIMPLICITY|COST]
142
+
143
+ ## Architecture Overview
144
+ ```mermaid
145
+ <!-- AI: Generate architecture diagram -->
146
+ ```
147
+
148
+ ## Technology Stack
149
+
150
+ ### Core Technologies
151
+ - **Language**: [Choice with rationale]
152
+ - **Framework**: [Choice with rationale]
153
+ - **Database**: [Choice with rationale]
154
+ - **Cache**: [Choice with rationale]
155
+
156
+ ### Supporting Tools
157
+ - **Testing**: [Framework choice]
158
+ - **CI/CD**: [Platform choice]
159
+ - **Monitoring**: [Solution choice]
160
+
161
+ ## Implementation Phases
162
+
163
+ ### Phase 0: Setup and Prerequisites
164
+ **Duration**: [Estimate]
165
+ **Tasks**:
166
+ 1. Environment setup
167
+ 2. Repository initialization
168
+ 3. Dependency installation
169
+ 4. Configuration
170
+
171
+ ### Phase 1: Data Layer
172
+ **Duration**: [Estimate]
173
+ **Deliverables**:
174
+ - Database schema
175
+ - Migration scripts
176
+ - Data models
177
+ - Repository pattern implementation
178
+
179
+ **Tasks**:
180
+ 1. Design database schema
181
+ 2. Create migration scripts
182
+ 3. Implement data models
183
+ 4. Create repository interfaces
184
+ 5. Write data layer tests
185
+
186
+ ### Phase 2: Business Logic
187
+ **Duration**: [Estimate]
188
+ **Deliverables**:
189
+ - Service layer
190
+ - Business rules implementation
191
+ - Validation logic
192
+
193
+ **Tasks**:
194
+ 1. Implement service interfaces
195
+ 2. Create business logic modules
196
+ 3. Add validation rules
197
+ 4. Implement error handling
198
+ 5. Write unit tests
199
+
200
+ ### Phase 3: API Layer
201
+ **Duration**: [Estimate]
202
+ **Deliverables**:
203
+ - REST/GraphQL endpoints
204
+ - API documentation
205
+ - Authentication/Authorization
206
+
207
+ **Tasks**:
208
+ 1. Design API contracts
209
+ 2. Implement endpoints
210
+ 3. Add authentication
211
+ 4. Create API documentation
212
+ 5. Write integration tests
213
+
214
+ ### Phase 4: Testing and Optimization
215
+ **Duration**: [Estimate]
216
+ **Deliverables**:
217
+ - Complete test suite
218
+ - Performance optimization
219
+ - Security hardening
220
+
221
+ **Tasks**:
222
+ 1. Complete test coverage
223
+ 2. Performance testing
224
+ 3. Security audit
225
+ 4. Load testing
226
+ 5. Documentation
227
+
228
+ ## File Structure
229
+ ```
230
+ [feature-name]/
231
+ ├── src/
232
+ │ ├── models/
233
+ │ ├── services/
234
+ │ ├── controllers/
235
+ │ └── utils/
236
+ ├── tests/
237
+ │ ├── unit/
238
+ │ ├── integration/
239
+ │ └── e2e/
240
+ ├── docs/
241
+ └── config/
242
+ ```
243
+
244
+ ## API Contracts
245
+
246
+ ### Endpoint: [ENDPOINT_NAME]
247
+ ```yaml
248
+ method: POST
249
+ path: /api/v1/[resource]
250
+ request:
251
+ headers:
252
+ Content-Type: application/json
253
+ Authorization: Bearer {token}
254
+ body:
255
+ field1: string
256
+ field2: number
257
+ response:
258
+ 200:
259
+ success: true
260
+ data: object
261
+ 400:
262
+ error: string
263
+ ```
264
+
265
+ ## Data Models
266
+
267
+ ### Entity: [ENTITY_NAME]
268
+ ```yaml
269
+ fields:
270
+ id: uuid
271
+ created_at: timestamp
272
+ updated_at: timestamp
273
+ [field_name]: [type]
274
+ relations:
275
+ [relation_name]: [type]
276
+ indexes:
277
+ - [field_name]
278
+ ```
279
+
280
+ ## Testing Strategy
281
+
282
+ ### Unit Tests
283
+ - Coverage Target: 80%
284
+ - Framework: [Choice]
285
+ - Mock Strategy: [Approach]
286
+
287
+ ### Integration Tests
288
+ - API Contract Tests
289
+ - Database Integration Tests
290
+ - External Service Tests
291
+
292
+ ### E2E Tests
293
+ - Critical User Journeys
294
+ - Performance Benchmarks
295
+ - Security Scenarios
296
+
297
+ ## Constitution Compliance
298
+
299
+ ### Principle Validation
300
+ - [ ] Single Responsibility: Each component has one purpose
301
+ - [ ] Test-First: Tests written before implementation
302
+ - [ ] Documentation: All code is documented
303
+ - [ ] Security: Security considered by design
304
+ - [ ] Performance: Meets performance targets
305
+
306
+ ## Risk Assessment
307
+
308
+ ### Technical Risks
309
+ | Risk | Probability | Impact | Mitigation |
310
+ |------|------------|--------|------------|
311
+ | [Risk] | [H/M/L] | [H/M/L] | [Strategy] |
312
+
313
+ ### Timeline Risks
314
+ | Risk | Probability | Impact | Mitigation |
315
+ |------|------------|--------|------------|
316
+ | [Risk] | [H/M/L] | [H/M/L] | [Strategy] |
317
+
318
+ ## Success Criteria
319
+ - [ ] All functional requirements implemented
320
+ - [ ] Test coverage > 80%
321
+ - [ ] Performance targets met
322
+ - [ ] Security audit passed
323
+ - [ ] Documentation complete
324
+ """
325
+
326
+ def get_task_template(self) -> str:
327
+ """Get task list template from file"""
328
+ template_path = self.resources_dir / "templates" / "task.md"
329
+ if template_path.exists():
330
+ with open(template_path, 'r', encoding='utf-8') as f:
331
+ return f.read()
332
+ # Fallback to embedded template if file not found
333
+ return """<!-- SpecPulse Task List Template v1.0 -->
334
+ <!-- AI Instructions: Generate from implementation plan -->
335
+
336
+ # Task List: [FEATURE_NAME]
337
+
338
+ ## Metadata
339
+ - **Plan Reference**: [PLAN_ID]
340
+ - **Total Tasks**: [COUNT]
341
+ - **Estimated Duration**: [TOTAL_HOURS]
342
+ - **Parallel Groups**: [COUNT]
343
+
344
+ ## Task Organization
345
+
346
+ ### 🔄 Parallel Group A
347
+ *These tasks can be executed simultaneously*
348
+
349
+ #### TASK-001: [Task Name]
350
+ - **Type**: [setup|development|testing|documentation]
351
+ - **Priority**: [HIGH|MEDIUM|LOW]
352
+ - **Estimate**: [hours]
353
+ - **Dependencies**: None
354
+ - **Description**: [What needs to be done]
355
+ - **Acceptance**: [How to verify completion]
356
+ - **Assignable**: [role/skill required]
357
+
358
+ #### TASK-002: [Task Name]
359
+ [Same structure as above]
360
+
361
+ ### 📝 Sequential Tasks
362
+ *These tasks must be completed in order*
363
+
364
+ #### TASK-003: [Task Name]
365
+ - **Dependencies**: TASK-001
366
+ [Rest of structure]
367
+
368
+ ### 🎯 Critical Path
369
+ *Tasks that directly impact timeline*
370
+
371
+ 1. TASK-001 TASK-003 TASK-007
372
+ 2. Estimated critical path duration: [hours]
373
+
374
+ ## Task Details
375
+
376
+ ### Development Tasks
377
+ - [ ] TASK-XXX: Implement [component]
378
+ - [ ] TASK-XXX: Create [feature]
379
+ - [ ] TASK-XXX: Integrate [service]
380
+
381
+ ### Testing Tasks
382
+ - [ ] TASK-XXX: Write unit tests for [component]
383
+ - [ ] TASK-XXX: Create integration tests
384
+ - [ ] TASK-XXX: Perform security testing
385
+
386
+ ### Documentation Tasks
387
+ - [ ] TASK-XXX: Document API endpoints
388
+ - [ ] TASK-XXX: Create user guide
389
+ - [ ] TASK-XXX: Update README
390
+
391
+ ## Execution Schedule
392
+
393
+ ### Day 1-2
394
+ - Morning: TASK-001, TASK-002 (parallel)
395
+ - Afternoon: TASK-003
396
+
397
+ ### Day 3-4
398
+ - Morning: TASK-004
399
+ - Afternoon: TASK-005, TASK-006
400
+
401
+ ## Progress Tracking
402
+ ```yaml
403
+ status:
404
+ total: [count]
405
+ completed: 0
406
+ in_progress: 0
407
+ blocked: 0
408
+
409
+ metrics:
410
+ velocity: [tasks/day]
411
+ estimated_completion: [date]
412
+ blockers: []
413
+ ```
414
+ """
415
+
416
+ def get_constitution_template(self) -> str:
417
+ """Get constitution template from file"""
418
+ template_path = self.resources_dir / "memory" / "constitution.md"
419
+ if template_path.exists():
420
+ with open(template_path, 'r', encoding='utf-8') as f:
421
+ return f.read()
422
+ # Fallback to embedded template if file not found
423
+ return """# Project Constitution
424
+
425
+ ## Immutable Principles
426
+
427
+ ### Principle 1: Simplicity First
428
+ Every solution must start with the simplest approach that could work.
429
+ Complexity is added only when proven necessary.
430
+
431
+ ### Principle 2: Test-Driven Development
432
+ No production code without tests.
433
+ Tests are written first, implementation follows.
434
+
435
+ ### Principle 3: Single Responsibility
436
+ Each module, function, and component does one thing well.
437
+ If you need "and" to describe it, split it.
438
+
439
+ ### Principle 4: Documentation as Code
440
+ Documentation lives with code.
441
+ If it's not documented, it doesn't exist.
442
+
443
+ ### Principle 5: Security by Design
444
+ Security is not an afterthought.
445
+ Every feature considers security implications from the start.
446
+
447
+ ## Technical Standards
448
+
449
+ ### Code Style
450
+ - Python: PEP 8 with type hints
451
+ - JavaScript: StandardJS
452
+ - Go: Official Go formatting
453
+
454
+ ### Testing Requirements
455
+ - Minimum 80% code coverage
456
+ - All API endpoints must have contract tests
457
+ - Critical paths require E2E tests
458
+
459
+ ### Performance Targets
460
+ - API response time: < 200ms (p95)
461
+ - Page load time: < 2 seconds
462
+ - Database queries: < 50ms
463
+
464
+ ### Security Requirements
465
+ - All data encrypted in transit (TLS 1.3+)
466
+ - Sensitive data encrypted at rest
467
+ - Authentication: OAuth 2.0 / JWT
468
+ - Authorization: RBAC with least privilege
469
+
470
+ ## Architecture Rules
471
+
472
+ ### Service Boundaries
473
+ - Services communicate only through defined APIs
474
+ - No shared databases between services
475
+ - Each service owns its data
476
+
477
+ ### Data Management
478
+ - Single source of truth for each data type
479
+ - Event sourcing for audit requirements
480
+ - CQRS where read/write patterns differ
481
+
482
+ ### Error Handling
483
+ - All errors are handled explicitly
484
+ - User-facing errors are helpful and actionable
485
+ - System errors are logged with context
486
+
487
+ ## Amendment Process
488
+
489
+ Changes to this constitution require:
490
+ 1. Documented rationale
491
+ 2. Team consensus
492
+ 3. Gradual migration plan
493
+ 4. Update to all affected documentation
494
+ """
495
+
496
+ def get_context_template(self) -> str:
497
+ """Get context template from file"""
498
+ template_path = self.resources_dir / "memory" / "context.md"
499
+ if template_path.exists():
500
+ with open(template_path, 'r', encoding='utf-8') as f:
501
+ return f.read()
502
+ # Fallback to embedded template if file not found
503
+ return """# Project Context
504
+
505
+ ## Current State
506
+ Last Updated: [AI updates this automatically]
507
+
508
+ ### Active Features
509
+ 1. **[feature-name]** (SPEC-XXX)
510
+ - Status: [Phase]
511
+ - Branch: [branch-name]
512
+ - Blockers: [None|List]
513
+
514
+ ### Recent Decisions
515
+ - [Decision with rationale]
516
+
517
+ ### Known Issues
518
+ - [Issue description]
519
+
520
+ ## Team Preferences
521
+
522
+ ### Technology Choices
523
+ - **Preferred Stack**: [Stack]
524
+ - **Testing**: [Framework]
525
+ - **CI/CD**: [Platform]
526
+ - **Deployment**: [Method]
527
+
528
+ ### Coding Patterns
529
+ - [Pattern preference]
530
+
531
+ ## Project Glossary
532
+
533
+ ### Domain Terms
534
+ - **[Term]**: [Definition]
535
+
536
+ ### Technical Terms
537
+ - **[Term]**: [Definition]
538
+ """
539
+
540
+ def get_decisions_template(self) -> str:
541
+ """Get architectural decisions template from file"""
542
+ template_path = self.resources_dir / "memory" / "decisions.md"
543
+ if template_path.exists():
544
+ with open(template_path, 'r', encoding='utf-8') as f:
545
+ return f.read()
546
+ # Fallback to embedded template if file not found
547
+ return """# Architectural Decisions
548
+
549
+ ## Decision Log
550
+
551
+ ### ADR-001: [Title]
552
+ **Date**: [DATE]
553
+ **Status**: [PROPOSED|ACCEPTED|DEPRECATED]
554
+ **Context**: [Why this decision was needed]
555
+ **Decision**: [What was decided]
556
+ **Consequences**: [What happens as a result]
557
+ **Alternatives Considered**: [Other options that were evaluated]
558
+
559
+ ---
560
+
561
+ ### ADR-002: [Title]
562
+ [Same structure as above]
563
+ """
564
+
565
+ def get_setup_script(self) -> str:
566
+ """Get pulse-init script for feature initialization from file"""
567
+ script_path = self.resources_dir / "scripts" / "pulse-init.sh"
568
+ if script_path.exists():
569
+ with open(script_path, 'r', encoding='utf-8') as f:
570
+ return f.read()
571
+ # Fallback to embedded script if file not found
572
+ return """#!/bin/bash
573
+ # SpecPulse Feature Initialization Script
574
+
575
+ set -e
576
+
577
+ # Get feature name from argument
578
+ FEATURE_NAME="$1"
579
+ if [ -z "$FEATURE_NAME" ]; then
580
+ echo "Error: Feature name required"
581
+ exit 1
582
+ fi
583
+
584
+ # Clean feature name (replace spaces with hyphens, lowercase)
585
+ CLEAN_NAME=$(echo "$FEATURE_NAME" | tr '[:upper:]' '[:lower:]' | tr ' ' '-' | tr '_' '-')
586
+
587
+ # Get next feature number
588
+ if [ -d "specs" ]; then
589
+ FEATURE_NUM=$(find specs -maxdepth 1 -type d -name "[0-9][0-9][0-9]-*" | wc -l)
590
+ FEATURE_NUM=$((FEATURE_NUM + 1))
591
+ else
592
+ FEATURE_NUM=1
593
+ fi
594
+
595
+ # Format with leading zeros
596
+ FEATURE_ID=$(printf "%03d" $FEATURE_NUM)
597
+ BRANCH_NAME="${FEATURE_ID}-${CLEAN_NAME}"
598
+
599
+ # Create directories
600
+ mkdir -p "specs/${BRANCH_NAME}"
601
+ mkdir -p "plans/${BRANCH_NAME}"
602
+ mkdir -p "tasks/${BRANCH_NAME}"
603
+
604
+ # Create feature branch if git is available
605
+ if command -v git &> /dev/null && [ -d ".git" ]; then
606
+ git checkout -b "$BRANCH_NAME" 2>/dev/null || git checkout "$BRANCH_NAME"
607
+ fi
608
+
609
+ # Output JSON result
610
+ echo "{"
611
+ echo " \\"branch_name\\": \\"$BRANCH_NAME\\","
612
+ echo " \\"feature_id\\": \\"$FEATURE_ID\\","
613
+ echo " \\"spec_dir\\": \\"specs/$BRANCH_NAME\\","
614
+ echo " \\"plan_dir\\": \\"plans/$BRANCH_NAME\\","
615
+ echo " \\"task_dir\\": \\"tasks/$BRANCH_NAME\\""
616
+ echo "}"
617
+ """
618
+
619
+ def get_spec_script(self) -> str:
620
+ """Get pulse-spec script for getting current feature context from file"""
621
+ script_path = self.resources_dir / "scripts" / "pulse-spec.sh"
622
+ if script_path.exists():
623
+ with open(script_path, 'r', encoding='utf-8') as f:
624
+ return f.read()
625
+ # Fallback to embedded script if file not found
626
+ return """#!/bin/bash
627
+ # SpecPulse Spec Context Script
628
+
629
+ # Check for --current flag
630
+ if [ "$1" == "--current" ]; then
631
+ # Find the current feature branch
632
+ if command -v git &> /dev/null && [ -d ".git" ]; then
633
+ BRANCH=$(git branch --show-current)
634
+ if [[ "$BRANCH" =~ ^[0-9]{3}-.* ]]; then
635
+ FEATURE_DIR="specs/$BRANCH"
636
+ if [ -d "$FEATURE_DIR" ]; then
637
+ echo "{"
638
+ echo " \\"branch\\": \\"$BRANCH\\","
639
+ echo " \\"spec_file\\": \\"$FEATURE_DIR/spec-001.md\\","
640
+ echo " \\"spec_dir\\": \\"$FEATURE_DIR\\""
641
+ echo "}"
642
+ exit 0
643
+ fi
644
+ fi
645
+ fi
646
+
647
+ # Fallback: find latest spec directory
648
+ LATEST=$(find specs -maxdepth 1 -type d -name "[0-9][0-9][0-9]-*" | sort -r | head -1)
649
+ if [ -n "$LATEST" ]; then
650
+ echo "{"
651
+ echo " \\"branch\\": \\"$(basename $LATEST)\\","
652
+ echo " \\"spec_file\\": \\"$LATEST/spec-001.md\\","
653
+ echo " \\"spec_dir\\": \\"$LATEST\\""
654
+ echo "}"
655
+ else
656
+ echo "{\\"error\\": \\"No active feature found\\"}"
657
+ exit 1
658
+ fi
659
+ fi
660
+ """
661
+
662
+ def get_plan_script(self) -> str:
663
+ """Get pulse-plan script for plan context from file"""
664
+ script_path = self.resources_dir / "scripts" / "pulse-plan.sh"
665
+ if script_path.exists():
666
+ with open(script_path, 'r', encoding='utf-8') as f:
667
+ return f.read()
668
+ # Fallback to embedded script if file not found
669
+ return """#!/bin/bash
670
+ # SpecPulse Plan Context Script
671
+
672
+ # Check for --current flag
673
+ if [ "$1" == "--current" ]; then
674
+ # Find the current feature branch
675
+ if command -v git &> /dev/null && [ -d ".git" ]; then
676
+ BRANCH=$(git branch --show-current)
677
+ if [[ "$BRANCH" =~ ^[0-9]{3}-.* ]]; then
678
+ SPEC_DIR="specs/$BRANCH"
679
+ PLAN_DIR="plans/$BRANCH"
680
+ if [ -d "$SPEC_DIR" ]; then
681
+ echo "{"
682
+ echo " \\"branch\\": \\"$BRANCH\\","
683
+ echo " \\"spec_file\\": \\"$SPEC_DIR/spec-001.md\\","
684
+ echo " \\"plan_file\\": \\"$PLAN_DIR/plan-001.md\\","
685
+ echo " \\"plan_dir\\": \\"$PLAN_DIR\\""
686
+ echo "}"
687
+ exit 0
688
+ fi
689
+ fi
690
+ fi
691
+
692
+ # Fallback: find latest directories
693
+ LATEST=$(find specs -maxdepth 1 -type d -name "[0-9][0-9][0-9]-*" | sort -r | head -1)
694
+ if [ -n "$LATEST" ]; then
695
+ BRANCH=$(basename "$LATEST")
696
+ echo "{"
697
+ echo " \\"branch\\": \\"$BRANCH\\","
698
+ echo " \\"spec_file\\": \\"specs/$BRANCH/spec-001.md\\","
699
+ echo " \\"plan_file\\": \\"plans/$BRANCH/plan-001.md\\","
700
+ echo " \\"plan_dir\\": \\"plans/$BRANCH\\""
701
+ echo "}"
702
+ else
703
+ echo "{\\"error\\": \\"No active feature found\\"}"
704
+ exit 1
705
+ fi
706
+ fi
707
+ """
708
+
709
+ def get_task_script(self) -> str:
710
+ """Get pulse-task script for task context from file"""
711
+ script_path = self.resources_dir / "scripts" / "pulse-task.sh"
712
+ if script_path.exists():
713
+ with open(script_path, 'r', encoding='utf-8') as f:
714
+ return f.read()
715
+ # Fallback to embedded script if file not found
716
+ return """#!/bin/bash
717
+ # SpecPulse Task Context Script
718
+
719
+ # Check for --current flag
720
+ if [ "$1" == "--current" ]; then
721
+ # Find the current feature branch
722
+ if command -v git &> /dev/null && [ -d ".git" ]; then
723
+ BRANCH=$(git branch --show-current)
724
+ if [[ "$BRANCH" =~ ^[0-9]{3}-.* ]]; then
725
+ SPEC_DIR="specs/$BRANCH"
726
+ PLAN_DIR="plans/$BRANCH"
727
+ TASK_DIR="tasks/$BRANCH"
728
+ if [ -d "$SPEC_DIR" ]; then
729
+ echo "{"
730
+ echo " \\"branch\\": \\"$BRANCH\\","
731
+ echo " \\"spec_file\\": \\"$SPEC_DIR/spec-001.md\\","
732
+ echo " \\"plan_file\\": \\"$PLAN_DIR/plan-001.md\\","
733
+ echo " \\"task_file\\": \\"$TASK_DIR/task-001.md\\","
734
+ echo " \\"task_dir\\": \\"$TASK_DIR\\""
735
+ echo "}"
736
+ exit 0
737
+ fi
738
+ fi
739
+ fi
740
+
741
+ # Fallback: find latest directories
742
+ LATEST=$(find specs -maxdepth 1 -type d -name "[0-9][0-9][0-9]-*" | sort -r | head -1)
743
+ if [ -n "$LATEST" ]; then
744
+ BRANCH=$(basename "$LATEST")
745
+ echo "{"
746
+ echo " \\"branch\\": \\"$BRANCH\\","
747
+ echo " \\"spec_file\\": \\"specs/$BRANCH/spec-001.md\\","
748
+ echo " \\"plan_file\\": \\"plans/$BRANCH/plan-001.md\\","
749
+ echo " \\"task_file\\": \\"tasks/$BRANCH/task-001.md\\","
750
+ echo " \\"task_dir\\": \\"tasks/$BRANCH\\""
751
+ echo "}"
752
+ else
753
+ echo "{\\"error\\": \\"No active feature found\\"}"
754
+ exit 1
755
+ fi
756
+ fi
757
+ """
758
+
759
+ def get_validate_script(self) -> str:
760
+ """Get validation script"""
761
+ return """#!/bin/bash
762
+ # SpecPulse Validation Script
763
+
764
+ validate_spec() {
765
+ local spec_file=$1
766
+ local errors=0
767
+
768
+ echo "Validating: $spec_file"
769
+
770
+ # Check required sections
771
+ if ! grep -q "## Requirements" $spec_file; then
772
+ echo " ❌ Missing Requirements section"
773
+ ((errors++))
774
+ fi
775
+
776
+ if ! grep -q "## User Stories" $spec_file; then
777
+ echo " Missing User Stories section"
778
+ ((errors++))
779
+ fi
780
+
781
+ if ! grep -q "## Acceptance Criteria" $spec_file; then
782
+ echo " ❌ Missing Acceptance Criteria section"
783
+ ((errors++))
784
+ fi
785
+
786
+ # Check for clarification markers
787
+ if grep -q "\\[NEEDS CLARIFICATION\\]" $spec_file; then
788
+ echo " ⚠️ Contains items needing clarification"
789
+ fi
790
+
791
+ if [ $errors -eq 0 ]; then
792
+ echo " Specification valid"
793
+ return 0
794
+ else
795
+ echo " ❌ Specification has $errors errors"
796
+ return 1
797
+ fi
798
+ }
799
+
800
+ # Main
801
+ if [ "$1" == "spec" ]; then
802
+ validate_spec $2
803
+ elif [ "$1" == "all" ]; then
804
+ for spec in specs/*/spec-001.md; do
805
+ validate_spec $spec
806
+ done
807
+ fi
808
+ """
809
+
810
+ def get_generate_script(self) -> str:
811
+ """Get generation script"""
812
+ return """#!/bin/bash
813
+ # SpecPulse Generation Script
814
+
815
+ generate_from_template() {
816
+ local template=$1
817
+ local output=$2
818
+ local feature_name=$3
819
+
820
+ # Replace placeholders
821
+ sed "s/\\[FEATURE_NAME\\]/$feature_name/g" $template > $output
822
+ sed -i "s/\\[DATE\\]/$(date +%Y-%m-%d)/g" $output
823
+ sed -i "s/\\[XXX\\]/$(printf '%03d' $RANDOM)/g" $output
824
+
825
+ echo "Generated: $output"
826
+ }
827
+
828
+ # Main
829
+ if [ "$1" == "spec" ]; then
830
+ generate_from_template templates/spec-001.md $2 $3
831
+ elif [ "$1" == "plan" ]; then
832
+ generate_from_template templates/plan-001.md $2 $3
833
+ elif [ "$1" == "task" ]; then
834
+ generate_from_template templates/task.md $2 $3
835
+ fi
836
+ """
837
+
838
+ def get_claude_instructions(self) -> str:
839
+ """Get Claude instructions"""
840
+ return """# SpecPulse Commands for Claude
841
+
842
+ You have access to SpecPulse commands for specification-driven development.
843
+
844
+ ## Available Commands
845
+
846
+ ### /sp-pulse <feature-name>
847
+ Initializes a new feature with proper structure.
848
+ - Creates feature branch
849
+ - Sets up specification directory
850
+ - Loads templates
851
+ - Updates context
852
+
853
+ ### /sp-spec create <description>
854
+ Creates a detailed specification from description.
855
+ - Use the template in templates/spec-001.md
856
+ - Mark uncertainties with [NEEDS CLARIFICATION]
857
+ - Ensure all sections are complete
858
+ - Validate against constitution
859
+
860
+ ### /sp-plan generate
861
+ Generates implementation plan from current specification.
862
+ - Read the active specification
863
+ - Create detailed phases
864
+ - Include technology decisions
865
+ - Add time estimates
866
+
867
+ ### /sp-task breakdown
868
+ Creates task list from implementation plan.
869
+ - Identify dependencies
870
+ - Mark parallel tasks with [P]
871
+ - Add time estimates
872
+ - Create critical path
873
+
874
+ ### /validate <component>
875
+ Validates specifications, plans, or project.
876
+ - Check completeness
877
+ - Verify consistency
878
+ - Ensure constitution compliance
879
+
880
+ ## Workflow
881
+
882
+ 1. User requests feature → Use `/sp-pulse`
883
+ 2. User describes requirements → Use `/sp-spec create`
884
+ 3. Specification complete → Use `/sp-plan generate`
885
+ 4. Plan approved → Use `/sp-task breakdown`
886
+ 5. Before implementation → Use `/validate all`
887
+
888
+ ## Constitution Rules
889
+
890
+ Always enforce these principles:
891
+ 1. Simplicity first
892
+ 2. Test-driven development
893
+ 3. Single responsibility
894
+ 4. Documentation as code
895
+ 5. Security by design
896
+
897
+ ## Context Management
898
+
899
+ - Read `memory/context.md` for project state
900
+ - Update context after major decisions
901
+ - Check `memory/constitution.md` for principles
902
+ - Reference previous specs for consistency
903
+
904
+ ## Templates
905
+
906
+ Always use templates from `templates/` directory:
907
+ - `spec-001.md` for specifications
908
+ - `plan-001.md` for implementation plans
909
+ - `task.md` for task lists
910
+
911
+ ## Best Practices
912
+
913
+ 1. Always validate before moving to next phase
914
+ 2. Keep specifications testable and measurable
915
+ 3. Update context.md with decisions
916
+ 4. Create atomic, focused commits
917
+ 5. Document rationale for technology choices
918
+ """
919
+
920
+ # Claude command getters
921
+ def get_claude_pulse_command(self) -> str:
922
+ """Get Claude pulse command"""
923
+ command_path = self.resources_dir / "commands" / "claude" / "pulse.md"
924
+ if command_path.exists():
925
+ with open(command_path, 'r', encoding='utf-8') as f:
926
+ return f.read()
927
+ return "# /sp-pulse command not found"
928
+
929
+ def get_claude_spec_command(self) -> str:
930
+ """Get Claude spec command"""
931
+ command_path = self.resources_dir / "commands" / "claude" / "spec-001.md"
932
+ if command_path.exists():
933
+ with open(command_path, 'r', encoding='utf-8') as f:
934
+ return f.read()
935
+ return "# /sp-spec command not found"
936
+
937
+ def get_claude_plan_command(self) -> str:
938
+ """Get Claude plan command"""
939
+ command_path = self.resources_dir / "commands" / "claude" / "plan-001.md"
940
+ if command_path.exists():
941
+ with open(command_path, 'r', encoding='utf-8') as f:
942
+ return f.read()
943
+ return "# /sp-plan command not found"
944
+
945
+ def get_claude_task_command(self) -> str:
946
+ """Get Claude task command"""
947
+ command_path = self.resources_dir / "commands" / "claude" / "task.md"
948
+ if command_path.exists():
949
+ with open(command_path, 'r', encoding='utf-8') as f:
950
+ return f.read()
951
+ return "# /sp-task command not found"
952
+
953
+ # Gemini command getters
954
+ def get_gemini_pulse_command(self) -> str:
955
+ """Get Gemini pulse command"""
956
+ command_path = self.resources_dir / "commands" / "gemini" / "pulse.toml"
957
+ if command_path.exists():
958
+ with open(command_path, 'r', encoding='utf-8') as f:
959
+ return f.read()
960
+ return "# Gemini pulse command not found"
961
+
962
+ def get_gemini_spec_command(self) -> str:
963
+ """Get Gemini spec command"""
964
+ command_path = self.resources_dir / "commands" / "gemini" / "spec.toml"
965
+ if command_path.exists():
966
+ with open(command_path, 'r', encoding='utf-8') as f:
967
+ return f.read()
968
+ return "# Gemini spec command not found"
969
+
970
+ def get_gemini_plan_command(self) -> str:
971
+ """Get Gemini plan command"""
972
+ command_path = self.resources_dir / "commands" / "gemini" / "plan.toml"
973
+ if command_path.exists():
974
+ with open(command_path, 'r', encoding='utf-8') as f:
975
+ return f.read()
976
+ return "# Gemini plan command not found"
977
+
978
+ def get_gemini_task_command(self) -> str:
979
+ """Get Gemini task command"""
980
+ command_path = self.resources_dir / "commands" / "gemini" / "task.toml"
981
+ if command_path.exists():
982
+ with open(command_path, 'r', encoding='utf-8') as f:
983
+ return f.read()
984
+ return "# Gemini task command not found"
985
+
986
+ def get_gemini_instructions(self) -> str:
987
+ """Get Gemini instructions"""
988
+ return """# SpecPulse Commands for Gemini CLI
989
+
990
+ This project uses SpecPulse for specification-driven development.
991
+
992
+ ## Command Reference
993
+
994
+ ### Initialization
995
+ ```
996
+ /sp-pulse <feature-name>
997
+ ```
998
+ Creates new feature structure and branch.
999
+
1000
+ ### Specification Creation
1001
+ ```
1002
+ /sp-spec create <description>
1003
+ ```
1004
+ Generates detailed specification from natural language.
1005
+
1006
+ Required sections:
1007
+ - Requirements (functional and non-functional)
1008
+ - User stories with acceptance criteria
1009
+ - Technical constraints
1010
+ - Dependencies
1011
+ - Risks and mitigations
1012
+
1013
+ ### Plan Generation
1014
+ ```
1015
+ /sp-plan generate [--optimize <focus>]
1016
+ ```
1017
+ Creates implementation plan from specification.
1018
+
1019
+ Optimization options:
1020
+ - performance: Speed and efficiency focus
1021
+ - security: Security-first approach
1022
+ - simplicity: Maintainable solution
1023
+ - cost: Resource optimization
1024
+
1025
+ ### Task Breakdown
1026
+ ```
1027
+ /sp-task breakdown [--parallel]
1028
+ ```
1029
+ Generates actionable task list.
1030
+
1031
+ Features:
1032
+ - Dependency detection
1033
+ - Parallel task identification
1034
+ - Time estimation
1035
+ - Critical path analysis
1036
+
1037
+ ### Validation
1038
+ ```
1039
+ /validate [all|spec|plan|constitution]
1040
+ ```
1041
+ Validates project components.
1042
+
1043
+ ## Templates Location
1044
+
1045
+ Use templates from `templates/` directory:
1046
+ - Specification: templates/spec-001.md
1047
+ - Implementation: templates/plan-001.md
1048
+ - Tasks: templates/task.md
1049
+
1050
+ ## Memory System
1051
+
1052
+ Project memory in `memory/` directory:
1053
+ - constitution.md: Immutable principles
1054
+ - context.md: Current project state
1055
+ - decisions.md: Architectural decisions
1056
+
1057
+ ## Workflow Process
1058
+
1059
+ 1. **Initialize Feature**
1060
+ - Run: `/sp-pulse feature-name`
1061
+ - Creates branch and structure
1062
+
1063
+ 2. **Create Specification**
1064
+ - Run: `/sp-spec create "description"`
1065
+ - Fill template completely
1066
+ - Mark unclear items: [NEEDS CLARIFICATION]
1067
+
1068
+ 3. **Generate Plan**
1069
+ - Run: `/sp-plan generate`
1070
+ - Choose optimization focus
1071
+ - Review technology choices
1072
+
1073
+ 4. **Create Tasks**
1074
+ - Run: `/sp-task breakdown`
1075
+ - Review dependencies
1076
+ - Check time estimates
1077
+
1078
+ 5. **Validate**
1079
+ - Run: `/validate all`
1080
+ - Fix any issues
1081
+ - Proceed to implementation
1082
+
1083
+ ## Constitution Principles
1084
+
1085
+ Enforce these rules:
1086
+ 1. Start simple, add complexity only when needed
1087
+ 2. Write tests before code
1088
+ 3. One responsibility per component
1089
+ 4. Document everything
1090
+ 5. Consider security from start
1091
+
1092
+ ## Project Structure
1093
+
1094
+ ```
1095
+ project/
1096
+ ├── specs/ # Specifications
1097
+ ├── plans/ # Implementation plans
1098
+ ├── tasks/ # Task lists
1099
+ ├── memory/ # Project memory
1100
+ ├── scripts/ # Automation
1101
+ └── templates/ # Templates
1102
+ ```
1103
+
1104
+ ## Important Notes
1105
+
1106
+ - Always update context.md after decisions
1107
+ - Validate specifications before planning
1108
+ - Use [P] marker for parallel tasks
1109
+ - Keep commits atomic and focused
1110
+ - Reference constitution for all decisions
1100
1111
  """