Skip to content

Commit

Permalink
Introduce @SwiftSyntaxRule & @Fold macros (#5253)
Browse files Browse the repository at this point in the history
These macros remove some of the boilerplate involved when writing rules.

This change also adds test infrastructure for the macros used within
SwiftLint.
  • Loading branch information
jpsim authored Oct 2, 2023
1 parent 2433e7b commit 5911540
Show file tree
Hide file tree
Showing 110 changed files with 339 additions and 514 deletions.
11 changes: 11 additions & 0 deletions BUILD
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,17 @@ load(

# Targets

swift_library(
name = "SwiftLintCoreMacrosLib",
module_name = "SwiftLintCoreMacros",
srcs = glob(["Source/SwiftLintCoreMacros/*.swift"]),
visibility = ["//visibility:public"],
deps = [
"@SwiftSyntax//:SwiftCompilerPlugin_opt",
"@SwiftSyntax//:SwiftSyntaxMacros_opt",
],
)

swift_compiler_plugin(
name = "SwiftLintCoreMacros",
srcs = glob(["Source/SwiftLintCoreMacros/*.swift"]),
Expand Down
7 changes: 7 additions & 0 deletions Package.swift
Original file line number Diff line number Diff line change
Expand Up @@ -131,5 +131,12 @@ let package = Package(
],
path: "Source/SwiftLintCoreMacros"
),
.testTarget(
name: "MacroTests",
dependencies: [
"SwiftLintCoreMacros",
.product(name: "SwiftSyntaxMacrosTestSupport", package: "swift-syntax"),
]
),
]
)
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import SwiftSyntax

struct BlockBasedKVORule: SwiftSyntaxRule, ConfigurationProviderRule {
@SwiftSyntaxRule
struct BlockBasedKVORule: ConfigurationProviderRule {
var configuration = SeverityConfiguration<Self>(.warning)

static let description = RuleDescription(
Expand Down Expand Up @@ -32,14 +33,10 @@ struct BlockBasedKVORule: SwiftSyntaxRule, ConfigurationProviderRule {
""")
]
)

func makeVisitor(file: SwiftLintFile) -> ViolationsSyntaxVisitor {
Visitor(viewMode: .sourceAccurate)
}
}

private extension BlockBasedKVORule {
private final class Visitor: ViolationsSyntaxVisitor {
final class Visitor: ViolationsSyntaxVisitor {
override func visitPost(_ node: FunctionDeclSyntax) {
guard node.modifiers.contains(keyword: .override),
case let parameterList = node.signature.parameterClause.parameters,
Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import SwiftSyntax

struct ConvenienceTypeRule: SwiftSyntaxRule, OptInRule, ConfigurationProviderRule {
@SwiftSyntaxRule
struct ConvenienceTypeRule: OptInRule, ConfigurationProviderRule {
var configuration = SeverityConfiguration<Self>(.warning)

static let description = RuleDescription(
Expand Down Expand Up @@ -114,10 +115,6 @@ struct ConvenienceTypeRule: SwiftSyntaxRule, OptInRule, ConfigurationProviderRul
""")
]
)

func makeVisitor(file: SwiftLintFile) -> ViolationsSyntaxVisitor {
Visitor(viewMode: .sourceAccurate)
}
}

