ima-claude 2.18.0 → 2.25.0

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 (103) hide show
  1. package/README.md +55 -9
  2. package/dist/cli.js +5 -1
  3. package/package.json +1 -1
  4. package/plugins/ima-claude/.claude-plugin/plugin.json +2 -2
  5. package/plugins/ima-claude/agents/explorer.md +29 -15
  6. package/plugins/ima-claude/agents/implementer.md +58 -13
  7. package/plugins/ima-claude/agents/memory.md +19 -19
  8. package/plugins/ima-claude/agents/reviewer.md +56 -34
  9. package/plugins/ima-claude/agents/tester.md +59 -16
  10. package/plugins/ima-claude/agents/wp-developer.md +66 -21
  11. package/plugins/ima-claude/hooks/bootstrap.sh +42 -44
  12. package/plugins/ima-claude/hooks/prompt_coach_digest.md +14 -17
  13. package/plugins/ima-claude/hooks/prompt_coach_system.md +10 -12
  14. package/plugins/ima-claude/personalities/README.md +17 -6
  15. package/plugins/ima-claude/personalities/enable-efficient.md +61 -0
  16. package/plugins/ima-claude/personalities/enable-terse.md +71 -0
  17. package/plugins/ima-claude/skills/agentic-workflows/SKILL.md +97 -0
  18. package/plugins/ima-claude/skills/agentic-workflows/references/phases/deliver.md +181 -0
  19. package/plugins/ima-claude/skills/agentic-workflows/references/phases/draft.md +99 -0
  20. package/plugins/ima-claude/skills/agentic-workflows/references/phases/gather.md +130 -0
  21. package/plugins/ima-claude/skills/agentic-workflows/references/phases/outline.md +106 -0
  22. package/plugins/ima-claude/skills/agentic-workflows/references/phases/review.md +137 -0
  23. package/plugins/ima-claude/skills/agentic-workflows/references/standards/draft-format.md +159 -0
  24. package/plugins/ima-claude/skills/agentic-workflows/references/standards/editorial-standards.md +160 -0
  25. package/plugins/ima-claude/skills/agentic-workflows/references/standards/outline-format.md +110 -0
  26. package/plugins/ima-claude/skills/agentic-workflows/references/templates/avada-construction-guide.md +263 -0
  27. package/plugins/ima-claude/skills/agentic-workflows/references/templates/avada-webinar-example.txt +275 -0
  28. package/plugins/ima-claude/skills/agentic-workflows/references/templates/cta-block-catalog.md +169 -0
  29. package/plugins/ima-claude/skills/agentic-workflows/references/templates/espo-email-preparation.md +241 -0
  30. package/plugins/ima-claude/skills/agentic-workflows/references/templates/webinar-recap-email-espo.html +339 -0
  31. package/plugins/ima-claude/skills/agentic-workflows/references/templates/webinar-reminder-email-espo.html +458 -0
  32. package/plugins/ima-claude/skills/agentic-workflows/references/workflows/editorial/webinar-summary.md +81 -0
  33. package/plugins/ima-claude/skills/architect/SKILL.md +54 -168
  34. package/plugins/ima-claude/skills/compound-bridge/SKILL.md +41 -94
  35. package/plugins/ima-claude/skills/design-to-code/SKILL.md +91 -0
  36. package/plugins/ima-claude/skills/design-to-code/references/guardrails.md +46 -0
  37. package/plugins/ima-claude/skills/design-to-code/references/phase-a-design-to-prompt.md +141 -0
  38. package/plugins/ima-claude/skills/design-to-code/references/phase-b-prompt-to-code.md +155 -0
  39. package/plugins/ima-claude/skills/design-to-code/references/prompt-template.md +95 -0
  40. package/plugins/ima-claude/skills/discourse/SKILL.md +79 -194
  41. package/plugins/ima-claude/skills/discourse-admin/SKILL.md +41 -103
  42. package/plugins/ima-claude/skills/docs-organize/SKILL.md +63 -203
  43. package/plugins/ima-claude/skills/ember-discourse/SKILL.md +90 -200
  44. package/plugins/ima-claude/skills/espocrm/SKILL.md +14 -23
  45. package/plugins/ima-claude/skills/espocrm-api/SKILL.md +79 -192
  46. package/plugins/ima-claude/skills/functional-programmer/SKILL.md +33 -237
  47. package/plugins/ima-claude/skills/gh-cli/SKILL.md +26 -65
  48. package/plugins/ima-claude/skills/ima-bootstrap/SKILL.md +71 -104
  49. package/plugins/ima-claude/skills/ima-bootstrap/references/ima-brand.md +32 -22
  50. package/plugins/ima-claude/skills/ima-brand/SKILL.md +18 -23
  51. package/plugins/ima-claude/skills/ima-copywriting/SKILL.md +68 -179
  52. package/plugins/ima-claude/skills/ima-doc2pdf/SKILL.md +32 -102
  53. package/plugins/ima-claude/skills/ima-editorial-scorecard/SKILL.md +38 -63
  54. package/plugins/ima-claude/skills/ima-editorial-workflow/SKILL.md +69 -114
  55. package/plugins/ima-claude/skills/ima-email-creator/SKILL.md +16 -22
  56. package/plugins/ima-claude/skills/ima-forms-expert/SKILL.md +21 -37
  57. package/plugins/ima-claude/skills/jira-checkpoint/SKILL.md +39 -120
  58. package/plugins/ima-claude/skills/jquery/SKILL.md +107 -233
  59. package/plugins/ima-claude/skills/js-fp/SKILL.md +75 -296
  60. package/plugins/ima-claude/skills/js-fp-api/SKILL.md +52 -162
  61. package/plugins/ima-claude/skills/js-fp-react/SKILL.md +47 -270
  62. package/plugins/ima-claude/skills/js-fp-vue/SKILL.md +55 -209
  63. package/plugins/ima-claude/skills/js-fp-wordpress/SKILL.md +59 -204
  64. package/plugins/ima-claude/skills/livecanvas/SKILL.md +19 -32
  65. package/plugins/ima-claude/skills/mcp-atlassian/SKILL.md +146 -136
  66. package/plugins/ima-claude/skills/mcp-atlassian/references/direct-api-attachments.md +115 -0
  67. package/plugins/ima-claude/skills/mcp-atlassian/references/direct-api-auth.md +103 -0
  68. package/plugins/ima-claude/skills/mcp-atlassian/references/direct-api-bulk.md +149 -0
  69. package/plugins/ima-claude/skills/mcp-atlassian/references/direct-api-misc.md +195 -0
  70. package/plugins/ima-claude/skills/mcp-atlassian/references/direct-api-sprints.md +158 -0
  71. package/plugins/ima-claude/skills/mcp-context7/SKILL.md +32 -64
  72. package/plugins/ima-claude/skills/mcp-gitea/SKILL.md +98 -188
  73. package/plugins/ima-claude/skills/mcp-github/SKILL.md +60 -124
  74. package/plugins/ima-claude/skills/mcp-memory/SKILL.md +1 -177
  75. package/plugins/ima-claude/skills/mcp-qdrant/SKILL.md +58 -115
  76. package/plugins/ima-claude/skills/mcp-sequential/SKILL.md +32 -87
  77. package/plugins/ima-claude/skills/mcp-serena/SKILL.md +54 -80
  78. package/plugins/ima-claude/skills/mcp-tavily/SKILL.md +40 -63
  79. package/plugins/ima-claude/skills/mcp-vestige/SKILL.md +75 -116
  80. package/plugins/ima-claude/skills/php-authnet/SKILL.md +32 -65
  81. package/plugins/ima-claude/skills/php-fp/SKILL.md +50 -129
  82. package/plugins/ima-claude/skills/php-fp-wordpress/SKILL.md +25 -73
  83. package/plugins/ima-claude/skills/phpunit-wp/SKILL.md +103 -463
  84. package/plugins/ima-claude/skills/playwright/SKILL.md +69 -220
  85. package/plugins/ima-claude/skills/prompt-starter/SKILL.md +35 -82
  86. package/plugins/ima-claude/skills/prompt-starter/references/code-review.md +38 -0
  87. package/plugins/ima-claude/skills/py-fp/SKILL.md +78 -384
  88. package/plugins/ima-claude/skills/quasar-fp/SKILL.md +54 -255
  89. package/plugins/ima-claude/skills/quickstart/SKILL.md +7 -11
  90. package/plugins/ima-claude/skills/rails/SKILL.md +63 -184
  91. package/plugins/ima-claude/skills/resume-session/SKILL.md +14 -35
  92. package/plugins/ima-claude/skills/rg/SKILL.md +61 -146
  93. package/plugins/ima-claude/skills/ruby-fp/SKILL.md +66 -163
  94. package/plugins/ima-claude/skills/save-session/SKILL.md +10 -39
  95. package/plugins/ima-claude/skills/scorecard/SKILL.md +24 -38
  96. package/plugins/ima-claude/skills/skill-analyzer/SKILL.md +42 -71
  97. package/plugins/ima-claude/skills/skill-creator/SKILL.md +79 -250
  98. package/plugins/ima-claude/skills/task-master/SKILL.md +11 -31
  99. package/plugins/ima-claude/skills/task-planner/SKILL.md +44 -153
  100. package/plugins/ima-claude/skills/task-runner/SKILL.md +61 -143
  101. package/plugins/ima-claude/skills/unit-testing/SKILL.md +59 -134
  102. package/plugins/ima-claude/skills/wp-ddev/SKILL.md +38 -120
  103. package/plugins/ima-claude/skills/wp-local/SKILL.md +26 -108
