vibes-plug 1.0.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 (141) hide show
  1. package/.github/ISSUE_TEMPLATE/feature_request.md +20 -0
  2. package/BLUEPRINT.md +125 -0
  3. package/CHANGELOG.md +195 -0
  4. package/CONTRIBUTING.md +199 -0
  5. package/LICENSE +21 -0
  6. package/README.md +263 -0
  7. package/SECURITY.md +21 -0
  8. package/banner.png +0 -0
  9. package/package.json +25 -0
  10. package/plugin.json +8 -0
  11. package/scripts/update_skills.js +75 -0
  12. package/skills/ai-llm-integration-expert/SKILL.md +162 -0
  13. package/skills/api-design-expert/SKILL.md +310 -0
  14. package/skills/app-analyzer-optimizer/SKILL.md +189 -0
  15. package/skills/asisten_ramah/SKILL.md +41 -0
  16. package/skills/authentication-identity-expert/SKILL.md +45 -0
  17. package/skills/auto-doc-updater/SKILL.md +204 -0
  18. package/skills/bootstrap-to-modern/SKILL.md +87 -0
  19. package/skills/brainstorming/SKILL.md +353 -0
  20. package/skills/bun-runtime-expert/SKILL.md +211 -0
  21. package/skills/ci-cd-devops-architect/SKILL.md +45 -0
  22. package/skills/cloud-hosting-expert/SKILL.md +244 -0
  23. package/skills/coderabbit/SKILL.md +192 -0
  24. package/skills/data-telemetry-expert/SKILL.md +213 -0
  25. package/skills/database-orm-expert/SKILL.md +294 -0
  26. package/skills/design-system-architect/SKILL.md +243 -0
  27. package/skills/e2e-testing-expert/SKILL.md +315 -0
  28. package/skills/event-driven-architect/SKILL.md +81 -0
  29. package/skills/firebase-security-expert/SKILL.md +195 -0
  30. package/skills/fullstack-expert/SKILL.md +202 -0
  31. package/skills/fullstack-expert/references/api_design_guide.md +466 -0
  32. package/skills/fullstack-expert/references/devops_infrastructure.md +477 -0
  33. package/skills/fullstack-expert/references/multi_language_backend.md +528 -0
  34. package/skills/fullstack-expert/references/system_design_patterns.md +358 -0
  35. package/skills/fullstack-expert/scripts/api_contract_validator.py +253 -0
  36. package/skills/fullstack-expert/scripts/architecture_analyzer.py +326 -0
  37. package/skills/gemini-agent-booster/SKILL.md +135 -0
  38. package/skills/global-a11y-i18n-expert/SKILL.md +81 -0
  39. package/skills/go-programming-expert/SKILL.md +295 -0
  40. package/skills/hig/SKILL.md +188 -0
  41. package/skills/js-backend-expert/SKILL.md +192 -0
  42. package/skills/mcp-server-architect/SKILL.md +194 -0
  43. package/skills/mobile-expo-expert/SKILL.md +186 -0
  44. package/skills/monday-design-aesthetic/SKILL.md +67 -0
  45. package/skills/monorepo-architect/SKILL.md +227 -0
  46. package/skills/mpa-orchestrator/SKILL.md +101 -0
  47. package/skills/multi-agent-orchestration/SKILL.md +234 -0
  48. package/skills/multiple-entry-points/SKILL.md +55 -0
  49. package/skills/mvc-expert/SKILL.md +231 -0
  50. package/skills/payment-gateway-expert/SKILL.md +45 -0
  51. package/skills/performance-web-vitals/SKILL.md +332 -0
  52. package/skills/prd-architect/SKILL.md +191 -0
  53. package/skills/production-ready-hardener/SKILL.md +469 -0
  54. package/skills/production-ready-hardener/references/performance_optimization.md +441 -0
  55. package/skills/production-ready-hardener/references/production_checklist.md +161 -0
  56. package/skills/production-ready-hardener/references/security_hardening_guide.md +379 -0
  57. package/skills/production-ready-hardener/scripts/production_readiness_scanner.py +875 -0
  58. package/skills/python-programming-expert/SKILL.md +271 -0
  59. package/skills/realtime-collaboration-expert/SKILL.md +45 -0
  60. package/skills/rust-programming-expert/SKILL.md +235 -0
  61. package/skills/saas-billing/SKILL.md +377 -0
  62. package/skills/saas-multi-tenant/SKILL.md +237 -0
  63. package/skills/saas-mvp-launcher/SKILL.md +231 -0
  64. package/skills/saas-transformer/SKILL.md +446 -0
  65. package/skills/saas-transformer/references/billing_integration_guide.md +401 -0
  66. package/skills/saas-transformer/references/feature_gating_patterns.md +137 -0
  67. package/skills/saas-transformer/references/saas_transformation_checklist.md +121 -0
  68. package/skills/saas-transformer/scripts/saas_transformation_scanner.py +254 -0
  69. package/skills/scalability-clean-code/SKILL.md +229 -0
  70. package/skills/secure-fuzz-testing/SKILL.md +201 -0
  71. package/skills/senior-frontend/SKILL.md +161 -0
  72. package/skills/senior-frontend/references/frontend_best_practices.md +806 -0
  73. package/skills/senior-frontend/references/nextjs_optimization_guide.md +724 -0
  74. package/skills/senior-frontend/references/react_patterns.md +746 -0
  75. package/skills/senior-frontend/scripts/bundle_analyzer.py +407 -0
  76. package/skills/senior-frontend/scripts/component_generator.py +329 -0
  77. package/skills/senior-frontend/scripts/frontend_scaffolder.py +1005 -0
  78. package/skills/senior-fullstack/SKILL.md +167 -0
  79. package/skills/senior-fullstack/references/architecture_patterns.md +160 -0
  80. package/skills/senior-fullstack/references/development_workflows.md +222 -0
  81. package/skills/senior-fullstack/references/tech_stack_guide.md +190 -0
  82. package/skills/senior-fullstack/scripts/code_quality_analyzer.py +114 -0
  83. package/skills/senior-fullstack/scripts/fullstack_scaffolder.py +114 -0
  84. package/skills/senior-fullstack/scripts/project_scaffolder.py +114 -0
  85. package/skills/seo/SKILL.md +225 -0
  86. package/skills/seo/references/cwv-thresholds.md +108 -0
  87. package/skills/seo/references/eeat-framework.md +214 -0
  88. package/skills/seo/references/quality-gates.md +155 -0
  89. package/skills/seo/references/schema-types.md +118 -0
  90. package/skills/seo-aeo-landing-page-writer/SKILL.md +97 -0
  91. package/skills/seo-geo/SKILL.md +188 -0
  92. package/skills/session-handoff-resume/SKILL.md +158 -0
  93. package/skills/skill_baru/SKILL.md +147 -0
  94. package/skills/spa-orchestrator/SKILL.md +288 -0
  95. package/skills/state-management-expert/SKILL.md +272 -0
  96. package/skills/supabase-migration/SKILL.md +45 -0
  97. package/skills/supabase-security-expert/SKILL.md +243 -0
  98. package/skills/tailwind-expert/SKILL.md +188 -0
  99. package/skills/tanstack-query-expert/SKILL.md +199 -0
  100. package/skills/tauri-expert/SKILL.md +97 -0
  101. package/skills/token-saver/SKILL.md +111 -0
  102. package/skills/typescript-expert/SKILL.md +279 -0
  103. package/skills/ui-components-expert/SKILL.md +63 -0
  104. package/skills/ui-ux-pro-max/SKILL.md +201 -0
  105. package/skills/ui-ux-pro-max/data/charts.csv +26 -0
  106. package/skills/ui-ux-pro-max/data/colors.csv +97 -0
  107. package/skills/ui-ux-pro-max/data/icons.csv +101 -0
  108. package/skills/ui-ux-pro-max/data/landing.csv +31 -0
  109. package/skills/ui-ux-pro-max/data/products.csv +97 -0
  110. package/skills/ui-ux-pro-max/data/prompts.csv +24 -0
  111. package/skills/ui-ux-pro-max/data/react-performance.csv +45 -0
  112. package/skills/ui-ux-pro-max/data/stacks/flutter.csv +53 -0
  113. package/skills/ui-ux-pro-max/data/stacks/html-tailwind.csv +56 -0
  114. package/skills/ui-ux-pro-max/data/stacks/nextjs.csv +53 -0
  115. package/skills/ui-ux-pro-max/data/stacks/nuxt-ui.csv +51 -0
  116. package/skills/ui-ux-pro-max/data/stacks/nuxtjs.csv +59 -0
  117. package/skills/ui-ux-pro-max/data/stacks/react-native.csv +52 -0
  118. package/skills/ui-ux-pro-max/data/stacks/react.csv +54 -0
  119. package/skills/ui-ux-pro-max/data/stacks/shadcn.csv +61 -0
  120. package/skills/ui-ux-pro-max/data/stacks/svelte.csv +54 -0
  121. package/skills/ui-ux-pro-max/data/stacks/swiftui.csv +51 -0
  122. package/skills/ui-ux-pro-max/data/stacks/vue.csv +50 -0
  123. package/skills/ui-ux-pro-max/data/styles.csv +59 -0
  124. package/skills/ui-ux-pro-max/data/typography.csv +58 -0
  125. package/skills/ui-ux-pro-max/data/ui-reasoning.csv +101 -0
  126. package/skills/ui-ux-pro-max/data/ux-guidelines.csv +100 -0
  127. package/skills/ui-ux-pro-max/data/web-interface.csv +31 -0
  128. package/skills/ui-ux-pro-max/scripts/__pycache__/core.cpython-310.pyc +0 -0
  129. package/skills/ui-ux-pro-max/scripts/__pycache__/core.cpython-312.pyc +0 -0
  130. package/skills/ui-ux-pro-max/scripts/__pycache__/design_system.cpython-310.pyc +0 -0
  131. package/skills/ui-ux-pro-max/scripts/__pycache__/design_system.cpython-312.pyc +0 -0
  132. package/skills/ui-ux-pro-max/scripts/core.py +257 -0
  133. package/skills/ui-ux-pro-max/scripts/design_system.py +493 -0
  134. package/skills/ui-ux-pro-max/scripts/search.py +81 -0
  135. package/skills/ui_ux_expert/SKILL.md +114 -0
  136. package/skills/vibe-code-gardener/SKILL.md +173 -0
  137. package/skills/web-scraper/SKILL.md +205 -0
  138. package/skills/web-scraper/references/data-transforms.md +397 -0
  139. package/skills/web-scraper/references/extraction-patterns.md +475 -0
  140. package/skills/web-scraper/references/output-templates.md +481 -0
  141. package/skills/zero-to-prod-orchestrator/SKILL.md +180 -0
