@salesforce/afv-skills 1.8.0 → 1.9.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 (488) hide show
  1. package/package.json +1 -1
  2. package/skills/activating-datacloud/CREDITS.md +5 -0
  3. package/skills/activating-datacloud/README.md +39 -0
  4. package/skills/activating-datacloud/SKILL.md +118 -0
  5. package/skills/analyzing-omnistudio-dependencies/CREDITS.md +5 -0
  6. package/skills/analyzing-omnistudio-dependencies/SKILL.md +477 -0
  7. package/skills/analyzing-omnistudio-dependencies/references/dependency-patterns.md +508 -0
  8. package/skills/analyzing-omnistudio-dependencies/references/namespace-guide.md +300 -0
  9. package/skills/building-omnistudio-callable-apex/CREDITS.md +9 -0
  10. package/skills/building-omnistudio-callable-apex/README.md +80 -0
  11. package/skills/building-omnistudio-callable-apex/SKILL.md +276 -0
  12. package/skills/building-omnistudio-callable-apex/assets/pattern_callable_openinterface.cls +40 -0
  13. package/skills/building-omnistudio-callable-apex/assets/pattern_callable_vanilla.cls +32 -0
  14. package/skills/building-omnistudio-callable-apex/assets/pattern_migration.cls +54 -0
  15. package/skills/building-omnistudio-callable-apex/assets/pattern_openinterface.cls +45 -0
  16. package/skills/building-omnistudio-callable-apex/assets/pattern_test_class.cls +65 -0
  17. package/skills/building-omnistudio-callable-apex/examples/Test_QuoteByProductCallable/IndustriesCallableException.cls +7 -0
  18. package/skills/building-omnistudio-callable-apex/examples/Test_QuoteByProductCallable/Industries_QuoteByProductCallable.cls +115 -0
  19. package/skills/building-omnistudio-callable-apex/examples/Test_QuoteByProductCallable/Industries_QuoteByProductCallableTest.cls +189 -0
  20. package/skills/building-omnistudio-callable-apex/examples/Test_QuoteByProductCallable/TRANSCRIPT.md +115 -0
  21. package/skills/building-omnistudio-callable-apex/examples/Test_VlocityOpenInterface2Conversion/IndustriesCallableException.cls +7 -0
  22. package/skills/building-omnistudio-callable-apex/examples/Test_VlocityOpenInterface2Conversion/MyCustomCallable.cls +74 -0
  23. package/skills/building-omnistudio-callable-apex/examples/Test_VlocityOpenInterface2Conversion/MyCustomCallableTest.cls +146 -0
  24. package/skills/building-omnistudio-callable-apex/examples/Test_VlocityOpenInterface2Conversion/MyCustomRemoteClass.cls +16 -0
  25. package/skills/building-omnistudio-callable-apex/examples/Test_VlocityOpenInterface2Conversion/TRANSCRIPT.md +120 -0
  26. package/skills/building-omnistudio-callable-apex/examples/Test_VlocityOpenInterfaceConversion/IndustriesCallableException.cls +7 -0
  27. package/skills/building-omnistudio-callable-apex/examples/Test_VlocityOpenInterfaceConversion/MyCustomCallable.cls +73 -0
  28. package/skills/building-omnistudio-callable-apex/examples/Test_VlocityOpenInterfaceConversion/MyCustomCallableTest.cls +128 -0
  29. package/skills/building-omnistudio-callable-apex/examples/Test_VlocityOpenInterfaceConversion/MyCustomVlocityOpenInterface2.cls +23 -0
  30. package/skills/building-omnistudio-callable-apex/examples/Test_VlocityOpenInterfaceConversion/TRANSCRIPT.md +75 -0
  31. package/skills/building-omnistudio-datamapper/CREDITS.md +5 -0
  32. package/skills/building-omnistudio-datamapper/SKILL.md +270 -0
  33. package/skills/building-omnistudio-datamapper/assets/completion-summary-template.md +28 -0
  34. package/skills/building-omnistudio-datamapper/assets/omni-data-transform-extract.json +6 -0
  35. package/skills/building-omnistudio-datamapper/assets/omni-data-transform-item.json +12 -0
  36. package/skills/building-omnistudio-datamapper/assets/omni-data-transform-load.json +6 -0
  37. package/skills/building-omnistudio-datamapper/assets/omni-data-transform-transform.json +6 -0
  38. package/skills/building-omnistudio-datamapper/references/best-practices.md +277 -0
  39. package/skills/building-omnistudio-datamapper/references/naming-conventions.md +145 -0
  40. package/skills/building-omnistudio-flexcard/CREDITS.md +5 -0
  41. package/skills/building-omnistudio-flexcard/SKILL.md +325 -0
  42. package/skills/building-omnistudio-flexcard/assets/omni-ui-card.json +10 -0
  43. package/skills/building-omnistudio-flexcard/references/best-practices.md +291 -0
  44. package/skills/building-omnistudio-flexcard/references/data-binding-guide.md +311 -0
  45. package/skills/building-omnistudio-flexcard/references/scoring-rubric.md +66 -0
  46. package/skills/building-omnistudio-flexcard/scripts/flexcard-commands.sh +24 -0
  47. package/skills/building-omnistudio-integration-procedure/CREDITS.md +5 -0
  48. package/skills/building-omnistudio-integration-procedure/SKILL.md +275 -0
  49. package/skills/building-omnistudio-integration-procedure/assets/omni-process-element-dr-extract.json +10 -0
  50. package/skills/building-omnistudio-integration-procedure/assets/omni-process-element-set-values.json +10 -0
  51. package/skills/building-omnistudio-integration-procedure/assets/omni-process-ip.json +12 -0
  52. package/skills/building-omnistudio-integration-procedure/assets/scoring-report-format.txt +14 -0
  53. package/skills/building-omnistudio-integration-procedure/references/best-practices.md +388 -0
  54. package/skills/building-omnistudio-integration-procedure/references/element-types.md +588 -0
  55. package/skills/building-omnistudio-integration-procedure/scripts/cli-commands.sh +18 -0
  56. package/skills/building-omnistudio-omniscript/CREDITS.md +5 -0
  57. package/skills/building-omnistudio-omniscript/SKILL.md +367 -0
  58. package/skills/building-omnistudio-omniscript/assets/omni-process-element-step.json +10 -0
  59. package/skills/building-omnistudio-omniscript/assets/omni-process-element-text-block.json +11 -0
  60. package/skills/building-omnistudio-omniscript/assets/omni-process-omniscript.json +12 -0
  61. package/skills/building-omnistudio-omniscript/references/best-practices.md +480 -0
  62. package/skills/building-omnistudio-omniscript/references/element-types.md +1172 -0
  63. package/skills/building-omnistudio-omniscript/scripts/check-duplicate-omniscript.sh +13 -0
  64. package/skills/building-omnistudio-omniscript/scripts/cli-reference.sh +21 -0
  65. package/skills/building-omnistudio-omniscript/scripts/deploy-omniscript.sh +29 -0
  66. package/skills/building-sf-integrations/CREDITS.md +5 -0
  67. package/skills/building-sf-integrations/README.md +95 -0
  68. package/skills/building-sf-integrations/SKILL.md +192 -0
  69. package/skills/building-sf-integrations/assets/callouts/callout-retry-handler.cls +167 -0
  70. package/skills/building-sf-integrations/assets/callouts/http-response-handler.cls +257 -0
  71. package/skills/building-sf-integrations/assets/callouts/rest-queueable-callout.cls +262 -0
  72. package/skills/building-sf-integrations/assets/callouts/rest-sync-callout.cls +211 -0
  73. package/skills/building-sf-integrations/assets/cdc/cdc-handler.cls +246 -0
  74. package/skills/building-sf-integrations/assets/cdc/cdc-subscriber-trigger.trigger +139 -0
  75. package/skills/building-sf-integrations/assets/endpoint-security/example.cspTrustedSite-meta.xml +58 -0
  76. package/skills/building-sf-integrations/assets/endpoint-security/example.remoteSite-meta.xml +39 -0
  77. package/skills/building-sf-integrations/assets/external-credentials/jwt-external-credential.externalCredential-meta.xml +90 -0
  78. package/skills/building-sf-integrations/assets/external-credentials/oauth-external-credential.externalCredential-meta.xml +87 -0
  79. package/skills/building-sf-integrations/assets/external-services/external-service-operations.md +221 -0
  80. package/skills/building-sf-integrations/assets/external-services/openapi-registration.externalServiceRegistration-meta.xml +193 -0
  81. package/skills/building-sf-integrations/assets/named-credentials/certificate-auth.namedCredential-meta.xml +62 -0
  82. package/skills/building-sf-integrations/assets/named-credentials/custom-auth.namedCredential-meta.xml +71 -0
  83. package/skills/building-sf-integrations/assets/named-credentials/oauth-client-credentials.namedCredential-meta.xml +51 -0
  84. package/skills/building-sf-integrations/assets/named-credentials/oauth-jwt-bearer.namedCredential-meta.xml +67 -0
  85. package/skills/building-sf-integrations/assets/platform-events/event-publisher.cls +191 -0
  86. package/skills/building-sf-integrations/assets/platform-events/event-subscriber-action.cls +295 -0
  87. package/skills/building-sf-integrations/assets/platform-events/event-subscriber-trigger.trigger +108 -0
  88. package/skills/building-sf-integrations/assets/platform-events/platform-event-definition.object-meta.xml +124 -0
  89. package/skills/building-sf-integrations/assets/soap/soap-callout-service.cls +186 -0
  90. package/skills/building-sf-integrations/assets/soap/wsdl2apex-guide.md +213 -0
  91. package/skills/building-sf-integrations/hooks/scripts/suggest_credential_setup.py +271 -0
  92. package/skills/building-sf-integrations/hooks/scripts/validate_integration.py +363 -0
  93. package/skills/building-sf-integrations/references/callout-patterns.md +719 -0
  94. package/skills/building-sf-integrations/references/cdc-guide.md +288 -0
  95. package/skills/building-sf-integrations/references/cli-reference.md +94 -0
  96. package/skills/building-sf-integrations/references/event-driven-architecture-guide.md +266 -0
  97. package/skills/building-sf-integrations/references/event-patterns.md +838 -0
  98. package/skills/building-sf-integrations/references/external-services-guide.md +303 -0
  99. package/skills/building-sf-integrations/references/messaging-api-v2.md +609 -0
  100. package/skills/building-sf-integrations/references/named-credentials-automation.md +201 -0
  101. package/skills/building-sf-integrations/references/named-credentials-guide.md +173 -0
  102. package/skills/building-sf-integrations/references/platform-events-guide.md +288 -0
  103. package/skills/building-sf-integrations/references/rest-callout-patterns.md +288 -0
  104. package/skills/building-sf-integrations/references/scoring-rubric.md +59 -0
  105. package/skills/building-sf-integrations/references/security-best-practices.md +248 -0
  106. package/skills/building-sf-integrations/scripts/README.md +100 -0
  107. package/skills/building-sf-integrations/scripts/configure-named-credential.sh +236 -0
  108. package/skills/building-sf-integrations/scripts/set-api-credential.sh +146 -0
  109. package/skills/building-sf-integrations/scripts/templates/setup-credentials-with-csp.sh +158 -0
  110. package/skills/configuring-connected-apps/CREDITS.md +3 -0
  111. package/skills/configuring-connected-apps/README.md +99 -0
  112. package/skills/configuring-connected-apps/SKILL.md +224 -0
  113. package/skills/configuring-connected-apps/assets/connected-app-basic.xml +29 -0
  114. package/skills/configuring-connected-apps/assets/connected-app-canvas.xml +62 -0
  115. package/skills/configuring-connected-apps/assets/connected-app-jwt.xml +49 -0
  116. package/skills/configuring-connected-apps/assets/connected-app-oauth.xml +65 -0
  117. package/skills/configuring-connected-apps/assets/eca-global-oauth.xml +36 -0
  118. package/skills/configuring-connected-apps/assets/eca-oauth-settings.xml +36 -0
  119. package/skills/configuring-connected-apps/assets/eca-policies.xml +36 -0
  120. package/skills/configuring-connected-apps/assets/external-client-app.xml +35 -0
  121. package/skills/configuring-connected-apps/references/example-usage.md +256 -0
  122. package/skills/configuring-connected-apps/references/migration-guide.md +328 -0
  123. package/skills/configuring-connected-apps/references/oauth-flows-reference.md +660 -0
  124. package/skills/configuring-connected-apps/references/security-checklist.md +209 -0
  125. package/skills/configuring-connected-apps/references/testing-validation-guide.md +275 -0
  126. package/skills/connecting-datacloud/CREDITS.md +5 -0
  127. package/skills/connecting-datacloud/README.md +59 -0
  128. package/skills/connecting-datacloud/SKILL.md +155 -0
  129. package/skills/connecting-datacloud/examples/connections/heroku-postgres.json +15 -0
  130. package/skills/connecting-datacloud/examples/connections/ingest-api-connection.json +5 -0
  131. package/skills/connecting-datacloud/examples/connections/ingest-api-schema.json +31 -0
  132. package/skills/connecting-datacloud/examples/connections/redshift.json +16 -0
  133. package/skills/connecting-datacloud/examples/connections/sharepoint-unstructured.json +20 -0
  134. package/skills/connecting-datacloud/examples/connections/snowflake-connection.json +42 -0
  135. package/skills/debugging-apex-logs/CREDITS.md +22 -0
  136. package/skills/debugging-apex-logs/README.md +74 -0
  137. package/skills/debugging-apex-logs/SKILL.md +172 -0
  138. package/skills/debugging-apex-logs/assets/benchmarking-template.cls +327 -0
  139. package/skills/debugging-apex-logs/assets/cpu-heap-optimization.cls +307 -0
  140. package/skills/debugging-apex-logs/assets/dml-in-loop-fix.cls +219 -0
  141. package/skills/debugging-apex-logs/assets/null-pointer-fix.cls +252 -0
  142. package/skills/debugging-apex-logs/assets/soql-in-loop-fix.cls +157 -0
  143. package/skills/debugging-apex-logs/references/analysis-playbook.md +53 -0
  144. package/skills/debugging-apex-logs/references/benchmarking-guide.md +287 -0
  145. package/skills/debugging-apex-logs/references/cli-commands.md +368 -0
  146. package/skills/debugging-apex-logs/references/common-issues.md +68 -0
  147. package/skills/debugging-apex-logs/references/debug-log-reference.md +328 -0
  148. package/skills/debugging-apex-logs/references/log-analysis-tools.md +248 -0
  149. package/skills/debugging-apex-logs/references/scoring-rubric.md +21 -0
  150. package/skills/deploying-metadata/CREDITS.md +25 -0
  151. package/skills/deploying-metadata/README.md +104 -0
  152. package/skills/deploying-metadata/SKILL.md +214 -0
  153. package/skills/deploying-metadata/assets/destructiveChanges.xml +143 -0
  154. package/skills/deploying-metadata/assets/package.xml +121 -0
  155. package/skills/deploying-metadata/references/agent-deployment-guide.md +628 -0
  156. package/skills/deploying-metadata/references/deploy.sh +73 -0
  157. package/skills/deploying-metadata/references/deployment-report-template.md +89 -0
  158. package/skills/deploying-metadata/references/deployment-workflows.md +395 -0
  159. package/skills/deploying-metadata/references/orchestration.md +183 -0
  160. package/skills/deploying-metadata/references/trigger-deployment-safety.md +376 -0
  161. package/skills/deploying-omnistudio-datapacks/CREDITS.md +5 -0
  162. package/skills/deploying-omnistudio-datapacks/README.md +88 -0
  163. package/skills/deploying-omnistudio-datapacks/SKILL.md +174 -0
  164. package/skills/deploying-omnistudio-datapacks/examples/business-internet-plus-bundle/TRANSCRIPT.md +124 -0
  165. package/skills/deploying-omnistudio-datapacks/examples/business-internet-plus-bundle/deploy-business-internet-plus-bundle.yaml +11 -0
  166. package/skills/deploying-omnistudio-datapacks/examples/business-internet-plus-bundle-deploy/TRANSCRIPT.md +142 -0
  167. package/skills/deploying-omnistudio-datapacks/examples/business-internet-plus-bundle-deploy/deploy-business-internet-plus-bundle.yaml +10 -0
  168. package/skills/deploying-omnistudio-datapacks/references/job-file-template.md +42 -0
  169. package/skills/deploying-omnistudio-datapacks/references/troubleshooting-matrix.md +24 -0
  170. package/skills/developing-agentforce/assets/metadata/http-callout-flow.flow-meta.xml +1 -1
  171. package/skills/developing-agentforce/references/actions-reference.md +8 -8
  172. package/skills/fetching-salesforce-docs/README.md +66 -0
  173. package/skills/fetching-salesforce-docs/SKILL.md +209 -0
  174. package/skills/fetching-salesforce-docs/requirements.txt +2 -0
  175. package/skills/fetching-salesforce-docs/scripts/extract_help_salesforce.py +497 -0
  176. package/skills/fetching-salesforce-docs/scripts/extract_salesforce_doc.py +357 -0
  177. package/skills/fetching-salesforce-docs/scripts/runtime_bootstrap.py +58 -0
  178. package/skills/generating-apex/CREDITS.md +1 -26
  179. package/skills/generating-apex-test/CREDITS.md +2 -27
  180. package/skills/generating-lwc-components/CREDITS.md +5 -0
  181. package/skills/generating-lwc-components/README.md +126 -0
  182. package/skills/generating-lwc-components/SKILL.md +191 -0
  183. package/skills/generating-lwc-components/assets/apex-controller/LwcController.cls +327 -0
  184. package/skills/generating-lwc-components/assets/basic-component/basicComponent.css +72 -0
  185. package/skills/generating-lwc-components/assets/basic-component/basicComponent.html +111 -0
  186. package/skills/generating-lwc-components/assets/basic-component/basicComponent.js +163 -0
  187. package/skills/generating-lwc-components/assets/basic-component/basicComponent.js-meta.xml +137 -0
  188. package/skills/generating-lwc-components/assets/datatable-component/datatableComponent.html +111 -0
  189. package/skills/generating-lwc-components/assets/datatable-component/datatableComponent.js +367 -0
  190. package/skills/generating-lwc-components/assets/flow-screen-component/flowScreenComponent.css +63 -0
  191. package/skills/generating-lwc-components/assets/flow-screen-component/flowScreenComponent.html +154 -0
  192. package/skills/generating-lwc-components/assets/flow-screen-component/flowScreenComponent.js +348 -0
  193. package/skills/generating-lwc-components/assets/flow-screen-component/flowScreenComponent.js-meta.xml +87 -0
  194. package/skills/generating-lwc-components/assets/form-component/formComponent.html +165 -0
  195. package/skills/generating-lwc-components/assets/form-component/formComponent.js +275 -0
  196. package/skills/generating-lwc-components/assets/graphql-component/graphqlComponent.html +100 -0
  197. package/skills/generating-lwc-components/assets/graphql-component/graphqlComponent.js +336 -0
  198. package/skills/generating-lwc-components/assets/jest-test/componentName.test.js.example +371 -0
  199. package/skills/generating-lwc-components/assets/message-channel/RecordSelected.messageChannel-meta.xml +71 -0
  200. package/skills/generating-lwc-components/assets/message-channel/lmsPublisher.js +103 -0
  201. package/skills/generating-lwc-components/assets/message-channel/lmsSubscriber.js +181 -0
  202. package/skills/generating-lwc-components/assets/modal-component/modalComponent.html +85 -0
  203. package/skills/generating-lwc-components/assets/modal-component/modalComponent.js +199 -0
  204. package/skills/generating-lwc-components/assets/record-picker/recordPicker.html +55 -0
  205. package/skills/generating-lwc-components/assets/record-picker/recordPicker.js +199 -0
  206. package/skills/generating-lwc-components/assets/state-store/store.js +282 -0
  207. package/skills/generating-lwc-components/assets/typescript-component/typescriptComponent.css +65 -0
  208. package/skills/generating-lwc-components/assets/typescript-component/typescriptComponent.html +95 -0
  209. package/skills/generating-lwc-components/assets/typescript-component/typescriptComponent.js-meta.xml +75 -0
  210. package/skills/generating-lwc-components/assets/typescript-component/typescriptComponent.test.ts.example +301 -0
  211. package/skills/generating-lwc-components/assets/typescript-component/typescriptComponent.ts +295 -0
  212. package/skills/generating-lwc-components/assets/workspace-api/workspaceComponent.html +71 -0
  213. package/skills/generating-lwc-components/assets/workspace-api/workspaceComponent.js +316 -0
  214. package/skills/generating-lwc-components/hooks/scripts/lwc-lsp-validate.py +295 -0
  215. package/skills/generating-lwc-components/hooks/scripts/post-tool-validate.py +347 -0
  216. package/skills/generating-lwc-components/hooks/scripts/slds_data/deprecated_patterns.json +74 -0
  217. package/skills/generating-lwc-components/hooks/scripts/slds_data/styling_hooks.json +111 -0
  218. package/skills/generating-lwc-components/hooks/scripts/slds_data/valid_slds_classes.json +127 -0
  219. package/skills/generating-lwc-components/hooks/scripts/slds_linter_wrapper.py +294 -0
  220. package/skills/generating-lwc-components/hooks/scripts/slds_rules/__init__.py +22 -0
  221. package/skills/generating-lwc-components/hooks/scripts/template_validator.py +332 -0
  222. package/skills/generating-lwc-components/hooks/scripts/validate_slds.py +595 -0
  223. package/skills/generating-lwc-components/references/accessibility-guide.md +843 -0
  224. package/skills/generating-lwc-components/references/advanced-features.md +108 -0
  225. package/skills/generating-lwc-components/references/async-notification-patterns.md +661 -0
  226. package/skills/generating-lwc-components/references/cli-commands.md +545 -0
  227. package/skills/generating-lwc-components/references/component-patterns.md +1476 -0
  228. package/skills/generating-lwc-components/references/flow-integration-guide.md +675 -0
  229. package/skills/generating-lwc-components/references/jest-testing.md +1011 -0
  230. package/skills/generating-lwc-components/references/lms-guide.md +860 -0
  231. package/skills/generating-lwc-components/references/lwc-best-practices.md +1310 -0
  232. package/skills/generating-lwc-components/references/performance-guide.md +861 -0
  233. package/skills/generating-lwc-components/references/scoring-and-testing.md +116 -0
  234. package/skills/generating-lwc-components/references/slds-blueprints.json +14389 -0
  235. package/skills/generating-lwc-components/references/slds-design-guide.md +166 -0
  236. package/skills/generating-lwc-components/references/state-management.md +642 -0
  237. package/skills/generating-lwc-components/references/template-anti-patterns.md +948 -0
  238. package/skills/generating-lwc-components/references/triangle-pattern.md +365 -0
  239. package/skills/generating-lwc-components/scripts/local-dev-preview.sh +34 -0
  240. package/skills/generating-mermaid-diagrams/CREDITS.md +46 -0
  241. package/skills/generating-mermaid-diagrams/README.md +114 -0
  242. package/skills/generating-mermaid-diagrams/SKILL.md +218 -0
  243. package/skills/generating-mermaid-diagrams/assets/agentforce/agent-flow.md +313 -0
  244. package/skills/generating-mermaid-diagrams/assets/architecture/system-landscape.md +351 -0
  245. package/skills/generating-mermaid-diagrams/assets/datamodel/b2b-commerce-erd.md +317 -0
  246. package/skills/generating-mermaid-diagrams/assets/datamodel/campaigns-erd.md +195 -0
  247. package/skills/generating-mermaid-diagrams/assets/datamodel/consent-erd.md +262 -0
  248. package/skills/generating-mermaid-diagrams/assets/datamodel/files-erd.md +266 -0
  249. package/skills/generating-mermaid-diagrams/assets/datamodel/forecasting-erd.md +261 -0
  250. package/skills/generating-mermaid-diagrams/assets/datamodel/fsl-erd.md +332 -0
  251. package/skills/generating-mermaid-diagrams/assets/datamodel/party-model-erd.md +237 -0
  252. package/skills/generating-mermaid-diagrams/assets/datamodel/quote-order-erd.md +277 -0
  253. package/skills/generating-mermaid-diagrams/assets/datamodel/revenue-cloud-erd.md +343 -0
  254. package/skills/generating-mermaid-diagrams/assets/datamodel/sales-cloud-erd.md +192 -0
  255. package/skills/generating-mermaid-diagrams/assets/datamodel/salesforce-erd.md +209 -0
  256. package/skills/generating-mermaid-diagrams/assets/datamodel/scheduler-erd.md +276 -0
  257. package/skills/generating-mermaid-diagrams/assets/datamodel/service-cloud-erd.md +217 -0
  258. package/skills/generating-mermaid-diagrams/assets/datamodel/territory-management-erd.md +241 -0
  259. package/skills/generating-mermaid-diagrams/assets/integration/api-sequence.md +387 -0
  260. package/skills/generating-mermaid-diagrams/assets/oauth/authorization-code-pkce.md +197 -0
  261. package/skills/generating-mermaid-diagrams/assets/oauth/authorization-code.md +152 -0
  262. package/skills/generating-mermaid-diagrams/assets/oauth/client-credentials.md +233 -0
  263. package/skills/generating-mermaid-diagrams/assets/oauth/device-authorization.md +295 -0
  264. package/skills/generating-mermaid-diagrams/assets/oauth/jwt-bearer.md +256 -0
  265. package/skills/generating-mermaid-diagrams/assets/oauth/refresh-token.md +281 -0
  266. package/skills/generating-mermaid-diagrams/assets/oauth/user-agent-social-sign-on.md +281 -0
  267. package/skills/generating-mermaid-diagrams/assets/role-hierarchy/user-hierarchy.md +322 -0
  268. package/skills/generating-mermaid-diagrams/references/color-palette.md +464 -0
  269. package/skills/generating-mermaid-diagrams/references/diagram-conventions.md +313 -0
  270. package/skills/generating-mermaid-diagrams/references/erd-conventions.md +320 -0
  271. package/skills/generating-mermaid-diagrams/references/mermaid-reference.md +434 -0
  272. package/skills/generating-mermaid-diagrams/references/mermaid-styling.md +81 -0
  273. package/skills/generating-mermaid-diagrams/references/preview-guide.md +49 -0
  274. package/skills/generating-mermaid-diagrams/references/usage-examples.md +340 -0
  275. package/skills/generating-mermaid-diagrams/scripts/README.md +160 -0
  276. package/skills/generating-mermaid-diagrams/scripts/mermaid_preview.py +654 -0
  277. package/skills/generating-mermaid-diagrams/scripts/query-org-metadata.py +293 -0
  278. package/skills/generating-visual-diagrams/CREDITS.md +80 -0
  279. package/skills/generating-visual-diagrams/README.md +83 -0
  280. package/skills/generating-visual-diagrams/SKILL.md +208 -0
  281. package/skills/generating-visual-diagrams/assets/architecture/integration-flow.md +55 -0
  282. package/skills/generating-visual-diagrams/assets/erd/core-objects.md +131 -0
  283. package/skills/generating-visual-diagrams/assets/erd/custom-objects.md +60 -0
  284. package/skills/generating-visual-diagrams/assets/lwc/dashboard-card.md +45 -0
  285. package/skills/generating-visual-diagrams/assets/lwc/data-table.md +57 -0
  286. package/skills/generating-visual-diagrams/assets/lwc/record-form.md +60 -0
  287. package/skills/generating-visual-diagrams/assets/review/apex-review.md +57 -0
  288. package/skills/generating-visual-diagrams/assets/review/lwc-review.md +48 -0
  289. package/skills/generating-visual-diagrams/references/architect-aesthetic-guide.md +257 -0
  290. package/skills/generating-visual-diagrams/references/examples-index.md +35 -0
  291. package/skills/generating-visual-diagrams/references/gemini-cli-setup.md +65 -0
  292. package/skills/generating-visual-diagrams/references/interview-questions.md +529 -0
  293. package/skills/generating-visual-diagrams/references/iteration-workflow.md +173 -0
  294. package/skills/generating-visual-diagrams/scripts/check-prerequisites.sh +101 -0
  295. package/skills/generating-visual-diagrams/scripts/generate_image.py +243 -0
  296. package/skills/handling-sf-data/CREDITS.md +5 -0
  297. package/skills/handling-sf-data/README.md +112 -0
  298. package/skills/handling-sf-data/SKILL.md +235 -0
  299. package/skills/handling-sf-data/assets/bulk/bulk-insert-10000.apex +293 -0
  300. package/skills/handling-sf-data/assets/bulk/bulk-insert-200.apex +208 -0
  301. package/skills/handling-sf-data/assets/bulk/bulk-insert-500.apex +219 -0
  302. package/skills/handling-sf-data/assets/bulk/bulk-upsert-external-id.apex +324 -0
  303. package/skills/handling-sf-data/assets/cleanup/delete-by-created-date.apex +319 -0
  304. package/skills/handling-sf-data/assets/cleanup/delete-by-name.apex +240 -0
  305. package/skills/handling-sf-data/assets/cleanup/delete-test-data.apex +311 -0
  306. package/skills/handling-sf-data/assets/cleanup/rollback-transaction.apex +266 -0
  307. package/skills/handling-sf-data/assets/csv/account-import.csv +11 -0
  308. package/skills/handling-sf-data/assets/csv/contact-import.csv +11 -0
  309. package/skills/handling-sf-data/assets/csv/custom-object-import.csv +11 -0
  310. package/skills/handling-sf-data/assets/csv/opportunity-import.csv +11 -0
  311. package/skills/handling-sf-data/assets/factories/account-factory.apex +165 -0
  312. package/skills/handling-sf-data/assets/factories/case-factory.apex +237 -0
  313. package/skills/handling-sf-data/assets/factories/contact-factory.apex +168 -0
  314. package/skills/handling-sf-data/assets/factories/custom-object-factory.apex +260 -0
  315. package/skills/handling-sf-data/assets/factories/event-factory.apex +275 -0
  316. package/skills/handling-sf-data/assets/factories/hierarchy-factory.apex +372 -0
  317. package/skills/handling-sf-data/assets/factories/lead-factory.apex +190 -0
  318. package/skills/handling-sf-data/assets/factories/opportunity-factory.apex +206 -0
  319. package/skills/handling-sf-data/assets/factories/task-factory.apex +246 -0
  320. package/skills/handling-sf-data/assets/factories/user-factory.apex +278 -0
  321. package/skills/handling-sf-data/assets/json/account-contact-tree.json +130 -0
  322. package/skills/handling-sf-data/assets/json/account-opportunity-tree.json +110 -0
  323. package/skills/handling-sf-data/assets/json/full-hierarchy-tree.json +188 -0
  324. package/skills/handling-sf-data/assets/soql/aggregate.soql +226 -0
  325. package/skills/handling-sf-data/assets/soql/child-to-parent.soql +162 -0
  326. package/skills/handling-sf-data/assets/soql/parent-to-child.soql +153 -0
  327. package/skills/handling-sf-data/assets/soql/polymorphic.soql +198 -0
  328. package/skills/handling-sf-data/assets/soql/subquery.soql +287 -0
  329. package/skills/handling-sf-data/references/anonymous-apex-guide.md +98 -0
  330. package/skills/handling-sf-data/references/bulk-operations-guide.md +94 -0
  331. package/skills/handling-sf-data/references/bulk-testing-example.md +194 -0
  332. package/skills/handling-sf-data/references/cleanup-rollback-example.md +322 -0
  333. package/skills/handling-sf-data/references/cleanup-rollback-guide.md +84 -0
  334. package/skills/handling-sf-data/references/crud-workflow-example.md +183 -0
  335. package/skills/handling-sf-data/references/governor-limits-reference.md +74 -0
  336. package/skills/handling-sf-data/references/orchestration.md +174 -0
  337. package/skills/handling-sf-data/references/relationship-query-examples.md +249 -0
  338. package/skills/handling-sf-data/references/sf-cli-data-commands.md +158 -0
  339. package/skills/handling-sf-data/references/soql-relationship-guide.md +84 -0
  340. package/skills/handling-sf-data/references/test-data-best-practices.md +104 -0
  341. package/skills/handling-sf-data/references/test-data-factory-usage.md +290 -0
  342. package/skills/handling-sf-data/references/test-data-patterns.md +98 -0
  343. package/skills/handling-sf-data/scripts/soql_validator.py +292 -0
  344. package/skills/handling-sf-data/scripts/validate_data_operation.py +379 -0
  345. package/skills/harmonizing-datacloud/CREDITS.md +3 -0
  346. package/skills/harmonizing-datacloud/README.md +31 -0
  347. package/skills/harmonizing-datacloud/SKILL.md +117 -0
  348. package/skills/modeling-omnistudio-epc-catalog/CREDITS.md +14 -0
  349. package/skills/modeling-omnistudio-epc-catalog/README.md +89 -0
  350. package/skills/modeling-omnistudio-epc-catalog/SKILL.md +395 -0
  351. package/skills/modeling-omnistudio-epc-catalog/assets/attribute-assignment-template.json +402 -0
  352. package/skills/modeling-omnistudio-epc-catalog/assets/compiled-attribute-overrides-template.json +43 -0
  353. package/skills/modeling-omnistudio-epc-catalog/assets/completion-block-template.txt +8 -0
  354. package/skills/modeling-omnistudio-epc-catalog/assets/decomposition-relationships-template.json +233 -0
  355. package/skills/modeling-omnistudio-epc-catalog/assets/examples/business-internet-premium-fttc-simple-offer/Business-Internet-Premium-FTTC_AttributeAssignments.json +514 -0
  356. package/skills/modeling-omnistudio-epc-catalog/assets/examples/business-internet-premium-fttc-simple-offer/Business-Internet-Premium-FTTC_CompiledAttributeOverrides.json +21 -0
  357. package/skills/modeling-omnistudio-epc-catalog/assets/examples/business-internet-premium-fttc-simple-offer/Business-Internet-Premium-FTTC_DataPack.json +649 -0
  358. package/skills/modeling-omnistudio-epc-catalog/assets/examples/business-internet-premium-fttc-simple-offer/Business-Internet-Premium-FTTC_DecompositionRelationships.json +200 -0
  359. package/skills/modeling-omnistudio-epc-catalog/assets/examples/business-internet-premium-fttc-simple-offer/Business-Internet-Premium-FTTC_ObjectFieldAttributes.json +138 -0
  360. package/skills/modeling-omnistudio-epc-catalog/assets/examples/business-internet-premium-fttc-simple-offer/Business-Internet-Premium-FTTC_OrchestrationScenarios.json +54 -0
  361. package/skills/modeling-omnistudio-epc-catalog/assets/examples/business-internet-premium-fttc-simple-offer/Business-Internet-Premium-FTTC_OverrideDefinitions.json +266 -0
  362. package/skills/modeling-omnistudio-epc-catalog/assets/examples/business-internet-premium-fttc-simple-offer/Business-Internet-Premium-FTTC_ParentKeys.json +23 -0
  363. package/skills/modeling-omnistudio-epc-catalog/assets/examples/business-internet-premium-fttc-simple-offer/Business-Internet-Premium-FTTC_PriceListEntries.json +54 -0
  364. package/skills/modeling-omnistudio-epc-catalog/assets/examples/business-internet-premium-fttc-simple-offer/Business-Internet-Premium-FTTC_PricebookEntries.json +35 -0
  365. package/skills/modeling-omnistudio-epc-catalog/assets/examples/business-internet-premium-fttc-simple-offer/Business-Internet-Premium-FTTC_ProductChildItems.json +34 -0
  366. package/skills/modeling-omnistudio-epc-catalog/assets/examples/business-internet-premium-fttc-simple-offer/Business-Internet-Premium-FTTC_RuleAssignments.json +21 -0
  367. package/skills/modeling-omnistudio-epc-catalog/assets/examples/business-internet-pro-vpl-simple-offer/Business-Internet-Pro-VPL_AttributeAssignments.json +410 -0
  368. package/skills/modeling-omnistudio-epc-catalog/assets/examples/business-internet-pro-vpl-simple-offer/Business-Internet-Pro-VPL_DataPack.json +535 -0
  369. package/skills/modeling-omnistudio-epc-catalog/assets/examples/business-internet-pro-vpl-simple-offer/Business-Internet-Pro-VPL_DecompositionRelationships.json +35 -0
  370. package/skills/modeling-omnistudio-epc-catalog/assets/examples/business-internet-pro-vpl-simple-offer/Business-Internet-Pro-VPL_ObjectFieldAttributes.json +138 -0
  371. package/skills/modeling-omnistudio-epc-catalog/assets/examples/business-internet-pro-vpl-simple-offer/Business-Internet-Pro-VPL_OrchestrationScenarios.json +28 -0
  372. package/skills/modeling-omnistudio-epc-catalog/assets/examples/business-internet-pro-vpl-simple-offer/Business-Internet-Pro-VPL_ParentKeys.json +23 -0
  373. package/skills/modeling-omnistudio-epc-catalog/assets/examples/business-internet-pro-vpl-simple-offer/Business-Internet-Pro-VPL_PriceListEntries.json +220 -0
  374. package/skills/modeling-omnistudio-epc-catalog/assets/examples/business-internet-pro-vpl-simple-offer/Business-Internet-Pro-VPL_PricebookEntries.json +35 -0
  375. package/skills/modeling-omnistudio-epc-catalog/assets/examples/business-internet-pro-vpl-simple-offer/Business-Internet-Pro-VPL_ProductChildItems.json +414 -0
  376. package/skills/modeling-omnistudio-epc-catalog/assets/examples/samsung-galaxy-s22-bundle/Samsung-Galaxy-S22-Bundle_AttributeAssignments.json +382 -0
  377. package/skills/modeling-omnistudio-epc-catalog/assets/examples/samsung-galaxy-s22-bundle/Samsung-Galaxy-S22-Bundle_DataPack.json +565 -0
  378. package/skills/modeling-omnistudio-epc-catalog/assets/examples/samsung-galaxy-s22-bundle/Samsung-Galaxy-S22-Bundle_DecompositionRelationships.json +35 -0
  379. package/skills/modeling-omnistudio-epc-catalog/assets/examples/samsung-galaxy-s22-bundle/Samsung-Galaxy-S22-Bundle_ObjectFieldAttributes.json +104 -0
  380. package/skills/modeling-omnistudio-epc-catalog/assets/examples/samsung-galaxy-s22-bundle/Samsung-Galaxy-S22-Bundle_OrchestrationScenarios.json +28 -0
  381. package/skills/modeling-omnistudio-epc-catalog/assets/examples/samsung-galaxy-s22-bundle/Samsung-Galaxy-S22-Bundle_ParentKeys.json +13 -0
  382. package/skills/modeling-omnistudio-epc-catalog/assets/examples/samsung-galaxy-s22-bundle/Samsung-Galaxy-S22-Bundle_PriceListEntries.json +106 -0
  383. package/skills/modeling-omnistudio-epc-catalog/assets/examples/samsung-galaxy-s22-bundle/Samsung-Galaxy-S22-Bundle_PricebookEntries.json +35 -0
  384. package/skills/modeling-omnistudio-epc-catalog/assets/examples/samsung-galaxy-s22-bundle/Samsung-Galaxy-S22-Bundle_ProductChildItems.json +72 -0
  385. package/skills/modeling-omnistudio-epc-catalog/assets/examples/static-ip-simple-offer/Static-IP_AttributeAssignments.json +142 -0
  386. package/skills/modeling-omnistudio-epc-catalog/assets/examples/static-ip-simple-offer/Static-IP_DataPack.json +377 -0
  387. package/skills/modeling-omnistudio-epc-catalog/assets/examples/static-ip-simple-offer/Static-IP_DecompositionRelationships.json +35 -0
  388. package/skills/modeling-omnistudio-epc-catalog/assets/examples/static-ip-simple-offer/Static-IP_ObjectFieldAttributes.json +36 -0
  389. package/skills/modeling-omnistudio-epc-catalog/assets/examples/static-ip-simple-offer/Static-IP_ParentKeys.json +8 -0
  390. package/skills/modeling-omnistudio-epc-catalog/assets/examples/static-ip-simple-offer/Static-IP_PriceListEntries.json +54 -0
  391. package/skills/modeling-omnistudio-epc-catalog/assets/examples/static-ip-simple-offer/Static-IP_PricebookEntries.json +35 -0
  392. package/skills/modeling-omnistudio-epc-catalog/assets/examples/static-ip-simple-offer/Static-IP_ProductChildItems.json +34 -0
  393. package/skills/modeling-omnistudio-epc-catalog/assets/object-field-attributes-template.json +138 -0
  394. package/skills/modeling-omnistudio-epc-catalog/assets/orchestration-scenarios-template.json +54 -0
  395. package/skills/modeling-omnistudio-epc-catalog/assets/override-definitions-template.json +134 -0
  396. package/skills/modeling-omnistudio-epc-catalog/assets/parent-keys-template.json +29 -0
  397. package/skills/modeling-omnistudio-epc-catalog/assets/price-list-entries-template.json +158 -0
  398. package/skills/modeling-omnistudio-epc-catalog/assets/pricebook-entries-template.json +35 -0
  399. package/skills/modeling-omnistudio-epc-catalog/assets/product-child-item-template.json +338 -0
  400. package/skills/modeling-omnistudio-epc-catalog/assets/product2-offer-template.json +527 -0
  401. package/skills/modeling-omnistudio-epc-catalog/examples/.gitkeep +1 -0
  402. package/skills/modeling-omnistudio-epc-catalog/examples/business-internet-plus-bundle/Business-Internet-Plus_AttributeAssignments.json +95 -0
  403. package/skills/modeling-omnistudio-epc-catalog/examples/business-internet-plus-bundle/Business-Internet-Plus_CompiledAttributeOverrides.json +1 -0
  404. package/skills/modeling-omnistudio-epc-catalog/examples/business-internet-plus-bundle/Business-Internet-Plus_DataPack.json +214 -0
  405. package/skills/modeling-omnistudio-epc-catalog/examples/business-internet-plus-bundle/Business-Internet-Plus_DecompositionRelationships.json +28 -0
  406. package/skills/modeling-omnistudio-epc-catalog/examples/business-internet-plus-bundle/Business-Internet-Plus_ObjectFieldAttributes.json +98 -0
  407. package/skills/modeling-omnistudio-epc-catalog/examples/business-internet-plus-bundle/Business-Internet-Plus_OrchestrationScenarios.json +22 -0
  408. package/skills/modeling-omnistudio-epc-catalog/examples/business-internet-plus-bundle/Business-Internet-Plus_OverrideDefinitions.json +1 -0
  409. package/skills/modeling-omnistudio-epc-catalog/examples/business-internet-plus-bundle/Business-Internet-Plus_ParentKeys.json +13 -0
  410. package/skills/modeling-omnistudio-epc-catalog/examples/business-internet-plus-bundle/Business-Internet-Plus_PriceListEntries.json +35 -0
  411. package/skills/modeling-omnistudio-epc-catalog/examples/business-internet-plus-bundle/Business-Internet-Plus_PricebookEntries.json +28 -0
  412. package/skills/modeling-omnistudio-epc-catalog/examples/business-internet-plus-bundle/Business-Internet-Plus_ProductChildItems.json +110 -0
  413. package/skills/modeling-omnistudio-epc-catalog/examples/business-internet-plus-bundle/TRANSCRIPT.md +58 -0
  414. package/skills/modeling-omnistudio-epc-catalog/references/epc-field-guide.md +90 -0
  415. package/skills/modeling-omnistudio-epc-catalog/references/naming-conventions.md +80 -0
  416. package/skills/modeling-omnistudio-epc-catalog/references/scoring-model.md +57 -0
  417. package/skills/modeling-omnistudio-epc-catalog/scripts/cli-validation-commands.sh +19 -0
  418. package/skills/modeling-omnistudio-epc-catalog/scripts/sample-invocations.sh +18 -0
  419. package/skills/orchestrating-datacloud/CREDITS.md +15 -0
  420. package/skills/orchestrating-datacloud/README.md +129 -0
  421. package/skills/orchestrating-datacloud/SKILL.md +236 -0
  422. package/skills/orchestrating-datacloud/UPSTREAM.md +45 -0
  423. package/skills/orchestrating-datacloud/assets/definitions/activation-target.template.json +5 -0
  424. package/skills/orchestrating-datacloud/assets/definitions/activation.template.json +7 -0
  425. package/skills/orchestrating-datacloud/assets/definitions/calculated-insight.template.json +7 -0
  426. package/skills/orchestrating-datacloud/assets/definitions/data-action-target.template.json +5 -0
  427. package/skills/orchestrating-datacloud/assets/definitions/data-action.template.json +5 -0
  428. package/skills/orchestrating-datacloud/assets/definitions/data-graph.template.json +21 -0
  429. package/skills/orchestrating-datacloud/assets/definitions/data-stream.template.json +55 -0
  430. package/skills/orchestrating-datacloud/assets/definitions/dmo.template.json +17 -0
  431. package/skills/orchestrating-datacloud/assets/definitions/identity-resolution.template.json +30 -0
  432. package/skills/orchestrating-datacloud/assets/definitions/mapping.template.json +14 -0
  433. package/skills/orchestrating-datacloud/assets/definitions/relationship.template.json +12 -0
  434. package/skills/orchestrating-datacloud/assets/definitions/search-index.template.json +9 -0
  435. package/skills/orchestrating-datacloud/assets/definitions/segment.template.json +16 -0
  436. package/skills/orchestrating-datacloud/references/feature-readiness.md +157 -0
  437. package/skills/orchestrating-datacloud/references/plugin-setup.md +140 -0
  438. package/skills/orchestrating-datacloud/scripts/bootstrap-plugin.sh +53 -0
  439. package/skills/orchestrating-datacloud/scripts/diagnose-org.mjs +511 -0
  440. package/skills/orchestrating-datacloud/scripts/generate-manifest.mjs +68 -0
  441. package/skills/orchestrating-datacloud/scripts/verify-plugin.sh +58 -0
  442. package/skills/preparing-datacloud/CREDITS.md +7 -0
  443. package/skills/preparing-datacloud/README.md +51 -0
  444. package/skills/preparing-datacloud/SKILL.md +191 -0
  445. package/skills/preparing-datacloud/examples/ingestion-api/.env.example +8 -0
  446. package/skills/preparing-datacloud/examples/ingestion-api/README.md +48 -0
  447. package/skills/preparing-datacloud/examples/ingestion-api/send-data.py +144 -0
  448. package/skills/querying-soql/CREDITS.md +21 -0
  449. package/skills/querying-soql/README.md +41 -0
  450. package/skills/querying-soql/SKILL.md +143 -0
  451. package/skills/querying-soql/assets/aggregate-queries.soql +242 -0
  452. package/skills/querying-soql/assets/basic-queries.soql +188 -0
  453. package/skills/querying-soql/assets/bulkified-query-pattern.cls +280 -0
  454. package/skills/querying-soql/assets/optimization-patterns.soql +259 -0
  455. package/skills/querying-soql/assets/relationship-queries.soql +203 -0
  456. package/skills/querying-soql/assets/selector-class.cls +219 -0
  457. package/skills/querying-soql/references/anti-patterns.md +348 -0
  458. package/skills/querying-soql/references/cli-commands.md +358 -0
  459. package/skills/querying-soql/references/field-coverage-rules.md +514 -0
  460. package/skills/querying-soql/references/query-optimization.md +142 -0
  461. package/skills/querying-soql/references/selector-patterns.md +479 -0
  462. package/skills/querying-soql/references/soql-reference.md +227 -0
  463. package/skills/querying-soql/references/soql-syntax-reference.md +208 -0
  464. package/skills/querying-soql/scripts/post-tool-validate.py +322 -0
  465. package/skills/retrieving-datacloud/CREDITS.md +7 -0
  466. package/skills/retrieving-datacloud/README.md +44 -0
  467. package/skills/retrieving-datacloud/SKILL.md +120 -0
  468. package/skills/retrieving-datacloud/examples/search-indexes/hybrid-structured.json +44 -0
  469. package/skills/retrieving-datacloud/examples/search-indexes/vector-knowledge.json +43 -0
  470. package/skills/running-apex-tests/CREDITS.md +22 -0
  471. package/skills/running-apex-tests/README.md +94 -0
  472. package/skills/running-apex-tests/SKILL.md +158 -0
  473. package/skills/running-apex-tests/assets/basic-test.cls +169 -0
  474. package/skills/running-apex-tests/assets/bulk-test.cls +255 -0
  475. package/skills/running-apex-tests/assets/dml-mock.cls +339 -0
  476. package/skills/running-apex-tests/assets/mock-callout-test.cls +353 -0
  477. package/skills/running-apex-tests/assets/stub-provider-example.cls +364 -0
  478. package/skills/running-apex-tests/assets/test-data-factory.cls +328 -0
  479. package/skills/running-apex-tests/hooks/scripts/parse-test-results.py +364 -0
  480. package/skills/running-apex-tests/references/cli-commands.md +289 -0
  481. package/skills/running-apex-tests/references/mocking-patterns.md +500 -0
  482. package/skills/running-apex-tests/references/performance-optimization.md +283 -0
  483. package/skills/running-apex-tests/references/test-fix-loop.md +49 -0
  484. package/skills/running-apex-tests/references/test-patterns.md +154 -0
  485. package/skills/running-apex-tests/references/testing-best-practices.md +509 -0
  486. package/skills/segmenting-datacloud/CREDITS.md +3 -0
  487. package/skills/segmenting-datacloud/README.md +36 -0
  488. package/skills/segmenting-datacloud/SKILL.md +115 -0