@@ -5,84 +5,59 @@ description: "Core FP principles with anti-over-engineering focus - Simple > Com
5
5
 
6
6
  # PHP Functional Programming
7
7
 
8
- Core functional programming principles for PHP with anti-over-engineering enforcement. This skill provides error-preventing essentials and references to deep-dive content.
8
+ ## Anti-Over-Engineering (PRIMARY)
9
9
 
10
- ## When to Use This Skill
10
+ "Simple > Complex | Evidence > Assumptions"
11
11
 
12
- - Implementing pure, testable PHP functions
13
- - Need FP architectural guidance for PHP
14
- - Preventing over-engineering and custom FP utility creation
15
- - Comprehensive testing strategies with PHPUnit
16
- - Evidence-based performance optimization
17
-
18
- ## CRITICAL: Anti-Over-Engineering (PRIMARY FOCUS)
19
-
20
- **Core Principle**: "Simple > Complex | Evidence > Assumptions"
21
-
22
- > **Clarification**: This skill prevents CREATING custom FP utility functions (pipe, compose, curry) to make PHP "feel" like Haskell. Using established libraries (Carbon, Collections, etc.) is perfectly fine. FP is a mindset—pure functions, immutability, composition—not a rigid API signature.
23
-
24
- ### Don't Create Custom FP Utilities
12
+ Don't CREATE custom FP utilities (pipe, compose, curry) to make PHP feel like Haskell. Using established libraries (Carbon, Collections) is fine. FP is a mindset — pure functions, immutability, composition — not an API signature.
25
13
 
