scc-universal 1.1.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 (271) hide show
  1. package/.claude-plugin/plugin.json +44 -0
  2. package/.cursor/agents/deep-researcher.md +142 -0
  3. package/.cursor/agents/doc-updater.md +219 -0
  4. package/.cursor/agents/eval-runner.md +335 -0
  5. package/.cursor/agents/learning-engine.md +210 -0
  6. package/.cursor/agents/loop-operator.md +245 -0
  7. package/.cursor/agents/refactor-cleaner.md +119 -0
  8. package/.cursor/agents/sf-admin-agent.md +127 -0
  9. package/.cursor/agents/sf-agentforce-agent.md +126 -0
  10. package/.cursor/agents/sf-apex-agent.md +117 -0
  11. package/.cursor/agents/sf-architect.md +426 -0
  12. package/.cursor/agents/sf-aura-reviewer.md +369 -0
  13. package/.cursor/agents/sf-bugfix-agent.md +101 -0
  14. package/.cursor/agents/sf-flow-agent.md +155 -0
  15. package/.cursor/agents/sf-integration-agent.md +141 -0
  16. package/.cursor/agents/sf-lwc-agent.md +123 -0
  17. package/.cursor/agents/sf-review-agent.md +357 -0
  18. package/.cursor/agents/sf-visualforce-reviewer.md +465 -0
  19. package/.cursor/hooks/adapter.js +81 -0
  20. package/.cursor/hooks/after-file-edit.js +26 -0
  21. package/.cursor/hooks/after-mcp-execution.js +12 -0
  22. package/.cursor/hooks/after-shell-execution.js +30 -0
  23. package/.cursor/hooks/after-tab-file-edit.js +12 -0
  24. package/.cursor/hooks/before-mcp-execution.js +11 -0
  25. package/.cursor/hooks/before-read-file.js +13 -0
  26. package/.cursor/hooks/before-shell-execution.js +29 -0
  27. package/.cursor/hooks/before-submit-prompt.js +23 -0
  28. package/.cursor/hooks/pre-compact.js +7 -0
  29. package/.cursor/hooks/session-end.js +10 -0
  30. package/.cursor/hooks/session-start.js +10 -0
  31. package/.cursor/hooks/stop.js +18 -0
  32. package/.cursor/hooks/subagent-start.js +10 -0
  33. package/.cursor/hooks/subagent-stop.js +10 -0
  34. package/.cursor/hooks.json +107 -0
  35. package/.cursor/skills/aside/SKILL.md +115 -0
  36. package/.cursor/skills/checkpoint/SKILL.md +50 -0
  37. package/.cursor/skills/configure-scc/SKILL.md +160 -0
  38. package/.cursor/skills/continuous-agent-loop/SKILL.md +260 -0
  39. package/.cursor/skills/mcp-server-patterns/SKILL.md +142 -0
  40. package/.cursor/skills/model-route/SKILL.md +81 -0
  41. package/.cursor/skills/prompt-optimizer/SKILL.md +366 -0
  42. package/.cursor/skills/refactor-clean/SKILL.md +133 -0
  43. package/.cursor/skills/resume-session/SKILL.md +111 -0
  44. package/.cursor/skills/save-session/SKILL.md +183 -0
  45. package/.cursor/skills/search-first/SKILL.md +140 -0
  46. package/.cursor/skills/security-scan/SKILL.md +142 -0
  47. package/.cursor/skills/sessions/SKILL.md +124 -0
  48. package/.cursor/skills/sf-agentforce-development/SKILL.md +449 -0
  49. package/.cursor/skills/sf-apex-async-patterns/SKILL.md +324 -0
  50. package/.cursor/skills/sf-apex-best-practices/SKILL.md +421 -0
  51. package/.cursor/skills/sf-apex-constraints/SKILL.md +79 -0
  52. package/.cursor/skills/sf-apex-cursor/SKILL.md +336 -0
  53. package/.cursor/skills/sf-apex-enterprise-patterns/SKILL.md +344 -0
  54. package/.cursor/skills/sf-apex-testing/SKILL.md +407 -0
  55. package/.cursor/skills/sf-api-design/SKILL.md +237 -0
  56. package/.cursor/skills/sf-approval-processes/SKILL.md +312 -0
  57. package/.cursor/skills/sf-aura-development/SKILL.md +260 -0
  58. package/.cursor/skills/sf-build-fix/SKILL.md +120 -0
  59. package/.cursor/skills/sf-data-modeling/SKILL.md +274 -0
  60. package/.cursor/skills/sf-debugging/SKILL.md +362 -0
  61. package/.cursor/skills/sf-deployment/SKILL.md +291 -0
  62. package/.cursor/skills/sf-deployment-constraints/SKILL.md +153 -0
  63. package/.cursor/skills/sf-devops-ci-cd/SKILL.md +322 -0
  64. package/.cursor/skills/sf-docs-lookup/SKILL.md +100 -0
  65. package/.cursor/skills/sf-e2e-testing/SKILL.md +321 -0
  66. package/.cursor/skills/sf-experience-cloud/SKILL.md +248 -0
  67. package/.cursor/skills/sf-flow-development/SKILL.md +376 -0
  68. package/.cursor/skills/sf-governor-limits/SKILL.md +319 -0
  69. package/.cursor/skills/sf-harness-audit/SKILL.md +139 -0
  70. package/.cursor/skills/sf-help/SKILL.md +156 -0
  71. package/.cursor/skills/sf-integration/SKILL.md +479 -0
  72. package/.cursor/skills/sf-lwc-constraints/SKILL.md +128 -0
  73. package/.cursor/skills/sf-lwc-development/SKILL.md +302 -0
  74. package/.cursor/skills/sf-lwc-testing/SKILL.md +387 -0
  75. package/.cursor/skills/sf-metadata-management/SKILL.md +285 -0
  76. package/.cursor/skills/sf-platform-events-cdc/SKILL.md +372 -0
  77. package/.cursor/skills/sf-quickstart/SKILL.md +170 -0
  78. package/.cursor/skills/sf-security/SKILL.md +330 -0
  79. package/.cursor/skills/sf-security-constraints/SKILL.md +125 -0
  80. package/.cursor/skills/sf-soql-constraints/SKILL.md +129 -0
  81. package/.cursor/skills/sf-soql-optimization/SKILL.md +353 -0
  82. package/.cursor/skills/sf-tdd-workflow/SKILL.md +332 -0
  83. package/.cursor/skills/sf-testing-constraints/SKILL.md +198 -0
  84. package/.cursor/skills/sf-trigger-constraints/SKILL.md +88 -0
  85. package/.cursor/skills/sf-trigger-frameworks/SKILL.md +343 -0
  86. package/.cursor/skills/sf-visualforce-development/SKILL.md +259 -0
  87. package/.cursor/skills/strategic-compact/SKILL.md +205 -0
  88. package/.cursor/skills/update-docs/SKILL.md +162 -0
  89. package/.cursor/skills/update-platform-docs/SKILL.md +86 -0
  90. package/.cursor-plugin/plugin.json +26 -0
  91. package/LICENSE +21 -0
  92. package/README.md +522 -0
  93. package/agents/deep-researcher.md +145 -0
  94. package/agents/doc-updater.md +222 -0
  95. package/agents/eval-runner.md +340 -0
  96. package/agents/learning-engine.md +211 -0
  97. package/agents/loop-operator.md +247 -0
  98. package/agents/refactor-cleaner.md +122 -0
  99. package/agents/sf-admin-agent.md +131 -0
  100. package/agents/sf-agentforce-agent.md +132 -0
  101. package/agents/sf-apex-agent.md +124 -0
  102. package/agents/sf-architect.md +435 -0
  103. package/agents/sf-aura-reviewer.md +372 -0
  104. package/agents/sf-bugfix-agent.md +105 -0
  105. package/agents/sf-flow-agent.md +159 -0
  106. package/agents/sf-integration-agent.md +146 -0
  107. package/agents/sf-lwc-agent.md +127 -0
  108. package/agents/sf-review-agent.md +366 -0
  109. package/agents/sf-visualforce-reviewer.md +468 -0
  110. package/assets/logo.svg +18 -0
  111. package/docs/ARCHITECTURE.md +133 -0
  112. package/docs/authoring-guide.md +373 -0
  113. package/docs/hook-development.md +578 -0
  114. package/docs/token-optimization.md +139 -0
  115. package/docs/workflow-examples.md +645 -0
  116. package/examples/agentforce-action/README.md +227 -0
  117. package/examples/apex-trigger-handler/README.md +114 -0
  118. package/examples/devops-pipeline/README.md +325 -0
  119. package/examples/flow-automation/README.md +188 -0
  120. package/examples/integration-pattern/README.md +416 -0
  121. package/examples/lwc-component/README.md +180 -0
  122. package/examples/platform-events/README.md +492 -0
  123. package/examples/scratch-org-setup/README.md +138 -0
  124. package/examples/security-audit/README.md +244 -0
  125. package/examples/visualforce-migration/README.md +314 -0
  126. package/hooks/hooks.json +338 -0
  127. package/hooks/memory-persistence/README.md +73 -0
  128. package/manifests/install-modules.json +217 -0
  129. package/manifests/install-profiles.json +17 -0
  130. package/mcp-configs/mcp-servers.json +19 -0
  131. package/package.json +89 -0
  132. package/schemas/hooks.schema.json +123 -0
  133. package/schemas/install-modules.schema.json +76 -0
  134. package/schemas/install-profiles.schema.json +28 -0
  135. package/schemas/install-state.schema.json +73 -0
  136. package/schemas/package-manager.schema.json +18 -0
  137. package/schemas/plugin.schema.json +112 -0
  138. package/schemas/scc-install-config.schema.json +29 -0
  139. package/schemas/state-store.schema.json +111 -0
  140. package/scripts/cli/install-apply.js +170 -0
  141. package/scripts/cli/uninstall.js +193 -0
  142. package/scripts/hooks/check-console-log.js +101 -0
  143. package/scripts/hooks/check-hook-enabled.js +17 -0
  144. package/scripts/hooks/check-platform-docs-age.js +48 -0
  145. package/scripts/hooks/cost-tracker.js +78 -0
  146. package/scripts/hooks/doc-file-warning.js +63 -0
  147. package/scripts/hooks/evaluate-session.js +98 -0
  148. package/scripts/hooks/governor-check.js +220 -0
  149. package/scripts/hooks/learning-observe.sh +206 -0
  150. package/scripts/hooks/mcp-health-check.js +588 -0
  151. package/scripts/hooks/post-bash-build-complete.js +34 -0
  152. package/scripts/hooks/post-bash-pr-created.js +43 -0
  153. package/scripts/hooks/post-edit-console-warn.js +61 -0
  154. package/scripts/hooks/post-edit-format.js +79 -0
  155. package/scripts/hooks/post-edit-typecheck.js +98 -0
  156. package/scripts/hooks/post-write.js +168 -0
  157. package/scripts/hooks/pre-bash-git-push-reminder.js +35 -0
  158. package/scripts/hooks/pre-bash-tmux-reminder.js +47 -0
  159. package/scripts/hooks/pre-compact.js +51 -0
  160. package/scripts/hooks/pre-tool-use.js +163 -0
  161. package/scripts/hooks/pre-write-doc-warn.js +9 -0
  162. package/scripts/hooks/quality-gate.js +251 -0
  163. package/scripts/hooks/run-with-flags-shell.sh +32 -0
  164. package/scripts/hooks/run-with-flags.js +135 -0
  165. package/scripts/hooks/session-end-marker.js +29 -0
  166. package/scripts/hooks/session-end.js +311 -0
  167. package/scripts/hooks/session-start.js +202 -0
  168. package/scripts/hooks/sfdx-scanner-check.js +142 -0
  169. package/scripts/hooks/sfdx-validate.js +119 -0
  170. package/scripts/hooks/stop-hook.js +170 -0
  171. package/scripts/hooks/suggest-compact.js +67 -0
  172. package/scripts/lib/agent-adapter.js +82 -0
  173. package/scripts/lib/apex-analysis.js +194 -0
  174. package/scripts/lib/hook-flags.js +74 -0
  175. package/scripts/lib/install-config.js +73 -0
  176. package/scripts/lib/install-executor.js +363 -0
  177. package/scripts/lib/install-state.js +121 -0
  178. package/scripts/lib/orchestration-session.js +299 -0
  179. package/scripts/lib/package-manager.js +124 -0
  180. package/scripts/lib/project-detect.js +228 -0
  181. package/scripts/lib/schema-validator.js +190 -0
  182. package/scripts/lib/skill-adapter.js +100 -0
  183. package/scripts/lib/state-store.js +376 -0
  184. package/scripts/lib/tmux-worktree-orchestrator.js +598 -0
  185. package/scripts/lib/utils.js +313 -0
  186. package/scripts/scc.js +164 -0
  187. package/skills/_reference/AGENTFORCE_PATTERNS.md +112 -0
  188. package/skills/_reference/APEX_CURSOR.md +159 -0
  189. package/skills/_reference/API_VERSIONS.md +78 -0
  190. package/skills/_reference/APPROVAL_PROCESSES.md +105 -0
  191. package/skills/_reference/ASYNC_PATTERNS.md +163 -0
  192. package/skills/_reference/AURA_COMPONENTS.md +146 -0
  193. package/skills/_reference/DATA_MIGRATION_PATTERNS.md +151 -0
  194. package/skills/_reference/DATA_MODELING.md +124 -0
  195. package/skills/_reference/DEBUGGING_TOOLS.md +140 -0
  196. package/skills/_reference/DEPLOYMENT_CHECKLIST.md +87 -0
  197. package/skills/_reference/DEPRECATIONS.md +79 -0
  198. package/skills/_reference/DOCKER_CI_PATTERNS.md +138 -0
  199. package/skills/_reference/ENTERPRISE_PATTERNS.md +122 -0
  200. package/skills/_reference/EXPERIENCE_CLOUD.md +143 -0
  201. package/skills/_reference/FLOW_PATTERNS.md +113 -0
  202. package/skills/_reference/GOVERNOR_LIMITS.md +77 -0
  203. package/skills/_reference/INTEGRATION_PATTERNS.md +105 -0
  204. package/skills/_reference/LWC_PATTERNS.md +79 -0
  205. package/skills/_reference/METADATA_TYPES.md +115 -0
  206. package/skills/_reference/NAMING_CONVENTIONS.md +84 -0
  207. package/skills/_reference/PACKAGE_DEVELOPMENT.md +150 -0
  208. package/skills/_reference/PLATFORM_EVENTS.md +121 -0
  209. package/skills/_reference/REPORTING_API.md +143 -0
  210. package/skills/_reference/SCRATCH_ORG_PATTERNS.md +126 -0
  211. package/skills/_reference/SECURITY_PATTERNS.md +127 -0
  212. package/skills/_reference/SHARING_MODEL.md +120 -0
  213. package/skills/_reference/SOQL_PATTERNS.md +119 -0
  214. package/skills/_reference/TESTING_STANDARDS.md +96 -0
  215. package/skills/_reference/TRIGGER_PATTERNS.md +114 -0
  216. package/skills/_reference/VISUALFORCE_PATTERNS.md +121 -0
  217. package/skills/aside/SKILL.md +118 -0
  218. package/skills/checkpoint/SKILL.md +53 -0
  219. package/skills/configure-scc/SKILL.md +163 -0
  220. package/skills/continuous-agent-loop/SKILL.md +264 -0
  221. package/skills/mcp-server-patterns/SKILL.md +146 -0
  222. package/skills/model-route/SKILL.md +84 -0
  223. package/skills/prompt-optimizer/SKILL.md +369 -0
  224. package/skills/refactor-clean/SKILL.md +136 -0
  225. package/skills/resume-session/SKILL.md +114 -0
  226. package/skills/save-session/SKILL.md +186 -0
  227. package/skills/search-first/SKILL.md +144 -0
  228. package/skills/security-scan/SKILL.md +146 -0
  229. package/skills/sessions/SKILL.md +127 -0
  230. package/skills/sf-agentforce-development/SKILL.md +450 -0
  231. package/skills/sf-apex-async-patterns/SKILL.md +326 -0
  232. package/skills/sf-apex-best-practices/SKILL.md +425 -0
  233. package/skills/sf-apex-constraints/SKILL.md +81 -0
  234. package/skills/sf-apex-cursor/SKILL.md +338 -0
  235. package/skills/sf-apex-enterprise-patterns/SKILL.md +348 -0
  236. package/skills/sf-apex-testing/SKILL.md +409 -0
  237. package/skills/sf-api-design/SKILL.md +238 -0
  238. package/skills/sf-approval-processes/SKILL.md +315 -0
  239. package/skills/sf-aura-development/SKILL.md +263 -0
  240. package/skills/sf-build-fix/SKILL.md +121 -0
  241. package/skills/sf-data-modeling/SKILL.md +278 -0
  242. package/skills/sf-debugging/SKILL.md +363 -0
  243. package/skills/sf-deployment/SKILL.md +295 -0
  244. package/skills/sf-deployment-constraints/SKILL.md +155 -0
  245. package/skills/sf-devops-ci-cd/SKILL.md +325 -0
  246. package/skills/sf-docs-lookup/SKILL.md +103 -0
  247. package/skills/sf-e2e-testing/SKILL.md +324 -0
  248. package/skills/sf-experience-cloud/SKILL.md +249 -0
  249. package/skills/sf-flow-development/SKILL.md +377 -0
  250. package/skills/sf-governor-limits/SKILL.md +323 -0
  251. package/skills/sf-harness-audit/SKILL.md +142 -0
  252. package/skills/sf-help/SKILL.md +159 -0
  253. package/skills/sf-integration/SKILL.md +483 -0
  254. package/skills/sf-lwc-constraints/SKILL.md +130 -0
  255. package/skills/sf-lwc-development/SKILL.md +303 -0
  256. package/skills/sf-lwc-testing/SKILL.md +388 -0
  257. package/skills/sf-metadata-management/SKILL.md +288 -0
  258. package/skills/sf-platform-events-cdc/SKILL.md +375 -0
  259. package/skills/sf-quickstart/SKILL.md +173 -0
  260. package/skills/sf-security/SKILL.md +334 -0
  261. package/skills/sf-security-constraints/SKILL.md +127 -0
  262. package/skills/sf-soql-constraints/SKILL.md +131 -0
  263. package/skills/sf-soql-optimization/SKILL.md +354 -0
  264. package/skills/sf-tdd-workflow/SKILL.md +336 -0
  265. package/skills/sf-testing-constraints/SKILL.md +200 -0
  266. package/skills/sf-trigger-constraints/SKILL.md +90 -0
  267. package/skills/sf-trigger-frameworks/SKILL.md +347 -0
  268. package/skills/sf-visualforce-development/SKILL.md +260 -0
  269. package/skills/strategic-compact/SKILL.md +208 -0
  270. package/skills/update-docs/SKILL.md +165 -0
  271. package/skills/update-platform-docs/SKILL.md +90 -0
