Skip to content

Commit

Permalink
Add documentation comments to all public declarations (realm#3027)
Browse files Browse the repository at this point in the history
  • Loading branch information
jpsim authored Jan 8, 2020
1 parent df6cf17 commit 37167a8
Show file tree
Hide file tree
Showing 57 changed files with 693 additions and 79 deletions.
10 changes: 10 additions & 0 deletions .jazzy.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -18,3 +18,13 @@ custom_categories:
- name: Rules
children:
- Rule Directory
- name: Reporters
children:
- CSVReporter
- CheckstyleReporter
- EmojiReporter
- GitHubActionsLoggingReporter
- HTMLReporter
- JSONReporter
- JUnitReporter
- MarkdownReporter
1 change: 1 addition & 0 deletions .sourcery/MasterRuleList.stencil
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
/// The rule list containing all available rules built into SwiftLint.
public let masterRuleList = RuleList(rules: [
{% for rule in types.structs where rule.name|hasSuffix:"Rule" or rule.name|hasSuffix:"Rules" %} {{ rule.name }}.self{% if not forloop.last %},{% endif %}
{% endfor %}])
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
/// User-facing documentation for a SwiftLint rule.
public struct RuleDocumentation {
struct RuleDocumentation {
private let ruleType: Rule.Type

/// Creates a RuleDocumentation instance from a Rule type.
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,8 @@ extension Configuration {
return cachedConfigurationsByPath[path]
}

/// Returns a copy of the current `Configuration` with its `computedCacheDescription` property set to the value of
/// `cacheDescription`, which is expensive to compute.
public func withPrecomputedCacheDescription() -> Configuration {
var result = self
result.computedCacheDescription = result.cacheDescription
Expand Down
Original file line number Diff line number Diff line change
@@ -1,10 +1,17 @@
public extension Configuration {
/// The style of indentation used in a Swift project.
enum IndentationStyle: Equatable {
/// Swift source code should be indented using tabs.
case tabs
/// Swift source code should be indented using spaces with `count` spaces per indentation level.
case spaces(count: Int)

/// The default indentation style if none is explicitly provided.
public static var `default` = spaces(count: 4)

/// Creates an indentation style based on an untyped configuration value.
///
/// - parameter object: The configuration value.
internal init?(_ object: Any?) {
switch object {
case let value as Int: self = .spaces(count: value)
Expand Down
Original file line number Diff line number Diff line change
@@ -1,11 +1,26 @@
import Foundation

extension Configuration {
/// Returns the files that can be linted by SwiftLint in the specified parent path.
///
/// - parameter path: The parent path in which to search for lintable files. Can be a directory or a file.
/// - parameter forceExclude: Whether or not excludes defined in this configuration should be applied even if `path`
/// is an exact match.
///
/// - returns: Files to lint.
public func lintableFiles(inPath path: String, forceExclude: Bool) -> [SwiftLintFile] {
return lintablePaths(inPath: path, forceExclude: forceExclude)
.compactMap(SwiftLintFile.init(pathDeferringReading:))
}

/// Returns the paths for files that can be linted by SwiftLint in the specified parent path.
///
/// - parameter path: The parent path in which to search for lintable files. Can be a directory or a file.
/// - parameter forceExclude: Whether or not excludes defined in this configuration should be applied even if `path`
/// is an exact match.
/// - parameter fileManager: The lintable file manager to use to search for lintable files.
///
/// - returns: Paths for files to lint.
internal func lintablePaths(inPath path: String, forceExclude: Bool,
fileManager: LintableFileManager = FileManager.default) -> [String] {
// If path is a file and we're not forcing excludes, skip filtering with excluded/included paths
Expand All @@ -18,9 +33,13 @@ extension Configuration {
}
return filterExcludedPaths(fileManager: fileManager, in: pathsForPath, includedPaths)
}
}

extension Configuration {
/// Returns an array of file paths after removing the excluded paths as defined by this configuration.
///
/// - parameter fileManager: The lintable file manager to use to expand the excluded paths into all matching paths.
/// - parameter paths: The input paths to filter.
///
/// - returns: The input paths after removing the excluded paths.
public func filterExcludedPaths(fileManager: LintableFileManager = FileManager.default,
in paths: [String]...) -> [String] {
let allPaths = paths.flatMap { $0 }
Expand All @@ -36,6 +55,12 @@ extension Configuration {
return result.map { $0 as! String }
}

/// Returns the file paths that are excluded by this configuration after expanding them using the specified file
/// manager.
///
/// - parameter fileManager: The file manager to get child paths in a given parent location.
///
/// - returns: The expanded excluded file paths.
internal func excludedPaths(fileManager: LintableFileManager) -> [String] {
return excluded
.flatMap(Glob.resolveGlob)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,12 @@ import Foundation
import SourceKittenFramework

extension Configuration {
/// Returns a new configuration that applies to the specified file by merging the current configuration with any
/// child configurations in the directory inheritance graph present until the level of the specified file.
///
/// - parameter file: The file for which to obtain a configuration value.
///
/// - returns: A new configuration.
public func configuration(for file: SwiftLintFile) -> Configuration {
if let containingDir = file.path?.bridge().deletingLastPathComponent {
return configuration(forPath: containingDir)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -52,6 +52,14 @@ extension Configuration {
return .default
}

/// Creates a Configuration value based on the specified parameters.
///
/// - parameter dict: The untyped dictionary to serve as the input for this typed configuration.
/// Typically generated from a YAML-formatted file.
/// - parameter ruleList: The list of rules to be available to this configuration.
/// - parameter enableAllRules: Whether all rules from `ruleList` should be enabled, regardless of the
/// settings in `dict`.
/// - parameter cachePath: The location of the persisted cache on disk.
public init?(dict: [String: Any], ruleList: RuleList = masterRuleList, enableAllRules: Bool = false,
cachePath: String? = nil, customRulesIdentifiers: [String] = []) {
// Use either new 'opt_in_rules' or deprecated 'enabled_rules' for now.
Expand Down
14 changes: 14 additions & 0 deletions Source/SwiftLintFramework/Extensions/Dictionary+SwiftLint.swift
Original file line number Diff line number Diff line change
@@ -1,16 +1,27 @@
import Foundation
import SourceKittenFramework

/// A collection of keys and values as parsed out of SourceKit, with many conveniences for accessing SwiftLint-specific
/// values.
public struct SourceKittenDictionary {
/// The underlying SourceKitten dictionary.
public let value: [String: SourceKitRepresentable]
/// The cached substructure for this dictionary. Empty if there is no substructure.
public let substructure: [SourceKittenDictionary]

/// The kind of Swift expression represented by this dictionary, if it is an expression.
public let expressionKind: SwiftExpressionKind?
/// The kind of Swift declaration represented by this dictionary, if it is a declaration.
public let declarationKind: SwiftDeclarationKind?
/// The kind of Swift statement represented by this dictionary, if it is a statement.
public let statementKind: StatementKind?

/// The accessibility level for this dictionary, if it is a declaration.
public let accessibility: AccessControlLevel?

/// Creates a SourceKitten dictionary given a `Dictionary<String, SourceKitRepresentable>` input.
///
/// - parameter value: The input dictionary/
init(_ value: [String: SourceKitRepresentable]) {
self.value = value

Expand Down Expand Up @@ -91,15 +102,18 @@ public struct SourceKittenDictionary {
return (value["key.doclength"] as? Int64).flatMap({ Int($0) })
}

/// The attribute for this dictionary, as returned by SourceKit.
var attribute: String? {
return value["key.attribute"] as? String
}

/// The `SwiftDeclarationAttributeKind` values associated with this dictionary.
var enclosedSwiftAttributes: [SwiftDeclarationAttributeKind] {
return swiftAttributes.compactMap { $0.attribute }
.compactMap(SwiftDeclarationAttributeKind.init(rawValue:))
}

/// The fully preserved SourceKitten dictionaries for all the attributes associated with this dictionary.
var swiftAttributes: [SourceKittenDictionary] {
let array = value["key.attributes"] as? [SourceKitRepresentable] ?? []
let dictionaries = array.compactMap { $0 as? [String: SourceKitRepresentable] }
Expand Down
20 changes: 18 additions & 2 deletions Source/SwiftLintFramework/Extensions/FileManager+SwiftLint.swift
Original file line number Diff line number Diff line change
@@ -1,8 +1,24 @@
import Foundation

/// An interface for enumerating files that can be linted by SwiftLint.
public protocol LintableFileManager {
func filesToLint(inPath: String, rootDirectory: String?) -> [String]
func modificationDate(forFileAtPath: String) -> Date?
/// Returns all files that can be linted in the specified path. If the path is relative, it will be appended to the
/// specified root path, or currentt working directory if no root directory is specified.
///
/// - parameter path: The path in which lintable files should be found.
/// - parameter rootDirectory: The parent directory for the specified path. If none is provided, the current working
/// directory will be used.
///
/// - returns: Files to lint.
func filesToLint(inPath path: String, rootDirectory: String?) -> [String]

/// Returns the date when the file at the specified path was last modified. Returns `nil` if the file cannot be
/// found or its last modification date cannot be determined.
///
/// - parameter path: The file whose modification date should be determined.
///
/// - returns: A date, if one was determined.
func modificationDate(forFileAtPath path: String) -> Date?
}

extension FileManager: LintableFileManager {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,17 +5,12 @@ private var regexCache = [RegexCacheKey: NSRegularExpression]()
private let regexCacheLock = NSLock()

private struct RegexCacheKey: Hashable {
// Disable unused private declaration rule here because even though we don't use these properties
// directly, we rely on them for their hashable and equatable behavior.
// swiftlint:disable unused_declaration
let pattern: String
let options: NSRegularExpression.Options
// swiftlint:enable unused_declaration
}

extension NSRegularExpression.Options: Hashable {
public func hash(into hasher: inout Hasher) {
hasher.combine(rawValue)
func hash(into hasher: inout Hasher) {
hasher.combine(pattern)
hasher.combine(options.rawValue)
}
}

Expand Down
6 changes: 3 additions & 3 deletions Source/SwiftLintFramework/Extensions/QueuedPrint.swift
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@ private let outputQueue: DispatchQueue = {
}()

/**
A thread-safe version of Swift's standard print().
A thread-safe version of Swift's standard `print()`.

- parameter object: Object to print.
*/
Expand All @@ -29,7 +29,7 @@ public func queuedPrint<T>(_ object: T) {
}

/**
A thread-safe, newline-terminated version of fputs(..., stderr).
A thread-safe, newline-terminated version of `fputs(..., stderr)`.

- parameter string: String to print.
*/
Expand All @@ -41,7 +41,7 @@ public func queuedPrintError(_ string: String) {
}

/**
A thread-safe, newline-terminated version of fatalError that doesn't leak
A thread-safe, newline-terminated version of `fatalError(...)` that doesn't leak
the source path from the compiled binary.
*/
public func queuedFatalError(_ string: String, file: StaticString = #file, line: UInt = #line) -> Never {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -74,6 +74,7 @@ extension String {
return NSRange(location: 0, length: utf16.count)
}

/// Returns a new string, converting the path to a canonical absolute path.
public func absolutePathStandardized() -> String {
return bridge().absolutePathRepresentation().bridge().standardizingPath
}
Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
import SourceKittenFramework

public extension SwiftDeclarationAttributeKind {
extension SwiftDeclarationAttributeKind {
enum ModifierGroup: String, CustomDebugStringConvertible {
case `override`
case acl
Expand Down Expand Up @@ -85,7 +85,7 @@ public extension SwiftDeclarationAttributeKind {
}
}

public var debugDescription: String {
var debugDescription: String {
return self.rawValue
}
}
Expand Down
Original file line number Diff line number Diff line change
@@ -1,9 +1,17 @@
/// The kind of expression for a contiguous set of Swift source tokens.
public enum SwiftExpressionKind: String {
/// A call to a named function or closure.
case call = "source.lang.swift.expr.call"
/// An argument value for a function or closure.
case argument = "source.lang.swift.expr.argument"
/// An Array expression.
case array = "source.lang.swift.expr.array"
/// A Dictionary expression.
case dictionary = "source.lang.swift.expr.dictionary"
/// An object literal expression. https://developer.apple.com/swift/blog/?id=33
case objectLiteral = "source.lang.swift.expr.object_literal"
/// A closure expression. https://docs.swift.org/swift-book/LanguageGuide/Closures.html
case closure = "source.lang.swift.expr.closure"
/// A tuple expression. https://docs.swift.org/swift-book/ReferenceManual/Types.html#ID448
case tuple = "source.lang.swift.expr.tuple"
}
Original file line number Diff line number Diff line change
Expand Up @@ -180,6 +180,7 @@ extension SwiftLintFile {
return syntaxKindsByLines
}

/// Invalidates all cached data for this file.
public func invalidateCache() {
responseCache.invalidate(self)
assertHandlerCache.invalidate(self)
Expand Down
12 changes: 6 additions & 6 deletions Source/SwiftLintFramework/Helpers/RegexHelpers.swift
Original file line number Diff line number Diff line change
@@ -1,19 +1,19 @@
struct RegexHelpers {
// A single variable
/// A single variable
static let varName = "[a-zA-Z_][a-zA-Z0-9_]+"

// A single variable in a group (capturable)
/// A single variable in a group (capturable)
static let varNameGroup = "\\s*(\(varName))\\s*"

// Two variables (capturables)
/// Two variables (capturables)
static let twoVars = "\(varNameGroup),\(varNameGroup)"

// A number
/// A number
static let number = "[\\-0-9\\.]+"

// A variable or a number (capturable)
/// A variable or a number (capturable)
static let variableOrNumber = "\\s*(\(varName)|\(number))\\s*"

// Two 'variable or number'
/// Two 'variable or number'
static let twoVariableOrNumber = "\(variableOrNumber),\(variableOrNumber)"
}
16 changes: 15 additions & 1 deletion Source/SwiftLintFramework/Models/AccessControlLevel.swift
Original file line number Diff line number Diff line change
@@ -1,10 +1,21 @@
/// The accessibility of a Swift source declaration.
///
/// - SeeAlso: https://github.com/apple/swift/blob/master/docs/AccessControl.rst
public enum AccessControlLevel: String, CustomStringConvertible {
/// Accessible by the declaration's immediate lexical scope.
case `private` = "source.lang.swift.accessibility.private"
/// Accessible by the declaration's same file.
case `fileprivate` = "source.lang.swift.accessibility.fileprivate"
/// Accessible by the declaration's same module, or modules importing it with the `@testable` attribute.
case `internal` = "source.lang.swift.accessibility.internal"
/// Accessible by the declaration's same program.
case `public` = "source.lang.swift.accessibility.public"
/// Accessible and customizable (via subclassing or overrides) by the declaration's same program.
case `open` = "source.lang.swift.accessibility.open"

/// Initializes an access control level by its Swift source keyword value.
///
/// - parameter value: The value used to describe this level in Swift source code.
internal init?(description value: String) {
switch value {
case "private": self = .private
Expand All @@ -16,7 +27,10 @@ public enum AccessControlLevel: String, CustomStringConvertible {
}
}

init?(identifier value: String) {
/// Initializes an access control level by its SourceKit unique identifier.
///
/// - parameter value: The value used by SourceKit to refer to this access control level.
internal init?(identifier value: String) {
self.init(rawValue: value)
}

Expand Down
Loading

0 comments on commit 37167a8

Please sign in to comment.