26
14
  ```php
27
15
  <?php
28
- // DON'T CREATE: pipe() utility
16
+ // DON'T: pipe() utility
29
17
  function pipe(...$functions) {
30
18
  return fn($value) => array_reduce($functions, fn($carry, $fn) => $fn($carry), $value);
31
19
  }
32
20
 
33
- // INSTEAD: Native early returns
21
+ // DO: native early returns
34
22
  function validateUser(array $userData): array {
35
23
  $requiredCheck = validateRequired(['email', 'name'], $userData);
36
24
  if (!$requiredCheck['valid']) return $requiredCheck;
37
25
  return validateEmail($userData);
38
26
  }
39
27
 
40
- // DON'T CREATE: curry() utility
41
- // INSTEAD: Native closures
28
+ // DON'T: curry() utility
29
+ // DO: native closures
42
30
  function createValidator(array $rules): callable {
43
31
  return fn($value): array => ['valid' => empty(array_filter($rules, fn($r) => !$r['validator']($value)))];
44
32
  }
45
33
 
46
- // DON'T CREATE: Complex monad implementations
47
- // INSTEAD: Simple result arrays
34
+ // DON'T: complex monad implementations
35
+ // DO: simple result arrays
48
36
  function divide(float $a, float $b): array {
49
37
  return $b === 0.0 ? ['success' => false, 'error' => 'Division by zero'] : ['success' => true, 'data' => $a / $b];
50
38
  }
51
39
  ```
52
40
 
53
- ### The 4-Question Quality Framework
54
-
55
- Before extracting or abstracting, ask:
56
-
57
- 1. **"Can this be pure?"** - Separate business logic from side effects
58
- 2. **"Can this use native patterns?"** - Avoid creating custom FP utilities, use PHP features
59
- 3. **"Can this be simplified?"** - Choose simple solution over complex abstraction
60
- 4. **"Is this complexity justified?"** - Evidence-based complexity decisions
41
+ ### 4-Question Quality Framework
61
42
 
62
- ### When NOT to Extract: WordPress Example
43
+ Before extracting or abstracting:
63
44
 
