diff --git a/CHANGELOG.md b/CHANGELOG.md index 71fa4ee90..57b9ff6fc 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -26,6 +26,10 @@ [Martin Redington](https://github.com/mildm8nnered) [#5681](https://github.com/realm/SwiftLint/issues/5681) +* Add new `allowed_types` option to `legacy_objc_type` rule to ignore certain types. + [kapitoshka438](https://github.com/kapitoshka438) + [#3723](https://github.com/realm/SwiftLint/issues/3723) + ### Bug Fixes * Fix issue referencing the Tests package from another Bazel workspace. diff --git a/Source/SwiftLintBuiltInRules/Rules/Idiomatic/LegacyObjcTypeRule.swift b/Source/SwiftLintBuiltInRules/Rules/Idiomatic/LegacyObjcTypeRule.swift index 35748478e..3df7918f1 100644 --- a/Source/SwiftLintBuiltInRules/Rules/Idiomatic/LegacyObjcTypeRule.swift +++ b/Source/SwiftLintBuiltInRules/Rules/Idiomatic/LegacyObjcTypeRule.swift @@ -30,7 +30,7 @@ private let legacyObjcTypes = [ @SwiftSyntaxRule(optIn: true) struct LegacyObjcTypeRule: Rule { - var configuration = SeverityConfiguration(.warning) + var configuration = LegacyObjcTypeConfiguration() static let description = RuleDescription( identifier: "legacy_objc_type", @@ -44,6 +44,12 @@ struct LegacyObjcTypeRule: Rule { Example("var className: String = NSStringFromClass(MyClass.self)"), Example("_ = URLRequest.CachePolicy.reloadIgnoringLocalCacheData"), Example(#"_ = Notification.Name("com.apple.Music.playerInfo")"#), + Example(#""" + class SLURLRequest: NSURLRequest { + let data = NSData() + let number: NSNumber + } + """#, configuration: ["allowed_types": ["NSData", "NSNumber", "NSURLRequest"]]), ], triggeringExamples: [ Example("var array = ↓NSArray()"), @@ -71,20 +77,24 @@ struct LegacyObjcTypeRule: Rule { private extension LegacyObjcTypeRule { final class Visitor: ViolationsSyntaxVisitor { override func visitPost(_ node: IdentifierTypeSyntax) { - if let typeName = node.typeName, legacyObjcTypes.contains(typeName) { + if let typeName = node.typeName, + legacyObjcTypes.contains(typeName), + !configuration.allowedTypes.contains(typeName) { violations.append(node.positionAfterSkippingLeadingTrivia) } } override func visitPost(_ node: DeclReferenceExprSyntax) { - if legacyObjcTypes.contains(node.baseName.text) { + if legacyObjcTypes.contains(node.baseName.text), + !configuration.allowedTypes.contains(node.baseName.text) { violations.append(node.baseName.positionAfterSkippingLeadingTrivia) } } override func visitPost(_ node: MemberTypeSyntax) { guard node.baseType.as(IdentifierTypeSyntax.self)?.typeName == "Foundation", - legacyObjcTypes.contains(node.name.text) + legacyObjcTypes.contains(node.name.text), + !configuration.allowedTypes.contains(node.name.text) else { return } diff --git a/Source/SwiftLintBuiltInRules/Rules/RuleConfigurations/LegacyObjcTypeConfiguration.swift b/Source/SwiftLintBuiltInRules/Rules/RuleConfigurations/LegacyObjcTypeConfiguration.swift new file mode 100644 index 000000000..7ecb334a9 --- /dev/null +++ b/Source/SwiftLintBuiltInRules/Rules/RuleConfigurations/LegacyObjcTypeConfiguration.swift @@ -0,0 +1,11 @@ +import SwiftLintCore + +@AutoConfigParser +struct LegacyObjcTypeConfiguration: SeverityBasedRuleConfiguration { + typealias Parent = LegacyObjcTypeRule + + @ConfigurationElement(key: "severity") + private(set) var severityConfiguration = SeverityConfiguration.warning + @ConfigurationElement(key: "allowed_types") + private(set) var allowedTypes: Set = [] +} diff --git a/Tests/IntegrationTests/default_rule_configurations.yml b/Tests/IntegrationTests/default_rule_configurations.yml index 44a66483b..a6400d28b 100644 --- a/Tests/IntegrationTests/default_rule_configurations.yml +++ b/Tests/IntegrationTests/default_rule_configurations.yml @@ -484,6 +484,7 @@ legacy_nsgeometry_functions: opt-in: false legacy_objc_type: severity: warning + allowed_types: [] meta: opt-in: true legacy_random: