Skip to content

kishikawakatsumi/swiftfmt

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

33 Commits
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

swiftfmt

Build Status

A tool for formatting Swift code according to style guidelines.

Live Demo

https://swiftfmt.kishikawakatsumi.com/

A Work In Progress

swiftfmt is still in active development.

Requirements

Swiftfmt requires Swift trunk toolchains.

Installation

Download and install the latest trunk Swift development toolchain.

git clone https://github.com/kishikawakatsumi/swiftfmt
cd swiftfmt
~/Library/Developer/Toolchains/swift-latest.xctoolchain/usr/bin/swift package update
~/Library/Developer/Toolchains/swift-latest.xctoolchain/usr/bin/swift build -c release

Copy the file (.build/release/swiftfmt) to your binary location.

Getting Started

swiftfmt [file or directory]

Usage

swiftfmt .

Configurations

Tabs and Indents

Use tab character

git clone https://github.com/kishikawakatsumi/swiftfmt
 class Shape {
-    var numberOfSides = 0
-    func simpleDescription() -> String {
-        return "A shape with \(numberOfSides) sides."
-    }
+       var numberOfSides = 0
+
+       func simpleDescription() -> String {
+               return "A shape with \(numberOfSides) sides."
+       }
 }

Indent

"indent" : 2

 class Shape {
-    var numberOfSides = 0
-    func simpleDescription() -> String {
-        return "A shape with \(numberOfSides) sides."
-    }
+  var numberOfSides = 0
+
+  func simpleDescription() -> String {
+    return "A shape with \(numberOfSides) sides."
+  }
 }

