Files
privacy.sexy/src/application/Parser/Script/Validation/Rules/NoDuplicatedLines.ts
undergroundwires a721e82a4f Bump TypeScript to 5.3 with verbatimModuleSyntax
This commit upgrades TypeScript to the latest version 5.3 and introduces
`verbatimModuleSyntax` in line with the official Vue guide
recommendatinos (vuejs/docs#2592).

By enforcing `import type` for type-only imports, this commit improves
code clarity and supports tooling optimization, ensuring imports are
only bundled when necessary for runtime.

Changes:

- Bump TypeScript to 5.3.3 across the project.
- Adjust import statements to utilize `import type` where applicable,
  promoting cleaner and more efficient code.
2024-02-27 04:20:22 +01:00

46 lines
1.7 KiB
TypeScript

import type { ILanguageSyntax } from '@/application/Parser/Script/Validation/Syntax/ILanguageSyntax';
import type { ICodeLine } from '../ICodeLine';
import type { ICodeValidationRule, IInvalidCodeLine } from '../ICodeValidationRule';
export class NoDuplicatedLines implements ICodeValidationRule {
constructor(private readonly syntax: ILanguageSyntax) { }
public analyze(lines: readonly ICodeLine[]): IInvalidCodeLine[] {
return lines
.map((line): IDuplicateAnalyzedLine => ({
index: line.index,
isIgnored: shouldIgnoreLine(line.text, this.syntax),
occurrenceIndices: lines
.filter((other) => other.text === line.text)
.map((duplicatedLine) => duplicatedLine.index),
}))
.filter((line) => hasInvalidDuplicates(line))
.map((line): IInvalidCodeLine => ({
index: line.index,
error: `Line is duplicated at line numbers ${line.occurrenceIndices.join(',')}.`,
}));
}
}
interface IDuplicateAnalyzedLine {
readonly index: number;
readonly occurrenceIndices: readonly number[];
readonly isIgnored: boolean;
}
function hasInvalidDuplicates(line: IDuplicateAnalyzedLine): boolean {
return !line.isIgnored && line.occurrenceIndices.length > 1;
}
function shouldIgnoreLine(codeLine: string, syntax: ILanguageSyntax): boolean {
const lowerCaseCodeLine = codeLine.toLowerCase();
const isCommentLine = () => syntax.commentDelimiters.some(
(delimiter) => lowerCaseCodeLine.startsWith(delimiter),
);
const consistsOfFrequentCommands = () => {
const trimmed = lowerCaseCodeLine.trim().split(' ');
return trimmed.every((part) => syntax.commonCodeParts.includes(part));
};
return isCommentLine() || consistsOfFrequentCommands();
}