64
- **Context**: CRMAPI class sends webhook data via HTTP POST.
65
-
66
- **Analysis**: Applied 4-question framework - NO pure function extraction needed.
67
-
68
- - `sanitize_data()` uses `sanitize_text_field()` which applies WordPress filters - NOT PURE
69
- - `send_api_request()` uses WordPress HTTP API - NATIVE PATTERNS ALREADY
70
- - Current structure: 239 lines, ~35 lines of logic - ALREADY SIMPLE
71
- - Extraction would add indirection without benefits - NOT JUSTIFIED
72
-
73
- **Result**: Grade B+ (Appropriate WordPress Wrapper). Don't extract pure functions when WordPress integration IS the business logic.
45
+ 1. **"Can this be pure?"** separate business logic from side effects
46
+ 2. **"Can this use native patterns?"** — avoid custom FP utilities
47
+ 3. **"Can this be simplified?"** simple > complex
48
+ 4. **"Is this complexity justified?"** — evidence required
74
49
 
75
50
  ### Context-Appropriate Complexity
76
51
 
77
52
  ```php
78
53
  <?php
79
- // CLI Script: Simple and direct
54
+ // CLI Script: direct
80
55
  function processFile(string $filePath): array {
81
56
  $data = file_get_contents($filePath);
82
57
  return array_map('strtoupper', array_filter(explode("\n", $data), fn($l) => trim($l) !== ''));
83
58
  }
84
59
 
85
- // Production Service: Appropriate error handling
60
+ // Production Service: appropriate error handling + logging
86
61
  function processFile(string $filePath, LoggerInterface $logger): array {
87
62
  try {
88
63
  if (!file_exists($filePath)) throw new InvalidArgumentException("File not found: {$filePath}");
@@ -96,20 +71,18 @@ function processFile(string $filePath, LoggerInterface $logger): array {
96
71
  }
97
72
  ```
98
73
 
99
- ## Core FP Patterns (Quick Reference)
74
+ ## Core Patterns
100
75
 
101
- ### 1. Purity and Side Effect Isolation
76
+ ### Purity + Side Effect Isolation
102
77
 
103
78
  ```php
104
79
  <?php
105
80
  declare(strict_types=1);
106
81
 
107
- // PURE: business logic
108
82
  function calculateTotal(array $items): float {
109
83
  return array_reduce($items, fn($sum, $item) => $sum + $item['price'], 0.0);
110
84
  }
111
85
 
112
- // ISOLATED: side effects separate
113
86
  function logAndCalculate(array $items, LoggerInterface $logger): float {
114
87
  $total = calculateTotal($items);
115
88
  $logger->info("Total: {$total}");
@@ -117,18 +90,16 @@ function logAndCalculate(array $items, LoggerInterface $logger): float {
117
90
  }
118
91
  ```
119
92
 
120
- ### 2. Composition Over Inheritance
93
+ ### Composition Over Inheritance
121
94
 
122
95
  ```php
123
96
  <?php
124
- // Simple validators that compose
125
97
  function validateRequired($value): bool { return $value !== null && $value !== ''; }
126
98
  function validateEmail(string $value): bool { return filter_var($value, FILTER_VALIDATE_EMAIL) !== false; }
127
99
  function validateLength(int $min, int $max): callable {
128
100
  return fn(string $value): bool => strlen($value) >= $min && strlen($value) <= $max;
129
101
  }
130
102
 
131
- // Composition without utilities
132
103
  function validateUserEmail(string $email): array {
133
104
  if (!validateRequired($email)) return ['valid' => false, 'error' => 'Required'];
134
105
  if (!validateEmail($email)) return ['valid' => false, 'error' => 'Invalid email'];
@@ -137,16 +108,14 @@ function validateUserEmail(string $email): array {
137
108
  }
138
109
  ```
139
110
 
140
- ### 3. Dependency Injection
111
+ ### Dependency Injection
141
112
 
142
113
  ```php
143
114
  <?php
144
- // Explicit dependencies, fully testable
145
115
  function saveUser(array $userData, PasswordHasherInterface $hasher, DatabaseInterface $db): array {
146
116
  return $db->save(['name' => $userData['name'], 'password' => $hasher->hash($userData['password'])]);
147
117
  }
148
118
 
149
- // Service with constructor DI
150
119
  class UserService {
151
120
  public function __construct(
152
121
  private readonly PasswordHasherInterface $hasher,
@@ -159,11 +128,10 @@ class UserService {
159
128
  }
160
129
  ```
161
130
 
162
- ### 4. Immutability
131
+ ### Immutability
163
132
 