private extension ConvenienceTypeRule {
Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import SwiftSyntax

struct DiscouragedAssertRule: SwiftSyntaxRule, OptInRule, ConfigurationProviderRule {
@SwiftSyntaxRule
struct DiscouragedAssertRule: OptInRule, ConfigurationProviderRule {
var configuration = SeverityConfiguration<Self>(.warning)

static let description = RuleDescription(
Expand All @@ -22,10 +23,6 @@ struct DiscouragedAssertRule: SwiftSyntaxRule, OptInRule, ConfigurationProviderR
Example(#"↓assert( false , "foobar")"#)
]
)

func makeVisitor(file: SwiftLintFile) -> ViolationsSyntaxVisitor {
Visitor(viewMode: .sourceAccurate)
}
}

private extension DiscouragedAssertRule {
Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import SwiftSyntax

struct DiscouragedNoneNameRule: SwiftSyntaxRule, OptInRule, ConfigurationProviderRule {
@SwiftSyntaxRule
struct DiscouragedNoneNameRule: OptInRule, ConfigurationProviderRule {
var configuration = SeverityConfiguration<Self>(.warning)

static var description = RuleDescription(
Expand Down Expand Up @@ -176,10 +177,6 @@ struct DiscouragedNoneNameRule: SwiftSyntaxRule, OptInRule, ConfigurationProvide
""")
]
)

func makeVisitor(file: SwiftLintFile) -> ViolationsSyntaxVisitor {
Visitor(viewMode: .sourceAccurate)
}
}

private extension DiscouragedNoneNameRule {
Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import SwiftSyntax

struct DiscouragedOptionalBooleanRule: OptInRule, ConfigurationProviderRule, SwiftSyntaxRule {
@SwiftSyntaxRule
struct DiscouragedOptionalBooleanRule: OptInRule, ConfigurationProviderRule {
var configuration = SeverityConfiguration<Self>(.warning)

static let description = RuleDescription(
Expand All @@ -11,10 +12,6 @@ struct DiscouragedOptionalBooleanRule: OptInRule, ConfigurationProviderRule, Swi
nonTriggeringExamples: DiscouragedOptionalBooleanRuleExamples.nonTriggeringExamples,
triggeringExamples: DiscouragedOptionalBooleanRuleExamples.triggeringExamples
)

func makeVisitor(file: SwiftLintFile) -> ViolationsSyntaxVisitor {
Visitor(viewMode: .sourceAccurate)
}
}

private extension DiscouragedOptionalBooleanRule {
Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import SwiftSyntax

struct ExplicitEnumRawValueRule: SwiftSyntaxRule, OptInRule, ConfigurationProviderRule {
@SwiftSyntaxRule
struct ExplicitEnumRawValueRule: OptInRule, ConfigurationProviderRule {
var configuration = SeverityConfiguration<Self>(.warning)

static let description = RuleDescription(
Expand Down Expand Up @@ -76,10 +77,6 @@ struct ExplicitEnumRawValueRule: SwiftSyntaxRule, OptInRule, ConfigurationProvid
""")
]
)

func makeVisitor(file: SwiftLintFile) -> ViolationsSyntaxVisitor {
Visitor(viewMode: .sourceAccurate)
}
}

private extension ExplicitEnumRawValueRule {
Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import SwiftSyntax

struct ExplicitTopLevelACLRule: SwiftSyntaxRule, OptInRule, ConfigurationProviderRule {
@SwiftSyntaxRule
struct ExplicitTopLevelACLRule: OptInRule, ConfigurationProviderRule {
var configuration = SeverityConfiguration<Self>(.warning)

static let description = RuleDescription(
Expand All @@ -27,10 +28,6 @@ struct ExplicitTopLevelACLRule: SwiftSyntaxRule, OptInRule, ConfigurationProvide
Example("internal let a = 0\n↓func b() {}")
]
)

func makeVisitor(file: SwiftLintFile) -> ViolationsSyntaxVisitor {
Visitor(viewMode: .sourceAccurate)
}
}

private extension ExplicitTopLevelACLRule {
Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import SwiftSyntax

struct FallthroughRule: SwiftSyntaxRule, ConfigurationProviderRule, OptInRule {
@SwiftSyntaxRule
struct FallthroughRule: ConfigurationProviderRule, OptInRule {
var configuration = SeverityConfiguration<Self>(.warning)

static let description = RuleDescription(
Expand All @@ -27,10 +28,6 @@ struct FallthroughRule: SwiftSyntaxRule, ConfigurationProviderRule, OptInRule {
""")
]
)

func makeVisitor(file: SwiftLintFile) -> ViolationsSyntaxVisitor {
Visitor(viewMode: .sourceAccurate)
}
}

private extension FallthroughRule {
Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import SwiftSyntax

struct FatalErrorMessageRule: SwiftSyntaxRule, ConfigurationProviderRule, OptInRule {
@SwiftSyntaxRule
struct FatalErrorMessageRule: ConfigurationProviderRule, OptInRule {
var configuration = SeverityConfiguration<Self>(.warning)

static let description = RuleDescription(
Expand Down Expand Up @@ -33,10 +34,6 @@ struct FatalErrorMessageRule: SwiftSyntaxRule, ConfigurationProviderRule, OptInR
""")
]
)

func makeVisitor(file: SwiftLintFile) -> ViolationsSyntaxVisitor {
Visitor(viewMode: .sourceAccurate)
}
}

private extension FatalErrorMessageRule {
Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import SwiftSyntax

struct ForceTryRule: ConfigurationProviderRule, SwiftSyntaxRule {
@SwiftSyntaxRule
struct ForceTryRule: ConfigurationProviderRule {
var configuration = SeverityConfiguration<Self>(.error)

static let description = RuleDescription(
Expand All @@ -23,10 +24,6 @@ struct ForceTryRule: ConfigurationProviderRule, SwiftSyntaxRule {
""")
]
)

func makeVisitor(file: SwiftLintFile) -> ViolationsSyntaxVisitor {
Visitor(viewMode: .sourceAccurate)
}
}

private extension ForceTryRule {
Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import SwiftSyntax

struct FunctionDefaultParameterAtEndRule: SwiftSyntaxRule, ConfigurationProviderRule, OptInRule {
@SwiftSyntaxRule
struct FunctionDefaultParameterAtEndRule: ConfigurationProviderRule, OptInRule {
var configuration = SeverityConfiguration<Self>(.warning)

static let description = RuleDescription(
Expand Down Expand Up @@ -48,10 +49,6 @@ struct FunctionDefaultParameterAtEndRule: SwiftSyntaxRule, ConfigurationProvider
Example("public ↓init?(for date: Date = Date(), coordinate: CLLocationCoordinate2D) {}")
]
)

func makeVisitor(file: SwiftLintFile) -> ViolationsSyntaxVisitor {
Visitor(viewMode: .sourceAccurate)
}
}

private extension FunctionDefaultParameterAtEndRule {
Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import SwiftSyntax

struct IsDisjointRule: SwiftSyntaxRule, ConfigurationProviderRule {
@SwiftSyntaxRule
struct IsDisjointRule: ConfigurationProviderRule {
var configuration = SeverityConfiguration<Self>(.warning)

static let description = RuleDescription(
Expand All @@ -19,10 +20,6 @@ struct IsDisjointRule: SwiftSyntaxRule, ConfigurationProviderRule {
Example("let isObjc = !objcAttributes.↓intersection(dictionary.enclosedSwiftAttributes).isEmpty")
]
)

func makeVisitor(file: SwiftLintFile) -> ViolationsSyntaxVisitor {
Visitor(viewMode: .sourceAccurate)
}
}

private extension IsDisjointRule {
Expand Down
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
import SwiftSyntax

@SwiftSyntaxRule
struct JoinedDefaultParameterRule: SwiftSyntaxCorrectableRule, ConfigurationProviderRule, OptInRule {
var configuration = SeverityConfiguration<Self>(.warning)

Expand Down Expand Up @@ -36,10 +37,6 @@ struct JoinedDefaultParameterRule: SwiftSyntaxCorrectableRule, ConfigurationProv
]
)

func makeVisitor(file: SwiftLintFile) -> ViolationsSyntaxVisitor {
Visitor(viewMode: .sourceAccurate)
}

func makeRewriter(file: SwiftLintFile) -> ViolationsSyntaxRewriter? {
Rewriter(
locationConverter: file.locationConverter,
Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import SwiftSyntax
import SwiftSyntaxBuilder

@SwiftSyntaxRule
struct LegacyConstantRule: SwiftSyntaxCorrectableRule, ConfigurationProviderRule {
var configuration = SeverityConfiguration<Self>(.warning)

Expand All @@ -14,10 +15,6 @@ struct LegacyConstantRule: SwiftSyntaxCorrectableRule, ConfigurationProviderRule
corrections: LegacyConstantRuleExamples.corrections
)

func makeVisitor(file: SwiftLintFile) -> ViolationsSyntaxVisitor {
Visitor(viewMode: .sourceAccurate)
}

func makeRewriter(file: SwiftLintFile) -> ViolationsSyntaxRewriter? {
Rewriter(
locationConverter: file.locationConverter,
Expand Down
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
import SwiftSyntax

@SwiftSyntaxRule
struct LegacyConstructorRule: SwiftSyntaxCorrectableRule, ConfigurationProviderRule {
var configuration = SeverityConfiguration<Self>(.warning)

Expand Down Expand Up @@ -122,10 +123,6 @@ struct LegacyConstructorRule: SwiftSyntaxCorrectableRule, ConfigurationProviderR
"NSEdgeInsetsMake": "NSEdgeInsets",
"UIOffsetMake": "UIOffset"]

func makeVisitor(file: SwiftLintFile) -> ViolationsSyntaxVisitor {
Visitor(viewMode: .sourceAccurate)
}

func makeRewriter(file: SwiftLintFile) -> ViolationsSyntaxRewriter? {
Rewriter(
locationConverter: file.locationConverter,
Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import SwiftSyntax

struct LegacyHashingRule: SwiftSyntaxRule, ConfigurationProviderRule {
@SwiftSyntaxRule
struct LegacyHashingRule: ConfigurationProviderRule {
var configuration = SeverityConfiguration<Self>(.warning)

static let description = RuleDescription(
Expand Down Expand Up @@ -72,14 +73,10 @@ struct LegacyHashingRule: SwiftSyntaxRule, ConfigurationProviderRule {
""")
]
)

func makeVisitor(file: SwiftLintFile) -> ViolationsSyntaxVisitor {
Visitor(viewMode: .sourceAccurate)
}
}

extension LegacyHashingRule {
private final class Visitor: ViolationsSyntaxVisitor {
private extension LegacyHashingRule {
final class Visitor: ViolationsSyntaxVisitor {
override func visitPost(_ node: VariableDeclSyntax) {
guard
node.parent?.is(MemberBlockItemSyntax.self) == true,
Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,8 @@
import SwiftSyntax

struct LegacyMultipleRule: OptInRule, ConfigurationProviderRule, SwiftSyntaxRule {
@Fold
@SwiftSyntaxRule
struct LegacyMultipleRule: OptInRule, ConfigurationProviderRule {
var configuration = SeverityConfiguration<Self>(.warning)

static let description = RuleDescription(
Expand Down Expand Up @@ -36,14 +38,6 @@ struct LegacyMultipleRule: OptInRule, ConfigurationProviderRule, SwiftSyntaxRule
""")
]
)

func preprocess(file: SwiftLintFile) -> SourceFileSyntax? {
file.foldedSyntaxTree
}

func makeVisitor(file: SwiftLintFile) -> ViolationsSyntaxVisitor {
Visitor(viewMode: .sourceAccurate)
}
}

private extension LegacyMultipleRule {
Expand Down
Loading

0 comments on commit 5911540

Please sign in to comment.