@@ -0,0 +1,254 @@
1
+ #!/usr/bin/env python3
2
+ """
3
+ SaaS Transformation Scanner
4
+ Automated scanner that runs a SaaS transformation readiness audit against a target project.
5
+ """
6
+
7
+ import os
8
+ import sys
9
+ import json
10
+ import argparse
11
+ import re
12
+ from pathlib import Path
13
+ from typing import Dict, List
14
+
15
+
16
+ class SaasTransformationScanner:
17
+ """Scans an existing codebase for SaaS transformation readiness across 8 pillars."""
18
+
19
+ PILLAR_WEIGHTS = {
20
+ 'tenancy': 0.20,
21
+ 'auth': 0.15,
22
+ 'billing': 0.20,
23
+ 'teams': 0.15,
24
+ 'frontend': 0.10,
25
+ 'api': 0.10,
26
+ 'hardening': 0.10,
27
+ }
28
+
29
+ def __init__(self, target_path: str, verbose: bool = False):
30
+ self.target_path = Path(target_path)
31
+ self.verbose = verbose
32
+ self.pillars: Dict[str, Dict] = {}
33
+ self.overall_score = 0
34
+
35
+ def run(self) -> Dict:
36
+ """Execute the full SaaS transformation readiness scan."""
37
+ print("🚀 SaaS Transformation Scanner")
38
+ print(f"📁 Target Project: {self.target_path}")
39
+ print("=" * 60)
40
+
41
+ if not self.target_path.exists():
42
+ print(f"❌ Target path does not exist: {self.target_path}")
43
+ sys.exit(1)
44
+
45
+ # Run audits
46
+ self._audit_tenancy()
47
+ self._audit_auth()
48
+ self._audit_billing()
49
+ self._audit_teams()
50
+ self._audit_frontend()
51
+ self._audit_api()
52
+ self._audit_hardening()
53
+
54
+ # Calculate score and report
55
+ self._calculate_overall_score()
56
+ self._generate_report()
57
+
58
+ return {
59
+ 'target': str(self.target_path),
60
+ 'overall_score': self.overall_score,
61
+ 'pillars': self.pillars,
62
+ }
63
+
64
+ def _init_pillar(self, name: str, display_name: str) -> Dict:
65
+ """Initialize a pillar result structure."""
66
+ pillar = {
67
+ 'name': display_name,
68
+ 'score': 100,
69
+ 'checks': [],
70
+ 'critical': 0,
71
+ 'warnings': 0,
72
+ 'passed': 0,
73
+ }
74
+ self.pillars[name] = pillar
75
+ if self.verbose:
76
+ print(f"\n📋 Pillar: {display_name}")
77
+ print("-" * 40)
78
+ return pillar
79
+
80
+ def _check(self, pillar: Dict, name: str, passed: bool, severity: str = 'warning', penalty: int = 15):
81
+ """Record check result and adjust scores."""
82
+ pillar['checks'].append({
83
+ 'name': name,
84
+ 'passed': passed,
85
+ 'severity': severity,
86
+ })
87
+ if passed:
88
+ pillar['passed'] += 1
89
+ if self.verbose:
90
+ print(f" ✅ {name}")
91
+ else:
92
+ if severity == 'critical':
93
+ pillar['critical'] += 1
94
+ pillar['score'] -= max(penalty, 25)
95
+ else:
96
+ pillar['warnings'] += 1
97
+ pillar['score'] -= penalty
98
+ pillar['score'] = max(0, pillar['score'])
99
+ icon = '🔴' if severity == 'critical' else '🟡'
100
+ if self.verbose:
101
+ print(f" {icon} {name}")
102
+
103
+ def _file_exists(self, *paths: str) -> bool:
104
+ return any((self.target_path / p).exists() for p in paths)
105
+
106
+ def _dir_exists(self, *paths: str) -> bool:
107
+ return any((self.target_path / p).is_dir() for p in paths)
108
+
109
+ def _grep_project(self, pattern: str, extensions: List[str] = None) -> List[str]:
110
+ matches = []
111
+ exts = extensions or ['.ts', '.tsx', '.js', '.jsx', '.py', '.go', '.rs', '.prisma']
112
+ for ext in exts:
113
+ for f in self.target_path.rglob(f'*{ext}'):
114
+ if any(x in str(f) for x in ['node_modules', '.next', 'dist', '.git']):
115
+ continue
116
+ try:
117
+ content = f.read_text(errors='ignore')
118
+ if re.search(pattern, content):
119
+ matches.append(str(f.relative_to(self.target_path)))
120
+ except (IOError, OSError):
121
+ continue
122
+ return matches
123
+
124
+ def _audit_tenancy(self):
125
+ p = self._init_pillar('tenancy', 'Multi-Tenancy Foundation')
126
+
127
+ # Check database schema structure
128
+ has_db_schema = self._file_exists('prisma/schema.prisma') or self._grep_project('pgTable|sqliteTable|mysqlTable', ['.ts', '.js'])
129
+ self._check(p, 'Database schema config exists', has_db_schema, severity='critical')
130
+
131
+ # Check tenant id usage
132
+ tenant_cols = self._grep_project(r'tenant_id|tenantId|workspace_id|workspaceId', ['.prisma', '.ts', '.js'])
133
+ self._check(p, 'tenant_id/workspace_id column configured in models', len(tenant_cols) > 0, severity='critical')
134
+
135
+ # Check RLS
136
+ has_rls = self._grep_project(r'ROW LEVEL SECURITY|ENABLE RLS|enableRowLevelSecurity', ['.sql', '.ts', '.js'])
137
+ self._check(p, 'PostgreSQL RLS setup or database policies present', len(has_rls) > 0)
138
+
139
+ # Check Tenant Middleware
140
+ has_mw = self._grep_project(r'tenantMiddleware|app\.current_tenant_id|tenantContext', ['.ts', '.js', '.py', '.go'])
141
+ self._check(p, 'Tenant-aware middleware initialized', len(has_mw) > 0)
142
+
143
+ def _audit_auth(self):
144
+ p = self._init_pillar('auth', 'Authentication & Authorization')
145
+
146
+ # Auth service provider detection
147
+ has_clerk = self._grep_project(r'clerkMiddleware|@clerk/nextjs', ['.ts', '.tsx', '.json'])
148
+ has_nextauth = self._grep_project(r'NextAuth|auth\.js', ['.ts', '.js'])
149
+ has_supabase_auth = self._grep_project(r'supabase\.auth|@supabase/ssr', ['.ts', '.tsx', '.js'])
150
+ self._check(p, 'Production auth provider configured (Clerk/NextAuth/Supabase Auth)',
151
+ bool(has_clerk or has_nextauth or has_supabase_auth), severity='critical')
152
+
153
+ # Roles / RBAC
154
+ has_roles = self._grep_project(r'role\s*:\s*["\'](admin|owner|member)["\']|requireRole|checkPermission', ['.ts', '.tsx', '.js', '.py'])
155
+ self._check(p, 'Role-Based Access Control (RBAC) definitions exist', len(has_roles) > 0)
156
+
157
+ def _audit_billing(self):
158
+ p = self._init_pillar('billing', 'Billing & Subscription')
159
+
160
+ # Payment Provider dependencies
161
+ has_stripe = self._grep_project(r'stripe|lemonsqueezy|paddle-sdk', ['.json', '.ts', '.js', '.py'])
162
+ self._check(p, 'Payment processor integrated (Stripe/LemonSqueezy)', len(has_stripe) > 0, severity='critical')
163
+
164
+ # Webhooks
165
+ has_webhook = self._grep_project(r'stripe\.webhooks|constructEvent|webhooks/stripe', ['.ts', '.js', '.py'])
166
+ self._check(p, 'Webhook listener for payment events implemented', len(has_webhook) > 0)
167
+
168
+ # Pricing and Plans config
169
+ has_pricing = self._grep_project(r'pricing|plans|subscriptionStatus|tier', ['.ts', '.tsx', '.js'])
170
+ self._check(p, 'Pricing plan definitions present', len(has_pricing) > 0)
171
+
172
+ def _audit_teams(self):
173
+ p = self._init_pillar('teams', 'Workspace & Team Management')
174
+
175
+ # Member list / Workspace switcher check
176
+ has_switcher = self._grep_project(r'workspaceSwitcher|WorkspaceSelect|switchWorkspace', ['.tsx', '.ts', '.js'])
177
+ self._check(p, 'Workspace switching controls found', len(has_switcher) > 0)
178
+
179
+ # Invite flow
180
+ has_invites = self._grep_project(r'workspace_invitations|inviteMember|invitationToken', ['.prisma', '.ts', '.js'])
181
+ self._check(p, 'Team invitation system models or methods exist', len(has_invites) > 0)
182
+
183
+ def _audit_frontend(self):
184
+ p = self._init_pillar('frontend', 'SaaS App Shell & Dashboard')
185
+
186
+ # Shell and settings pages
187
+ has_billing_ui = self._grep_project(r'/settings/billing|BillingSettings', ['.tsx', '.ts', '.js'])
188
+ self._check(p, 'Billing/subscription settings page implemented', len(has_billing_ui) > 0)
189
+
190
+ has_team_ui = self._grep_project(r'/settings/team|TeamSettings', ['.tsx', '.ts', '.js'])
191
+ self._check(p, 'Team/member settings page implemented', len(has_team_ui) > 0)
192
+
193
+ def _audit_api(self):
194
+ p = self._init_pillar('api', 'API Layer & Feature Gating')
195
+
196
+ # Gated flags or plan limits
197
+ has_gating = self._grep_project(r'PLAN_LIMITS|PLAN_CONFIGS|hasFeature|assertHasFeature', ['.ts', '.tsx', '.js'])
198
+ self._check(p, 'Feature gating / usage limit configuration map defined', len(has_gating) > 0)
199
+
200
+ # Usage metering log
201
+ has_metering = self._grep_project(r'usage_records|usageRecords|usageMeter|incrementUsage', ['.prisma', '.ts', '.js'])
202
+ self._check(p, 'Usage metering / metric tracking database model exists', len(has_metering) > 0)
203
+
204
+ def _audit_hardening(self):
205
+ p = self._init_pillar('hardening', 'Production Hardening')
206
+
207
+ # Basic rate limits
208
+ has_rate_limit = self._grep_project(r'rate.?limit|upstash/ratelimit|limiter', ['.ts', '.js', '.py'])
209
+ self._check(p, 'API Rate Limiting setup configured', len(has_rate_limit) > 0)
210
+
211
+ # Env validation
212
+ has_env_spec = self._file_exists('.env.example', '.env.template')
213
+ self._check(p, 'Environment example schema exists', has_env_spec)
214
+
215
+ def _calculate_overall_score(self):
216
+ total = 0
217
+ for pillar_key, weight in self.PILLAR_WEIGHTS.items():
218
+ if pillar_key in self.pillars:
219
+ total += self.pillars[pillar_key]['score'] * weight
220
+ self.overall_score = round(total)
221
+
222
+ def _get_grade(self, score: int) -> str:
223
+ if score >= 90:
224
+ return 'A'
225
+ elif score >= 80:
226
+ return 'B'
227
+ elif score >= 70:
228
+ return 'C'
229
+ elif score >= 60:
230
+ return 'D'
231
+ return 'F'
232
+
233
+ def _generate_report(self):
234
+ grade = self._get_grade(self.overall_score)
235
+ print(f"\n🎯 Overall SaaS Readiness: {self.overall_score}/100 ({grade})")
236
+ print("-" * 60)
237
+
238
+ for k, p in self.pillars.items():
239
+ icon = '✅' if p['score'] >= 85 else ('🟡' if p['score'] >= 50 else '🔴')
240
+ print(f" {icon} {p['name']:<30} {p['score']:>4}/100 (Crit: {p['critical']}, Warn: {p['warnings']})")
241
+
242
+
243
+ def main():
244
+ parser = argparse.ArgumentParser(description="SaaS Transformation Scanner")
245
+ parser.add_argument('target', help='Path of project to audit')
246
+ parser.add_argument('--verbose', '-v', action='store_true', help='Show check details')
247
+ args = parser.parse_args()
248
+
249
+ scanner = SaasTransformationScanner(args.target, verbose=args.verbose)
250
+ scanner.run()
251
+
252
+
253
+ if __name__ == '__main__':
254
+ main()
@@ -0,0 +1,229 @@
1
+ ---
2
+ name: scalability-clean-code
3
+ description: "Software architecture guidelines to maintain code readability (Clean Code, SOLID, DRY) and application scalability / Panduan arsitektur perangkat lunak untuk menjaga keterbacaan kode (Clean Code, SOLID, DRY) dan kemampuan skalabilitas aplikasi."
4
+ author: "Roedy Rustam"
5
+ ---
6
+
7
+ # Scalability & Clean Code (2026 Edition)
8
+
9
+ [English](#english) | [Bahasa Indonesia](#bahasa-indonesia)
10
+
11
+ ---
12
+
13
+ <a name="english"></a>
14
+ ## English
15
+
16
+ ### Description
17
+ Software architecture guidelines for writing clean, scalable, and maintainable code. Covers SOLID principles, DRY/YAGNI/KISS, Clean Architecture layers, **Vertical Slice Architecture** (the modern alternative to layered architecture), Domain-Driven Design (DDD) patterns, and practical refactoring techniques.
18
+
19
+ ### Trigger Conditions
20
+ - Refactoring a codebase that has become hard to understand or modify.
21
+ - Designing the architecture for a new feature or service.
22
+ - Identifying and eliminating code smells (God Classes, Feature Envy, Long Methods).
23
+ - Deciding between Layered Architecture vs Vertical Slice Architecture.
24
+ - Applying SOLID principles to a specific code problem.
25
+
26
+ ### The SOLID Principles (With Modern Context)
27
+
28
+ #### Single Responsibility Principle (SRP)
29
+ A module/class/function should have one reason to change. In 2026 React/Node.js context:
30
+ - **Bad**: A React component that fetches data, transforms it, and renders UI.
31
+ - **Good**: Separate `useUserQuery()` hook (fetch), `transformUser()` util (transform), `UserCard` component (render).
32
+
33
+ #### Open/Closed Principle (OCP)
34
+ Open for extension, closed for modification. Use composition and strategy pattern:
35
+ ```typescript
36
+ // Bad: modify existing code every time a new payment provider is added
37
+ function processPayment(type: 'stripe' | 'polar' | 'paypal', amount: number) {
38
+ if (type === 'stripe') { /* ... */ }
39
+ else if (type === 'polar') { /* ... */ }
40
+ }
41
+
42
+ // Good: extend by adding new providers, not modifying existing code
43
+ interface PaymentProvider {
44
+ charge(amount: number): Promise<Receipt>;
45
+ }
46
+
47
+ class StripeProvider implements PaymentProvider { ... }
48
+ class PolarProvider implements PaymentProvider { ... }
49
+
50
+ function processPayment(provider: PaymentProvider, amount: number) {
51
+ return provider.charge(amount);
52
+ }
53
+ ```
54
+
55
+ #### Dependency Inversion Principle (DIP)
56
+ High-level modules should not depend on low-level modules — both should depend on abstractions:
57
+ ```typescript
58
+ // Bad: handler directly imports concrete DB client
59
+ import { db } from './postgres-client';
60
+
61
+ // Good: inject the repository interface
62
+ interface UserRepository {
63
+ findById(id: string): Promise<User | null>;
64
+ save(user: User): Promise<void>;
65
+ }
66
+
67
+ async function getUser(repo: UserRepository, id: string) {
68
+ return repo.findById(id);
69
+ }
70
+ ```
71
+
72
+ ### Vertical Slice Architecture (VSA)
73
+ The modern alternative to traditional layered architecture (Controller → Service → Repository). Organize code by **feature** (vertical slice) rather than by **technical layer** (horizontal slice):
74
+
75
+ ```
76
+ Traditional (Layered):
77
+ src/
78
+ controllers/ ← all controllers together
79
+ services/ ← all services together
80
+ repositories/ ← all repositories together
81
+
82
+ Vertical Slice:
83
+ src/
84
+ features/
85
+ users/
86
+ create-user.handler.ts ← all logic for "create user" in one place
87
+ create-user.schema.ts
88
+ create-user.test.ts
89
+ products/
90
+ list-products.handler.ts
91
+ list-products.schema.ts
92
+ ```
93
+
94
+ **Benefits of VSA**:
95
+ - Features are self-contained — easy to add, modify, delete, or move.
96
+ - No need to navigate 3-4 layers just to trace one user story.
97
+ - Natural boundary for microservice extraction.
98
+
99
+ ```typescript
100
+ // features/users/create-user.handler.ts
101
+ // One file contains the complete "create user" vertical slice
102
+ import { z } from 'zod';
103
+ import { db } from '@/lib/db';
104
+ import { sendWelcomeEmail } from '@/lib/email';
105
+
106
+ export const CreateUserSchema = z.object({
107
+ name: z.string().min(2),
108
+ email: z.string().email(),
109
+ });
110
+
111
+ export type CreateUserInput = z.infer<typeof CreateUserSchema>;
112
+
113
+ export async function handleCreateUser(input: CreateUserInput) {
114
+ const validated = CreateUserSchema.parse(input);
115
+
116
+ const user = await db.user.create({ data: validated });
117
+ await sendWelcomeEmail(user.email, user.name);
118
+
119
+ return user;
120
+ }
121
+ ```
122
+
123
+ ### Clean Code Principles
124
+
125
+ #### Functions
126
+ - **Do one thing**: Functions should do one thing and do it well.
127
+ - **Small**: Aim for < 20 lines. If longer, extract sub-functions.
128
+ - **Descriptive names**: `getUsersByWorkspace()` not `getData()`.
129
+ - **No side effects**: Pure functions are predictable and testable.
130
+
131
+ #### Naming
132
+ - Variables: noun phrases (`userCount`, `activeWorkspaces`).
133
+ - Functions: verb phrases (`fetchUser`, `validateInput`, `sendEmail`).
134
+ - Boolean: question form (`isActive`, `hasPermission`, `canEdit`).
135
+ - Avoid abbreviations: `workspace` not `ws`, `configuration` not `cfg`.
136
+
137
+ #### Comments
138
+ - **Don't comment bad code — rewrite it.**
139
+ - Write self-documenting code: well-named variables and functions eliminate the need for most comments.
140
+ - **Do** comment: why (intent), not what (obvious from code).
141
+
142
+ #### DRY, YAGNI, KISS
143
+ - **DRY**: Don't Repeat Yourself — extract shared logic. But: avoid premature abstraction.
144
+ - **YAGNI**: You Aren't Gonna Need It — don't build features "just in case".
145
+ - **KISS**: Keep It Simple, Stupid — the simplest solution that works is usually best.
146
+
147
+ ### Code Smells & Refactoring
148
+
149
+ | Smell | Symptom | Refactoring |
150
+ |---|---|---|
151
+ | **God Class** | Class does everything | Extract Class, Move Method |
152
+ | **Long Method** | Method > 30 lines | Extract Method |
153
+ | **Feature Envy** | Method uses another class's data excessively | Move Method |
154
+ | **Data Clumps** | Same 3+ params appear together repeatedly | Introduce Parameter Object |
155
+ | **Magic Numbers** | `if (status === 3)` | Extract Constant |
156
+ | **Shotgun Surgery** | One change requires edits in many places | Move Method, Inline Class |
157
+ | **Primitive Obsession** | Using string/int for domain concepts | Replace with Value Object |
158
+
159
+ ### Architecture Decision Framework
160
+ When choosing an architecture, ask:
161
+ 1. **What changes together?** Organize code that changes together.
162
+ 2. **What is independently deployable?** Separate services by deployment boundary.
163
+ 3. **What has different scaling needs?** Scale independently only what needs it.
164
+ 4. **What is the team size?** Microservices add overhead — start monolith, extract when needed.
165
+
166
+ ---
167
+
168
+ <a name="bahasa-indonesia"></a>
169
+ ## Bahasa Indonesia
170
+
171
+ ### Deskripsi
172
+ Panduan arsitektur perangkat lunak untuk menulis kode yang bersih, skalabel, dan mudah dirawat. Mencakup prinsip SOLID, DRY/YAGNI/KISS, lapisan Clean Architecture, **Vertical Slice Architecture** (alternatif modern dari layered architecture), pola Domain-Driven Design (DDD), dan teknik refactoring praktis.
173
+
174
+ ### Kondisi Pemicu
175
+ - Merefaktor codebase yang sulit dipahami atau dimodifikasi.
176
+ - Merancang arsitektur untuk fitur atau layanan baru.
177
+ - Mengidentifikasi dan menghilangkan code smell (God Class, Feature Envy, Long Method).
178
+ - Memutuskan antara Layered Architecture vs Vertical Slice Architecture.
179
+ - Menerapkan prinsip SOLID pada masalah kode tertentu.
180
+
181
+ ### Prinsip SOLID
182
+
183
+ #### SRP — Single Responsibility Principle
184
+ Setiap modul/kelas/fungsi harus memiliki satu alasan untuk berubah. Pisahkan pengambilan data, transformasi data, dan rendering UI.
185
+
186
+ #### OCP — Open/Closed Principle
187
+ Terbuka untuk ekstensi, tertutup untuk modifikasi. Gunakan komposisi dan pola strategi — tambah provider baru tanpa mengubah kode yang ada.
188
+
189
+ #### DIP — Dependency Inversion Principle
190
+ Modul tingkat tinggi tidak boleh bergantung pada modul tingkat rendah — keduanya harus bergantung pada abstraksi (interface).
191
+
192
+ ### Vertical Slice Architecture (VSA)
193
+ Alternatif modern dari layered architecture tradisional. Organisasikan kode berdasarkan **fitur** (irisan vertikal), bukan lapisan teknis (irisan horizontal).
194
+
195
+ **Keuntungan VSA:**
196
+ - Fitur bersifat self-contained — mudah ditambah, dimodifikasi, dihapus, atau dipindah.
197
+ - Tidak perlu menavigasi 3-4 layer hanya untuk melacak satu user story.
198
+ - Batas natural untuk ekstraksi microservice.
199
+
200
+ ### Prinsip Clean Code
201
+
202
+ #### Fungsi
203
+ - Lakukan satu hal dan lakukan dengan baik.
204
+ - Nama deskriptif: `getUsersByWorkspace()` bukan `getData()`.
205
+ - Tanpa efek samping: fungsi murni dapat diprediksi dan diuji.
206
+
207
+ #### Penamaan
208
+ - Variabel: frasa kata benda (`jumlahPengguna`, `workspaceAktif`).
209
+ - Fungsi: frasa kata kerja (`ambilPengguna`, `validasiInput`).
210
+ - Boolean: bentuk pertanyaan (`aktif`, `punyaIzin`, `bisaEdit`).
211
+
212
+ #### Komentar
213
+ - Jangan komen kode buruk — tulis ulang.
214
+ - Tulis kode yang mendokumentasikan dirinya sendiri.
215
+ - Komentar: **mengapa** (niat), bukan apa (jelas dari kode).
216
+
217
+ #### DRY, YAGNI, KISS
218
+ - **DRY**: Jangan ulangi diri sendiri — ekstrak logika bersama.
219
+ - **YAGNI**: Anda tidak akan membutuhkannya — jangan bangun fitur "untuk jaga-jaga".
220
+ - **KISS**: Tetap sederhana — solusi paling sederhana yang berfungsi biasanya terbaik.
221
+
222
+ ### Code Smell & Refactoring
223
+ Identifikasi dan perbaiki: God Class, Long Method, Feature Envy, Data Clumps, Magic Numbers, Shotgun Surgery, Primitive Obsession.
224
+
225
+ ### Framework Keputusan Arsitektur
226
+ 1. **Apa yang berubah bersama?** Organisasikan kode yang berubah bersama.
227
+ 2. **Apa yang dapat di-deploy secara independen?** Pisahkan layanan berdasarkan batas deployment.
228
+ 3. **Apa yang memiliki kebutuhan scaling berbeda?** Scale secara independen hanya yang membutuhkannya.
229
+ 4. **Berapa besar tim?** Microservices menambah overhead — mulai monolith, ekstrak saat diperlukan.
@@ -0,0 +1,201 @@
1
+ ---
2
+ name: secure-fuzz-testing
3
+ description: "Expert-level skill for writing and integrating coverage-guided fuzz tests in Python, Rust, and Go for secure code validation in English and Indonesian."
4
+ author: "Roedy Rustam"
5
+ ---
6
+
7
+ # Secure Fuzz Testing
8
+
9
+ [English](#english) | [Bahasa Indonesia](#bahasa-indonesia)
10
+
11
+ ---
12
+
13
+ <a name="english"></a>
14
+ ## English
15
+
16
+ ### Description
17
+ Expert-level guidance for writing, running, and integrating coverage-guided fuzz tests (fuzzing) to identify security vulnerabilities, memory leaks, and input-validation issues in software applications. This skill covers writing fuzz targets in **Python**, **Rust**, and **Go**, configuring compilers with sanitizers (ASan, MSan, UBSan), and setting up automated CI/CD security pipelines.
18
+
19
+ ### Trigger Conditions
20
+ - Use when designing or reviewing data parsers, serialization/deserialization logic, or file formats.
21
+ - Use when writing libraries that process untrusted network input or binary data streams.
22
+ - Use when integrating automated security testing into a DevSecOps pipeline (CI/CD).
23
+ - Use when troubleshooting complex memory bugs, edge-case crashes, or unhandled exceptions.
24
+
25
+ ### Writing Fuzz Targets
26
+ Coverage-guided fuzzers need a target function that accepts a stream of bytes and processes it.
27
+
28
+ #### 1. Python Fuzzing (Atheris)
29
+ `Atheris` is a coverage-guided fuzzer for Python. It can fuzz Python code and native extensions:
30
+ ```python
31
+ import sys
32
+ import atheris
33
+
34
+ with atheris.instrument_imports():
35
+ import our_parser # Import target module inside instrument_imports
36
+
37
+ def TestOneInput(data):
38
+ if len(data) < 4:
39
+ return
40
+ try:
41
+ # Decode and parse the byte data
42
+ text = data.decode("utf-8", errors="ignore")
43
+ our_parser.parse_config(text)
44
+ except our_parser.ParseException:
45
+ # Expected exceptions should be caught to avoid false positives
46
+ pass
47
+
48
+ atheris.Setup(sys.argv, TestOneInput)
49
+ atheris.Fuzz()
50
+ ```
51
+
52
+ #### 2. Rust Fuzzing (cargo-fuzz & libFuzzer)
53
+ Rust has first-class fuzzing support via `cargo-fuzz` which wraps `libFuzzer`:
54
+ ```rust
55
+ #![no_main]
56
+ use libfuzzer_sys::fuzz_target;
57
+
58
+ fuzz_target!(|data: &[u8]| {
59
+ if let Ok(input_str) = std::str::from_utf8(data) {
60
+ let _ = our_crate::parse_config(input_str);
61
+ }
62
+ });
63
+ ```
64
+ - **Run Fuzzer**: Execute `cargo +nightly fuzz run <target_name>`.
65
+
66
+ #### 3. Go Fuzzing (Native Go Fuzz)
67
+ Go supports native fuzzing in its standard library (`testing` package):
68
+ ```go
69
+ package main
70
+
71
+ import (
72
+ "testing"
73
+ "ourmodule/parser"
74
+ )
75
+
76
+ func FuzzParseConfig(f *testing.F) {
77
+ // Add seed corpus for initial coverage guidance
78
+ f.Add([]byte("config_key = value"))
79
+
80
+ f.Fuzz(func(t *testing.T, data []byte) {
81
+ _, err := parser.ParseConfig(data)
82
+ if err != nil {
83
+ t.Skip() // Skip expected/graceful errors
84
+ }
85
+ })
86
+ }
87
+ ```
88
+ - **Run Fuzzer**: Run `go test -fuzz=FuzzParseConfig -fuzztime=10m`.
89
+
90
+ ### Diagnostics & Sanitizers
91
+ Use compiler instrumentation flags to expose hidden bugs:
92
+ - **AddressSanitizer (ASan)**: Detects out-of-bounds access, use-after-free, and memory leaks.
93
+ - **UndefinedBehaviorSanitizer (UBSan)**: Detects integer overflows, alignment issues, and division by zero.
94
+ - **ThreadSanitizer (TSan)**: Finds data races in multithreaded environments.
95
+
96
+ ### DevSecOps & CI Integration
97
+ - **OSS-Fuzz**: For open-source projects, integrate with Google's OSS-Fuzz for continuous fuzzing infrastructure.
98
+ - **GitHub Actions**: Run fuzz targets on pull requests with short run times (`fuzztime=5m`) to catch regression errors without blocking pipelines.
99
+
100
+ ---
101
+
102
+ ### Troubleshooting & Common Gotchas
103
+ - **False Positives**: Ensure expected API errors and clean validation errors do not cause the fuzzer to abort. Catch expected exceptions or use `t.Skip()` where appropriate.
104
+ - **State Pollution**: Fuzz targets must be stateless. Avoid sharing mutable global states between iterations.
105
+ - **Infinite Loops**: Guard against code that hangs. Configure timeouts (`-timeout=25` in libFuzzer) to automatically crash long-running executions.
106
+
107
+ ---
108
+
109
+ <a name="bahasa-indonesia"></a>
110
+ ## Bahasa Indonesia
111
+
112
+ ### Deskripsi
113
+ Panduan tingkat ahli untuk menulis, menjalankan, dan mengintegrasikan pengujian berbasis cakupan (*coverage-guided fuzzing*) untuk mengidentifikasi celah keamanan, kebocoran memori, dan kesalahan validasi input dalam aplikasi perangkat lunak. Skill ini mencakup penulisan target fuzzing dalam bahasa **Python**, **Rust**, dan **Go**, konfigurasi compiler dengan sanitizer (ASan, MSan, UBSan), serta penyiapan pipa otomatisasi keamanan CI/CD.
114
+
115
+ ### Kondisi Pemicu
116
+ - Gunakan saat merancang atau memeriksa parser data, logika serialisasi/deserialisasi, atau pemroses format berkas.
117
+ - Gunakan saat menulis pustaka (*library*) yang memproses input jaringan yang tidak tepercaya atau aliran data biner.
118
+ - Gunakan saat mengintegrasikan pengujian keamanan otomatis ke dalam alur kerja DevSecOps (CI/CD).
119
+ - Gunakan saat mendiagnosis bug memori yang kompleks, crash pada kasus ekstrem (*edge-cases*), atau *exception* yang tidak ditangani.
120
+
121
+ ### Penulisan Target Fuzzing
122
+ Fuzzer berbasis cakupan memerlukan fungsi target yang menerima aliran byte untuk kemudian diproses secara dinamis.
123
+
124
+ #### 1. Fuzzing Python (Atheris)
125
+ `Atheris` adalah fuzzer berbasis cakupan untuk kode Python dan ekstensi native (C/C++):
126
+ ```python
127
+ import sys
128
+ import atheris
129
+
130
+ with atheris.instrument_imports():
131
+ import our_parser # Impor modul target di dalam instrument_imports
132
+
133
+ def TestOneInput(data):
134
+ if len(data) < 4:
135
+ return
136
+ try:
137
+ # Dekode data byte menjadi teks
138
+ text = data.decode("utf-8", errors="ignore")
139
+ our_parser.parse_config(text)
140
+ except our_parser.ParseException:
141
+ # Tangkap exception yang diharapkan agar tidak dianggap crash palsu
142
+ pass
143
+
144
+ atheris.Setup(sys.argv, TestOneInput)
145
+ atheris.Fuzz()
146
+ ```
147
+
148
+ #### 2. Fuzzing Rust (cargo-fuzz & libFuzzer)
149
+ Rust memiliki dukungan fuzzing kelas satu melalui utilitas `cargo-fuzz` yang menggunakan pustaka `libFuzzer`:
150
+ ```rust
151
+ #![no_main]
152
+ use libfuzzer_sys::fuzz_target;
153
+
154
+ fuzz_target!(|data: &[u8]| {
155
+ if let Ok(input_str) = std::str::from_utf8(data) {
156
+ let _ = our_crate::parse_config(input_str);
157
+ }
158
+ });
159
+ ```
160
+ - **Jalankan Fuzzer**: Eksekusi perintah `cargo +nightly fuzz run <nama_target>`.
161
+
162
+ #### 3. Fuzzing Go (Native Go Fuzz)
163
+ Go mendukung pengujian fuzzing secara native dalam pustaka standarnya (`testing` package):
164
+ ```go
165
+ package main
166
+
167
+ import (
168
+ "testing"
169
+ "ourmodule/parser"
170
+ )
171
+
172
+ func FuzzParseConfig(f *testing.F) {
173
+ // Tambahkan seed corpus awal sebagai panduan awal cakupan fuzzer
174
+ f.Add([]byte("config_key = value"))
175
+
176
+ f.Fuzz(func(t *testing.T, data []byte) {
177
+ _, err := parser.ParseConfig(data)
178
+ if err != nil {
179
+ t.Skip() // Lewati error yang memang diharapkan (ditangani dengan aman)
180
+ }
181
+ })
182
+ }
183
+ ```
184
+ - **Jalankan Fuzzer**: Eksekusi perintah `go test -fuzz=FuzzParseConfig -fuzztime=10m`.
185
+
186
+ ### Diagnosis & Sanitizer
187
+ Gunakan tanda instrumentasi kompiler untuk mendeteksi bug tersembunyi secara dini:
188
+ - **AddressSanitizer (ASan)**: Mendeteksi akses memori di luar batas (*out-of-bounds*), penggunaan setelah dibebaskan (*use-after-free*), dan kebocoran memori (*memory leak*).
189
+ - **UndefinedBehaviorSanitizer (UBSan)**: Mendeteksi overflow integer, masalah penyelarasan memori (*alignment*), dan pembagian dengan nol.
190
+ - **ThreadSanitizer (TSan)**: Menemukan perebutan data (*data race*) pada eksekusi multithread.
191
+
192
+ ### Integrasi DevSecOps & CI
193
+ - **OSS-Fuzz**: Untuk proyek open-source, integrasikan dengan platform OSS-Fuzz dari Google untuk pemantauan berkelanjutan.
194
+ - **GitHub Actions**: Jalankan target fuzzing pada pull request dengan batasan waktu yang singkat (`fuzztime=5m`) untuk menangkap regresi kode tanpa menghambat alur build.
195
+
196
+ ---
197
+
198
+ ### Pemecahan Masalah & Kesalahan Umum
199
+ - **Crash Palsu (False Positives)**: Pastikan error API yang ditangani dengan aman tidak membuat fuzzer berhenti. Tangkap exception tersebut atau gunakan `t.Skip()` pada Go.
200
+ - **Polusi State (State Pollution)**: Pastikan target fuzzing bersifat stateless. Jangan biarkan state global mutable dibagikan antar iterasi pengujian.
201
+ - **Loop Tak Terbatas**: Waspadai kode yang mengalami hang. Konfigurasikan batas waktu (`-timeout=25` pada libFuzzer) agar eksekusi yang macet secara otomatis dilaporkan sebagai crash.