164
133
  ```php
165
134
  <?php
166
- // Always return new arrays
167
135
  function updateUserSettings(array $user, array $settings): array {
168
136
  return [...$user, 'settings' => array_merge($user['settings'] ?? [], $settings), 'updated_at' => time()];
169
137
  }
@@ -175,15 +143,12 @@ function updateItem(array $items, int $id, array $updates): array {
175
143
  }
176
144
  ```
177
145
 
178
- ## PHP-Specific Patterns
179
-
180
- ### Native Array Functions + Strict Types (MANDATORY)
146
+ ## PHP-Specific: Native Array Functions + Strict Types (MANDATORY)
181
147
 
182
148
  ```php
183
149
  <?php
184
150
  declare(strict_types=1);
185
151
 
186
- // Native array methods over loops
187
152
  function processUsers(array $users): array {
188
153
  return array_slice(
189
154
  array_map(fn($u) => [...$u, 'display_name' => "{$u['first_name']} {$u['last_name']}"],
@@ -192,7 +157,7 @@ function processUsers(array $users): array {
192
157
  );
193
158
  }
194
159
 
195
- // Match expressions (PHP 8.0+)
160
+ // match over switch (PHP 8.0+)
196
161
  function getTierDiscount(string $tier): float {
197
162
  return match($tier) {
198
163
  'bronze' => 0.05, 'silver' => 0.10, 'gold' => 0.15, 'platinum' => 0.20, default => 0.0
@@ -209,12 +174,11 @@ function processResult(array|false $result): array {
209
174
 
210
175
  ```php
211
176
  <?php
212
- // Standard result shape
213
177
  function createResult($data = null, ?string $error = null): array {
214
178
  return $error !== null ? ['success' => false, 'error' => $error] : ['success' => true, 'data' => $data];
215
179
  }
216
180
 
