finish json reporter
This commit is contained in:
parent
e8b6e331e9
commit
0826b7ecba
|
@ -163,7 +163,9 @@ Rule inclusion:
|
||||||
Reporter inclusion:
|
Reporter inclusion:
|
||||||
|
|
||||||
* xcode: Warnings displayed in the IDE.
|
* xcode: Warnings displayed in the IDE.
|
||||||
* json: Generate a warnings json file.
|
* json: Generate a json file named `pecker.result.json`, you can set path by `output_file`, if unspecified, the default is current project directory path.
|
||||||
|
|
||||||
|

|
||||||
|
|
||||||
```yaml
|
```yaml
|
||||||
reporter: "xcode"
|
reporter: "xcode"
|
||||||
|
@ -184,6 +186,8 @@ blacklist_files: # files to ignore during detecting, only need to add file name,
|
||||||
blacklist_symbols: # symbols to ignore during detecting, contains class, struct, enum, etc.
|
blacklist_symbols: # symbols to ignore during detecting, contains class, struct, enum, etc.
|
||||||
- AppDelegate
|
- AppDelegate
|
||||||
- viewDidLoad
|
- viewDidLoad
|
||||||
|
|
||||||
|
output_file: "/Users/ming/Desktop/PeckerResultDirectory"
|
||||||
```
|
```
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -157,7 +157,8 @@ extension UnusedExample {
|
||||||
报告方式包含:
|
报告方式包含:
|
||||||
|
|
||||||
* xcode: 在Xcode中显示warning。
|
* xcode: 在Xcode中显示warning。
|
||||||
* json: 生成warning的json文件。
|
* json: 生成名为`pecker.result.json`的文件,你可以通过`output_file`来自定义路径,如果没有指定,默认为当前检测项目的文件下的路径。
|
||||||
|

|
||||||
|
|
||||||
```yaml
|
```yaml
|
||||||
reporter: "xcode"
|
reporter: "xcode"
|
||||||
|
@ -178,6 +179,8 @@ blacklist_files: # files to ignore during detecting, only need to add file name,
|
||||||
blacklist_symbols: # symbols to ignore during detecting, contains class, struct, enum, etc.
|
blacklist_symbols: # symbols to ignore during detecting, contains class, struct, enum, etc.
|
||||||
- AppDelegate
|
- AppDelegate
|
||||||
- viewDidLoad
|
- viewDidLoad
|
||||||
|
|
||||||
|
output_file: "/Users/ming/Desktop/PeckerResultDirectory"
|
||||||
```
|
```
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -13,14 +13,14 @@ fileprivate func main(_ arguments: [String]) -> Int32 {
|
||||||
let configuration = try createConfiguration(options: options)
|
let configuration = try createConfiguration(options: options)
|
||||||
let analyzer = try Analyzer(configuration: configuration)
|
let analyzer = try Analyzer(configuration: configuration)
|
||||||
let unusedSources = try analyzer.analyze()
|
let unusedSources = try analyzer.analyze()
|
||||||
configuration.reporter.report(sources: unusedSources)
|
configuration.reporter.report(configuration, sources: unusedSources)
|
||||||
} catch {
|
} catch {
|
||||||
log(error.localizedDescription, level: .error)
|
log(error.localizedDescription, level: .error)
|
||||||
return 1
|
return 1
|
||||||
}
|
}
|
||||||
return 0
|
return 0
|
||||||
case .version:
|
case .version:
|
||||||
print("0.0.7")
|
print("0.0.8")
|
||||||
return 0
|
return 0
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -18,6 +18,8 @@ public struct Configuration {
|
||||||
|
|
||||||
public let blacklistSymbols: [String]
|
public let blacklistSymbols: [String]
|
||||||
|
|
||||||
|
public let outputFile: AbsolutePath
|
||||||
|
|
||||||
/// The project path
|
/// The project path
|
||||||
public let projectPath: AbsolutePath
|
public let projectPath: AbsolutePath
|
||||||
|
|
||||||
|
@ -35,7 +37,8 @@ public struct Configuration {
|
||||||
included: [AbsolutePath],
|
included: [AbsolutePath],
|
||||||
excluded: [AbsolutePath],
|
excluded: [AbsolutePath],
|
||||||
blacklistFiles: [String],
|
blacklistFiles: [String],
|
||||||
blacklistSymbols: [String]) {
|
blacklistSymbols: [String],
|
||||||
|
outputFile: AbsolutePath) {
|
||||||
self.projectPath = projectPath
|
self.projectPath = projectPath
|
||||||
self.indexStorePath = indexStorePath
|
self.indexStorePath = indexStorePath
|
||||||
self.indexDatabasePath = indexDatabasePath ?? NSTemporaryDirectory() + "index_\(getpid())"
|
self.indexDatabasePath = indexDatabasePath ?? NSTemporaryDirectory() + "index_\(getpid())"
|
||||||
|
@ -45,6 +48,7 @@ public struct Configuration {
|
||||||
self.excluded = excluded
|
self.excluded = excluded
|
||||||
self.blacklistFiles = blacklistFiles
|
self.blacklistFiles = blacklistFiles
|
||||||
self.blacklistSymbols = blacklistSymbols
|
self.blacklistSymbols = blacklistSymbols
|
||||||
|
self.outputFile = outputFile
|
||||||
}
|
}
|
||||||
|
|
||||||
public init(projectPath: AbsolutePath, indexStorePath: String = "", indexDatabasePath: String? = nil) {
|
public init(projectPath: AbsolutePath, indexStorePath: String = "", indexDatabasePath: String? = nil) {
|
||||||
|
@ -61,6 +65,7 @@ public struct Configuration {
|
||||||
|
|
||||||
let reporter = ReporterFactory.make(yamlConfiguration?.reporter)
|
let reporter = ReporterFactory.make(yamlConfiguration?.reporter)
|
||||||
let rules = RuleFactory.make(yamlConfiguration?.disabledRules)
|
let rules = RuleFactory.make(yamlConfiguration?.disabledRules)
|
||||||
|
let outputFilePath = AbsolutePath(yamlConfiguration?.outputFile ?? projectPath.asURL.path).appending(component: "pecker.result.json")
|
||||||
self.init(projectPath: projectPath,
|
self.init(projectPath: projectPath,
|
||||||
indexStorePath: indexStorePath,
|
indexStorePath: indexStorePath,
|
||||||
indexDatabasePath: indexDatabasePath,
|
indexDatabasePath: indexDatabasePath,
|
||||||
|
@ -69,6 +74,7 @@ public struct Configuration {
|
||||||
included: (yamlConfiguration?.included ?? [""]).map{ projectPath.appending(component: $0)},
|
included: (yamlConfiguration?.included ?? [""]).map{ projectPath.appending(component: $0)},
|
||||||
excluded: (yamlConfiguration?.excluded ?? []).map{ projectPath.appending(component: $0)} ,
|
excluded: (yamlConfiguration?.excluded ?? []).map{ projectPath.appending(component: $0)} ,
|
||||||
blacklistFiles: yamlConfiguration?.blacklistFiles ?? [],
|
blacklistFiles: yamlConfiguration?.blacklistFiles ?? [],
|
||||||
blacklistSymbols: yamlConfiguration?.blacklistSymbols ?? [])
|
blacklistSymbols: yamlConfiguration?.blacklistSymbols ?? [],
|
||||||
|
outputFile: outputFilePath)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -20,6 +20,9 @@ public struct YamlConfiguration: Decodable {
|
||||||
/// Acts as a blacklist, the symbols specified in this list will ignore
|
/// Acts as a blacklist, the symbols specified in this list will ignore
|
||||||
public let blacklistSymbols: [String]?
|
public let blacklistSymbols: [String]?
|
||||||
|
|
||||||
|
/// The path of the output json file
|
||||||
|
public let outputFile: String?
|
||||||
|
|
||||||
enum CodingKeys: String, CodingKey {
|
enum CodingKeys: String, CodingKey {
|
||||||
case disabledRules = "disabled_rules"
|
case disabledRules = "disabled_rules"
|
||||||
case reporter
|
case reporter
|
||||||
|
@ -27,6 +30,7 @@ public struct YamlConfiguration: Decodable {
|
||||||
case excluded
|
case excluded
|
||||||
case blacklistFiles = "blacklist_files"
|
case blacklistFiles = "blacklist_files"
|
||||||
case blacklistSymbols = "blacklist_symbols"
|
case blacklistSymbols = "blacklist_symbols"
|
||||||
|
case outputFile = "output_file"
|
||||||
}
|
}
|
||||||
|
|
||||||
public init(from decoder: Decoder) throws {
|
public init(from decoder: Decoder) throws {
|
||||||
|
@ -37,6 +41,7 @@ public struct YamlConfiguration: Decodable {
|
||||||
self.excluded = try container.decodeIfPresent([String].self, forKey: .excluded)
|
self.excluded = try container.decodeIfPresent([String].self, forKey: .excluded)
|
||||||
self.blacklistFiles = try container.decodeIfPresent([String].self, forKey: .blacklistFiles)
|
self.blacklistFiles = try container.decodeIfPresent([String].self, forKey: .blacklistFiles)
|
||||||
self.blacklistSymbols = try container.decodeIfPresent([String].self, forKey: .blacklistSymbols)
|
self.blacklistSymbols = try container.decodeIfPresent([String].self, forKey: .blacklistSymbols)
|
||||||
|
self.outputFile = try container.decodeIfPresent(String.self, forKey: .outputFile)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -49,6 +54,7 @@ extension YamlConfiguration: Hashable {
|
||||||
hasher.combine(excluded)
|
hasher.combine(excluded)
|
||||||
hasher.combine(blacklistFiles)
|
hasher.combine(blacklistFiles)
|
||||||
hasher.combine(blacklistSymbols)
|
hasher.combine(blacklistSymbols)
|
||||||
|
hasher.combine(outputFile)
|
||||||
}
|
}
|
||||||
|
|
||||||
public static func == (lhs: YamlConfiguration, rhs: YamlConfiguration) -> Bool {
|
public static func == (lhs: YamlConfiguration, rhs: YamlConfiguration) -> Bool {
|
||||||
|
@ -57,6 +63,7 @@ extension YamlConfiguration: Hashable {
|
||||||
(lhs.included == rhs.included) &&
|
(lhs.included == rhs.included) &&
|
||||||
(lhs.excluded == rhs.excluded) &&
|
(lhs.excluded == rhs.excluded) &&
|
||||||
(lhs.blacklistFiles == rhs.blacklistFiles) &&
|
(lhs.blacklistFiles == rhs.blacklistFiles) &&
|
||||||
(lhs.blacklistSymbols == rhs.blacklistSymbols)
|
(lhs.blacklistSymbols == rhs.blacklistSymbols) &&
|
||||||
|
(lhs.outputFile == rhs.outputFile)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -2,8 +2,23 @@ import Foundation
|
||||||
|
|
||||||
public struct JSONReporter: Reporter {
|
public struct JSONReporter: Reporter {
|
||||||
|
|
||||||
// TODO: -
|
public func report(_ configuration: Configuration, sources: [SourceDetail]) {
|
||||||
public func report(sources: [SourceDetail]) {
|
var entries = sources.map { $0.location.description }
|
||||||
|
let count = entries.count
|
||||||
|
entries.insert("count: \(count)", at: 0)
|
||||||
|
do {
|
||||||
|
try writeEntries(entries: entries, to: configuration.outputFile.asURL)
|
||||||
|
} catch {
|
||||||
|
log("Output json file failed: \(error.localizedDescription)", level: .warning)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private func writeEntries(entries: [String], to path: URL) throws {
|
||||||
|
do {
|
||||||
|
let encoder = JSONEncoder()
|
||||||
|
encoder.outputFormatting = .prettyPrinted
|
||||||
|
let data = try encoder.encode(entries)
|
||||||
|
try data.write(to: path, options: .atomic)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -2,5 +2,5 @@ import Foundation
|
||||||
|
|
||||||
public protocol Reporter {
|
public protocol Reporter {
|
||||||
|
|
||||||
func report(sources: [SourceDetail])
|
func report(_ configuration: Configuration, sources: [SourceDetail])
|
||||||
}
|
}
|
||||||
|
|
|
@ -3,7 +3,7 @@ import SwiftSyntax
|
||||||
|
|
||||||
public struct XcodeReporter: Reporter {
|
public struct XcodeReporter: Reporter {
|
||||||
|
|
||||||
public func report(sources: [SourceDetail]) {
|
public func report(_ configuration: Configuration, sources: [SourceDetail]) {
|
||||||
let diagnosticEngine = makeDiagnosticEngine()
|
let diagnosticEngine = makeDiagnosticEngine()
|
||||||
for source in sources {
|
for source in sources {
|
||||||
let message = Diagnostic.Message(.warning, "Pecker: \(source.sourceKind) \(source.name) was never used; consider removing it")
|
let message = Diagnostic.Message(.warning, "Pecker: \(source.sourceKind) \(source.name) was never used; consider removing it")
|
||||||
|
|
Loading…
Reference in New Issue