Skip to content

Commit fa55508

Browse files
committed
Migrate from Commandant to swift-argument-parser
1 parent 82b00bf commit fa55508

19 files changed

+360
-563
lines changed

.swiftlint.yml

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -36,7 +36,6 @@ opt_in_rules:
3636
- last_where
3737
- legacy_multiple
3838
- legacy_random
39-
- let_var_whitespace
4039
- literal_expression_end_indentation
4140
- lower_acl_than_parent
4241
- modifier_order

Package.resolved

Lines changed: 0 additions & 27 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

Package.swift

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
// swift-tools-version:5.0
1+
// swift-tools-version:5.2
22
import PackageDescription
33

44
#if canImport(CommonCrypto)
@@ -14,7 +14,7 @@ let package = Package(
1414
.library(name: "SwiftLintFramework", targets: ["SwiftLintFramework"])
1515
],
1616
dependencies: [
17-
.package(url: "https://github.com/Carthage/Commandant.git", .upToNextMinor(from: "0.17.0")),
17+
.package(name: "swift-argument-parser", url: "https://github.com/apple/swift-argument-parser.git", .upToNextMinor(from: "0.3.1")),
1818
.package(url: "https://github.com/jpsim/SourceKitten.git", .upToNextMinor(from: "0.31.0")),
1919
.package(url: "https://github.com/jpsim/Yams.git", from: "4.0.2"),
2020
.package(url: "https://github.com/scottrhoyt/SwiftyTextTable.git", from: "0.9.0"),
@@ -23,15 +23,15 @@ let package = Package(
2323
.target(
2424
name: "swiftlint",
2525
dependencies: [
26-
"Commandant",
26+
.product(name: "ArgumentParser", package: "swift-argument-parser"),
2727
"SwiftLintFramework",
2828
"SwiftyTextTable",
2929
]
3030
),
3131
.target(
3232
name: "SwiftLintFramework",
3333
dependencies: [
34-
"SourceKittenFramework",
34+
.product(name: "SourceKittenFramework", package: "SourceKitten"),
3535
"Yams",
3636
] + (addCryptoSwift ? ["CryptoSwift"] : [])
3737
),
Lines changed: 44 additions & 90 deletions
Original file line numberDiff line numberDiff line change
@@ -1,98 +1,52 @@
1-
import Commandant
1+
import ArgumentParser
22
import SwiftLintFramework
33

4-
struct AnalyzeCommand: CommandProtocol {
5-
let verb = "analyze"
6-
let function = "[Experimental] Run analysis rules"
4+
extension SwiftLint {
5+
struct Analyze: ParsableCommand {
6+
static let configuration = CommandConfiguration(abstract: "Run analysis rules")
77

8-
func run(_ options: AnalyzeOptions) -> Result<(), CommandantError<()>> {
9-
let options = LintOrAnalyzeOptions(options)
10-
if options.autocorrect {
11-
return autocorrect(options)
12-
} else {
13-
return LintOrAnalyzeCommand.run(options)
14-
}
15-
}
16-
17-
private func autocorrect(_ options: LintOrAnalyzeOptions) -> Result<(), CommandantError<()>> {
18-
let storage = RuleStorage()
19-
let configuration = Configuration(options: options)
20-
return configuration.visitLintableFiles(options: options, cache: nil, storage: storage) { linter in
21-
let corrections = linter.correct(using: storage)
22-
if !corrections.isEmpty && !options.quiet {
23-
let correctionLogs = corrections.map({ $0.consoleDescription })
24-
queuedPrint(correctionLogs.joined(separator: "\n"))
25-
}
26-
}.flatMap { files in
27-
if !options.quiet {
28-
let pluralSuffix = { (collection: [Any]) -> String in
29-
return collection.count != 1 ? "s" : ""
30-
}
31-
queuedPrintError("Done correcting \(files.count) file\(pluralSuffix(files))!")
32-
}
33-
return .success(())
34-
}
35-
}
36-
}
8+
@OptionGroup
9+
var common: LintOrAnalyzeArguments
10+
@Option(help: pathOptionDescription(for: .analyze))
11+
var path: String?
12+
@Flag(help: quietOptionDescription(for: .analyze))
13+
var quiet = false
14+
@Option(help: "The path of the full xcodebuild log to use when running AnalyzerRules.")
15+
var compilerLogPath: String?
16+
@Option(help: "The path of a compilation database to use when running AnalyzerRules.")
17+
var compileCommands: String?
18+
@Argument(help: pathsArgumentDescription(for: .analyze))
19+
var paths = [String]()
3720

38-
struct AnalyzeOptions: OptionsProtocol {
39-
let paths: [String]
40-
let configurationFiles: [String]
41-
let strict: Bool
42-
let lenient: Bool
43-
let forceExclude: Bool
44-
let excludeByPrefix: Bool
45-
let useScriptInputFiles: Bool
46-
let benchmark: Bool
47-
let reporter: String
48-
let quiet: Bool
49-
let enableAllRules: Bool
50-
let autocorrect: Bool
51-
let compilerLogPath: String
52-
let compileCommands: String
21+
mutating func run() throws {
22+
let options = LintOrAnalyzeOptions(
23+
mode: .analyze,
24+
paths: paths + [path ?? ""],
25+
useSTDIN: false,
26+
configurationFiles: common.config,
27+
strict: common.strict,
28+
lenient: common.lenient,
29+
forceExclude: common.forceExclude,
30+
useExcludingByPrefix: common.useAlternativeExcluding,
31+
useScriptInputFiles: common.useScriptInputFiles,
32+
benchmark: common.benchmark,
33+
reporter: common.reporter,
34+
quiet: quiet,
35+
cachePath: nil,
36+
ignoreCache: true,
37+
enableAllRules: false,
38+
autocorrect: common.fix,
39+
compilerLogPath: compilerLogPath,
40+
compileCommands: compileCommands
41+
)
5342

54-
// swiftlint:disable line_length
55-
static func create(_ path: String) -> (_ configurationFiles: [String]) -> (_ strict: Bool) -> (_ lenient: Bool) -> (_ forceExclude: Bool) -> (_ excludeByPrefix: Bool) -> (_ useScriptInputFiles: Bool) -> (_ benchmark: Bool) -> (_ reporter: String) -> (_ quiet: Bool) -> (_ enableAllRules: Bool) -> (_ autocorrect: Bool) -> (_ compilerLogPath: String) -> (_ compileCommands: String) -> (_ paths: [String]) -> AnalyzeOptions {
56-
return { configurationFiles in { strict in { lenient in { forceExclude in { excludeByPrefix in { useScriptInputFiles in { benchmark in { reporter in { quiet in { enableAllRules in { autocorrect in { compilerLogPath in { compileCommands in { paths in
57-
let allPaths: [String]
58-
if !path.isEmpty {
59-
allPaths = [path]
60-
} else {
61-
allPaths = paths
43+
let result = LintOrAnalyzeCommand.run(options)
44+
switch result {
45+
case .success:
46+
return
47+
case .failure(let error):
48+
throw error
6249
}
63-
64-
return self.init(paths: allPaths, configurationFiles: configurationFiles, strict: strict, lenient: lenient, forceExclude: forceExclude, excludeByPrefix: excludeByPrefix, useScriptInputFiles: useScriptInputFiles, benchmark: benchmark, reporter: reporter, quiet: quiet, enableAllRules: enableAllRules, autocorrect: autocorrect, compilerLogPath: compilerLogPath, compileCommands: compileCommands)
65-
// swiftlint:enable line_length
66-
}}}}}}}}}}}}}}
67-
}
68-
69-
static func evaluate(_ mode: CommandMode) -> Result<AnalyzeOptions, CommandantError<CommandantError<()>>> {
70-
return create
71-
<*> mode <| pathOption(action: "analyze")
72-
<*> mode <| configOption
73-
<*> mode <| Option(key: "strict", defaultValue: false,
74-
usage: "upgrades warnings to serious violations (errors)")
75-
<*> mode <| Option(key: "lenient", defaultValue: false,
76-
usage: "downgrades serious violations to warnings, warning threshold is disabled")
77-
<*> mode <| Option(key: "force-exclude", defaultValue: false,
78-
usage: "exclude files in config `excluded` even if their paths are explicitly specified")
79-
<*> mode <| useAlternativeExcludingOption
80-
<*> mode <| useScriptInputFilesOption
81-
<*> mode <| Option(key: "benchmark", defaultValue: false,
82-
usage: "save benchmarks to benchmark_files.txt " +
83-
"and benchmark_rules.txt")
84-
<*> mode <| Option(key: "reporter", defaultValue: "",
85-
usage: "the reporter used to log errors and warnings")
86-
<*> mode <| quietOption(action: "linting")
87-
<*> mode <| Option(key: "enable-all-rules", defaultValue: false,
88-
usage: "run all rules, even opt-in and disabled ones, ignoring `only_rules`")
89-
<*> mode <| Option(key: "autocorrect", defaultValue: false,
90-
usage: "correct violations whenever possible")
91-
<*> mode <| Option(key: "compiler-log-path", defaultValue: "",
92-
usage: "the path of the full xcodebuild log to use when linting AnalyzerRules")
93-
<*> mode <| Option(key: "compile-commands", defaultValue: "",
94-
usage: "the path of a compilation database to use when linting AnalyzerRules")
95-
// This should go last to avoid eating other args
96-
<*> mode <| pathsArgument(action: "analyze")
50+
}
9751
}
9852
}

Source/swiftlint/Commands/AutoCorrect.swift

Lines changed: 0 additions & 91 deletions
This file was deleted.
Lines changed: 19 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -1,30 +1,29 @@
1-
import Commandant
1+
import ArgumentParser
22
import Foundation
33

4-
struct ShowDocsCommand: CommandProtocol {
5-
let verb = "docs"
6-
let function = "Open SwiftLint Docs on web browser"
4+
extension SwiftLint {
5+
struct Docs: ParsableCommand {
6+
static let configuration = CommandConfiguration(
7+
abstract: "Open SwiftLint documentation website in the default web browser"
8+
)
79

8-
func run(_ options: NoOptions<CommandantError<()>>) -> Result<(), CommandantError<()>> {
9-
let url = URL(string: "https://realm.github.io/SwiftLint")!
10-
open(url)
11-
return .success(())
10+
mutating func run() throws {
11+
open(URL(string: "https://realm.github.io/SwiftLint")!)
12+
}
1213
}
1314
}
1415

15-
private extension ShowDocsCommand {
16-
func open(_ url: URL) {
17-
let process = Process()
16+
private func open(_ url: URL) {
17+
let process = Process()
1818
#if os(Linux)
19-
process.executableURL = URL(fileURLWithPath: "/usr/bin/env")
20-
let command = "xdg-open"
21-
process.arguments = [command, url.absoluteString]
22-
try? process.run()
19+
process.executableURL = URL(fileURLWithPath: "/usr/bin/env")
20+
let command = "xdg-open"
21+
process.arguments = [command, url.absoluteString]
22+
try? process.run()
2323
#else
24-
process.launchPath = "/usr/bin/env"
25-
let command = "open"
26-
process.arguments = [command, url.absoluteString]
27-
process.launch()
24+
process.launchPath = "/usr/bin/env"
25+
let command = "open"
26+
process.arguments = [command, url.absoluteString]
27+
process.launch()
2828
#endif
29-
}
3029
}

0 commit comments

Comments
 (0)