We use the Swift.org API Design Guidelines as the base. We refer to the raywenderlich.com Swift Style Guide for guides that are not described here.
We use SwiftLint to enforce as many of our rules as we can. It is integrated in the build process so you should see any violations in Xcode.
You can the lint check manually by executing bundle exec rake lint
in the command line. You can also run bundle exec rake lint:autocorrect
to automatically fix any lint issues.
The SwiftLint rules are automatically enforced by Hound when pull requests are submitted.
Closing braces should always be placed on a new line regardless of the number of enclosed statements.
Preferred:
guard condition else {
return
}
if condition {
} else {
}
Not Preferred:
guard condition else { return }
if condition { } else { }
As an exception to this rule, guarding for a safe self
is allowed to be expressed in one line.
guard let self = self else { return }
Parentheses around conditionals are not required and should be omitted.
Preferred:
if name == "Hello" {
print("World")
}
Not Preferred:
if (name == "Hello") {
print("World")
}
Avoid using as!
to force a downcast, or !
to force unwrap. Prefer using as?
to attempt the cast, then deal with the failure case explicitly.
Preferred:
func process(someObject: Any) {
guard let element = someObject as? Element else {
// Optional error handling goes here
return
}
process(element)
}
Not Preferred:
func process(someObject: Any) {
process(someObject as! Element)
}
Avoid using try?
when a function may throw an error, as it would fail silently. We can use a do-catch
block instead to handle and log the error as needed.
Preferred:
do {
let fetchResults = try resultsController.performFetch()
} catch {
DDLogError("Unable to fetch results controller: \(error)")
}
Not Preferred:
let fetchResults = try? resultsController.performFetch()