Keep indents on empty lines

 class Shape {
     var numberOfSides = 0
+    
     func simpleDescription() -> String {
         return "A shape with \(numberOfSides) sides."
     }

Indent 'case' branches

 let someCharacter: Character = "z"
 switch someCharacter {
-case "a":
-    print("The first letter of the alphabet")
-case "z":
-    print("The last letter of the alphabet")
-default:
-    print("Some other character")
+    case "a":
+        print("The first letter of the alphabet")
+    case "z":
+        print("The last letter of the alphabet")
+    default:
+        print("Some other character")
 }

Spaces

Before Parentheses

Method/function declaration parentheses

 class Counter {
     var count = 0
-    
-    func increment() {
+
+    func increment () {
         count += 1
     }
 
-    func increment(by amount: Int) {
+    func increment (by amount: Int) {
         count += amount
     }
 
-    func reset() {
+    func reset () {
         count = 0
     }
 }

Method/function call parentheses

 struct Point {
     var x = 0.0, y = 0.0
+
     mutating func moveBy(x deltaX: Double, y deltaY: Double) {
-        self = Point(x: x + deltaX, y: y + deltaY)
+        self = Point (x: x + deltaX, y: y + deltaY)
     }
 }

'if' parentheses

-if(temperatureInFahrenheit <= 32) {
+if (temperatureInFahrenheit <= 32) {
     print("It's very cold. Consider wearing a scarf.")
-} else if(temperatureInFahrenheit >= 86) {
+} else if (temperatureInFahrenheit >= 86) {
     print("It's really warm. Don't forget to wear sunscreen.")
 }

'while' parentheses

 var square = 0
 var diceRoll = 0
-while(square < finalSquare) {
+while (square < finalSquare) {
     // roll the dice
     diceRoll += 1
     if diceRoll == 7 { diceRoll = 1 }

'switch' parentheses

 let someCharacter: Character = "z"
-switch(someCharacter) {
+switch (someCharacter) {
 case "a":
     print("The first letter of the alphabet")
 case "z":

'catch' parentheses

 do {
     try throwable()
 } catch Error.unexpected(let cause) {
     print("unexpected error!")
-} catch(Error.unknown) {
+} catch (Error.unknown) {
     print("unknown error!")
 }

Attribute parentheses

-@available (swift 3.0.2)
-@available (macOS 10.12, *)
+@available(swift 3.0.2)
+@available(macOS 10.12, *)
 struct MyStruct {
     // struct definition
 }

Around Operators

Assignment Operators (=, +=, ...)

-let contentHeight=40
-let hasHeader=true
+let contentHeight = 40
+let hasHeader = true
 let rowHeight: Int
 if hasHeader {
-    rowHeight=contentHeight+50
+    rowHeight = contentHeight + 50
 } else {
-    rowHeight=contentHeight+20
+    rowHeight = contentHeight + 20
 }

Logical Operators (&&, ||)

-if enteredDoorCode&&passedRetinaScan||hasDoorKey||knowsOverridePassword {
+if enteredDoorCode && passedRetinaScan || hasDoorKey || knowsOverridePassword {
     print("Welcome!")
 } else {
     print("ACCESS DENIED")

Equality Operator (==)

 let name = "world"
-if name=="world" {
+if name == "world" {
     print("hello, world")
 } else {
     print("I'm sorry \(name), but I don't recognize you")

Relational Operators (<, >, <=, >=)

-2>1    // true because 2 is greater than 1
-1<2    // true because 1 is less than 2
-1>=1   // true because 1 is greater than or equal to 1
-2<=1   // false because 2 is not less than or equal to 1
+2 > 1 // true because 2 is greater than 1
+1 < 2 // true because 1 is less than 2
+1 >= 1 // true because 1 is greater than or equal to 1
+2 <= 1 // false because 2 is not less than or equal to 1

Bitwise Operators (&, |, ^)

 for i in 0..<x {
-    y += (y^0x123) << 2
+    y += (y ^ 0x123) << 2
 }

Additive Operators (+, -)

 while (x != y) {
-    x = f(x * 3+5)
+    x = f(x * 3 + 5)
 }

Multiplicative Operators (*, /, %)

 while (x != y) {
-    x = f(x*3 + 5)
+    x = f(x * 3 + 5)
 }

Shift Operators (<<, >>)

 for i in 0..<x {
-    y += (y ^ 0x123)<<2
+    y += (y ^ 0x123) << 2
 }
 if (0 < x && x <= 10) {
     while (x != y) {

Range Operators (..., ..<)

-for index in 1 ... 5 {
+for index in 1...5 {
     print("\(index) times 5 is \(index * 5)")
 }

Closure Arrow (->)

-func greet(person: String)->String {
+func greet(person: String) -> String {
     let greeting = "Hello, " + person + "!"
     return greeting
 }

Before Left Brace

Type declaration left brace

-struct Resolution{
+struct Resolution {
     var width = 0
     var height = 0
 }
-class VideoMode{
+
+class VideoMode {
     var resolution = Resolution()
     var interlaced = false
     var frameRate = 0.0

Method/function left brace

-func greet(person: String) -> String{
+func greet(person: String) -> String {
     let greeting = "Hello, " + person + "!"
     return greeting
 }

'if' left brace

 var temperatureInFahrenheit = 30
-if temperatureInFahrenheit <= 32{
+if temperatureInFahrenheit <= 32 {
     print("It's very cold. Consider wearing a scarf.")
 }

'else' left brace

 temperatureInFahrenheit = 40
 if temperatureInFahrenheit <= 32 {
     print("It's very cold. Consider wearing a scarf.")
-} else{
+} else {
     print("It's not that cold. Wear a t-shirt.")
 }

'for' left brace

 let names = ["Anna", "Alex", "Brian", "Jack"]
-for name in names{
+for name in names {
     print("Hello, \(name)!")
 }

'while' left brace

 var square = 0
 var diceRoll = 0
-while square < finalSquare{
+while square < finalSquare {
     // roll the dice
     diceRoll += 1
     if diceRoll == 7 { diceRoll = 1 }

'do' left brace

-do{
+do {
     try throwable()
 } catch Error.unexpected(let cause) {
     print("unexpected error!")

'switch' left brace

 let someCharacter: Character = "z"
-switch someCharacter{
+switch someCharacter {
 case "a":
     print("The first letter of the alphabet")
 case "z":

'catch' left brace

 do {
     try throwable()
-} catch Error.unexpected(let cause){
+} catch Error.unexpected(let cause) {
     print("unexpected error!")
-} catch (Error.unknown){
+} catch (Error.unknown) {
     print("unknown error!")
 }

Before Keywords

'else' keyword

 temperatureInFahrenheit = 40
 if temperatureInFahrenheit <= 32 {
     print("It's very cold. Consider wearing a scarf.")
-}else {
+} else {
     print("It's not that cold. Wear a t-shirt.")
 }

'while' keyword

     if diceRoll == 7 { diceRoll = 1 }
     // move by the rolled amount
     square += diceRoll
-}while square < finalSquare
+} while square < finalSquare
 print("Game over!")

'catch' keyword

 do {
     try throwable()
-}catch Error.unexpected(let cause) {
+} catch Error.unexpected(let cause) {
     print("unexpected error!")
-}catch (Error.unknown) {
+} catch (Error.unknown) {
     print("unknown error!")
 }

Within

Code braces

Brackets

"brackets" : true

     len = 10
 }
 repeat {
-    text[ext++] = "$"
+    text[ ext++ ] = "$"
 } while (ext < len)
 
 len = len > 10000 ? len : 0

Array and dictionary literal brackets

"arrayAndDictionaryLiteralBrackets" : true

-var shoppingList = ["Eggs", "Milk"]
-shoppingList += ["Baking Powder"]
-shoppingList += ["Chocolate Spread", "Cheese", "Butter"]
+var shoppingList = [ "Eggs", "Milk" ]
+shoppingList += [ "Baking Powder" ]
+shoppingList += [ "Chocolate Spread", "Cheese", "Butter" ]

Grouping parenthesese

 var ext = x
 var len = y
 for i in 0..<x {
-    y += (y ^ 0x123) << 2
+    y += ( y ^ 0x123 ) << 2
 }
 repeat {
     text[ext++] = "$"

Method/function declaration parenthesese

"functionDeclarationParentheses" : true

-func greet(person: String) -> String {
+func greet( person: String ) -> String {
     let greeting = "Hello, " + person + "!"
     return greeting
 }

Empty method/function declaration parenthesese

-func sayHelloWorld() -> String {
+func sayHelloWorld( ) -> String {
     return "hello, world"
 }
 print(sayHelloWorld())

Method/function call parenthesese

 func greet(person: String, alreadyGreeted: Bool) -> String {
     if alreadyGreeted {
-        return greetAgain(person: person)
+        return greetAgain( person: person )
     } else {
-        return greet(person: person)
+        return greet( person: person )
     }
 }

Empty method/function call parenthesese

 func sayHelloWorld() -> String {
     return "hello, world"
 }
-print(sayHelloWorld())
+print(sayHelloWorld( ))

'if' parenthesese

 while square < finalSquare {
     // roll the dice
     diceRoll += 1
-    if (diceRoll == 7) { diceRoll = 1 }
+    if ( diceRoll == 7 ) { diceRoll = 1 }
     // move by the rolled amount
     square += diceRoll
-    if (square < board.count) {
+    if ( square < board.count ) {
         // if we're still on the board, move up or down for a snake or a ladder
         square += board[square]
     }

'while' parenthesese

 var square = 0
 var diceRoll = 0
-while (square < finalSquare) {
+while ( square < finalSquare ) {
     repeat {
         // move up or down for a snake or ladder
         square += board[square]
@@ -9,5 +9,5 @@ while (square < finalSquare) {
         if diceRoll == 7 { diceRoll = 1 }
         // move by the rolled amount
         square += diceRoll
-    } while (square < finalSquare)
+    } while ( square < finalSquare )
 }

'switch' parenthesese

 let someCharacter: Character = "z"
-switch (someCharacter) {
+switch ( someCharacter ) {
 case "a":
     print("The first letter of the alphabet")
 case "z":

'catch' parenthesese

     try throwable()
 } catch Error.unexpected(let cause) {
     print("unexpected error!")
-} catch (Error.unknown) {
+} catch ( Error.unknown ) {
     print("unknown error!")
 }

Attribute parenthesese

-@available(swift 3.0.2)
-@available(macOS 10.12, *)
+@available( swift 3.0.2 )
+@available( macOS 10.12, * )
 struct MyStruct {
     // struct definition
 }

In Ternary Operator (:?)

After '?'

 let contentHeight = 40
 let hasHeader = true
-let rowHeight = contentHeight + (hasHeader ?50:20)
+let rowHeight = contentHeight + (hasHeader ? 50:20)

Before ':'

 let contentHeight = 40
 let hasHeader = true
-let rowHeight = contentHeight + (hasHeader ?50:20)
+let rowHeight = contentHeight + (hasHeader ?50: 20)

After ':'

 let contentHeight = 40
 let hasHeader = true
-let rowHeight = contentHeight + (hasHeader ?50:20)
+let rowHeight = contentHeight + (hasHeader ?50: 20)

Around colons

Before colon in type annotations

-func greet(person: String, alreadyGreeted: Bool) -> String {
+func greet(person : String, alreadyGreeted : Bool) -> String {
     if alreadyGreeted {
-        return greetAgain(person: person)
+        return greetAgain(person : person)
     } else {
-        return greet(person: person)
+        return greet(person : person)
     }
 }

After colon in type annotations

-func greet(person:String, alreadyGreeted:Bool) -> String {
+func greet(person: String, alreadyGreeted: Bool) -> String {
     if alreadyGreeted {
-        return greetAgain(person:person)
+        return greetAgain(person: person)
     } else {
-        return greet(person:person)
+        return greet(person: person)
     }
 }

Before colon in type inheritance clauses

-class Movie: MediaItem {
+class Movie : MediaItem {
     var director: String
     init(name: String, director: String) {
         self.director = director

After colon in type inheritance clauses

-class Movie :MediaItem {
+class Movie : MediaItem {
     var director: String
     init(name: String, director: String) {
         self.director = director

Before colon in dictionary types

-var airports: [String: String] = ["YYZ": "Toronto Pearson", "DUB": "Dublin"]
-var emptyDictionary: [String: Int] = [:]
+var airports: [String : String] = ["YYZ": "Toronto Pearson", "DUB": "Dublin"]
+var emptyDictionary: [String : Int] = [:]

After colon in dictionary types

-var airports: [String:String] = ["YYZ": "Toronto Pearson", "DUB": "Dublin"]
-var emptyDictionary: [String:Int] = [:]
+var airports: [String: String] = ["YYZ": "Toronto Pearson", "DUB": "Dublin"]
+var emptyDictionary: [String: Int] = [:]

Before colon in dictionary literal 'key:value' pair

-var airports: [String: String] = ["YYZ": "Toronto Pearson", "DUB": "Dublin"]
+var airports: [String: String] = ["YYZ" : "Toronto Pearson", "DUB" : "Dublin"]
 var emptyDictionary: [String: Int] = [:]

After colon in dictionary literal 'key:value' pair

-var airports: [String: String] = ["YYZ":"Toronto Pearson", "DUB":"Dublin"]
+var airports: [String: String] = ["YYZ": "Toronto Pearson", "DUB": "Dublin"]
 var emptyDictionary: [String: Int] = [:]

Within Type Arguments

After comma

-func allItemsMatch<C1: Container,C2: Container>
+func allItemsMatch<C1: Container, C2: Container>
 (_ someContainer: C1,_ anotherContainer: C2) -> Bool
-where C1.Item == C2.Item,C1.Item:Equatable {
+where C1.Item == C2.Item, C1.Item: Equatable {
     // Check that both containers contain the same number of items.
     if someContainer.count != anotherContainer.count {
         return false

Other

Before comma

 enum State {
-    case none, all
+    case none , all
 }
 
-typealias Status = (Int, String)
+typealias Status = (Int , String)
 
-func +++(l: String, r: String) -> String {
+func +++(l: String , r: String) -> String {
     return ""
 }
 
-let array = ["One", "Two", "Three", "Four", "Five"]
+let array = ["One" , "Two" , "Three" , "Four" , "Five"]
 
-let dictionary = ["One": 1, "Two": 2, "Three": 3, "Four": 4, "Five": 5]
+let dictionary = ["One": 1 , "Two": 2 , "Three": 3 , "Four": 4 , "Five": 5]

After comma

 enum State {
-    case none,all
+    case none, all
 }
 
-typealias Status = (Int,String)
+typealias Status = (Int, String)
 
 struct S {
 }
@@ -15,16 +15,16 @@ struct S {
 protocol P {
 }
 
-func +++(l: String,r: String) -> String {
+func +++(l: String, r: String) -> String {
     return ""
 }
 
-let array = ["One","Two","Three","Four","Five"]
+let array = ["One", "Two", "Three", "Four", "Five"]
 var emptyArray = []
 
-let dictionary = ["One": 1,"Two": 2,"Three": 3,"Four": 4,"Five": 5]
+let dictionary = ["One": 1, "Two": 2, "Three": 3, "Four": 4, "Five": 5]
 var emptyDictionary: [String: Int] = [:]

Before semicolon

After semicolon

Wrapping and Braces

Blank Lines

Keep Maximum Blank Lines

In declarations

In code

Before '}'

Minimum Blank Lines

Before imports

"beforeImports" : 1

 //
 //  Created by Kishikawa Katsumi on 2018/02/14.
 //
+
 import Foundation
 import Basic
 import SwiftSyntax

After imports

"afterImports" : 1

 import Foundation
 import Basic
 import SwiftSyntax
+
 public struct Processor {
     private let options: [String]

Around type declarations

"aroundTypeDeclarations" : 1

@@ -9,6 +9,7 @@ fileprivate class Bracket : Indentation {
         self.lineNumber = lineNumber
     }
 }
+
 fileprivate class SwitchStatement {
     var lineNumber: Int
 
@@ -16,6 +17,7 @@ fileprivate class SwitchStatement {
         self.lineNumber = lineNumber
     }
 }
+
 fileprivate class CaseBranch {
     var lineNumber: Int
 
@@ -23,6 +25,7 @@ fileprivate class CaseBranch {
         self.lineNumber = lineNumber
     }
 }
+
 protocol Indentation {
     var indent: Bool { get set }
     var alignment: Int { get set }

Around property in protocol

"aroundPropertyInProtocol" : 0

Around property

"aroundProperty" : 1

Around method/function in protocol

"aroundFunctionInProtocol" : 0

Around method/function

"aroundFunction" : 1

Before method/function body

"beforeFunctionBody" : 0

Author

Kishikawa Katsumi, [email protected]

License

Swiftfmt is available under the Apache 2.0 license. See the LICENSE file for more info.

Releases

No releases published

Packages

No packages published

Languages