217
- // Chain results with early return
181
+ // Chain with early return
218
182
  function calculate(float $a, float $b, float $c): array {
219
183
  $r1 = divide($a, $b);
220
184
  if (!$r1['success']) return $r1;
@@ -222,20 +186,16 @@ function calculate(float $a, float $b, float $c): array {
222
186
  }
223
187
  ```
224
188
 
225
- > **Deep dive**: See `references/core-principles.md` for complete Result Type patterns and error handling strategies.
226
-
227
- ## Testing Essentials
189
+ ## Testing
228
190
 
229
- Pure functions enable testing ALL edge cases systematically.
191
+ Pure functions enable systematic edge-case coverage.
230
192
 
231
193
  ```php
232
194
  <?php
233
195
  use PHPUnit\Framework\TestCase;
234
196
 
235
197
  class CalculatorTest extends TestCase {
236
- /**
237
- * @dataProvider discountProvider
238
- */
198
+ /** @dataProvider discountProvider */
239
199
  public function testCalculateDiscount(float $price, float $rate, float $expected): void {
240
200
  $this->assertEquals($expected, calculateDiscount($price, $rate));
241
201
  }
@@ -243,26 +203,22 @@ class CalculatorTest extends TestCase {
243
203
  public function discountProvider(): array {
244
204
  return [
245
205
  'standard' => [100.0, 0.1, 90.0],
246
- 'zero' => [100.0, 0.0, 100.0],
247
- 'full' => [100.0, 1.0, 0.0],
206
+ 'zero' => [100.0, 0.0, 100.0],
207
+ 'full' => [100.0, 1.0, 0.0],
248
208
  ];
249
209
  }
250
210
  }
251
211
  ```
252
212
 
253
- > **Deep dive**: See `references/testing-patterns.md` for comprehensive PHPUnit strategies, edge case patterns, mocking, and test organization.
213
+ ## Performance: Configuration Pre-Compilation (Evidence-Based)
254
214
 
255
- ## Performance Patterns (Evidence-Based)
256
-
257
- Optimize only when needed with evidence. Key pattern: **Configuration Pre-Compilation**.
215
+ Optimize only with evidence. Key pattern: pre-compile config once, execute linearly.
258
216
 
259
217
  ```php
260
218
  <?php
261
- // Problem: O(records x config) - config accessed every iteration
262
- // Solution: Pre-compile configuration once
263
-
219
+ // Problem: O(records × config) config accessed every iteration
220
+ // Solution: pre-compile once
264
221
  function createRecordProcessor(array $schema): callable {
265
- // Setup once
266
222
  $fieldProcessors = array_map(fn($f) => fn($v) => transformField($v, $f['type']), $schema['fields']);
267
223
 
268
224
  return function(array $record) use ($schema, $fieldProcessors): array {
@@ -274,60 +230,25 @@ function createRecordProcessor(array $schema): callable {
274
230
  };
275
231
  }
276
232
 
277
- $processor = createRecordProcessor($schema); // Setup phase
278
- $results = array_map($processor, $records); // Linear execution
233
+ $processor = createRecordProcessor($schema); // setup once
234
+ $results = array_map($processor, $records); // linear execution
279
235
  ```
280
236
 
281
- **Real-world result**: Email validation in ima-espo achieved 2-5x speedup with function factory pattern. 130 tests, 236 assertions, <30ms total.
282
-
283
- ## Quality Gates Checklist
284
-
285
- Before implementation:
286
-
287
- 1. **"Can this be pure?"** - Separate business logic from side effects
288
- 2. **"Can this use native patterns?"** - Avoid creating custom FP utilities
289
- 3. **"Can this be simplified?"** - Simple > complex
290
- 4. **"Is this complexity justified?"** - Evidence required
291
- 5. **"Is this testable?"** - Pure functions enable comprehensive testing
292
- 6. **"Are strict types used?"** - `declare(strict_types=1)` at file top
293
-
294
- ## When to Load Reference Files
295
-
296
- ### Deep Principles and Explanations
297
- **File**: `references/core-principles.md`
298
- **Load when**:
299
- - Learning mode or explaining WHY behind patterns
300
- - Making architectural decisions
301
- - Need complete Result Type patterns
302
- - Anti-pattern recognition details
303
- - Cross-pattern comparisons
304
-
305
- ### Testing Methodology
306
- **File**: `references/testing-patterns.md`
307
- **Load when**:
308
- - Building comprehensive test suites
309
- - Improving test coverage
310
- - Edge case analysis and boundary testing
311
- - Setting up mocking strategies
312
- - Performance testing pure functions
313
-
314
- ### Working Examples
315
- **Directory**: `examples/`
316
- **Load when**:
317
- - Need complete working code
318
- - Integration examples
319
- - Learning implementation patterns
320
-
321
- ## Integration with Domain Skills
322
-
323
- This core skill provides the foundation for:
237
+ Real result: ima-espo email validation — 2-5x speedup, 130 tests, 236 assertions, <30ms total.
324
238
 
325
- - **php-fp-wordpress**: WordPress patterns with FP principles
326
- - **php-fp-laravel**: Laravel patterns with FP principles (future)
327
- - **php-fp-symfony**: Symfony patterns with FP principles (future)
239
+ ## Quality Gates
328
240
 
329
- Each domain skill references this core and adds domain-specific patterns.
241
+ 1. Pure? business logic separated from side effects
242
+ 2. Native? — no custom FP utilities
243
+ 3. Simple? — simple > complex
244
+ 4. Justified? — evidence for complexity
245
+ 5. Testable? — pure functions have tests
246
+ 6. Strict types? — `declare(strict_types=1)` at file top
330
247
 
331
- ## Philosophy
248
+ ## Reference Files
332
249
 
333
- *"Pure functions, native PHP patterns, strict types, appropriate complexity, and comprehensive testing for maintainable, predictable code that respects the language and solves real problems simply."*
250
+ | File | Load When |
251
+ |------|-----------|
252
+ | `references/core-principles.md` | Architectural decisions, full Result Type patterns, anti-pattern recognition |
253
+ | `references/testing-patterns.md` | Comprehensive test suites, edge cases, mocking, performance testing |
254
+ | `examples/` | Complete working code, integration examples |
@@ -5,28 +5,13 @@ description: "Security-first WordPress development with PHP FP principles - pure
5
5
 
6
6
  # PHP FP - WordPress
7
7
 
8
- Security-first WordPress development combining PHP functional programming principles with mandatory WordPress security practices.
8
+ Security-first WordPress development: pure functions for business logic, WordPress wrappers with mandatory security.
9
9
 
10
- ## When to Use This Skill
11
-
12
- - Building WordPress plugins or themes
13
- - Need security-first development practices
14
- - Implementing pure business logic with WordPress integration
15
- - Testing WordPress functionality
16
-
17
- ## Core Philosophy
18
-
19
- **Security practices prevent vulnerabilities, not architectural patterns.**
20
-
21
- Hybrid approach:
22
- 1. **Pure functions** for business logic (testable, no WordPress deps)
23
- 2. **WordPress wrappers** with mandatory security (capability, nonce, sanitize, escape, prepare)
24
-
25
- **Foundation**: Reference `../php-fp/SKILL.md` for PHP FP core principles.
10
+ **Foundation**: `../php-fp/SKILL.md` for PHP FP core.
26
11
 
27
12
  ## The 5 Non-Negotiable Security Practices
28
13
 
29
- **Evidence**: Analysis of 7,966 vulnerabilities (2024) shows these prevent 95%+ of WordPress plugin vulnerabilities.
14
+ Evidence: 7,966 vulnerabilities (2024) these prevent 95%+ of WordPress plugin vulnerabilities.
30
15
 
31
16
  | Practice | Prevents | Rule |
32
17
  |----------|----------|------|
@@ -36,18 +21,20 @@ Hybrid approach:
36
21
  | **Output Escaping** | XSS | Escape ALL output by context |
37
22
  | **Prepared Statements** | SQL injection | `$wpdb->prepare()` for ALL queries |
38
23
 
39
- ### Quick Reference: Security Functions
24
+ ### Security Function Reference
40
25
 
41
26
  **Sanitization (Input)**:
27
+
42
28
  | Function | Use For |
43
29
  |----------|---------|
44
30
  | `sanitize_text_field()` | Plain text |
45
31
  | `sanitize_email()` | Email addresses |
46
32
  | `absint()` | Positive integers |
47
33
  | `wp_kses_post()` | HTML content |
48
- | `esc_url_raw()` | URLs (for storage) |
34
+ | `esc_url_raw()` | URLs (storage) |
49
35
 
50
36
  **Escaping (Output)**:
37
+
51
38
  | Function | Context |
52
39
  |----------|---------|
53
40
  | `esc_html()` | HTML body |
@@ -60,37 +47,30 @@ Hybrid approach:
60
47
  ```php
61
48
  <?php
62
49
  add_action('wp_ajax_my_action', function() {
63
- // 1. Capability check
64
50
  if (!current_user_can('edit_posts')) {
65
51
  wp_send_json_error('Unauthorized', 403);
66
52
  }
67
53
 
68
- // 2. Nonce verification
69
54
  check_ajax_referer('my_action_nonce', 'nonce');
70
55
 
71
- // 3. Sanitize input
72
- $id = absint($_POST['id']);
56
+ $id = absint($_POST['id']);
73
57
  $name = sanitize_text_field($_POST['name']);
74
58
 
75
- // 4. Use prepared statement
76
59
  global $wpdb;
77
60
  $result = $wpdb->get_row($wpdb->prepare(
78
61
  "SELECT * FROM {$wpdb->prefix}my_table WHERE id = %d",
79
62
  $id
80
63
  ));
81
64
 
82
- // 5. Escape output
83
65
  wp_send_json_success(['name' => esc_html($result->name)]);
84
66
  });
85
67
  ```
86
68
 
87
69
  ## Pure Logic + WordPress Wrapper Pattern
88
70
 
89
- **Separate testable business logic from WordPress integration.**
90
-
91
71
  ```php
92
72
  <?php
93
- // PURE: Zero WordPress dependencies, fully testable
73
+ // PURE: zero WordPress dependencies, fully testable
94
74
  namespace MyPlugin\Pure;
95
75
 
96
76
  function calculate_discount(float $price, string $tier): float {
@@ -103,7 +83,6 @@ namespace MyPlugin;
103
83
 
104
84
  add_filter('product_price', function($price) {
105
85
  if (!is_user_logged_in()) return $price;
106
-
107
86
  $tier = get_user_meta(get_current_user_id(), 'tier', true);
108
87
  return Pure\calculate_discount($price, $tier);
109
88
  });
@@ -111,7 +90,7 @@ add_filter('product_price', function($price) {
111
90
 
112
91
  ## Inter-Plugin Communication: Hooks Only
113
92
 
114
- **Rule**: ALL cross-plugin calls use WordPress hooks. NEVER `function_exists()`.
93
+ ALL cross-plugin calls use WordPress hooks. NEVER `function_exists()`.
115
94
 
116
95
  Hooks are safe no-ops — if nobody listens, nothing happens. `function_exists()` is tight coupling disguised as loose coupling.
117
96
 
@@ -125,21 +104,20 @@ if (function_exists('ima_discourse_refresh_user_meta')) {
125
104
  // GOOD — fire-and-forget side effect
126
105
  do_action('ima_discourse_refresh_user_meta', $user_id);
127
106
 
128
- // GOOD — transform with safe default (function composition via WP)
107
+ // GOOD — transform with safe default
129
108
  $result = apply_filters('ima_membership_cancel_subscription', ['success' => true], $user_id, $sub_id);
130
109
  ```
131
110
 
132
- **Actions** (`do_action`): Side effects — "something happened, react if you care."
133
- **Filters** (`apply_filters`): Data transformation — chained function composition with a default return.
111
+ - **Actions** (`do_action`): side effects — "something happened, react if you care"
112
+ - **Filters** (`apply_filters`): data transformation — chained composition with default return
134
113
 
135
- The handler registers itself:
136
114
  ```php
137
115
  <?php
138
- // ima-discourse registers onceor doesn't. Either way, callers don't crash.
116
+ // Handler registers itselfcallers never crash if plugin is absent
139
117
  add_action('ima_discourse_refresh_user_meta', 'ima_discourse_refresh_user_meta', 10, 1);
140
118
  ```
141
119
 
142
- **When `function_exists()` is acceptable**: Internal guard clauses within a single plugin checking if its own functions are loaded, or checking PHP extensions (`function_exists('sodium_crypto_secretbox')`).
120
+ `function_exists()` is acceptable only for internal guards within a single plugin, or checking PHP extensions (`function_exists('sodium_crypto_secretbox')`).
143
121
 
144
122
  ## Plugin Complexity Guide
145
123
 
@@ -149,7 +127,7 @@ add_action('ima_discourse_refresh_user_meta', 'ima_discourse_refresh_user_meta',
149
127
  | Medium | 500-2000 | Classes + pure functions |
150
128
  | Complex | 2000+ | DI Container + Services |
151
129
 
152
- **Rule**: Start simple, add complexity only when needed.
130
+ Start simple, add complexity only when needed.
153
131
 
154
132
  ## File Organization
155
133
 
@@ -165,7 +143,7 @@ my-plugin/
165
143
  └── integration/ # WordPress tests
166
144
  ```
167
145
 
168
- ## Security Checklist
146
+ ## Quality Gates
169
147
 
170
148
  - [ ] Capability checks on all privileged operations
171
149
  - [ ] Nonces on all form/AJAX submissions
@@ -176,41 +154,15 @@ my-plugin/
176
154
  - [ ] No hardcoded credentials
177
155
  - [ ] Cross-plugin calls use hooks, not `function_exists()`
178
156
 
179
- ## Quality Gates
180
-
181
- 1. **Security**: All 5 mandatory practices implemented?
182
- 2. **Pure logic**: Business logic separated from WordPress?
183
- 3. **Testability**: Pure functions have unit tests?
184
- 4. **Complexity**: Architecture matches plugin size?
185
-
186
- ## When to Load Reference Files
187
-
188
- ### Security Deep-Dive
189
- **File**: [`references/security-examples.md`](references/security-examples.md)
190
- **Load when**: Need detailed security patterns, vulnerable vs. safe comparisons
191
- **Contains**: Full examples for all 5 practices, security function reference tables
192
-
193
- ### FP Patterns
194
- **File**: [`references/fp-patterns.md`](references/fp-patterns.md)
195
- **Load when**: Implementing pure logic + wrapper pattern, function factories
196
- **Contains**: Complete membership system example, production email validator example
197
-
198
- ### Plugin Architecture
199
- **File**: [`references/plugin-architecture.md`](references/plugin-architecture.md)
200
- **Load when**: Deciding plugin structure, implementing DI container
201
- **Contains**: Simple/medium/complex plugin patterns, file organization examples
202
-
203
- ### Testing Strategy
204
- **File**: [`references/testing-strategy.md`](references/testing-strategy.md)
205
- **Load when**: Setting up tests, writing security tests
206
- **Contains**: Unit/integration test examples, minimal mock bootstrap, security test patterns
207
-
208
- ## Success Metrics
157
+ ## Reference Files
209
158
 
210
- - **Security**: Zero vulnerabilities from missing practices
211
- - **Testability**: 95%+ coverage for pure functions
212
- - **Maintainability**: Clear separation of concerns
159
+ | File | Load When |
160
+ |------|-----------|
161
+ | `references/security-examples.md` | Detailed security patterns, vulnerable vs. safe comparisons |
162
+ | `references/fp-patterns.md` | Pure logic + wrapper pattern, function factories, production examples |
163
+ | `references/plugin-architecture.md` | Plugin structure decisions, DI container implementation |
164
+ | `references/testing-strategy.md` | Unit/integration tests, security tests, minimal mock bootstrap |
213
165
 
214
166
  ---
215
167
 
216
- **Evidence Base**: Analysis of 7,966 WordPress vulnerabilities (2024), WordPress Core Team standards, Wordfence/Patchstack research.
168
+ Evidence: 7,966 WordPress vulnerabilities (2024), WordPress Core Team standards, Wordfence/Patchstack research.