-
Notifications
You must be signed in to change notification settings - Fork 9
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Merge pull request #136 from rrd108/rrd/if-without-curly-braces
feat: add rrd if without curly braces rule w tests fix #111
- Loading branch information
Showing
8 changed files
with
180 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,37 @@ | ||
# If Without Curly Braces | ||
|
||
Check if `if` statements are missing curly braces, even when they contain only one line of code. | ||
|
||
## 📖 What does this rule enforce? | ||
|
||
This rule ensures that all `if` statements, regardless of the number of lines they contain, use curly braces `{}` to enclose the code block. | ||
|
||
## ❓ Why it's good to follow this rule? | ||
|
||
- **Readability:** Curly braces make the structure of the code clear, reducing the likelihood of misunderstandings. Even if the `if` statement has only one line, using braces ensures that the code is easy to read and follow. | ||
- **Consistency:** Enforcing curly braces for all `if` statements helps maintain a consistent coding style throughout the project, making the codebase easier to navigate. | ||
- **Maintainability:** Code changes often, and what starts as a one-line `if` statement can easily grow into something more complex. If braces are already in place, adding new lines of code becomes less error-prone. | ||
- **Avoiding Bugs:** Omitting braces can lead to subtle bugs, especially when additional statements are added later. With braces, there's no ambiguity about which statements are controlled by the `if`. | ||
|
||
## 😱 Examples of code for which this rule will throw a warning | ||
|
||
::: warning | ||
The following code omits curly braces in the `if` statement: | ||
::: | ||
|
||
```ts | ||
if (condition) | ||
doSomething() | ||
``` | ||
|
||
## 🤩 How to fix it? | ||
|
||
::: tip | ||
Always use curly braces to enclose the code block within `if` statements, even if it's just one line. | ||
::: | ||
|
||
```ts | ||
if (condition) { | ||
doSomething() | ||
} | ||
``` |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,86 @@ | ||
import { beforeEach, describe, expect, it } from 'vitest' | ||
import type { SFCScriptBlock } from '@vue/compiler-sfc' | ||
import { BG_ERR, BG_RESET, TEXT_INFO, TEXT_RESET, TEXT_WARN } from '../asceeCodes' | ||
import { checkIfWithoutCurlyBraces, reportIfWithoutCurlyBraces, resetIfWithoutCurlyBraces } from './ifWithoutCurlyBraces' | ||
|
||
describe('ifWithoutCurlyBraces', () => { | ||
beforeEach(() => { | ||
resetIfWithoutCurlyBraces() | ||
}) | ||
|
||
it('should not report files where if statements use curly braces', () => { | ||
const script = { | ||
content: ` | ||
<script setup> | ||
if (isLoading) { | ||
doSomething(); | ||
} | ||
</script> | ||
`, | ||
} as SFCScriptBlock | ||
const filename = 'if-with-curly-braces.vue' | ||
checkIfWithoutCurlyBraces(script, filename) | ||
expect(reportIfWithoutCurlyBraces().length).toBe(0) | ||
expect(reportIfWithoutCurlyBraces()).toStrictEqual([]) | ||
}) | ||
|
||
it('should not report files where if statements are written in a single line with curly braces', () => { | ||
const script = { | ||
content: ` | ||
<script setup> | ||
if (isLoading) { doSomething(); } | ||
if (isError) { handleError(); } | ||
</script> | ||
`, | ||
} as SFCScriptBlock | ||
const filename = 'if-with-single-line-curly-braces.vue' | ||
checkIfWithoutCurlyBraces(script, filename) | ||
expect(reportIfWithoutCurlyBraces().length).toBe(0) | ||
expect(reportIfWithoutCurlyBraces()).toStrictEqual([]) | ||
}) | ||
|
||
it('should report files where an if statement does not use curly braces', () => { | ||
const script = { | ||
content: ` | ||
<script setup> | ||
if (isLoading) doSomething(); | ||
</script> | ||
`, | ||
} as SFCScriptBlock | ||
const filename = 'if-without-curly-braces.vue' | ||
const statement = 'if (isLoading) doSomething();' | ||
checkIfWithoutCurlyBraces(script, filename) | ||
expect(reportIfWithoutCurlyBraces().length).toBe(1) | ||
expect(reportIfWithoutCurlyBraces()).toStrictEqual([{ | ||
file: filename, | ||
rule: `${TEXT_INFO}rrd ~ if without curly braces${TEXT_RESET}`, | ||
description: `👉 ${TEXT_WARN}All if statements must be enclosed in curly braces for better readability and maintainability.${TEXT_RESET} See: https://vue-mess-detector.webmania.cc/rules/rrd/if-without-curly-braces.html`, | ||
message: `line #2 if statement without curly braces: ${BG_ERR}${statement}${BG_RESET} 🚨`, | ||
}]) | ||
}) | ||
|
||
it('should report files where multiple if statements do not use curly braces', () => { | ||
const script = { | ||
content: ` | ||
<script setup> | ||
if (isLoading) doSomething(); | ||
if (isError) handleError(); | ||
</script> | ||
`, | ||
} as SFCScriptBlock | ||
const filename = 'multiple-if-without-curly-braces.vue' | ||
checkIfWithoutCurlyBraces(script, filename) | ||
expect(reportIfWithoutCurlyBraces().length).toBe(2) | ||
expect(reportIfWithoutCurlyBraces()).toStrictEqual([{ | ||
file: filename, | ||
rule: `${TEXT_INFO}rrd ~ if without curly braces${TEXT_RESET}`, | ||
description: `👉 ${TEXT_WARN}All if statements must be enclosed in curly braces for better readability and maintainability.${TEXT_RESET} See: https://vue-mess-detector.webmania.cc/rules/rrd/if-without-curly-braces.html`, | ||
message: `line #2 if statement without curly braces: ${BG_ERR}if (isLoading) doSomething();${BG_RESET} 🚨`, | ||
}, { | ||
file: filename, | ||
rule: `${TEXT_INFO}rrd ~ if without curly braces${TEXT_RESET}`, | ||
description: `👉 ${TEXT_WARN}All if statements must be enclosed in curly braces for better readability and maintainability.${TEXT_RESET} See: https://vue-mess-detector.webmania.cc/rules/rrd/if-without-curly-braces.html`, | ||
message: `line #3 if statement without curly braces: ${BG_ERR}if (isError) handleError();${BG_RESET} 🚨`, | ||
}]) | ||
}) | ||
}) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,50 @@ | ||
import type { SFCScriptBlock } from '@vue/compiler-sfc' | ||
import { BG_ERR, BG_RESET, TEXT_INFO, TEXT_RESET, TEXT_WARN } from '../asceeCodes' | ||
import type { FileCheckResult, Offense } from '../../types' | ||
|
||
const results: FileCheckResult[] = [] | ||
|
||
const checkIfWithoutCurlyBraces = (script: SFCScriptBlock | null, filePath: string) => { | ||
if (!script) { | ||
return | ||
} | ||
|
||
const content = script.content | ||
const lines = content.split('\n') | ||
|
||
lines.forEach((line, index) => { | ||
const trimmedLine = line.trim() | ||
|
||
// Check if the line contains an `if` statement and is not followed by curly braces | ||
if (trimmedLine.startsWith('if (') && !trimmedLine.includes('{')) { | ||
// Check if the next line is not a continuation of the if statement with curly braces | ||
const nextLine = lines[index + 1]?.trim() | ||
if (!nextLine || (!nextLine.startsWith('{') && !trimmedLine.endsWith('{'))) { | ||
results.push({ | ||
filePath, | ||
message: `line #${index} if statement without curly braces: ${BG_ERR}${trimmedLine}${BG_RESET}`, | ||
}) | ||
} | ||
} | ||
}) | ||
} | ||
|
||
const reportIfWithoutCurlyBraces = () => { | ||
const offenses: Offense[] = [] | ||
|
||
if (results.length > 0) { | ||
results.forEach((result) => { | ||
offenses.push({ | ||
file: result.filePath, | ||
rule: `${TEXT_INFO}rrd ~ if without curly braces${TEXT_RESET}`, | ||
description: `👉 ${TEXT_WARN}All if statements must be enclosed in curly braces for better readability and maintainability.${TEXT_RESET} See: https://vue-mess-detector.webmania.cc/rules/rrd/if-without-curly-braces.html`, | ||
message: `${result.message} 🚨`, | ||
}) | ||
}) | ||
} | ||
return offenses | ||
} | ||
|
||
const resetIfWithoutCurlyBraces = () => (results.length = 0) | ||
|
||
export { checkIfWithoutCurlyBraces, reportIfWithoutCurlyBraces, resetIfWithoutCurlyBraces } |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters