Skip to content

Commit

Permalink
Support for multiple paths
Browse files Browse the repository at this point in the history
  • Loading branch information
benasher44 committed May 27, 2017
1 parent 6c0cf07 commit 454eff1
Show file tree
Hide file tree
Showing 5 changed files with 45 additions and 21 deletions.
4 changes: 4 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -430,6 +430,10 @@
[Aaron McTavish](https://github.com/aamctustwo)
[#1198](https://github.com/realm/SwiftLint/issues/1198)

* Support for passing multiple path arguments.
[Ben Asher](https://github.com/benasher44)
[#810](https://github.com/realm/SwiftLint/issues/810)

##### Bug Fixes

* Fix false positives on `shorthand_operator` rule.
Expand Down
14 changes: 8 additions & 6 deletions Source/swiftlint/Commands/AutoCorrectCommand.swift
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@ struct AutoCorrectCommand: CommandProtocol {
let function = "Automatically correct warnings and errors"

func run(_ options: AutoCorrectOptions) -> Result<(), CommandantError<()>> {
return Configuration(options: options).visitLintableFiles(path: options.path, action: "Correcting",
return Configuration(options: options).visitLintableFiles(paths: options.paths, action: "Correcting",
quiet: options.quiet, useScriptInputFiles: options.useScriptInputFiles) { linter in
let corrections = linter.correct()
if !corrections.isEmpty && !options.quiet {
Expand All @@ -39,23 +39,25 @@ struct AutoCorrectCommand: CommandProtocol {
}

struct AutoCorrectOptions: OptionsProtocol {
let path: String
let paths: [String]
let configurationFile: String
let useScriptInputFiles: Bool
let quiet: Bool
let format: Bool

// swiftlint:disable line_length
static func create(_ path: String) -> (_ configurationFile: String) -> (_ useScriptInputFiles: Bool) -> (_ quiet: Bool) -> (_ format: Bool) -> AutoCorrectOptions {
return { configurationFile in { useScriptInputFiles in { quiet in { format in
self.init(path: path, configurationFile: configurationFile, useScriptInputFiles: useScriptInputFiles, quiet: quiet, format: format)
}}}}
static func create(_ path: String) -> (_ paths: [String]) -> (_ configurationFile: String) -> (_ useScriptInputFiles: Bool) -> (_ quiet: Bool) -> (_ format: Bool) -> AutoCorrectOptions {
return { paths in { configurationFile in { useScriptInputFiles in { quiet in { format in
let allPaths = Set([path] + paths)
return self.init(paths: Array(allPaths), configurationFile: configurationFile, useScriptInputFiles: useScriptInputFiles, quiet: quiet, format: format)
}}}}}
}

static func evaluate(_ mode: CommandMode) -> Result<AutoCorrectOptions, CommandantError<CommandantError<()>>> {
// swiftlint:enable line_length
return create
<*> mode <| pathOption(action: "correct")
<*> mode <| pathsArgument(action: "correct")
<*> mode <| configOption
<*> mode <| useScriptInputFilesOption
<*> mode <| quietOption(action: "correcting")
Expand Down
12 changes: 7 additions & 5 deletions Source/swiftlint/Commands/LintCommand.swift
Original file line number Diff line number Diff line change
Expand Up @@ -124,7 +124,7 @@ struct LintCommand: CommandProtocol {
}

struct LintOptions: OptionsProtocol {
let path: String
let paths: [String]
let useSTDIN: Bool
let configurationFile: String
let strict: Bool
Expand All @@ -138,16 +138,18 @@ struct LintOptions: OptionsProtocol {
let enableAllRules: Bool

// swiftlint:disable line_length
static func create(_ path: String) -> (_ useSTDIN: Bool) -> (_ configurationFile: String) -> (_ strict: Bool) -> (_ lenient: Bool) -> (_ useScriptInputFiles: Bool) -> (_ benchmark: Bool) -> (_ reporter: String) -> (_ quiet: Bool) -> (_ cachePath: String) -> (_ ignoreCache: Bool) -> (_ enableAllRules: Bool) -> LintOptions {
return { useSTDIN in { configurationFile in { strict in { lenient in { useScriptInputFiles in { benchmark in { reporter in { quiet in { cachePath in { ignoreCache in { enableAllRules in
self.init(path: path, useSTDIN: useSTDIN, configurationFile: configurationFile, strict: strict, lenient: lenient, useScriptInputFiles: useScriptInputFiles, benchmark: benchmark, reporter: reporter, quiet: quiet, cachePath: cachePath, ignoreCache: ignoreCache, enableAllRules: enableAllRules)
}}}}}}}}}}}
static func create(_ path: String) -> (_ paths: [String]) -> (_ useSTDIN: Bool) -> (_ configurationFile: String) -> (_ strict: Bool) -> (_ lenient: Bool) -> (_ useScriptInputFiles: Bool) -> (_ benchmark: Bool) -> (_ reporter: String) -> (_ quiet: Bool) -> (_ cachePath: String) -> (_ ignoreCache: Bool) -> (_ enableAllRules: Bool) -> LintOptions {
return { paths in { useSTDIN in { configurationFile in { strict in { lenient in { useScriptInputFiles in { benchmark in { reporter in { quiet in { cachePath in { ignoreCache in { enableAllRules in
let allPaths = Set([path] + paths)
return self.init(paths: Array(allPaths), useSTDIN: useSTDIN, configurationFile: configurationFile, strict: strict, lenient: lenient, useScriptInputFiles: useScriptInputFiles, benchmark: benchmark, reporter: reporter, quiet: quiet, cachePath: cachePath, ignoreCache: ignoreCache, enableAllRules: enableAllRules)
}}}}}}}}}}}}
}

static func evaluate(_ mode: CommandMode) -> Result<LintOptions, CommandantError<CommandantError<()>>> {
// swiftlint:enable line_length
return create
<*> mode <| pathOption(action: "lint")
<*> mode <| pathsArgument(action: "lint")
<*> mode <| Option(key: "use-stdin", defaultValue: false,
usage: "lint standard input")
<*> mode <| configOption
Expand Down
31 changes: 21 additions & 10 deletions Source/swiftlint/Extensions/Configuration+CommandLine.swift
Original file line number Diff line number Diff line change
Expand Up @@ -56,15 +56,15 @@ private func autoreleasepool(block: () -> Void) { block() }

extension Configuration {

func visitLintableFiles(path: String, action: String, useSTDIN: Bool = false,
func visitLintableFiles(paths: [String], action: String, useSTDIN: Bool = false,
quiet: Bool = false, useScriptInputFiles: Bool,
cache: LinterCache? = nil, parallel: Bool = false,
visitorBlock: @escaping (Linter) -> Void) -> Result<[File], CommandantError<()>> {
return getFiles(path: path, action: action, useSTDIN: useSTDIN, quiet: quiet,
return getFiles(paths: paths, action: action, useSTDIN: useSTDIN, quiet: quiet,
useScriptInputFiles: useScriptInputFiles)
.flatMap { files -> Result<[File], CommandantError<()>> in
if files.isEmpty {
let errorMessage = "No lintable files found at path '\(path)'"
let errorMessage = "No lintable files found at paths: '\(paths.joined(separator: ", "))'"
return .failure(.usageError(description: errorMessage))
}
return .success(files)
Expand Down Expand Up @@ -100,7 +100,7 @@ extension Configuration {
}
}

fileprivate func getFiles(path: String, action: String, useSTDIN: Bool, quiet: Bool,
fileprivate func getFiles(paths: [String], action: String, useSTDIN: Bool, quiet: Bool,
useScriptInputFiles: Bool) -> Result<[File], CommandantError<()>> {
if useSTDIN {
let stdinData = FileHandle.standardInput.readDataToEndOfFile()
Expand All @@ -112,30 +112,41 @@ extension Configuration {
return scriptInputFiles()
}
if !quiet {
let message = "\(action) Swift files " + (path.isEmpty ? "in current working directory" : "at path \(path)")
let filesInfo = paths.isEmpty ? "in current working directory" : "at paths \(paths.joined(separator: ", "))"
let message = "\(action) Swift files \(filesInfo)"
queuedPrintError(message)
}
return .success(lintableFiles(inPath: path))
return .success(paths.flatMap(lintableFiles(inPath:)))
}

private static func rootPath(from paths: [String]) -> String? {
// We don't know the root when more than one path is passed (i.e. not useful if the root of 2 paths is ~)
return paths.count == 1 ? paths.first : nil
}

// MARK: Lint Command

init(options: LintOptions) {
let cachePath = options.cachePath.isEmpty ? nil : options.cachePath
self.init(commandLinePath: options.configurationFile, rootPath: options.path, quiet: options.quiet,
enableAllRules: options.enableAllRules, cachePath: cachePath)
self.init(commandLinePath: options.configurationFile,
rootPath: type(of: self).rootPath(from: options.paths),
quiet: options.quiet,
enableAllRules: options.enableAllRules,
cachePath: cachePath)
}

func visitLintableFiles(options: LintOptions, cache: LinterCache? = nil,
visitorBlock: @escaping (Linter) -> Void) -> Result<[File], CommandantError<()>> {
return visitLintableFiles(path: options.path, action: "Linting", useSTDIN: options.useSTDIN,
return visitLintableFiles(paths: options.paths, action: "Linting", useSTDIN: options.useSTDIN,
quiet: options.quiet, useScriptInputFiles: options.useScriptInputFiles,
cache: cache, parallel: true, visitorBlock: visitorBlock)
}

// MARK: AutoCorrect Command

init(options: AutoCorrectOptions) {
self.init(commandLinePath: options.configurationFile, rootPath: options.path, quiet: options.quiet)
self.init(commandLinePath: options.configurationFile,
rootPath: type(of: self).rootPath(from: options.paths),
quiet: options.quiet)
}
}
5 changes: 5 additions & 0 deletions Source/swiftlint/Helpers/CommonOptions.swift
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,11 @@ func pathOption(action: String) -> Option<String> {
usage: "the path to the file or directory to \(action)")
}

func pathsArgument(action: String) -> Argument<[String]> {
return Argument(defaultValue: [""],
usage: "list of paths to the files or directories to \(action)")
}

let configOption = Option(key: "config",
defaultValue: Configuration.fileName,
usage: "the path to SwiftLint's configuration file")
Expand Down

0 comments on commit 454eff1

Please sign in to comment.