@flow-scanner/lightning-flow-scanner-core 6.5.1 → 6.6.1

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.
package/README.md CHANGED
@@ -1,409 +1,428 @@
1
- <p align="center">
2
- <a href="https://github.com/Flow-Scanner">
3
- <img src="assets/media/bannerslim.png" style="width: 43%;" />
4
- </a>
5
- </p>
6
-
7
- <p align="center"><i>UMD-compatible Flow metadata engine for Node.js & browsers—20+ rules to catch issues.</i></p>
8
-
9
- ---
10
-
11
- ## Table of contens
12
-
13
- - **[Default Rules](#default-rules)**
14
- - **[Configuration](#configuration)**
15
- - [Defining Severity Levels](#defining-severity-levels)
16
- - [Configuring Expressions](#configuring-expressions)
17
- - [Specifying Exceptions](#specifying-exceptions)
18
- - [Report Detail Level](#report-detail-level)
19
- - [Include Beta Rules](#include-beta-rules)
20
- - **[Usage](#Usage)**
21
- - [Examples](#examples)
22
- - [Functions](#functions)
23
- - **[Installation](#installation)**
24
- - **[Development](#development)**
25
-
26
- ---
27
-
28
- ## Default Rules
29
-
30
- <p>📌<strong>Tip:</strong> To link directly to a specific rule, use the full GitHub anchor link format. Example:</p>
31
- <p><em><a href="https://github.com/Flow-Scanner/lightning-flow-scanner-core#unsafe-running-context">https://github.com/Flow-Scanner/lightning-flow-scanner-core#unsafe-running-context</a></em></p>
32
-
33
- > Want to code a new rule? → See [How to Write a Rule](docs/write-a-rule.md)
34
-
35
- ### Action Calls In Loop(Beta)
36
-
37
- _[ActionCallsInLoop](https://github.com/Flow-Scanner/lightning-flow-scanner-core/tree/main/src/main/rules/ActionCallsInLoop.ts)_ - To prevent exceeding Apex governor limits, it is advisable to consolidate and bulkify your apex calls, utilizing a single action call containing a collection variable at the end of the loop.
38
-
39
- ### Outdated API Version
40
-
41
- _[APIVersion](https://github.com/Flow-Scanner/lightning-flow-scanner-core/tree/main/src/main/rules/APIVersion.ts)_ - Introducing newer API components may lead to unexpected issues with older versions of Flows, as they might not align with the underlying mechanics. Starting from API version 50.0, the **Api Version** attribute has been readily available on the Flow Object. To ensure smooth operation and reduce discrepancies between API versions, it is strongly advised to regularly update and maintain them.
42
-
43
- ### Auto Layout
44
-
45
- _[AutoLayout](https://github.com/Flow-Scanner/lightning-flow-scanner-core/tree/main/src/main/rules/AutoLayout.ts)_ - With Canvas Mode set to Auto‑Layout, elements are spaced, connected, and aligned automatically, keeping your Flow neatly organized—saving you time.
46
-
47
- ### Copy API Name
48
-
49
- _[CopyAPIName](https://github.com/Flow-Scanner/lightning-flow-scanner-core/tree/main/src/main/rules/CopyAPIName.ts)_ - Maintaining multiple elements with a similar name, like `Copy_X_Of_Element`, can diminish the overall readability of your Flow. When copying and pasting these elements, remember to update the API name of the newly created copy.
50
-
51
- ### Cyclomatic Complexity
52
-
53
- _[CyclomaticComplexity](https://github.com/Flow-Scanner/lightning-flow-scanner-core/tree/main/src/main/rules/CyclomaticComplexity.ts)_ - The number of loops and decision rules, plus the number of decisions. Use a combination of 1) subflows and 2) breaking flows into multiple concise trigger‑ordered flows to reduce cyclomatic complexity within a single flow, ensuring maintainability and simplicity.
54
-
55
- ### DML Statement In A Loop
56
-
57
- _[DMLStatementInLoop](https://github.com/Flow-Scanner/lightning-flow-scanner-core/tree/main/src/main/rules/DMLStatementInLoop.ts)_ - To prevent exceeding Apex governor limits, consolidate all your database operations—record creation, updates, or deletions—at the conclusion of the flow.
58
-
59
- ### Duplicate DML Operation
60
-
61
- _[DuplicateDMLOperation](https://github.com/Flow-Scanner/lightning-flow-scanner-core/tree/main/src/main/rules/DuplicateDMLOperation.ts)_ - When a flow executes database changes or actions between two screens, prevent users from navigating backward between screens; otherwise, duplicate database operations may be performed.
62
-
63
- ### Flow Naming Convention
64
-
65
- _[FlowName](https://github.com/Flow-Scanner/lightning-flow-scanner-core/tree/main/src/main/rules/FlowName.ts)_ - The readability of a flow is paramount. Establishing a naming convention significantly enhances findability, searchability, and overall consistency. Include at least a domain and a brief description of the flow’s actions, for example `Service_OrderFulfillment`.
66
-
67
- ### Get Record All Fields
68
-
69
- _[GetRecordAllFields](https://github.com/Flow-Scanner/lightning-flow-scanner-core/tree/main/src/main/rules/GetRecordAllFields.ts)_ - Following the principle of least privilege (PoLP), avoid using **Get Records** with “Automatically store all fields” unless necessary.
70
-
71
- ### Hardcoded Id
72
-
73
- _[HardcodedId](https://github.com/Flow-Scanner/lightning-flow-scanner-core/tree/main/src/main/rules/HardcodedId.ts)_ - Avoid hard‑coding IDs because they are org specific. Instead, pass them into variables at the start of the flow—via merge‑field URL parameters or a **Get Records** element.
74
-
75
- ### Hardcoded Url
76
-
77
- _[HardcodedUrl](https://github.com/Flow-Scanner/lightning-flow-scanner-core/tree/main/src/main/rules/HardcodedUrl.ts)_ - Avoid hard‑coding URLs because they are environment specific. Use an `$API` formula (preferred) or environment‑specific sources like custom labels, metadata, or settings.
78
-
79
- ### Inactive Flow
80
-
81
- _[InactiveFlow](https://github.com/Flow-Scanner/lightning-flow-scanner-core/tree/main/src/main/rules/InactiveFlow.ts)_ - Like cleaning out your closet: deleting unused flows is essential. Inactive flows can still cause trouble—such as accidentally deleting records during testing, or being activated as subflows.
82
-
83
- ### Missing Fault Path
84
-
85
- _[MissingFaultPath](https://github.com/Flow-Scanner/lightning-flow-scanner-core/tree/main/src/main/rules/MissingFaultPath.ts)_ - A flow may fail to execute an operation as intended. By default, the flow displays an error to the user and emails the creator. Customize this behavior by incorporating a Fault Path.
86
-
87
- ### Missing Flow Description
88
-
89
- _[FlowDescription](https://github.com/Flow-Scanner/lightning-flow-scanner-core/tree/main/src/main/rules/FlowDescription.ts)_ - Descriptions play a vital role in documentation. We highly recommend including details about where flows are used and their intended purpose.
90
-
91
- ### Missing Null Handler
92
-
93
- _[MissingNullHandler](https://github.com/Flow-Scanner/lightning-flow-scanner-core/tree/main/src/main/rules/MissingNullHandler.ts)_ - When a **Get Records** operation finds no data, it returns `null`. Validate data by using a Decision element to check for a non‑null result.
94
-
95
- ### Process Builder
96
-
97
- _[ProcessBuilder](https://github.com/Flow-Scanner/lightning-flow-scanner-core/tree/main/src/main/rules/ProcessBuilder.ts)_ - Salesforce is transitioning away from Workflow Rules and Process Builder in favor of Flow. Begin migrating your organization’s automation to Flow.
98
-
99
- ### Recursive After Update
100
-
101
- _[RecursiveAfterUpdate](https://github.com/Flow-Scanner/lightning-flow-scanner-core/tree/main/src/main/rules/RecursiveAfterUpdate.ts)_ - After‑update flows are meant for modifying **other** records. Using them on the same record can cause recursion. Consider **before‑save** flows for same‑record updates.
102
-
103
- ### Same Record Field Updates
104
-
105
- _[SameRecordFieldUpdates](https://github.com/Flow-Scanner/lightning-flow-scanner-core/tree/main/src/main/rules/SameRecordFieldUpdates.ts)_ - Similar to triggers, **before‑save** contexts can update the same record via `$Record` without invoking DML.
106
-
107
- ### SOQL Query In A Loop
108
-
109
- _[SOQLQueryInLoop](https://github.com/Flow-Scanner/lightning-flow-scanner-core/tree/main/src/main/rules/SOQLQueryInLoop.ts)_ - To prevent exceeding Apex governor limits, consolidate all SOQL queries at the end of the flow.
110
-
111
- ### Trigger Order
112
-
113
- _[TriggerOrder](https://github.com/Flow-Scanner/lightning-flow-scanner-core/tree/main/src/main/rules/TriggerOrder.ts)_ - Guarantee your flow execution order with the **Trigger Order** property introduced in Spring ’22.
114
-
115
- ### Unconnected Element
116
-
117
- _[UnconnectedElement](https://github.com/Flow-Scanner/lightning-flow-scanner-core/tree/main/src/main/rules/UnconnectedElement.ts)_ - Avoid unconnected elements that are not used by the flow to keep flows efficient and maintainable.
118
-
119
- ### Unsafe Running Context
120
-
121
- _[UnsafeRunningContext](https://github.com/Flow-Scanner/lightning-flow-scanner-core/tree/main/src/main/rules/UnsafeRunningContext.ts)_ - This flow is configured to run in **System Mode without Sharing**, granting all users permission to view and edit all data. This can lead to unsafe data access.
122
-
123
- ### Unused Variable
124
-
125
- _[UnusedVariable](https://github.com/Flow-Scanner/lightning-flow-scanner-core/tree/main/src/main/rules/UnusedVariable.ts)_ - To maintain efficiency and manageability, avoid including variables that are never referenced.
126
-
127
- ---
128
-
129
- ## Configuration
130
-
131
- Lightning Flow Scanner is plug-and-play by default, but we recommend configuring and defining:
132
-
133
- - The rules to be executed.
134
- - The severity of violating any specific rule.
135
- - Rule properties such as REGEX expressions.
136
- - Any known exceptions that should be ignored during scanning.
137
-
138
- ```json
139
- {
140
- "rules": {
141
- // Your rules here
142
- },
143
- "exceptions": {
144
- // Your exceptions here
145
- }
146
- }
147
- ```
148
-
149
- Using the rules section of your configurations, you can specify the list of rules to be run. Furthermore, you can define the severity and configure expressions of rules. Below is a breakdown of the available attributes of rule configuration:
150
-
151
- ```json
152
- {
153
- "rules": {
154
- "<RuleName>": {
155
- "severity": "<Severity>",
156
- "expression": "<Expression>"
157
- }
158
- }
159
- }
160
- ```
161
-
162
- ### Defining Severity Levels
163
-
164
- When the severity is not provided it will be `warning` by default. Other available values for severity are `error` and `note`. Define the severity per rule as shown below:
165
-
166
- ```json
167
- {
168
- "rules": {
169
- "FlowDescription": {
170
- "severity": "error"
171
- },
172
- "UnusedVariable": {
173
- "severity": "note"
174
- }
175
- }
176
- }
177
- ```
178
-
179
- ### Configuring Expressions
180
-
181
- Some rules have additional attributes to configure, such as the expression, that will overwrite default values. These can be configured in the same way as severity as shown in the following example.
182
-
183
- ```json
184
- {
185
- "rules": {
186
- "APIVersion": {
187
- "severity": "error",
188
- "expression": "===58" // comparison operator
189
- },
190
- "FlowName": {
191
- "severity": "note",
192
- "expression": "[A-Za-z0-9]" // regular expression
193
- }
194
- }
195
- }
196
- ```
197
-
198
- ### Specifying Exceptions
199
-
200
- Specifying exceptions allows you to exclude specific scenarios from rule enforcement. Exceptions can be specified at the flow, rule, or result level to provide fine-grained control. Below is a breakdown of the available attributes of exception configuration:
201
-
202
- ```json
203
- {
204
- "exceptions": {
205
- "<FlowName>": {
206
- "<RuleName>": [
207
- // Suppress a specific result:
208
- "<ResultName>",
209
- // Suppress ALL results of rule:
210
- "*",
211
- ...
212
- ]
213
- },
214
- ...
215
- }
216
- }
217
- ```
218
-
219
- _Example_
220
-
221
- ```json
222
- {
223
- "exceptions": {
224
- "MyFlow": {
225
- "MissingNullHandler": ["*"],
226
- "HardcodedId": ["Old_Lookup_1"]
227
- }
228
- }
229
- }
230
- ```
231
-
232
- ### Report Detail Level
233
-
234
- Control the verbosity of violation reports via detailLevel. By default (`enriched`), outputs include element or flow-level details like variable data types, node connectors/locations, or attribute expressions for comprehensive reports. Set to `simple` for lighter output with only line and column numbers.
235
-
236
- ```json
237
- {
238
- "rules": {
239
- ...
240
- },
241
- "exceptions": {
242
- ...
243
- },
244
- "detailLevel": "simple"
245
- }
246
- ```
247
-
248
- ### Include Beta Rules
249
-
250
- New rules are introduced in Beta mode before being added to the default ruleset. To include current Beta rules, enable the optional betamode parameter in your configuration:
251
-
252
- ```json
253
- {
254
- "rules": {
255
- ...
256
- },
257
- "exceptions": {
258
- ...
259
- },
260
- "betaMode": true
261
- }
262
-
263
- ```
264
-
265
- ---
266
-
267
- ## Usage
268
-
269
- Use `lightning-flow-scanner-core` as a Node.js/browser dependency or standalone UMD module.
270
-
271
- ### Examples
272
-
273
- ```js
274
- // Basic
275
- import { parse, scan } from "@flow-scanner/lightning-flow-scanner-core";
276
- parse("flows/*.xml").then(scan);
277
-
278
- // Apply available patches
279
- import { parse, scan, fix } from "@flow-scanner/lightning-flow-scanner-core";
280
- parse("flows/*.xml").then(scan).then(fix);
281
-
282
- // Get SARIF output
283
- import { parse, scan, exportSarif } from "@flow-scanner/lightning-flow-scanner-core";
284
- parse("flows/*.xml").then(scan).then(exportSarif); //.then((sarif) => save("results.sarif", sarif));
285
-
286
- // Browser Usage (Tooling API)
287
- const { Flow, scan } = window.lightningflowscanner;
288
- const metadataRes = await conn.tooling.query(`SELECT Id, FullName, Metadata FROM Flow`);
289
- const results = scan(
290
- metadataRes.records.map((r) => ({
291
- uri: `/services/data/v60.0/tooling/sobjects/Flow/${r.Id}`,
292
- flow: new Flow(r.FullName, r.Metadata),
293
- })) //, optionsForScan
294
- );
295
- ```
296
-
297
- **Privacy:** Zero user data collected. All processing is client-side. → See our [Security Policy](https://github.com/Flow-Scanner/lightning-flow-scanner-core?tab=security-ov-file).
298
-
299
- ### Functions
300
-
301
- #### [`getRules(ruleNames?: string[]): IRuleDefinition[]`](https://github.com/Flow-Scanner/lightning-flow-scanner-core/tree/main/src/main/libs/GetRuleDefinitions.ts)
302
-
303
- _Retrieves rule definitions used in the scanner._
304
-
305
- #### [`parse(selectedUris: any): Promise<ParsedFlow[]>`](https://github.com/Flow-Scanner/lightning-flow-scanner-core/tree/main/src/main/libs/ParseFlows.ts)
306
-
307
- _Loads Flow XML files into in-memory models.(Node.js only)_
308
-
309
- #### [`scan(parsedFlows: ParsedFlow[], ruleOptions?: IRulesConfig): ScanResult[]`](https://github.com/Flow-Scanner/lightning-flow-scanner-core/tree/main/src/main/libs/ScanFlows.ts)
310
-
311
- _Runs all enabled rules and returns detailed violations._
312
-
313
- #### [`fix(results: ScanResult[]): ScanResult[]`](https://github.com/Flow-Scanner/lightning-flow-scanner-core/tree/main/src/main/libs/FixFlows.ts)
314
-
315
- _Automatically applies available fixes(removing variables and unconnected elements)._
316
-
317
- #### [`exportSarif(results: ScanResult[]): string`](https://github.com/Flow-Scanner/lightning-flow-scanner-core/tree/main/src/main/libs/exportAsSarif.ts)
318
-
319
- _Get SARIF output including exact line numbers of violations._
320
-
321
- ---
322
-
323
- ## Installation
324
-
325
- [![GitHub stars](https://img.shields.io/github/stars/Flow-Scanner/lightning-flow-scanner-core)](https://img.shields.io/github/stars/Flow-Scanner/lightning-flow-scanner-core)
326
- [![GitHub contributors](https://img.shields.io/github/contributors/Flow-Scanner/lightning-flow-scanner-core.svg)](https://gitHub.com/Flow-Scanner/lightning-flow-scanner-core/graphs/contributors/)
327
- [![License](https://img.shields.io/npm/l/lightning-flow-scanner-core.svg)](https://github.com/Flow-Scanner/lightning-flow-scanner-core/raw/main/LICENSE.md)
328
- [![npm version](https://img.shields.io/npm/v/@flow-scanner/lightning-flow-scanner-core)](https://www.npmjs.com/package/@flow-scanner/lightning-flow-scanner-core)
329
- [![Known Vulnerabilities](https://snyk.io/test/github/Flow-Scanner/lightning-flow-scanner-core/badge.svg)](https://snyk.io/test/github/Flow-Scanner/lightning-flow-scanner-core)
330
-
331
- **To install with npm:**
332
-
333
- ```bash
334
- npm install @flow-scanner/lightning-flow-scanner-core
335
- ```
336
-
337
- ---
338
-
339
- ## Development
340
-
341
- > This project optionally uses [Volta](https://volta.sh) to manage Node.js versions. Install Volta with:
342
- >
343
- > ```sh
344
- > curl https://get.volta.sh | bash
345
- > ```
346
- >
347
- > Volta will automatically use the Node.js version defined in `package.json`.
348
-
349
- 1. Clone the repository
350
-
351
- ```bash
352
- git clone https://github.com/Flow-Scanner/lightning-flow-scanner-core.git
353
- ```
354
-
355
- 2. Install dependencies:
356
-
357
- ```bash
358
- npm install
359
- ```
360
-
361
- 3. Compile a new version:
362
-
363
- ```bash
364
- npm run build
365
- ```
366
-
367
- 4. Run tests:
368
-
369
- ```bash
370
- npm run test
371
- ```
372
-
373
- 5. Testing the module locally(Optional):
374
-
375
- To link the module, run:
376
-
377
- ```bash
378
- npm run link
379
- ```
380
-
381
- a. Ad-Hoc Testing with node:
382
-
383
- ```bash
384
- npm run link
385
- ```
386
-
387
- b. Test in a dependent project (e.g. VSX or CLI):
388
-
389
- ```bash
390
- npm link @flow-scanner/lightning-flow-scanner-core
391
- ```
392
-
393
- Your local module will now replace any installed version and update on rebuild.
394
-
395
- 6. Deploy Demo Flows (Optional):
396
-
397
- ```bash
398
- cd assets/example-flows && sf project deploy start &&
399
- ```
400
-
401
- Navigate to the [Demo Readme](assets\example-flows\README.md) for full details
402
-
403
- 7. Create a standalone UMD Module(Optional):
404
-
405
- ```bash
406
- npm run vite:dist // creates UMD at`dist/lightning-flow-scanner-core.umd.js`.
407
- ```
408
-
409
- <p><strong>Want to help improve Lightning Flow Scanner? See our <a href="https://github.com/Flow-Scanner/lightning-flow-scanner-core?tab=contributing-ov-file">Contributing Guidelines</a></strong></p>
1
+ <p align="center">
2
+ <a href="https://github.com/Flow-Scanner">
3
+ <img src="assets/media/banner.png" style="width: 43%;" />
4
+ </a>
5
+ </p>
6
+
7
+ <p align="center"><i>Detect unsafe contexts, queries in loops, hardcoded IDs, and more to optimize Salesforce Flows</i></p>
8
+
9
+ ---
10
+
11
+ ## Table of contens
12
+
13
+ - **[Distributions](#distributions)**
14
+ - **[Default Rules](#default-rules)**
15
+ - **[Configuration](#configuration)**
16
+ - [Defining Severity Levels](#defining-severity-levels)
17
+ - [Configuring Expressions](#configuring-expressions)
18
+ - [Specifying Exceptions](#specifying-exceptions)
19
+ - [Report Detail Level](#report-detail-level)
20
+ - [Include Beta Rules](#include-beta-rules)
21
+ - **[Installation](#installation)**
22
+ - [Salesforce CLI Plugin](#salesforce-cli-plugin)
23
+ - [Core Module](#core-module)
24
+ - [CICD Templates](#cicd-templates)
25
+ - **[Quick Start](#quick-start)**
26
+ - **[Development](#development)**
27
+
28
+ ---
29
+
30
+ ## Distributions
31
+
32
+ | Distribution | Best for | Repository | Install / Use |
33
+ |-------------------------------------|-----------------------------------------------|----------------------------------------------------------------------------------------------|--------------------------------------------------------------------------------|
34
+ | **Salesforce CLI Plugin** | Local development, scratch orgs, CI/CD | [Flow-Scanner/lightning-flow-scanner](https://github.com/Flow-Scanner/lightning-flow-scanner) | `sf plugins install lightning-flow-scanner` |
35
+ | **VS Code Extension** | Real-time scanning inside VS Code | [Flow-Scanner/lightning-flow-scanner-vsx](https://github.com/Flow-Scanner/lightning-flow-scanner-vsx) | `code --install-extension ForceConfigControl.lightning-flow-scanner-vsx` |
36
+ | **Salesforce App** | Run scans directly inside any Salesforce org | [Flow-Scanner/lightning-flow-scanner-app](https://github.com/Flow-Scanner/lightning-flow-scanner-app) | <a href="https://login.salesforce.com/packaging/installPackage.apexp?p0=04tgK0000007M73QAE"><img alt="Install Managed Package" src="https://raw.githubusercontent.com/afawcett/githubsfdeploy/master/deploy.png"></a> |
37
+ | **GitHub Action** | Native PR checks | [Flow-Scanner/lightning-flow-scanner-action](https://github.com/Flow-Scanner/lightning-flow-scanner-action) | [GitHub Marketplace](https://github.com/marketplace/actions/run-flow-scanner) |
38
+ | **Copado Plugin** | Copado CI/CD pipelines | [Flow-Scanner/lightning-flow-scanner-copado](https://github.com/Flow-Scanner/lightning-flow-scanner-copado) | [Copado Marketplace](https://success.copado.com/s/listing-detail?language=en_US&recordId=a54P7000003G3gBIAS) |
39
+ | **Core Library** (Node.js + Browser)| Custom tools, scripts, extensions, web apps | [Flow-Scanner/lightning-flow-scanner](https://github.com/Flow-Scanner/lightning-flow-scanner) | `npm install @flow-scanner/lightning-flow-scanner-core` |
40
+
41
+ **Privacy:** Zero user data collected. All processing is client-side. → See our [Security Policy](https://github.com/Flow-Scanner/lightning-flow-scanner?tab=security-ov-file).
42
+
43
+ ## Default Rules
44
+
45
+ <p>📌<strong>Tip:</strong> To link directly to a specific rule, use the full GitHub anchor link format. Example:</p>
46
+ <p><em><a href="https://github.com/Flow-Scanner/lightning-flow-scanner#unsafe-running-context">https://github.com/Flow-Scanner/lightning-flow-scanner#unsafe-running-context</a></em></p>
47
+
48
+ > Want to code a new rule? → See [How to Write a Rule](https://github.com/Flow-Scanner/lightning-flow-scanner/blob/main/docs/write-a-rule.md)
49
+
50
+ ### Action Calls In Loop
51
+
52
+ _[ActionCallsInLoop](https://github.com/Flow-Scanner/lightning-flow-scanner/blob/main/packages/core/src/main/rules/ActionCallsInLoop.ts)_ - To prevent exceeding Apex governor limits, it is advisable to consolidate and bulkify your apex calls, utilizing a single action call containing a collection variable at the end of the loop.
53
+
54
+ ### Outdated API Version
55
+
56
+ _[APIVersion](https://github.com/Flow-Scanner/lightning-flow-scanner/blob/main/packages/core/src/main/rules/APIVersion.ts)_ - Introducing newer API components may lead to unexpected issues with older versions of Flows, as they might not align with the underlying mechanics. Starting from API version 50.0, the **Api Version** attribute has been readily available on the Flow Object. To ensure smooth operation and reduce discrepancies between API versions, it is strongly advised to regularly update and maintain them.
57
+
58
+ ### Auto Layout
59
+
60
+ _[AutoLayout](https://github.com/Flow-Scanner/lightning-flow-scanner/blob/main/packages/core/src/main/rules/AutoLayout.ts)_ - With Canvas Mode set to Auto‑Layout, elements are spaced, connected, and aligned automatically, keeping your Flow neatly organized—saving you time.
61
+
62
+ ### Copy API Name
63
+
64
+ _[CopyAPIName](https://github.com/Flow-Scanner/lightning-flow-scanner/blob/main/packages/core/src/main/rules/CopyAPIName.ts)_ - Maintaining multiple elements with a similar name, like `Copy_X_Of_Element`, can diminish the overall readability of your Flow. When copying and pasting these elements, remember to update the API name of the newly created copy.
65
+
66
+ ### Cyclomatic Complexity
67
+
68
+ _[CyclomaticComplexity](https://github.com/Flow-Scanner/lightning-flow-scanner/blob/main/packages/core/src/main/rules/CyclomaticComplexity.ts)_ - The number of loops and decision rules, plus the number of decisions. Use a combination of 1) subflows and 2) breaking flows into multiple concise trigger‑ordered flows to reduce cyclomatic complexity within a single flow, ensuring maintainability and simplicity.
69
+
70
+ ### DML Statement In A Loop
71
+
72
+ _[DMLStatementInLoop](https://github.com/Flow-Scanner/lightning-flow-scanner/blob/main/packages/core/src/main/rules/DMLStatementInLoop.ts)_ - To prevent exceeding Apex governor limits, consolidate all your database operations—record creation, updates, or deletions—at the conclusion of the flow.
73
+
74
+ ### Duplicate DML Operation
75
+
76
+ _[DuplicateDMLOperation](https://github.com/Flow-Scanner/lightning-flow-scanner/blob/main/packages/core/src/main/rules/DuplicateDMLOperation.ts)_ - When a flow executes database changes or actions between two screens, prevent users from navigating backward between screens; otherwise, duplicate database operations may be performed.
77
+
78
+ ### Flow Naming Convention
79
+
80
+ _[FlowName](https://github.com/Flow-Scanner/lightning-flow-scanner/blob/main/packages/core/src/main/rules/FlowName.ts)_ - The readability of a flow is paramount. Establishing a naming convention significantly enhances findability, searchability, and overall consistency. Include at least a domain and a brief description of the flow’s actions, for example `Service_OrderFulfillment`.
81
+
82
+ ### Get Record All Fields
83
+
84
+ _[GetRecordAllFields](https://github.com/Flow-Scanner/lightning-flow-scanner/blob/main/packages/core/src/main/rules/GetRecordAllFields.ts)_ - Following the principle of least privilege (PoLP), avoid using **Get Records** with “Automatically store all fields” unless necessary.
85
+
86
+ ### Hardcoded Id
87
+
88
+ _[HardcodedId](https://github.com/Flow-Scanner/lightning-flow-scanner/blob/main/packages/core/src/main/rules/HardcodedId.ts)_ - Avoid hard‑coding IDs because they are org specific. Instead, pass them into variables at the start of the flow—via merge‑field URL parameters or a **Get Records** element.
89
+
90
+ ### Hardcoded Url
91
+
92
+ _[HardcodedUrl](https://github.com/Flow-Scanner/lightning-flow-scanner/blob/main/packages/core/src/main/rules/HardcodedUrl.ts)_ - Avoid hard‑coding URLs because they are environment specific. Use an `$API` formula (preferred) or environment‑specific sources like custom labels, metadata, or settings.
93
+
94
+ ### Inactive Flow
95
+
96
+ _[InactiveFlow](https://github.com/Flow-Scanner/lightning-flow-scanner/blob/main/packages/core/src/main/rules/InactiveFlow.ts)_ - Like cleaning out your closet: deleting unused flows is essential. Inactive flows can still cause trouble—such as accidentally deleting records during testing, or being activated as subflows.
97
+
98
+ ### Missing Fault Path
99
+
100
+ _[MissingFaultPath](https://github.com/Flow-Scanner/lightning-flow-scanner/blob/main/packages/core/src/main/rules/MissingFaultPath.ts)_ - A flow may fail to execute an operation as intended. By default, the flow displays an error to the user and emails the creator. Customize this behavior by incorporating a Fault Path.
101
+
102
+ ### Missing Flow Description
103
+
104
+ _[FlowDescription](https://github.com/Flow-Scanner/lightning-flow-scanner/blob/main/packages/core/src/main/rules/FlowDescription.ts)_ - Descriptions play a vital role in documentation. We highly recommend including details about where flows are used and their intended purpose.
105
+
106
+ ### Missing Metadata Description
107
+
108
+ _[MissingMetadataDescription](https://github.com/Flow-Scanner/lightning-flow-scanner/blob/main/packages/core/src/main/rules/MissingMetadataDescription.ts)_ – Flags Flow elements (Get Records, Assignments, Decisions, Actions, etc.) and metadata components (Variables, Formulas, Constants, Text Templates) that lack a description. Adding concise descriptions greatly improves readability, maintainability, and helps AI tools understand your automation intent.
109
+
110
+ ### Missing Null Handler
111
+
112
+ _[MissingNullHandler](https://github.com/Flow-Scanner/lightning-flow-scanner/blob/main/packages/core/src/main/rules/MissingNullHandler.ts)_ - When a **Get Records** operation finds no data, it returns `null`. Validate data by using a Decision element to check for a non‑null result.
113
+
114
+ ### Process Builder
115
+
116
+ _[ProcessBuilder](https://github.com/Flow-Scanner/lightning-flow-scanner/blob/main/packages/core/src/main/rules/ProcessBuilder.ts)_ - Salesforce is transitioning away from Workflow Rules and Process Builder in favor of Flow. Begin migrating your organization’s automation to Flow.
117
+
118
+ ### Recursive After Update
119
+
120
+ _[RecursiveAfterUpdate](https://github.com/Flow-Scanner/lightning-flow-scanner/blob/main/packages/core/src/main/rules/RecursiveAfterUpdate.ts)_ - After‑update flows are meant for modifying **other** records. Using them on the same record can cause recursion. Consider **before‑save** flows for same‑record updates.
121
+
122
+ ### Same Record Field Updates
123
+
124
+ _[SameRecordFieldUpdates](https://github.com/Flow-Scanner/lightning-flow-scanner/blob/main/packages/core/src/main/rules/SameRecordFieldUpdates.ts)_ - Similar to triggers, **before‑save** contexts can update the same record via `$Record` without invoking DML.
125
+
126
+ ### SOQL Query In A Loop
127
+
128
+ _[SOQLQueryInLoop](https://github.com/Flow-Scanner/lightning-flow-scanner/blob/main/packages/core/src/main/rules/SOQLQueryInLoop.ts)_ - To prevent exceeding Apex governor limits, consolidate all SOQL queries at the end of the flow.
129
+
130
+ ### Trigger Order
131
+
132
+ _[TriggerOrder](https://github.com/Flow-Scanner/lightning-flow-scanner/blob/main/packages/core/src/main/rules/TriggerOrder.ts)_ - Guarantee your flow execution order with the **Trigger Order** property introduced in Spring ’22.
133
+
134
+ ### Unconnected Element
135
+
136
+ _[UnconnectedElement](https://github.com/Flow-Scanner/lightning-flow-scanner/blob/main/packages/core/src/main/rules/UnconnectedElement.ts)_ - Avoid unconnected elements that are not used by the flow to keep flows efficient and maintainable.
137
+
138
+ ### Unsafe Running Context
139
+
140
+ _[UnsafeRunningContext](https://github.com/Flow-Scanner/lightning-flow-scanner/blob/main/packages/core/src/main/rules/UnsafeRunningContext.ts)_ - This flow is configured to run in **System Mode without Sharing**, granting all users permission to view and edit all data. This can lead to unsafe data access.
141
+
142
+ ### Unused Variable
143
+
144
+ _[UnusedVariable](https://github.com/Flow-Scanner/lightning-flow-scanner/blob/main/packages/core/src/main/rules/UnusedVariable.ts)_ - To maintain efficiency and manageability, avoid including variables that are never referenced.
145
+
146
+ ---
147
+
148
+ ## Configuration
149
+
150
+ It is recommend to configure and define:
151
+
152
+ - The rules to be executed.
153
+ - The severity of violating any specific rule.
154
+ - Rule properties such as REGEX expressions.
155
+ - Any known exceptions that should be ignored during scanning.
156
+
157
+ ```json
158
+ {
159
+ "rules": {
160
+ // Your rules here
161
+ },
162
+ "exceptions": {
163
+ // Your exceptions here
164
+ }
165
+ }
166
+ ```
167
+
168
+ Most Lightning Flow Scanner distributions automatically resolve configurations from `.flow-scanner.yml`, `.flow-scanner.json`, or `package.json` → `flowScanner`.
169
+
170
+ Using the rules section of your configurations, you can specify the list of rules to be run. Furthermore, you can define the severity and configure expressions of rules. Below is a breakdown of the available attributes of rule configuration:
171
+
172
+ ```json
173
+ {
174
+ "rules": {
175
+ "<RuleName>": {
176
+ "severity": "<Severity>",
177
+ "expression": "<Expression>"
178
+ }
179
+ }
180
+ }
181
+ ```
182
+
183
+ ### Defining Severity Levels
184
+
185
+ When the severity is not provided it will be `warning` by default. Other available values for severity are `error` and `note`. Define the severity per rule as shown below:
186
+
187
+ ```json
188
+ {
189
+ "rules": {
190
+ "FlowDescription": {
191
+ "severity": "error"
192
+ },
193
+ "UnusedVariable": {
194
+ "severity": "note"
195
+ }
196
+ }
197
+ }
198
+ ```
199
+
200
+ ### Configuring Expressions
201
+
202
+ Some rules have additional attributes to configure, such as the expression, that will overwrite default values. These can be configured in the same way as severity as shown in the following example.
203
+
204
+ ```json
205
+ {
206
+ "rules": {
207
+ "APIVersion": {
208
+ "severity": "error",
209
+ "expression": "===58" // comparison operator
210
+ },
211
+ "FlowName": {
212
+ "severity": "note",
213
+ "expression": "[A-Za-z0-9]" // regular expression
214
+ }
215
+ }
216
+ }
217
+ ```
218
+
219
+ ### Specifying Exceptions
220
+
221
+ Specifying exceptions allows you to exclude specific scenarios from rule enforcement. Exceptions can be specified at the flow, rule, or result level to provide fine-grained control. Below is a breakdown of the available attributes of exception configuration:
222
+
223
+ ```json
224
+ {
225
+ "exceptions": {
226
+ "<FlowName>": {
227
+ "<RuleName>": [
228
+ // Suppress a specific result:
229
+ "<ResultName>",
230
+ // Suppress ALL results of rule:
231
+ "*",
232
+ ...
233
+ ]
234
+ },
235
+ ...
236
+ }
237
+ }
238
+ ```
239
+
240
+ _Example_
241
+
242
+ ```json
243
+ {
244
+ "exceptions": {
245
+ "MyFlow": {
246
+ "MissingNullHandler": ["*"],
247
+ "HardcodedId": ["Old_Lookup_1"]
248
+ }
249
+ }
250
+ }
251
+ ```
252
+
253
+ ### Report Detail Level
254
+
255
+ Control the verbosity of violation reports via detailLevel. By default (`enriched`), outputs include element or flow-level details like variable data types, node connectors/locations, or attribute expressions for comprehensive reports. Set to `simple` for lighter output with only line and column numbers.
256
+
257
+ ```json
258
+ {
259
+ "rules": {
260
+ ...
261
+ },
262
+ "exceptions": {
263
+ ...
264
+ },
265
+ "detailLevel": "simple"
266
+ }
267
+ ```
268
+
269
+ ### Include Beta Rules
270
+
271
+ New rules are introduced in Beta mode before being added to the default ruleset. To include current Beta rules, enable the optional betamode parameter in your configuration:
272
+
273
+ ```json
274
+ {
275
+ "rules": {
276
+ ...
277
+ },
278
+ "exceptions": {
279
+ ...
280
+ },
281
+ "betaMode": true
282
+ }
283
+
284
+ ```
285
+
286
+ ## Installation
287
+
288
+ [![GitHub stars](https://img.shields.io/github/stars/Flow-Scanner/lightning-flow-scanner)](https://img.shields.io/github/stars/Flow-Scanner/lightning-flow-scanner)
289
+ [![GitHub contributors](https://img.shields.io/github/contributors/Flow-Scanner/lightning-flow-scanner.svg)](https://gitHub.com/Flow-Scanner/lightning-flow-scanner/graphs/contributors/)
290
+ [![License](https://img.shields.io/npm/l/lightning-flow-scanner.svg)](github.com/Flow-Scanner/lightning-flow-scanner/raw/main/LICENSE.md)
291
+
292
+ ### Salesforce CLI Plugin
293
+ [![npm](https://img.shields.io/npm/v/lightning-flow-scanner?label=)](https://www.npmjs.com/package/lightning-flow-scanner)
294
+
295
+ ```bash
296
+ sf plugins install lightning-flow-scanner
297
+ ```
298
+ OR
299
+ ```bash
300
+ npm install -g lightning-flow-scanner
301
+ ```
302
+
303
+ ### Core Module
304
+ [![npm](https://img.shields.io/npm/v/@flow-scanner/lightning-flow-scanner-core?label=)](https://www.npmjs.com/package/@flow-scanner/lightning-flow-scanner-core)
305
+
306
+ ```bash
307
+ npm install -g @flow-scanner/lightning-flow-scanner-core
308
+ ```
309
+
310
+ ---
311
+
312
+ ### CICD Templates
313
+ Ready-to-use CI/CD templates and a **native GitHub Action**.
314
+
315
+ | Platform | Template Type | Link |
316
+ |----------------|-----------------------------------|------|
317
+ | Azure DevOps | Full Project Scan | [`azure-pipelines-flow-FullScan.yml`](https://github.com/Flow-Scanner/lightning-flow-scanner/blob/main/docs/examples/azure-devops/azure-pipelines-flow-FullScan.yml) |
318
+ | Azure DevOps | Change-Based Scan | [`azure-pipelines-flow-changedFiles.yml`](https://github.com/Flow-Scanner/lightning-flow-scanner/blob/main/docs/examples/azure-devops/azure-pipelines-flow-changedFiles.yml) |
319
+ | Copado DevOps | Full & Change-Based Scans | [CI/CD Plugin](https://github.com/Flow-Scanner/lightning-flow-scanner-copado) |
320
+ | GitHub | Full & Change-Based Scans | [`scan-flows.yml`](https://github.com/Flow-Scanner/lightning-flow-scanner/blob/main/docs/examples/github-action/scan-flows.yml) |
321
+
322
+ ## Quick Start
323
+
324
+ ### Salesforce CLI Plugin
325
+
326
+ Use `lightning-flow-scanner` in the Salesforce CLI:
327
+
328
+ ```bash
329
+ sf flow:scan
330
+ sf flow:fix -d src/force-app
331
+ sf flow:scan --sarif > report.sarif
332
+ ```
333
+
334
+ ### Core Module
335
+ Use `lightning-flow-scanner-core` as a Node.js/browser dependency:
336
+
337
+ ```js
338
+ // Basic
339
+ import { parse, scan } from "@flow-scanner/lightning-flow-scanner-core";
340
+ parse("flows/*.xml").then(scan);
341
+
342
+ // Get SARIF output
343
+ import { parse, scan, exportSarif } from "@flow-scanner/lightning-flow-scanner-core";
344
+ parse("flows/*.xml").then(scan).then(exportSarif);
345
+ ```
346
+
347
+ ## Development
348
+
349
+ > This project optionally uses [Volta](https://volta.sh) to guarantee the exact same Node.js and tool versions for every contributor. Install Volta with:
350
+ >
351
+ > ```sh
352
+ > curl https://get.volta.sh | bash
353
+ > ```
354
+ >
355
+ > ```sh
356
+ > winget install Volta.Volta
357
+ > ```
358
+ > Volta will automatically lock the exact versions of **Node.js**, **pnpm**, and all tools defined in `package.json`.
359
+
360
+ 1. Clone the repository
361
+
362
+ ```bash
363
+ git clone https://github.com/Flow-Scanner/lightning-flow-scanner.git
364
+ ```
365
+
366
+ 2. Install dependencies:
367
+
368
+ ```bash
369
+ pnpm install
370
+ ```
371
+
372
+ 3. Compile:
373
+
374
+ ```bash
375
+ pnpm run build
376
+ ```
377
+
378
+ To compile just the core package::
379
+ ```bash
380
+ pnpm build:core
381
+ ```
382
+
383
+ 4. Run tests:
384
+
385
+ ```bash
386
+ pnpm test
387
+ ```
388
+
389
+ Or to test a new version of the core:
390
+ ```bash
391
+ pnpm test:core
392
+ ```
393
+
394
+ 5. Linking the core module locally(Optional):
395
+
396
+ To link the module, run:
397
+
398
+ ```bash
399
+ pnpm link --global @flow-scanner/lightning-flow-scanner-core
400
+ ```
401
+
402
+ You can now do Ad-Hoc Testing with node:
403
+
404
+ ```bash
405
+ node -i -e "import('@flow-scanner/lightning-flow-scanner-core').then(m => { Object.assign(global, m.default ? m.default : m); console.log('✅ Core loaded! Try: await parse(...), scan(...), etc.'); })"
406
+ ```
407
+
408
+ Or test in a dependent project:
409
+
410
+ ```bash
411
+ npm link @flow-scanner/lightning-flow-scanner-core
412
+ ```
413
+
414
+ 6. Deploy Demo Flows (Optional):
415
+
416
+ ```bash
417
+ cd assets/example-flows && sf project deploy start
418
+ ```
419
+
420
+ Navigate to the [Demo Readme](https://github.com/Flow-Scanner/lightning-flow-scanner/blob/main/assets/example-flows\README.md) for full details
421
+
422
+ 7. Create a standalone UMD Module(Optional):
423
+
424
+ ```bash
425
+ pnpm dist // creates UMD at`dist/lightning-flow-scanner-core.umd.js`.
426
+ ```
427
+
428
+ <p><strong>Want to help improve Lightning Flow Scanner? See our <a href="https://github.com/Flow-Scanner/lightning-flow-scanner?tab=contributing-ov-file">Contributing Guidelines</a></strong></p>