@@ -0,0 +1,173 @@
1
+ ---
2
+ name: sf-quickstart
3
+ description: >-
4
+ Use when setting up SCC on a Salesforce project. Detect Apex, LWC, or mixed
5
+ project type, recommend configuration, install appropriate profile.
6
+ origin: SCC
7
+ user-invocable: true
8
+ ---
9
+
10
+ # SCC Quickstart — Interactive Onboarding
11
+
12
+ Interactive onboarding for Salesforce Claude Code. Detects your project setup and recommends the right SCC configuration.
13
+
14
+ ## When to Use
15
+
16
+ - When setting up SCC for the first time on a Salesforce project
17
+ - When onboarding a new developer to an existing Salesforce org or project
18
+ - When you need to detect the project's tech stack and recommend the right SCC install profile
19
+ - When verifying that SCC is properly installed and configured
20
+ - When switching projects and need to reconfigure SCC for a different project type
21
+
22
+ ## Workflow
23
+
24
+ ### Step 1 — Detect Project Context
25
+
26
+ Check for Salesforce project markers:
27
+
28
+ ```bash
29
+ # Core project file (required for SF project)
30
+ cat sfdx-project.json 2>/dev/null
31
+
32
+ # Scratch org definition
33
+ cat config/project-scratch-def.json 2>/dev/null
34
+
35
+ # Deployment config
36
+ cat .forceignore 2>/dev/null | head -5
37
+
38
+ # Node.js tooling
39
+ cat package.json 2>/dev/null | grep -A5 '"scripts"'
40
+
41
+ # SF CLI version
42
+ sf --version 2>/dev/null
43
+ ```
44
+
45
+ If `sfdx-project.json` does not exist, this is not a Salesforce project. Report that and suggest running `/sf-help` for general SCC guidance.
46
+
47
+ ### Step 2 — Analyze Tech Stack
48
+
49
+ Scan the project to detect what technologies are in use:
50
+
51
+ ```bash
52
+ # Apex classes (not test classes)
53
+ find force-app -name "*.cls" 2>/dev/null | grep -v -E '(Test\.cls$|_Test\.cls$|TestUtils|TestData|TestFactory|TestHelper)' | wc -l
54
+
55
+ # Apex test classes
56
+ find force-app -name "*.cls" 2>/dev/null | grep -E '(Test\.cls$|_Test\.cls$|TestUtils|TestData|TestFactory|TestHelper)' | wc -l
57
+
58
+ # Apex triggers
59
+ find force-app -name "*.trigger" 2>/dev/null | wc -l
60
+
61
+ # LWC components
62
+ find force-app -path "*/lwc/*" -name "*.js" -not -name "*.test.js" 2>/dev/null | wc -l
63
+
64
+ # Aura components
65
+ find force-app -path "*/aura/*" -name "*.cmp" 2>/dev/null | wc -l
66
+
67
+ # Visualforce pages
68
+ find force-app -name "*.page" 2>/dev/null | wc -l
69
+
70
+ # Flows
71
+ find force-app -name "*.flow-meta.xml" 2>/dev/null | wc -l
72
+
73
+ # Custom objects
74
+ find force-app -name "*.object-meta.xml" 2>/dev/null | wc -l
75
+ ```
76
+
77
+ > Naive test detection with `find force-app -name "*Test.cls"` misses patterns like `*_Test.cls`, `TestUtils.cls`, `TestDataFactory.cls`, and `TestHelper.cls`. The commands above catch all standard patterns.
78
+
79
+ ### Step 3 — Recommend Install Profile
80
+
81
+ Based on detection results, recommend the best SCC profile:
82
+
83
+ | Detected Stack | Recommended Profile | Command |
84
+ |---------------|--------------------|---------|
85
+ | Apex + LWC + Flows + triggers | `all` | `npx scc install all` |
86
+ | Primarily Apex (classes + triggers) | `apex` | `npx scc install apex` |
87
+ | Primarily LWC with some Apex | `lwc` | `npx scc install lwc` |
88
+
89
+ **Profile details:**
90
+
91
+ | Profile | Agents | Skills (user-invocable) | Rules | Hooks |
92
+ |---------|--------|------------------------|-------|-------|
93
+ | `apex` | 12 | 22 (14) | common + apex + soql | all |
94
+ | `lwc` | 10 | 18 (12) | common + lwc | all |
95
+ | `all` | 27 | 45 (26) | all domains | all |
96
+
97
+ ### Step 4 — Suggest First Commands
98
+
99
+ Based on the project state, suggest 3-5 commands to start with:
100
+
101
+ | Project State | Suggested Action |
102
+ |--------------|-----------------|
103
+ | No test classes found | `sf-tdd-workflow` skill -- start writing tests |
104
+ | Triggers without handler classes | `sf-trigger-frameworks` skill -- refactor to handler pattern |
105
+ | Low test coverage | `sf-apex-testing` skill -- analyze gaps |
106
+ | Deployment files present | `sf-deployment` skill -- pre-deployment check |
107
+ | Security review needed | `sf-security` skill -- full security audit |
108
+ | Build errors | `/sf-build-fix` -- fix build and deployment errors |
109
+ | Any project | `/sf-help` -- browse all available commands and skills |
110
+
111
+ ### Step 5 — Verify SCC Installation
112
+
113
+ Check that SCC is properly configured:
114
+
115
+ ```bash
116
+ # Check hooks are loaded
117
+ test -f .claude/hooks/hooks.json && echo "Hooks: ACTIVE" || echo "Hooks: MISSING (run npx scc install)"
118
+
119
+ # Check hook profile
120
+ echo "Hook Profile: ${SCC_HOOK_PROFILE:-standard (default)}"
121
+
122
+ # Check for governor-check hook
123
+ grep -q "governor-check" .claude/hooks/hooks.json 2>/dev/null && echo "Governor Check: ACTIVE" || echo "Governor Check: MISSING"
124
+
125
+ # Check for quality-gate hook
126
+ grep -q "quality-gate" .claude/hooks/hooks.json 2>/dev/null && echo "Quality Gate: ACTIVE" || echo "Quality Gate: MISSING"
127
+ ```
128
+
129
+ ### Step 6 — Report
130
+
131
+ Present findings in this format:
132
+
133
+ ```text
134
+ SCC Quickstart Report
135
+ ======================================
136
+
137
+ Project: my-salesforce-app
138
+ SF CLI: @salesforce/cli/2.x.x
139
+
140
+ Tech Stack Detected:
141
+ Apex Classes: 45 (32 test classes)
142
+ Apex Triggers: 8
143
+ LWC Components: 12
144
+ Aura Components: 3 (consider migration)
145
+ Flows: 6
146
+ Custom Objects: 15
147
+
148
+ Recommended Profile: all
149
+ -> npx scc install all
150
+
151
+ SCC Status:
152
+ Hooks: ACTIVE (standard profile)
153
+ Governor Check: ACTIVE
154
+ Quality Gate: ACTIVE
155
+
156
+ Suggested Next Steps:
157
+ 1. sf-trigger-frameworks skill -- 3 triggers without handler classes detected
158
+ 2. sf-apex-testing skill -- Current coverage unknown, run analysis
159
+ 3. sf-security skill -- Verify CRUD/FLS before next deployment
160
+ 4. /sf-help -- Browse all available commands and skills
161
+ ```
162
+
163
+ ## Examples
164
+
165
+ ```
166
+ sf-quickstart
167
+ sf-quickstart Set up SCC for my new Salesforce DX project
168
+ sf-quickstart What SCC profile should I use for an ISV package?
169
+ ```
170
+
171
+ ## Related
172
+
173
+ - **Constraints**: (none -- this is an onboarding workflow)
@@ -0,0 +1,334 @@
1
+ ---
2
+ name: sf-security
3
+ description: >-
4
+ Use when implementing Salesforce Apex security — CRUD/FLS enforcement,
5
+ sharing keywords, SOQL injection prevention, AppExchange review prep.
6
+ Do NOT use for general Apex or LWC patterns.
7
+ origin: SCC
8
+ user-invocable: false
9
+ ---
10
+
11
+ # Salesforce Security
12
+
13
+ Salesforce has a layered security model. Each layer must be respected in Apex code, SOQL queries, and UI components.
14
+
15
+ @../_reference/SECURITY_PATTERNS.md
16
+ @../_reference/SHARING_MODEL.md
17
+
18
+ ## When to Use
19
+
20
+ - Preparing for a Salesforce security review or ISV managed package submission
21
+ - Apex classes missing `with sharing` or using unexplained `without sharing`
22
+ - SOQL queries using dynamic strings without bind variables
23
+ - CRUD/FLS checks absent from controller or service classes
24
+ - Running a security health check before a major deployment
25
+ - A penetration test or AppExchange security review flags vulnerabilities
26
+
27
+ ## CRUD Enforcement in Apex
28
+
29
+ ### WITH USER_MODE / AccessLevel.USER_MODE (see @../_reference/API_VERSIONS.md for minimum version)
30
+
31
+ The modern standard for CRUD + FLS enforcement. This replaces explicit CRUD checks and `Security.stripInaccessible` for most use cases.
32
+
33
+ ```apex
34
+ // SOQL enforces both object CRUD and FLS for the running user
35
+ List<Account> accounts = [SELECT Id, Name FROM Account WITH USER_MODE];
36
+
37
+ // For DML, use Database methods with AccessLevel
38
+ Database.insert(records, false, AccessLevel.USER_MODE);
39
+ Database.update(records, false, AccessLevel.USER_MODE);
40
+ Database.delete(records, false, AccessLevel.USER_MODE);
41
+ ```
42
+
43
+ ### When to Check CRUD
44
+
45
+ | Context | Check CRUD? |
46
+ |---|---|
47
+ | Apex called from LWC/Aura/VF page | Yes |
48
+ | Service layer called by user-facing code | Yes |
49
+ | Internal utility called by system batch | Usually no — runs in system context |
50
+ | Apex REST/SOAP API endpoint | Yes |
51
+ | Scheduled/Batch internal processing | Usually no — document justification |
52
+
53
+ ---
54
+
55
+ ## Field-Level Security (FLS)
56
+
57
+ ### Security.stripInaccessible — Bulk FLS Enforcement
58
+
59
+ `stripInaccessible()` silently removes fields the user cannot access. The returned records look normal but stripped fields are `null`. Check `getRemovedFields()` before passing records downstream.
60
+
61
+ ```apex
62
+ public List<Account> getAccountsForDisplay() {
63
+ List<Account> accounts = [
64
+ SELECT Id, Name, AnnualRevenue, SSN__c, Internal_Notes__c
65
+ FROM Account WHERE Type = 'Customer'
66
+ ];
67
+
68
+ SObjectAccessDecision decision = Security.stripInaccessible(
69
+ AccessType.READABLE, accounts
70
+ );
71
+
72
+ Map<String, Set<String>> removed = decision.getRemovedFields();
73
+ if (removed.containsKey('Account')) {
74
+ System.debug(LoggingLevel.WARN, 'Stripped fields: ' + removed.get('Account'));
75
+ }
76
+
77
+ return decision.getRecords();
78
+ }
79
+ ```
80
+
81
+ ### WITH USER_MODE for FLS in SOQL
82
+
83
+ `WITH USER_MODE` throws a `QueryException` if the running user lacks field-level access to any field in the SELECT or WHERE clause. Use `Security.stripInaccessible()` when you need to silently remove inaccessible fields instead of throwing.
84
+
85
+ ```apex
86
+ // Defensive approach: check accessibility first
87
+ List<String> selectFields = new List<String>{ 'Id', 'Name' };
88
+ if (Schema.SObjectType.Account.Fields.AnnualRevenue.getDescribe().isAccessible()) {
89
+ selectFields.add('AnnualRevenue');
90
+ }
91
+ // ... build and execute dynamic SOQL with validated fields
92
+ ```
93
+
94
+ ---
95
+
96
+ ## Sharing Keywords
97
+
98
+ ### with sharing (Default)
99
+
100
+ ```apex
101
+ public with sharing class AccountsSelector {
102
+ public List<Account> selectAll() {
103
+ return [SELECT Id, Name FROM Account]; // Only returns records user can see
104
+ }
105
+ }
106
+ ```
107
+
108
+ ### without sharing (Use Sparingly)
109
+
110
+ ```apex
111
+ /**
112
+ * Batch processor for automated data enrichment.
113
+ * Uses without sharing because:
114
+ * 1. Runs as a system user (scheduled job)
115
+ * 2. Needs to process ALL accounts regardless of ownership
116
+ * 3. Sharing is irrelevant for automated system processing
117
+ */
118
+ public without sharing class AccountEnrichmentBatch
119
+ implements Database.Batchable<SObject> {
120
+ // ...
121
+ }
122
+ ```
123
+
124
+ ### inherited sharing
125
+
126
+ ```apex
127
+ // Adopts the sharing mode of the calling class
128
+ public inherited sharing class QueryHelper {
129
+ public List<Account> getAccountsForCaller() {
130
+ return [SELECT Id, Name FROM Account];
131
+ // If called by "with sharing" class: enforces sharing
132
+ // If called by "without sharing" class: bypasses sharing
133
+ // If top-level: defaults to "with sharing"
134
+ }
135
+ }
136
+ ```
137
+
138
+ ### Decision Tree
139
+
140
+ ```
141
+ User-facing (LWC, VF, Aura, REST API)? → with sharing
142
+ Utility that respects caller's context? → inherited sharing
143
+ Scheduled/batch as system user? → without sharing (documented)
144
+ Permission elevation utility? → without sharing (narrow scope, documented)
145
+ Unsure? → with sharing
146
+ ```
147
+
148
+ > Sharing context does NOT propagate to called classes. A `with sharing` class calling a `without sharing` class runs the called method **without sharing**.
149
+
150
+ ---
151
+
152
+ ## SOQL Injection Prevention
153
+
154
+ ### Static SOQL with Bind Variables (Preferred)
155
+
156
+ ```apex
157
+ public List<Account> searchAccounts(String nameFilter) {
158
+ return [SELECT Id, Name FROM Account WHERE Name = :nameFilter WITH USER_MODE];
159
+ }
160
+ ```
161
+
162
+ ### Database.queryWithBinds (For Dynamic SOQL)
163
+
164
+ ```apex
165
+ public List<Account> searchAccounts(String nameFilter) {
166
+ Map<String, Object> binds = new Map<String, Object>{
167
+ 'nameFilter' => nameFilter
168
+ };
169
+ return Database.queryWithBinds(
170
+ 'SELECT Id, Name FROM Account WHERE Name = :nameFilter WITH USER_MODE',
171
+ binds, AccessLevel.USER_MODE
172
+ );
173
+ }
174
+ ```
175
+
176
+ ### Safe Dynamic SOQL with Whitelist Validation
177
+
178
+ ```apex
179
+ public class SafeDynamicQueryBuilder {
180
+ private static final Set<String> ALLOWED_SORT_FIELDS = new Set<String>{
181
+ 'Name', 'CreatedDate', 'AnnualRevenue', 'Type'
182
+ };
183
+ private static final Set<String> ALLOWED_DIRECTIONS = new Set<String>{
184
+ 'ASC', 'DESC'
185
+ };
186
+
187
+ public List<Account> getAccountsSorted(String sortField, String sortDirection) {
188
+ if (!ALLOWED_SORT_FIELDS.contains(sortField)) {
189
+ sortField = 'Name';
190
+ }
191
+ if (!ALLOWED_DIRECTIONS.contains(sortDirection?.toUpperCase())) {
192
+ sortDirection = 'ASC';
193
+ }
194
+
195
+ String query = 'SELECT Id, Name, AnnualRevenue, Type '
196
+ + 'FROM Account WITH USER_MODE '
197
+ + 'ORDER BY ' + sortField + ' ' + sortDirection
198
+ + ' LIMIT 200';
199
+ return Database.query(query);
200
+ }
201
+ }
202
+ ```
203
+
204
+ ---
205
+
206
+ ## XSS Prevention
207
+
208
+ ### Visualforce — Use Context-Appropriate Encoding
209
+
210
+ ```xml
211
+ <!-- HTML body → HTMLENCODE -->
212
+ <div>{!HTMLENCODE(accountDescription)}</div>
213
+
214
+ <!-- JS string → JSENCODE -->
215
+ <script>var accountName = '{!JSENCODE(account.Name)}';</script>
216
+
217
+ <!-- JS in HTML attribute → JSINHTMLENCODE -->
218
+ <div onclick="handleClick('{!JSINHTMLENCODE(account.Name)}')">Click</div>
219
+
220
+ <!-- URL parameter → URLENCODE -->
221
+ <a href="/mypage?name={!URLENCODE(account.Name)}">View</a>
222
+
223
+ <!-- Safe by default -->
224
+ <apex:outputField value="{!account.Name}" />
225
+ <apex:outputText value="{!account.Description}" escape="true" />
226
+ ```
227
+
228
+ ### LWC — Safe by Default
229
+
230
+ LWC templates auto-encode HTML. Avoid `innerHTML`:
231
+
232
+ ```javascript
233
+ // Safe — LWC encodes the value as text content
234
+ this.accountName = '<script>alert(1)</script>'; // Rendered as literal text
235
+
236
+ // Use textContent, not innerHTML
237
+ this.template.querySelector('.description').textContent = userProvidedContent;
238
+
239
+ // For rich text, use lightning-formatted-rich-text (sanitizes automatically)
240
+ ```
241
+
242
+ ---
243
+
244
+ ## Named Credentials and External Credentials
245
+
246
+ ### Secure Callout Pattern
247
+
248
+ ```apex
249
+ public class ERPIntegrationService {
250
+ public HttpResponse callERPEndpoint(String path, String method, String body) {
251
+ HttpRequest req = new HttpRequest();
252
+ req.setEndpoint('callout:ERP_System' + path);
253
+ req.setMethod(method);
254
+ req.setHeader('Content-Type', 'application/json');
255
+ if (String.isNotBlank(body)) {
256
+ req.setBody(body);
257
+ }
258
+ return new Http().send(req);
259
+ }
260
+ }
261
+ ```
262
+
263
+ ### What Belongs in Named/External Credentials
264
+
265
+ - OAuth client secrets, API keys, JWT private keys
266
+ - Endpoint URLs (use Named Credentials, not hardcoded strings)
267
+ - Per-user vs Named Principal authentication
268
+
269
+ ### Custom Metadata for Configuration
270
+
271
+ ```apex
272
+ // No SOQL limits, deployable config
273
+ Map<String, Service_Config__mdt> configs = new Map<String, Service_Config__mdt>();
274
+ for (Service_Config__mdt config : Service_Config__mdt.getAll().values()) {
275
+ configs.put(config.DeveloperName, config);
276
+ }
277
+ ```
278
+
279
+ ---
280
+
281
+ ## Enterprise Security Features
282
+
283
+ ### Shield Platform Encryption
284
+
285
+ | Encryption Type | Query Support | Use Case |
286
+ |---|---|---|
287
+ | Deterministic | Exact match only in WHERE | SSN lookup, email search |
288
+ | Probabilistic | No SOQL filtering | Health data, financial records |
289
+
290
+ Encrypted fields cannot be used in ORDER BY, GROUP BY, or LIKE queries (probabilistic). Code must handle null returns when user lacks decryption permission.
291
+
292
+ ### Event Monitoring
293
+
294
+ - **Login Events** — detect unauthorized access
295
+ - **API Events** — detect data exfiltration
296
+ - **Report Export Events** — data loss prevention
297
+
298
+ ### Transaction Security
299
+
300
+ Real-time threat detection: block large data exports, enforce MFA for sensitive operations, block restricted locations.
301
+
302
+ ---
303
+
304
+ ## Common Security Review Failures
305
+
306
+ | Failure | Fix |
307
+ |---|---|
308
+ | CRUD not checked before DML | Use `AccessLevel.USER_MODE` |
309
+ | FLS not checked before field access | Use `WITH USER_MODE` or `stripInaccessible` |
310
+ | Dynamic SOQL with string concatenation | Use bind variables or `queryWithBinds()` |
311
+ | `without sharing` on user-facing class | Switch to `with sharing` |
312
+ | Hardcoded credentials | Use Named/External Credentials |
313
+ | Sensitive data in debug logs | Remove `System.debug` of PII |
314
+ | Unrestricted SOQL rows | Add WHERE + LIMIT |
315
+ | innerHTML with user input | Use textContent or sanitized components |
316
+
317
+ ---
318
+
319
+ ## Security Skills Cross-Reference
320
+
321
+ Security guidance is distributed across multiple skills. Use this index to find the right skill:
322
+
323
+ | Skill | Focus | Type |
324
+ |---|---|---|
325
+ | `sf-security` (this skill) | CRUD/FLS, sharing, injection, Named Credentials, AppExchange prep | Implementation guide |
326
+ | `sf-security-constraints` | Hard never/always rules for security compliance | Constraint (auto-loaded) |
327
+ | `sf-apex-constraints` | Apex-specific security: `with sharing`, bind variables, `without sharing` justification | Constraint (auto-loaded) |
328
+ | `sf-soql-constraints` | SOQL injection prevention, selective queries, bind variables | Constraint (auto-loaded) |
329
+ | `sf-lwc-constraints` | LWC XSS prevention, `lwc:dom="manual"` restrictions, CSP | Constraint (auto-loaded) |
330
+
331
+ ## Related
332
+
333
+ - **Agent**: `sf-review-agent` — For interactive, in-depth guidance
334
+ - **Constraints**: `sf-security-constraints` — Hard rules for security compliance
@@ -0,0 +1,127 @@
1
+ ---
2
+ name: sf-security-constraints
3
+ description: "Enforce CRUD/FLS, sharing model, SOQL injection prevention, and XSS protection for Apex and LWC. Use when writing or reviewing ANY Apex, trigger, LWC, or VF page. Do NOT use for Flow-only configuration."
4
+ origin: SCC
5
+ user-invocable: false
6
+ allowed-tools: Read, Grep, Glob
7
+ ---
8
+
9
+ # Security Constraints for Salesforce Code
10
+
11
+ ## When to Use
12
+
13
+ This skill auto-activates when writing, reviewing, or modifying any Apex class, trigger, LWC component, or Visualforce page. It enforces CRUD/FLS checks, sharing model compliance, SOQL injection prevention, and XSS protection for all Salesforce code.
14
+
15
+ Hard rules that apply to every Apex class, trigger, LWC component, and Visualforce page. Violating any constraint below is a blocking issue that must be fixed before the code is considered complete.
16
+
17
+ Reference: @../_reference/SECURITY_PATTERNS.md, @../_reference/SHARING_MODEL.md
18
+ @../_reference/DEPRECATIONS.md
19
+
20
+ ---
21
+
22
+ ## Never Do
23
+
24
+ | # | Constraint | Why |
25
+ |---|---|---|
26
+ | N1 | Skip CRUD/FLS checks on user-facing SOQL or DML | Exposes data the running user should not see or modify |
27
+ | N2 | Use `without sharing` without a written justification comment | Silently bypasses record-level security for every query in the class |
28
+ | N3 | Build SOQL with string concatenation of user input | SOQL injection -- attacker can read or modify arbitrary records |
29
+ | N4 | Trust client-side input without server-side validation | Client payloads are trivially forgeable; all validation must repeat in Apex |
30
+ | N5 | Use `element.innerHTML = userInput` in LWC | Direct XSS vector; LWC auto-encoding is bypassed |
31
+ | N6 | Hardcode API keys, tokens, passwords, or record IDs in Apex | Credentials leak via source control; IDs differ across orgs |
32
+ | N7 | Log sensitive field values with `System.debug` | Debug logs are accessible to admins and can be exported |
33
+ | N8 | Omit the sharing keyword on a class entirely | Defaults to `without sharing` in most contexts -- an implicit security bypass |
34
+
35
+ ---
36
+
37
+ ## Always Do
38
+
39
+ | # | Constraint | How |
40
+ |---|---|---|
41
+ | A1 | Enforce CRUD + FLS on user-facing queries | `WITH USER_MODE` in SOQL (see @../_reference/API_VERSIONS.md for minimum version) |
42
+ | A2 | Enforce CRUD + FLS on user-facing DML | `Database.insert(records, false, AccessLevel.USER_MODE)` |
43
+ | A3 | Use `with sharing` as the default class keyword | Switch to `inherited sharing` only for utility/helper classes |
44
+ | A4 | Use bind variables for SOQL filter values | Static SOQL `:bindVar` or `Database.queryWithBinds()` |
45
+ | A5 | Sanitize output in Visualforce | `HTMLENCODE`, `JSENCODE`, `JSINHTMLENCODE`, `URLENCODE` per context |
46
+ | A6 | Use `textContent` or `<lightning-formatted-rich-text>` in LWC | Never assign user-controlled strings to `innerHTML` |
47
+ | A7 | Store credentials in Named Credentials / External Credentials | Use `callout:NamedCredential` prefix in Apex HTTP requests |
48
+ | A8 | Document every `without sharing` usage | Include: why sharing bypass is needed, who approved, date reviewed |
49
+ | A9 | Whitelist-validate dynamic SOQL components | Sort fields, directions, object/field names must match a known-safe set |
50
+ | A10 | Use `Security.stripInaccessible()` when silent field removal is acceptable | Always check `getRemovedFields()` to avoid downstream `NullPointerException` |
51
+
52
+ ---
53
+
54
+ ## Sharing Keyword Decision
55
+
56
+ Apply the correct keyword on every class. Reference: @../_reference/SHARING_MODEL.md
57
+
58
+ ```
59
+ User-facing code (LWC, VF, Aura, REST API)? --> with sharing
60
+ Utility / helper called from mixed contexts? --> inherited sharing
61
+ Scheduled batch / system-only processing? --> without sharing (document justification)
62
+ Trigger handler? --> with sharing (call without sharing helper only if justified)
63
+ Inner class? --> declare explicitly (does NOT inherit outer class keyword)
64
+ Omitted / unsure? --> with sharing
65
+ ```
66
+
67
+ Key rule: sharing context does **not** propagate to called classes. A `with sharing` class calling a `without sharing` class runs the called method **without sharing**.
68
+
69
+ ---
70
+
71
+ ## Anti-Pattern Table
72
+
73
+ | Anti-Pattern | Security Impact | Correct Pattern |
74
+ |---|---|---|
75
+ | `Database.query('... WHERE Name = \'' + input + '\'')` | SOQL injection -- attacker reads/modifies arbitrary data | `[SELECT ... WHERE Name = :input WITH USER_MODE]` or `Database.queryWithBinds()` |
76
+ | `public class FooController { ... }` (no sharing keyword) | Implicit `without sharing` -- returns all records | `public with sharing class FooController { ... }` |
77
+ | `public without sharing class AccountCtrl` (user-facing) | All records visible regardless of OWD, role hierarchy, sharing rules | `public with sharing class AccountCtrl` |
78
+ | `insert records;` in user-facing code | No CRUD/FLS enforcement | `Database.insert(records, false, AccessLevel.USER_MODE);` |
79
+ | `element.innerHTML = serverData` in LWC | Stored/reflected XSS | `element.textContent = serverData` |
80
+ | `req.setHeader('Authorization', 'Bearer ' + hardcodedToken)` | Credential in source code; leaks via SCM | `callout:Named_Credential` with External Credentials |
81
+ | `{!rawMergeField}` in Visualforce | Reflected XSS | `{!HTMLENCODE(rawMergeField)}` or `<apex:outputText escape="true">` |
82
+ | `System.debug('SSN: ' + contact.SSN__c)` | PII in debug logs | Remove sensitive field logging; use opaque identifiers |
83
+ | `API_Keys__c.getOrgDefaults().Token__c` for auth | Secrets in queryable Custom Setting | External Credentials (see @../_reference/API_VERSIONS.md for minimum version) |
84
+ | SOQL without `LIMIT` in user-facing context | Unbounded query; governor limit risk + data exposure | Add `LIMIT` clause; paginate with `OFFSET` or cursor |
85
+
86
+ ---
87
+
88
+ ## CRUD/FLS Enforcement Quick Reference
89
+
90
+ Reference: @../_reference/SECURITY_PATTERNS.md
91
+
92
+ | Approach | Min API | Enforces | On Violation |
93
+ |---|---|---|---|
94
+ | `WITH USER_MODE` (SOQL) | See @../_reference/API_VERSIONS.md | CRUD + FLS | Throws `QueryException` |
95
+ | `AccessLevel.USER_MODE` (DML) | See @../_reference/API_VERSIONS.md | CRUD + FLS | Throws `DmlException` |
96
+ | `WITH SECURITY_ENFORCED` (SOQL) | See @../_reference/API_VERSIONS.md | CRUD + FLS (reads) | Throws `QueryException` |
97
+ | `Security.stripInaccessible()` | See @../_reference/API_VERSIONS.md | FLS only | Silently strips fields |
98
+ | Manual `isAccessible()` / `isCreateable()` | All | CRUD only | Developer-controlled |
99
+
100
+ Prefer `WITH USER_MODE` / `AccessLevel.USER_MODE` for all new code (see @../_reference/API_VERSIONS.md for minimum version). Fall back to `stripInaccessible` only when silent field removal is the desired behavior.
101
+
102
+ ---
103
+
104
+ ## Visualforce Encoding Quick Reference
105
+
106
+ | Output Context | Encoding Function | Example |
107
+ |---|---|---|
108
+ | HTML body | `HTMLENCODE` | `{!HTMLENCODE(account.Description)}` |
109
+ | HTML attribute | `HTMLENCODE` | `title="{!HTMLENCODE(account.Name)}"` |
110
+ | JavaScript string | `JSENCODE` | `var x = '{!JSENCODE(account.Name)}'` |
111
+ | JS in HTML attribute | `JSINHTMLENCODE` | `onclick="fn('{!JSINHTMLENCODE(val)}')"` |
112
+ | URL parameter | `URLENCODE` | `href="/page?q={!URLENCODE(val)}"` |
113
+
114
+ Use `<apex:outputField>` or `<apex:outputText escape="true">` where possible -- they handle encoding automatically.
115
+
116
+ ---
117
+
118
+ ## Enforcement Priority
119
+
120
+ When reviewing or writing code, check constraints in this order:
121
+
122
+ 1. **Sharing keyword** declared on every class (N2, N8, A3)
123
+ 2. **CRUD/FLS** enforced on all user-facing SOQL and DML (N1, A1, A2)
124
+ 3. **SOQL injection** -- no string concatenation with user input (N3, A4, A9)
125
+ 4. **XSS** -- correct encoding in VF; no innerHTML in LWC (N5, A5, A6)
126
+ 5. **Credentials** -- no hardcoded secrets; use Named/External Credentials (N6, A7)
127
+ 6. **Logging** -- no sensitive data in debug statements (N7)