diff --git a/CHANGELOG.md b/CHANGELOG.md index 121db6d70aa..c14d1bd1441 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -18,6 +18,12 @@ [SimplyDanny](https://github.com/SimplyDanny) [#3804](https://github.com/realm/SwiftLint/issues/3804) +* Ignore MARK in multiline comment, fixing cases that would previous crash or + produce invalid results when correcting. + [goranche](https://github.com/goranche) + [#1749](https://github.com/realm/SwiftLint/issues/1749) + [#3841](https://github.com/realm/SwiftLint/issues/3841) + ## 0.46.3: Detergent Spill #### Breaking diff --git a/Source/SwiftLintFramework/Rules/Lint/MarkRule.swift b/Source/SwiftLintFramework/Rules/Lint/MarkRule.swift index 2a53f2e7d19..d3df027cda2 100644 --- a/Source/SwiftLintFramework/Rules/Lint/MarkRule.swift +++ b/Source/SwiftLintFramework/Rules/Lint/MarkRule.swift @@ -17,7 +17,8 @@ public struct MarkRule: CorrectableRule, ConfigurationProviderRule { Example("// MARK: -\n"), Example("// BOOKMARK"), Example("//BOOKMARK"), - Example("// BOOKMARKS") + Example("// BOOKMARKS"), + issue1749Example ], triggeringExamples: [ Example("↓//MARK: bad"), @@ -64,7 +65,8 @@ public struct MarkRule: CorrectableRule, ConfigurationProviderRule { Example("↓// MARKK -"): Example("// MARK: -"), Example("↓/// MARK:"): Example("// MARK:"), Example("↓/// MARK comment"): Example("// MARK: comment"), - issue1029Example: issue1029Correction + issue1029Example: issue1029Correction, + issue1749Example: issue1749Correction ] ) @@ -183,11 +185,20 @@ public struct MarkRule: CorrectableRule, ConfigurationProviderRule { } private func violationRanges(in file: SwiftLintFile, matching pattern: String) -> [NSRange] { - return file.rangesAndTokens(matching: pattern).filter { _, syntaxTokens in - guard let syntaxKind = syntaxTokens.first?.kind else { + return file.rangesAndTokens(matching: pattern).filter { matchRange, syntaxTokens in + guard let syntaxToken = syntaxTokens.first, let syntaxKind = syntaxToken.kind else { return false } - return syntaxTokens.isNotEmpty && SyntaxKind.commentKinds.contains(syntaxKind) + guard SyntaxKind.commentKinds.contains(syntaxKind) else { + return false + } + let tokenLocation = Location(file: file, byteOffset: ByteCount(syntaxToken.offset.value)) + let matchLocation = Location(file: file, characterOffset: matchRange.location) + // Skip those MARKs that are part of a multiline comment + guard let tokenLine = tokenLocation.line, let matchLine = matchLocation.line, matchLine == tokenLine else { + return false + } + return true }.compactMap { range, syntaxTokens in let byteRange = ByteRange(location: syntaxTokens[0].offset, length: 0) let identifierRange = file.stringView.byteRangeToNSRange(byteRange) @@ -212,6 +223,21 @@ private let issue1029Correction = Example(""" extension MarkTest {} """) +// https://github.com/realm/SwiftLint/issues/1749 +// https://github.com/realm/SwiftLint/issues/3841 +private let issue1749Example = Example(""" + /* + func test1() { + } + //MARK: mark + func test2() { + } + */ + """) + +// This example should not trigger changes +private let issue1749Correction = issue1749Example + // These need to be at the bottom of the file to work around https://bugs.swift.org/browse/SR-10486 private let nonSpace = "[^ ]"