@@ -0,0 +1,294 @@
1
+ #!/usr/bin/env python3
2
+ """
3
+ Wrapper for official @salesforce-ux/slds-linter npm package.
4
+
5
+ Provides integration with SLDS Linter for:
6
+ - HTML template validation
7
+ - CSS styling hooks validation
8
+ - Automated linting with structured output
9
+
10
+ The SLDS Linter is optional - if not installed, validation gracefully
11
+ degrades to custom Python-based validators.
12
+
13
+ Installation:
14
+ npm install -g @salesforce-ux/slds-linter
15
+ """
16
+
17
+ import subprocess
18
+ import json
19
+ import os
20
+ from typing import Dict, List, Any, Optional
21
+
22
+
23
+ class SLDSLinterWrapper:
24
+ """Wrapper for npm-based SLDS Linter."""
25
+
26
+ def __init__(self, project_root: Optional[str] = None):
27
+ """
28
+ Initialize the SLDS Linter wrapper.
29
+
30
+ Args:
31
+ project_root: Root directory for linting context (optional)
32
+ """
33
+ self.project_root = project_root or os.getcwd()
34
+ self._available: Optional[bool] = None
35
+
36
+ def is_available(self) -> bool:
37
+ """
38
+ Check if slds-linter is installed and available.
39
+
40
+ Returns:
41
+ True if linter is available, False otherwise
42
+ """
43
+ if self._available is not None:
44
+ return self._available
45
+
46
+ try:
47
+ result = subprocess.run(
48
+ ['npx', '@salesforce-ux/slds-linter', '--version'],
49
+ capture_output=True,
50
+ text=True,
51
+ timeout=10
52
+ )
53
+ self._available = result.returncode == 0
54
+ except (subprocess.TimeoutExpired, FileNotFoundError, Exception):
55
+ self._available = False
56
+
57
+ return self._available
58
+
59
+ def lint_file(self, file_path: str) -> Dict[str, Any]:
60
+ """
61
+ Lint a single file using SLDS Linter.
62
+
63
+ Args:
64
+ file_path: Path to HTML or CSS file to lint
65
+
66
+ Returns:
67
+ dict with success status, violations list, and any errors
68
+ """
69
+ if not self.is_available():
70
+ return {
71
+ 'success': False,
72
+ 'error': 'slds-linter not installed. Install with: npm i -g @salesforce-ux/slds-linter',
73
+ 'violations': []
74
+ }
75
+
76
+ try:
77
+ # Run SLDS Linter with JSON output
78
+ result = subprocess.run(
79
+ [
80
+ 'npx', '@salesforce-ux/slds-linter', 'lint',
81
+ file_path,
82
+ '--format', 'json'
83
+ ],
84
+ capture_output=True,
85
+ text=True,
86
+ timeout=30,
87
+ cwd=self.project_root
88
+ )
89
+
90
+ violations = self._parse_output(result.stdout, result.stderr)
91
+
92
+ return {
93
+ 'success': True,
94
+ 'violations': violations,
95
+ 'exit_code': result.returncode
96
+ }
97
+
98
+ except subprocess.TimeoutExpired:
99
+ return {
100
+ 'success': False,
101
+ 'error': 'slds-linter timed out after 30 seconds',
102
+ 'violations': []
103
+ }
104
+ except FileNotFoundError:
105
+ return {
106
+ 'success': False,
107
+ 'error': 'npx not found - ensure Node.js is installed',
108
+ 'violations': []
109
+ }
110
+ except Exception as e:
111
+ return {
112
+ 'success': False,
113
+ 'error': str(e),
114
+ 'violations': []
115
+ }
116
+
117
+ def lint_directory(self, dir_path: str, extensions: List[str] = None) -> Dict[str, Any]:
118
+ """
119
+ Lint all matching files in a directory.
120
+
121
+ Args:
122
+ dir_path: Directory path to lint
123
+ extensions: File extensions to lint (default: ['.html', '.css'])
124
+
125
+ Returns:
126
+ dict with success status, file_results, and total violations
127
+ """
128
+ if extensions is None:
129
+ extensions = ['.html', '.css']
130
+
131
+ if not self.is_available():
132
+ return {
133
+ 'success': False,
134
+ 'error': 'slds-linter not installed',
135
+ 'file_results': {},
136
+ 'total_violations': 0
137
+ }
138
+
139
+ file_results = {}
140
+ total_violations = 0
141
+
142
+ for root, dirs, files in os.walk(dir_path):
143
+ for file in files:
144
+ if any(file.endswith(ext) for ext in extensions):
145
+ file_path = os.path.join(root, file)
146
+ result = self.lint_file(file_path)
147
+ file_results[file_path] = result
148
+ total_violations += len(result.get('violations', []))
149
+
150
+ return {
151
+ 'success': True,
152
+ 'file_results': file_results,
153
+ 'total_violations': total_violations
154
+ }
155
+
156
+ def _parse_output(self, stdout: str, stderr: str) -> List[Dict]:
157
+ """
158
+ Parse SLDS Linter JSON output into structured violations.
159
+
160
+ Args:
161
+ stdout: Standard output from linter
162
+ stderr: Standard error from linter
163
+
164
+ Returns:
165
+ List of violation dictionaries
166
+ """
167
+ violations = []
168
+
169
+ # Try to parse JSON output
170
+ try:
171
+ if stdout.strip():
172
+ data = json.loads(stdout)
173
+
174
+ # Handle ESLint-style JSON output
175
+ if isinstance(data, list):
176
+ for file_result in data:
177
+ for message in file_result.get('messages', []):
178
+ violations.append({
179
+ 'rule': message.get('ruleId', 'unknown'),
180
+ 'message': message.get('message', ''),
181
+ 'line': message.get('line', 0),
182
+ 'column': message.get('column', 0),
183
+ 'severity': self._map_severity(message.get('severity', 1)),
184
+ 'source': 'slds-linter',
185
+ 'file': file_result.get('filePath', '')
186
+ })
187
+
188
+ # Handle single object output
189
+ elif isinstance(data, dict):
190
+ for message in data.get('messages', []):
191
+ violations.append({
192
+ 'rule': message.get('ruleId', 'unknown'),
193
+ 'message': message.get('message', ''),
194
+ 'line': message.get('line', 0),
195
+ 'column': message.get('column', 0),
196
+ 'severity': self._map_severity(message.get('severity', 1)),
197
+ 'source': 'slds-linter'
198
+ })
199
+
200
+ except json.JSONDecodeError:
201
+ # If not valid JSON, try to extract violations from text output
202
+ violations.extend(self._parse_text_output(stdout))
203
+ violations.extend(self._parse_text_output(stderr))
204
+
205
+ return violations
206
+
207
+ def _parse_text_output(self, output: str) -> List[Dict]:
208
+ """
209
+ Parse plain text linter output for violations.
210
+
211
+ Args:
212
+ output: Text output from linter
213
+
214
+ Returns:
215
+ List of violation dictionaries
216
+ """
217
+ violations = []
218
+
219
+ if not output:
220
+ return violations
221
+
222
+ # Common patterns for linter output
223
+ # Example: "filename.html:10:5: error - message"
224
+ import re
225
+ pattern = r'(\S+):(\d+):(\d+):\s*(error|warning|info)\s*[-:]\s*(.+)'
226
+
227
+ for line in output.splitlines():
228
+ match = re.match(pattern, line, re.IGNORECASE)
229
+ if match:
230
+ violations.append({
231
+ 'file': match.group(1),
232
+ 'line': int(match.group(2)),
233
+ 'column': int(match.group(3)),
234
+ 'severity': match.group(4).upper(),
235
+ 'message': match.group(5).strip(),
236
+ 'rule': 'slds',
237
+ 'source': 'slds-linter'
238
+ })
239
+
240
+ return violations
241
+
242
+ def _map_severity(self, level: int) -> str:
243
+ """
244
+ Map ESLint severity levels to our labels.
245
+
246
+ Args:
247
+ level: ESLint severity (1=warning, 2=error)
248
+
249
+ Returns:
250
+ Severity label string
251
+ """
252
+ return {
253
+ 0: 'INFO',
254
+ 1: 'WARNING',
255
+ 2: 'HIGH'
256
+ }.get(level, 'INFO')
257
+
258
+
259
+ def is_slds_linter_available() -> bool:
260
+ """
261
+ Convenience function to check if SLDS Linter is available.
262
+
263
+ Returns:
264
+ True if available, False otherwise
265
+ """
266
+ wrapper = SLDSLinterWrapper()
267
+ return wrapper.is_available()
268
+
269
+
270
+ def lint_lwc_file(file_path: str) -> Dict[str, Any]:
271
+ """
272
+ Convenience function to lint a single LWC file.
273
+
274
+ Args:
275
+ file_path: Path to file to lint
276
+
277
+ Returns:
278
+ Linting results dictionary
279
+ """
280
+ wrapper = SLDSLinterWrapper()
281
+ return wrapper.lint_file(file_path)
282
+
283
+
284
+ if __name__ == "__main__":
285
+ import sys
286
+
287
+ if len(sys.argv) < 2:
288
+ print("Usage: python slds_linter_wrapper.py <file.html|file.css>")
289
+ print("\nChecking SLDS Linter availability...")
290
+ print(f"Available: {is_slds_linter_available()}")
291
+ sys.exit(0)
292
+
293
+ result = lint_lwc_file(sys.argv[1])
294
+ print(json.dumps(result, indent=2))
@@ -0,0 +1,22 @@
1
+ """
2
+ SLDS 2 Validation Rules Package.
3
+
4
+ This package contains modular validation rules for SLDS 2 compliance:
5
+ - class_validator: SLDS utility class validation
6
+ - a11y_validator: Accessibility checks
7
+ - darkmode_validator: Dark mode compatibility
8
+ - migration_validator: SLDS 1 → 2 migration detection
9
+ - styling_hooks: CSS variable validation
10
+
11
+ Main validation logic is in validate_slds.py which uses these modules
12
+ as optional extensions.
13
+ """
14
+
15
+ __version__ = "1.0.0"
16
+ __all__ = [
17
+ 'class_validator',
18
+ 'a11y_validator',
19
+ 'darkmode_validator',
20
+ 'migration_validator',
21
+ 'styling_hooks'
22
+ ]
@@ -0,0 +1,332 @@
1
+ #!/usr/bin/env python3
2
+ """
3
+ LWC Template Anti-Pattern Validator.
4
+
5
+ Detects common mistakes that LLMs make when generating LWC templates:
6
+ 1. Inline JavaScript expressions ({a + b})
7
+ 2. Ternary operators in templates ({x ? a : b})
8
+ 3. Object/array literals in attributes
9
+ 4. Method calls in templates ({items.length})
10
+ 5. Comparison operators in if:true
11
+ 6. Event handlers with inline arguments
12
+
13
+ This validator is ADVISORY - it provides warnings but does not block operations.
14
+
15
+ Source: https://salesforcediaries.com/2026/01/16/llm-mistakes-in-apex-lwc-salesforce-code-generation-rules/
16
+ """
17
+
18
+ import re
19
+ import os
20
+ from typing import Dict, List, Set
21
+
22
+
23
+ class LWCTemplateValidator:
24
+ """Detects LLM-specific anti-patterns in LWC HTML templates."""
25
+
26
+ # Patterns for inline expressions (arithmetic, concatenation)
27
+ INLINE_EXPRESSION_PATTERNS = [
28
+ # Arithmetic operations
29
+ (r'\{[^}]*\s*[\+\-\*\/]\s*[^}]*\}', 'Arithmetic expression', 'Use a getter in your JS file'),
30
+ # Ternary operators
31
+ (r'\{[^}]*\s*\?\s*[^}]+\s*:\s*[^}]*\}', 'Ternary operator', 'Use a getter or if:true/if:false'),
32
+ # String concatenation with +
33
+ (r"\{[^}]*['\"]\s*\+\s*[^}]*\}", 'String concatenation', 'Use a getter with template literals'),
34
+ # Template literals (backticks)
35
+ (r'\{`[^`]*`\}', 'Template literal', 'Template literals not supported; use getter'),
36
+ ]
37
+
38
+ # Patterns for method calls in templates
39
+ METHOD_CALL_PATTERNS = [
40
+ # .method() call
41
+ (r'\{[^}]*\.\w+\s*\(\s*[^)]*\)\s*[^}]*\}', 'Method call', 'Use a getter instead of calling methods'),
42
+ # .length, .size, etc. (common array/string properties that need getters)
43
+ (r'\{[^}]*\.length[^}]*\}', 'Array/string .length', 'Use a getter: get count() { return this.items.length; }'),
44
+ (r'\{[^}]*\.size[^}]*\}', 'Collection .size', 'Use a getter'),
45
+ # Common method patterns
46
+ (r'\{[^}]*\.toUpperCase\s*\(\)', 'toUpperCase()', 'Use a getter'),
47
+ (r'\{[^}]*\.toLowerCase\s*\(\)', 'toLowerCase()', 'Use a getter'),
48
+ (r'\{[^}]*\.trim\s*\(\)', 'trim()', 'Use a getter'),
49
+ (r'\{[^}]*\.toString\s*\(\)', 'toString()', 'Use a getter'),
50
+ (r'\{[^}]*\.join\s*\(', 'join()', 'Use a getter'),
51
+ (r'\{[^}]*\.slice\s*\(', 'slice()', 'Use a getter'),
52
+ (r'\{[^}]*\.split\s*\(', 'split()', 'Use a getter'),
53
+ (r'\{[^}]*\.filter\s*\(', 'filter()', 'Use a getter'),
54
+ (r'\{[^}]*\.map\s*\(', 'map()', 'Use a getter'),
55
+ (r'\{[^}]*\.find\s*\(', 'find()', 'Use a getter'),
56
+ (r'\{[^}]*\.includes\s*\(', 'includes()', 'Use a getter'),
57
+ (r'\{[^}]*JSON\.stringify\s*\(', 'JSON.stringify()', 'Use a getter'),
58
+ (r'\{[^}]*JSON\.parse\s*\(', 'JSON.parse()', 'Use a getter'),
59
+ ]
60
+
61
+ # Patterns for comparisons in if:true/if:false
62
+ COMPARISON_PATTERNS = [
63
+ # Comparison operators in if:true
64
+ (r'if:true=\{[^}]*\s*[><=!]+\s*[^}]*\}', 'Comparison in if:true', 'Use a getter: get isGreater() { return x > 5; }'),
65
+ (r'if:false=\{[^}]*\s*[><=!]+\s*[^}]*\}', 'Comparison in if:false', 'Use a getter'),
66
+ # Logical operators
67
+ (r'if:true=\{[^}]*\s*&&\s*[^}]*\}', 'Logical AND in if:true', 'Use a getter: get bothTrue() { return a && b; }'),
68
+ (r'if:false=\{[^}]*\s*&&\s*[^}]*\}', 'Logical AND in if:false', 'Use a getter'),
69
+ (r'if:true=\{[^}]*\s*\|\|\s*[^}]*\}', 'Logical OR in if:true', 'Use a getter'),
70
+ (r'if:false=\{[^}]*\s*\|\|\s*[^}]*\}', 'Logical OR in if:false', 'Use a getter'),
71
+ # Negation
72
+ (r'if:true=\{!\w', 'Negation in if:true', 'Use if:false instead, or use a getter'),
73
+ ]
74
+
75
+ # Patterns for object/array literals
76
+ LITERAL_PATTERNS = [
77
+ # Object literal in attribute
78
+ (r'=\{\s*\{[^}]+\}\s*\}', 'Inline object literal', 'Define objects in your JS file as properties'),
79
+ # Array literal in attribute
80
+ (r"=\{\s*\[[^\]]+\]\s*\}", 'Inline array literal', 'Define arrays in your JS file as properties'),
81
+ ]
82
+
83
+ # Patterns for incorrect event handler syntax
84
+ EVENT_HANDLER_PATTERNS = [
85
+ # Event handler with parentheses/arguments
86
+ (r'on\w+=\{[\w.]+\s*\([^)]+\)\s*\}', 'Event handler with arguments', 'Use data-* attributes instead'),
87
+ # Arrow function in handler
88
+ (r'on\w+=\{\s*\([^)]*\)\s*=>', 'Arrow function in handler', 'Define handler method in JS, use data-* for context'),
89
+ # .bind() in handler
90
+ (r'on\w+=\{[\w.]+\.bind\s*\(', '.bind() in handler', 'Use data-* attributes for context instead'),
91
+ ]
92
+
93
+ # Patterns for common Vue/React/Angular syntax mistakes
94
+ FRAMEWORK_SYNTAX_PATTERNS = [
95
+ # Vue v-model / v-bind / v-on
96
+ (r'\bv-model\s*=', 'Vue v-model syntax', 'LWC uses value={prop} with onchange handler'),
97
+ (r'\bv-bind:', 'Vue v-bind syntax', 'LWC uses {property} binding'),
98
+ (r'\bv-on:', 'Vue v-on syntax', 'LWC uses on* handlers (onclick, onchange)'),
99
+ (r'\bv-if\s*=', 'Vue v-if syntax', 'LWC uses if:true={condition}'),
100
+ (r'\bv-for\s*=', 'Vue v-for syntax', 'LWC uses for:each={array} for:item="item"'),
101
+ (r'\bv-show\s*=', 'Vue v-show syntax', 'LWC uses if:true/if:false or CSS classes'),
102
+ # React patterns
103
+ (r'\bclassName\s*=', 'React className', 'LWC uses class={classString}'),
104
+ (r'\bhtmlFor\s*=', 'React htmlFor', 'LWC uses for attribute or lightning-input label'),
105
+ (r'\bonClick\s*=\s*\{[^}]*\(\s*\)', 'React onClick with call', 'LWC uses onclick={handler} without parentheses'),
106
+ # Angular patterns
107
+ (r'\[\(ngModel\)\]', 'Angular two-way binding', 'LWC uses value={prop} with onchange'),
108
+ (r'\*ngIf\s*=', 'Angular *ngIf', 'LWC uses if:true={condition}'),
109
+ (r'\*ngFor\s*=', 'Angular *ngFor', 'LWC uses for:each={array} for:item="item"'),
110
+ (r'\(click\)\s*=', 'Angular event binding', 'LWC uses onclick={handler}'),
111
+ ]
112
+
113
+ # Missing key in iteration
114
+ ITERATION_PATTERNS = [
115
+ (r'for:each=\{[^}]+\}\s+for:item="[^"]+"\s*>', 'for:each without key', 'Add key={item.id} to the first child element'),
116
+ ]
117
+
118
+ def __init__(self, file_path: str):
119
+ """
120
+ Initialize the validator with an LWC HTML file.
121
+
122
+ Args:
123
+ file_path: Path to .html file
124
+ """
125
+ self.file_path = file_path
126
+ self.content = ""
127
+ self.lines = []
128
+ self.issues = []
129
+
130
+ try:
131
+ with open(file_path, 'r', encoding='utf-8') as f:
132
+ self.content = f.read()
133
+ self.lines = self.content.split('\n')
134
+ except Exception as e:
135
+ self.issues.append({
136
+ 'severity': 'ERROR',
137
+ 'category': 'file',
138
+ 'message': f'Cannot read file: {e}',
139
+ 'line': 0
140
+ })
141
+
142
+ def validate(self) -> Dict:
143
+ """
144
+ Run all LWC template validations.
145
+
146
+ Returns:
147
+ Dictionary with validation results
148
+ """
149
+ if not self.content:
150
+ return {
151
+ 'file': os.path.basename(self.file_path),
152
+ 'issues': self.issues,
153
+ 'issue_count': len(self.issues)
154
+ }
155
+
156
+ # Run all checks
157
+ self._check_patterns(self.INLINE_EXPRESSION_PATTERNS, 'inline_expression', 'CRITICAL')
158
+ self._check_patterns(self.METHOD_CALL_PATTERNS, 'method_call', 'CRITICAL')
159
+ self._check_patterns(self.COMPARISON_PATTERNS, 'comparison', 'CRITICAL')
160
+ self._check_patterns(self.LITERAL_PATTERNS, 'literal', 'CRITICAL')
161
+ self._check_patterns(self.EVENT_HANDLER_PATTERNS, 'event_handler', 'WARNING')
162
+ self._check_patterns(self.FRAMEWORK_SYNTAX_PATTERNS, 'framework_syntax', 'CRITICAL')
163
+ self._check_iteration_keys()
164
+
165
+ return {
166
+ 'file': os.path.basename(self.file_path),
167
+ 'issues': self.issues,
168
+ 'issue_count': len(self.issues)
169
+ }
170
+
171
+ def _check_patterns(self, patterns: List, category: str, severity: str):
172
+ """Check for pattern matches in the template."""
173
+ for i, line in enumerate(self.lines, 1):
174
+ # Skip HTML comments
175
+ if '<!--' in line and '-->' in line:
176
+ continue
177
+
178
+ for pattern, name, fix in patterns:
179
+ matches = re.finditer(pattern, line)
180
+ for match in matches:
181
+ # Avoid duplicate issues for same line/category
182
+ existing = any(
183
+ issue['line'] == i and
184
+ issue['category'] == category and
185
+ name in issue['message']
186
+ for issue in self.issues
187
+ )
188
+ if not existing:
189
+ self.issues.append({
190
+ 'severity': severity,
191
+ 'category': category,
192
+ 'message': f'{name} not supported in LWC templates',
193
+ 'line': i,
194
+ 'fix': fix,
195
+ 'source': 'template-validator'
196
+ })
197
+
198
+ def _check_iteration_keys(self):
199
+ """Check for missing key attribute in for:each iterations."""
200
+ in_foreach = False
201
+ foreach_line = 0
202
+ foreach_item = ""
203
+
204
+ for i, line in enumerate(self.lines, 1):
205
+ # Detect for:each start
206
+ foreach_match = re.search(r'for:each=\{([^}]+)\}\s+for:item="([^"]+)"', line)
207
+ if foreach_match:
208
+ in_foreach = True
209
+ foreach_line = i
210
+ foreach_item = foreach_match.group(2)
211
+ continue
212
+
213
+ if in_foreach:
214
+ # Look for key attribute in the next few lines
215
+ if 'key=' in line or 'key =' in line:
216
+ in_foreach = False
217
+ continue
218
+
219
+ # If we hit a closing tag or another element without key
220
+ if '>' in line and not line.strip().startswith('<!--'):
221
+ # Check if it's a template tag (doesn't need key directly)
222
+ if '<template' not in line:
223
+ self.issues.append({
224
+ 'severity': 'WARNING',
225
+ 'category': 'iteration',
226
+ 'message': f'for:each iteration (line {foreach_line}) may be missing key attribute',
227
+ 'line': i,
228
+ 'fix': f'Add key={{{foreach_item}.id}} to identify each item uniquely',
229
+ 'source': 'template-validator'
230
+ })
231
+ in_foreach = False
232
+
233
+
234
+ def validate_lwc_template(file_path: str) -> Dict:
235
+ """
236
+ Validate an LWC HTML template for anti-patterns.
237
+
238
+ Args:
239
+ file_path: Path to .html file
240
+
241
+ Returns:
242
+ Dictionary with validation results
243
+ """
244
+ validator = LWCTemplateValidator(file_path)
245
+ return validator.validate()
246
+
247
+
248
+ def format_output(results: Dict) -> str:
249
+ """Format validation results for display."""
250
+ issues = results.get('issues', [])
251
+
252
+ if not issues:
253
+ return ""
254
+
255
+ output_parts = []
256
+ output_parts.append("")
257
+ output_parts.append(f"🔍 LWC Template Check: {results['file']}")
258
+ output_parts.append("─" * 50)
259
+
260
+ # Group by severity
261
+ critical = [i for i in issues if i['severity'] == 'CRITICAL']
262
+ warnings = [i for i in issues if i['severity'] == 'WARNING']
263
+
264
+ if critical:
265
+ output_parts.append(f"🔴 Critical ({len(critical)}):")
266
+ for issue in critical[:10]:
267
+ output_parts.append(f" L{issue['line']}: {issue['message']}")
268
+ if issue.get('fix'):
269
+ fix = issue['fix'][:120] + '...' if len(issue['fix']) > 120 else issue['fix']
270
+ output_parts.append(f" 💡 {fix}")
271
+
272
+ if warnings:
273
+ output_parts.append(f"🟡 Warnings ({len(warnings)}):")
274
+ for issue in warnings[:5]:
275
+ output_parts.append(f" L{issue['line']}: {issue['message']}")
276
+ if issue.get('fix'):
277
+ fix = issue['fix'][:120] + '...' if len(issue['fix']) > 120 else issue['fix']
278
+ output_parts.append(f" 💡 {fix}")
279
+
280
+ remaining = len(issues) - len(critical[:10]) - len(warnings[:5])
281
+ if remaining > 0:
282
+ output_parts.append(f" ... and {remaining} more issues")
283
+
284
+ output_parts.append("─" * 50)
285
+ output_parts.append("📚 See: generating-lwc-components/references/template-anti-patterns.md")
286
+
287
+ return "\n".join(output_parts)
288
+
289
+
290
+ if __name__ == "__main__":
291
+ import sys
292
+ import json
293
+
294
+ file_path = None
295
+
296
+ # Mode 1: Hook mode - read from stdin JSON
297
+ if not sys.stdin.isatty():
298
+ try:
299
+ hook_input = json.load(sys.stdin)
300
+ tool_input = hook_input.get("tool_input", {})
301
+ file_path = tool_input.get("file_path", "")
302
+ except (json.JSONDecodeError, EOFError):
303
+ pass
304
+
305
+ # Mode 2: CLI mode - read from command-line argument
306
+ if not file_path and len(sys.argv) >= 2:
307
+ file_path = sys.argv[1]
308
+
309
+ # No file path from either mode
310
+ if not file_path:
311
+ print("Usage: python template_validator.py <component.html>")
312
+ print(" Or: echo '{\"tool_input\": {\"file_path\": \"...\"}}' | python template_validator.py")
313
+ sys.exit(0)
314
+
315
+ # Only validate .html files in lwc folders
316
+ if not file_path.endswith('.html') or '/lwc/' not in file_path:
317
+ sys.exit(0)
318
+
319
+ if not os.path.exists(file_path):
320
+ print(f"Error: File not found: {file_path}")
321
+ sys.exit(1)
322
+
323
+ results = validate_lwc_template(file_path)
324
+
325
+ # Print formatted output
326
+ output = format_output(results)
327
+ if output:
328
+ print(output)
329
+ else:
330
+ print(f"✅ No template anti-patterns detected in {results['file']}")
331
+
332
+ sys.exit(0) # Advisory only - don't block