diff --git a/.circleci/config.yml b/.circleci/config.yml
index adae20e3..581c84e3 100644
--- a/.circleci/config.yml
+++ b/.circleci/config.yml
@@ -1,6 +1,29 @@
version: 2
jobs:
+ danger:
+ macos:
+ xcode: 10.2.0
+ steps:
+ - checkout
+ - run:
+ name: Set Ruby Version
+ command: echo "ruby-2.4" > ~/.ruby-version
+ - restore_cache:
+ key: 1-gems-{{ checksum "Gemfile.lock" }}
+ - run:
+ name: Install Ruby Dependencies
+ command: bundle check || bundle install
+ environment:
+ BUNDLE_JOBS: 4
+ BUNDLE_RETRY: 3
+ - save_cache:
+ key: 1-gems-{{ checksum "Gemfile.lock" }}
+ paths:
+ - vendor/bundle
+ - run:
+ name: Danger
+ command: bundle exec danger
macos:
environment:
TEST_REPORTS: /tmp/test-results
@@ -51,5 +74,10 @@ workflows:
version: 2
tests:
jobs:
- - linux
- - macos
\ No newline at end of file
+ - danger
+ - linux:
+ requires:
+ - danger
+ - macos:
+ requires:
+ - danger
\ No newline at end of file
diff --git a/.swiftlint.yml b/.swiftlint.yml
index a3eb31a9..59522755 100644
--- a/.swiftlint.yml
+++ b/.swiftlint.yml
@@ -1,5 +1,21 @@
+
+identifier_name:
+ min_length: # only min_length
+ warning: 2
+ error: 2 # only error
+ excluded: # excluded via string array
+ - ok
+ - Name
+ - DEFAULT_MIME_TYPE
+ - sin_port
+ - no_sig_pipe
+
disabled_rules:
- line_length
- statement_position
- trailing_whitespace
- - variable_name_min_length
\ No newline at end of file
+
+excluded: # paths to ignore during linting. Takes precedence over `included`.
+ - LinuxMain.swift
+ - Tests/XCTestManifests.swift
+ - Package.swift
diff --git a/CHANGELOG.md b/CHANGELOG.md
index 52ea94c6..236ab854 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -20,6 +20,7 @@ All notable changes to this project will be documented in this file. Changes not
## Added
- A new `CHANGELOG.md` to keep track of changes in the project. ([#385](https://github.com/httpswift/swifter/pull/385)) by [@Vkt0r](https://github.com/Vkt0r)
+- Added [Danger](https://danger.systems/ruby/) and Swiftlint to the project. ([#398](https://github.com/httpswift/swifter/pull/398)) by [@Vkt0r](https://github.com/Vkt0r)
## Fixed
- An issue in the `HttpRouter` causing issues to handle routes with overlapping in the tail. ([#379](https://github.com/httpswift/swifter/pull/359), [#382](https://github.com/httpswift/swifter/pull/382)) by [@Vkt0r](https://github.com/Vkt0r)
diff --git a/Dangerfile b/Dangerfile
new file mode 100644
index 00000000..ea9e7d1d
--- /dev/null
+++ b/Dangerfile
@@ -0,0 +1,36 @@
+# send a welcome message for the user
+message "Hey, @#{github.pr_author} 👋."
+
+# Just to let people know
+warn("PR is classed as Work in Progress.") if github.pr_title.include? "[WIP]"
+
+# Warn when there is a big PR
+warn("Big PR") if git.lines_of_code > 500
+
+# ensure there is a summary for a PR
+fail "Please provide a summary in the Pull Request description." if github.pr_body.length < 5
+
+# Changelog entries are required for changes to library files.
+fail("Please include a CHANGELOG entry. You can find it at [CHANGELOG.md](https://github.com/httpswift/swifter/blob/stable/CHANGELOG.md).") unless git.modified_files.include?("CHANGELOG.md") || git.added_files.include?("CHANGELOG.md")
+
+# Don't accept PR on master for now
+fail "Please re-submit this PR to stable, you're trying to merge the PR on master." if github.branch_for_base == "master"
+
+# If these are all empty something has gone wrong, better to raise it in a comment
+if git.modified_files.empty? && git.added_files.empty? && git.deleted_files.empty?
+ fail "This PR has no changes at all, this is likely a developer issue."
+end
+
+# Run SwiftLint
+swiftlint.config_file = '.swiftlint.yml'
+swiftlint.lint_files
+
+# Warn when new tests are added but the XCTestManifests wasn't updated to run on Linux
+tests_added_or_modified = git.modified_files.grep(/XCode\/Tests/).empty? || git.added_files.grep(/XCode\/Tests/).empty?
+xc_manifest_updated = !git.modified_files.grep(/XCode\/Tests\/XCTestManifests.swift/).empty?
+if tests_added_or_modified && !xc_manifest_updated
+ warn("It seems like you've added new tests to the library. If that's the case, please update the [XCTestManifests.swift](https://github.com/httpswift/swifter/blob/stable/XCode/Tests/XCTestManifests.swift) file running in your terminal the command `swift test --generate-linuxmain`.")
+
+ # This is a temporary warning to remove the entry for the failed test until we solve the issue in Linux
+ warn("If you ran the command `swift test --generate-linuxmain` in your terminal, please remove the line `testCase(IOSafetyTests.__allTests__IOSafetyTests),` from `public func __allTests() -> [XCTestCaseEntry]` in the bottom of the file. For more reference see [#366](https://github.com/httpswift/swifter/issues/366).")
+end
\ No newline at end of file
diff --git a/Gemfile b/Gemfile
new file mode 100644
index 00000000..72abe727
--- /dev/null
+++ b/Gemfile
@@ -0,0 +1,8 @@
+# frozen_string_literal: true
+
+source "https://rubygems.org"
+
+git_source(:github) {|repo_name| "https://github.com/#{repo_name}" }
+
+gem 'danger'
+gem 'danger-swiftlint'
diff --git a/Gemfile.lock b/Gemfile.lock
new file mode 100644
index 00000000..c01e6ec4
--- /dev/null
+++ b/Gemfile.lock
@@ -0,0 +1,63 @@
+GEM
+ remote: https://rubygems.org/
+ specs:
+ addressable (2.5.2)
+ public_suffix (>= 2.0.2, < 4.0)
+ claide (1.0.2)
+ claide-plugins (0.9.2)
+ cork
+ nap
+ open4 (~> 1.3)
+ colored2 (3.1.2)
+ cork (0.3.0)
+ colored2 (~> 3.1)
+ danger (6.0.6)
+ claide (~> 1.0)
+ claide-plugins (>= 0.9.2)
+ colored2 (~> 3.1)
+ cork (~> 0.1)
+ faraday (~> 0.9)
+ faraday-http-cache (~> 1.0)
+ git (~> 1.5)
+ kramdown (~> 2.0)
+ kramdown-parser-gfm (~> 1.0)
+ no_proxy_fix
+ octokit (~> 4.7)
+ terminal-table (~> 1)
+ danger-swiftlint (0.20.1)
+ danger
+ rake (> 10)
+ thor (~> 0.19)
+ faraday (0.15.4)
+ multipart-post (>= 1.2, < 3)
+ faraday-http-cache (1.3.1)
+ faraday (~> 0.8)
+ git (1.5.0)
+ kramdown (2.1.0)
+ kramdown-parser-gfm (1.0.1)
+ kramdown (~> 2.0)
+ multipart-post (2.0.0)
+ nap (1.1.0)
+ no_proxy_fix (0.1.2)
+ octokit (4.14.0)
+ sawyer (~> 0.8.0, >= 0.5.3)
+ open4 (1.3.4)
+ public_suffix (3.0.3)
+ rake (12.3.2)
+ sawyer (0.8.1)
+ addressable (>= 2.3.5, < 2.6)
+ faraday (~> 0.8, < 1.0)
+ terminal-table (1.8.0)
+ unicode-display_width (~> 1.1, >= 1.1.1)
+ thor (0.20.3)
+ unicode-display_width (1.5.0)
+
+PLATFORMS
+ ruby
+
+DEPENDENCIES
+ danger
+ danger-swiftlint
+
+BUNDLED WITH
+ 1.16.5
diff --git a/Package.swift b/Package.swift
index e84c3595..1e46ba28 100644
--- a/Package.swift
+++ b/Package.swift
@@ -13,7 +13,7 @@ let package = Package(
dependencies: [],
targets: [
- .target(name: "Swifter", dependencies: [], path: "Sources"),
+ .target(name: "Swifter", dependencies: [], path: "XCode/Sources"),
.target(name: "Example", dependencies: ["Swifter"], path: "Example"),
.testTarget(name: "SwifterTests", dependencies: ["Swifter"], path: "XCode/Tests")
]
diff --git a/Sources/DemoServer.swift b/XCode/Sources/DemoServer.swift
similarity index 77%
rename from Sources/DemoServer.swift
rename to XCode/Sources/DemoServer.swift
index 46598ce5..215284fb 100644
--- a/Sources/DemoServer.swift
+++ b/XCode/Sources/DemoServer.swift
@@ -7,7 +7,7 @@
import Foundation
-
+// swiftlint:disable function_body_length
public func demoServer(_ publicDir: String) -> HttpServer {
print(publicDir)
@@ -32,17 +32,17 @@ public func demoServer(_ publicDir: String) -> HttpServer {
server["/magic"] = { .ok(.html("You asked for " + $0.path)) }
- server["/test/:param1/:param2"] = { r in
+ server["/test/:param1/:param2"] = { request in
scopes {
html {
body {
- h3 { inner = "Address: \(r.address ?? "unknown")" }
- h3 { inner = "Url: \(r.path)" }
- h3 { inner = "Method: \(r.method)" }
+ h3 { inner = "Address: \(request.address ?? "unknown")" }
+ h3 { inner = "Url: \(request.path)" }
+ h3 { inner = "Method: \(request.method)" }
h3 { inner = "Query:" }
- table(r.queryParams) { param in
+ table(request.queryParams) { param in
tr {
td { inner = param.0 }
td { inner = param.1 }
@@ -51,7 +51,7 @@ public func demoServer(_ publicDir: String) -> HttpServer {
h3 { inner = "Headers:" }
- table(r.headers) { header in
+ table(request.headers) { header in
tr {
td { inner = header.0 }
td { inner = header.1 }
@@ -60,7 +60,7 @@ public func demoServer(_ publicDir: String) -> HttpServer {
h3 { inner = "Route params:" }
- table(r.params) { param in
+ table(request.params) { param in
tr {
td { inner = param.0 }
td { inner = param.1 }
@@ -68,7 +68,7 @@ public func demoServer(_ publicDir: String) -> HttpServer {
}
}
}
- }(r)
+ }(request)
}
server.GET["/upload"] = scopes {
@@ -92,9 +92,9 @@ public func demoServer(_ publicDir: String) -> HttpServer {
}
}
- server.POST["/upload"] = { r in
+ server.POST["/upload"] = { request in
var response = ""
- for multipart in r.parseMultiPartFormData() {
+ for multipart in request.parseMultiPartFormData() {
guard let name = multipart.name, let fileName = multipart.fileName else { continue }
response += "Name: \(name) File name: \(fileName) Size: \(multipart.body.count)
"
}
@@ -134,8 +134,8 @@ public func demoServer(_ publicDir: String) -> HttpServer {
}
}
- server.POST["/login"] = { r in
- let formFields = r.parseUrlencodedForm()
+ server.POST["/login"] = { request in
+ let formFields = request.parseUrlencodedForm()
return HttpResponse.ok(.html(formFields.map({ "\($0.0) = \($0.1)" }).joined(separator: "
")))
}
@@ -150,32 +150,32 @@ public func demoServer(_ publicDir: String) -> HttpServer {
}
}
- server["/raw"] = { r in
+ server["/raw"] = { _ in
return HttpResponse.raw(200, "OK", ["XXX-Custom-Header": "value"], { try $0.write([UInt8]("test".utf8)) })
}
- server["/redirect/permanently"] = { r in
+ server["/redirect/permanently"] = { _ in
return .movedPermanently("http://www.google.com")
}
- server["/redirect/temporarily"] = { r in
+ server["/redirect/temporarily"] = { _ in
return .movedTemporarily("http://www.google.com")
}
- server["/long"] = { r in
+ server["/long"] = { _ in
var longResponse = ""
- for k in 0..<1000 { longResponse += "(\(k)),->" }
+ for index in 0..<1000 { longResponse += "(\(index)),->" }
return .ok(.html(longResponse))
}
- server["/wildcard/*/test/*/:param"] = { r in
- return .ok(.html(r.path))
+ server["/wildcard/*/test/*/:param"] = { request in
+ return .ok(.html(request.path))
}
- server["/stream"] = { r in
- return HttpResponse.raw(200, "OK", nil, { w in
- for i in 0...100 {
- try w.write([UInt8]("[chunk \(i)]".utf8))
+ server["/stream"] = { _ in
+ return HttpResponse.raw(200, "OK", nil, { writer in
+ for index in 0...100 {
+ try writer.write([UInt8]("[chunk \(index)]".utf8))
}
})
}
@@ -184,20 +184,20 @@ public func demoServer(_ publicDir: String) -> HttpServer {
session.writeText(text)
}, binary: { (session, binary) in
session.writeBinary(binary)
- }, pong: { (session, pong) in
+ }, pong: { (_, _) in
// Got a pong frame
- }, connected: { (session) in
+ }, connected: { _ in
// New client connected
- }, disconnected: { (session) in
+ }, disconnected: { _ in
// Client disconnected
})
- server.notFoundHandler = { r in
+ server.notFoundHandler = { _ in
return .movedPermanently("https://github.com/404")
}
- server.middleware.append { r in
- print("Middleware: \(r.address ?? "unknown address") -> \(r.method) -> \(r.path)")
+ server.middleware.append { request in
+ print("Middleware: \(request.address ?? "unknown address") -> \(request.method) -> \(request.path)")
return nil
}
diff --git a/Sources/Errno.swift b/XCode/Sources/Errno.swift
similarity index 100%
rename from Sources/Errno.swift
rename to XCode/Sources/Errno.swift
diff --git a/Sources/Files.swift b/XCode/Sources/Files.swift
similarity index 88%
rename from Sources/Files.swift
rename to XCode/Sources/Files.swift
index 24748c59..758c75fb 100644
--- a/Sources/Files.swift
+++ b/XCode/Sources/Files.swift
@@ -8,7 +8,7 @@
import Foundation
public func shareFile(_ path: String) -> ((HttpRequest) -> HttpResponse) {
- return { r in
+ return { _ in
if let file = try? path.openForReading() {
return .raw(200, "OK", [:], { writer in
try? writer.write(file)
@@ -20,8 +20,8 @@ public func shareFile(_ path: String) -> ((HttpRequest) -> HttpResponse) {
}
public func shareFilesFromDirectory(_ directoryPath: String, defaults: [String] = ["index.html", "default.html"]) -> ((HttpRequest) -> HttpResponse) {
- return { r in
- guard let fileRelativePath = r.params.first else {
+ return { request in
+ guard let fileRelativePath = request.params.first else {
return .notFound
}
if fileRelativePath.value.isEmpty {
@@ -35,7 +35,7 @@ public func shareFilesFromDirectory(_ directoryPath: String, defaults: [String]
}
}
if let file = try? (directoryPath + String.pathSeparator + fileRelativePath.value).openForReading() {
- let mimeType = fileRelativePath.value.mimeType();
+ let mimeType = fileRelativePath.value.mimeType()
return .raw(200, "OK", ["Content-Type": mimeType], { writer in
try? writer.write(file)
@@ -47,8 +47,8 @@ public func shareFilesFromDirectory(_ directoryPath: String, defaults: [String]
}
public func directoryBrowser(_ dir: String) -> ((HttpRequest) -> HttpResponse) {
- return { r in
- guard let (_, value) = r.params.first else {
+ return { request in
+ guard let (_, value) = request.params.first else {
return HttpResponse.notFound
}
let filePath = dir + String.pathSeparator + value
@@ -66,7 +66,7 @@ public func directoryBrowser(_ dir: String) -> ((HttpRequest) -> HttpResponse) {
tr {
td {
a {
- href = r.path + "/" + file
+ href = request.path + "/" + file
inner = file
}
}
@@ -74,7 +74,7 @@ public func directoryBrowser(_ dir: String) -> ((HttpRequest) -> HttpResponse) {
}
}
}
- }(r)
+ }(request)
} else {
guard let file = try? filePath.openForReading() else {
return .notFound
diff --git a/Sources/HttpParser.swift b/XCode/Sources/HttpParser.swift
similarity index 71%
rename from Sources/HttpParser.swift
rename to XCode/Sources/HttpParser.swift
index bf07ea00..63507778 100644
--- a/Sources/HttpParser.swift
+++ b/XCode/Sources/HttpParser.swift
@@ -8,7 +8,7 @@
import Foundation
enum HttpParserError: Error {
- case InvalidStatusLine(String)
+ case invalidStatusLine(String)
}
public class HttpParser {
@@ -19,7 +19,7 @@ public class HttpParser {
let statusLine = try socket.readLine()
let statusLineTokens = statusLine.components(separatedBy: " ")
if statusLineTokens.count < 3 {
- throw HttpParserError.InvalidStatusLine(statusLine)
+ throw HttpParserError.invalidStatusLine(statusLine)
}
let request = HttpRequest()
request.method = statusLineTokens[0]
@@ -53,27 +53,27 @@ public class HttpParser {
#endif
return query.components(separatedBy: "&")
- .reduce([(String, String)]()) { (c, s) -> [(String, String)] in
+ .reduce([(String, String)]()) { (result, stringValue) -> [(String, String)] in
#if compiler(>=5.0)
- guard let nameEndIndex = s.firstIndex(of: "=") else {
- return c
+ guard let nameEndIndex = stringValue.firstIndex(of: "=") else {
+ return result
}
#else
- guard let nameEndIndex = s.index(of: "=") else {
- return c
+ guard let nameEndIndex = stringValue.index(of: "=") else {
+ return result
}
#endif
- guard let name = String(s[s.startIndex.. [String: String] {
var headers = [String: String]()
- while case let headerLine = try socket.readLine() , !headerLine.isEmpty {
+ while case let headerLine = try socket.readLine(), !headerLine.isEmpty {
let headerTokens = headerLine.split(separator: ":", maxSplits: 1, omittingEmptySubsequences: true).map(String.init)
if let name = headerTokens.first, let value = headerTokens.last {
headers[name.lowercased()] = value.trimmingCharacters(in: .whitespaces)
diff --git a/Sources/HttpRequest.swift b/XCode/Sources/HttpRequest.swift
similarity index 98%
rename from Sources/HttpRequest.swift
rename to XCode/Sources/HttpRequest.swift
index 5a3442a7..1b59ef3d 100644
--- a/Sources/HttpRequest.swift
+++ b/XCode/Sources/HttpRequest.swift
@@ -44,7 +44,7 @@ public class HttpRequest {
return (name.replacingOccurrences(of: "+", with: " "),
value.replacingOccurrences(of: "+", with: " "))
}
- return ("","")
+ return ("", "")
}
}
@@ -86,7 +86,7 @@ public class HttpRequest {
guard let contentType = contentTypeHeaderTokens.first, contentType == "multipart/form-data" else {
return []
}
- var boundary: String? = nil
+ var boundary: String?
contentTypeHeaderTokens.forEach({
let tokens = $0.components(separatedBy: "=")
if let key = tokens.first, key == "boundary" && tokens.count == 2 {
@@ -142,13 +142,14 @@ public class HttpRequest {
return String(bytes: temp, encoding: String.Encoding.utf8)
}
+ // swiftlint:disable identifier_name
static let CR = UInt8(13)
static let NL = UInt8(10)
private func nextMultiPartBody(_ generator: inout IndexingIterator<[UInt8]>, boundary: String) -> [UInt8]? {
var body = [UInt8]()
let boundaryArray = [UInt8](boundary.utf8)
- var matchOffset = 0;
+ var matchOffset = 0
while let x = generator.next() {
matchOffset = ( x == boundaryArray[matchOffset] ? matchOffset + 1 : 0 )
body.append(x)
diff --git a/Sources/HttpResponse.swift b/XCode/Sources/HttpResponse.swift
similarity index 86%
rename from Sources/HttpResponse.swift
rename to XCode/Sources/HttpResponse.swift
index 31377477..df64d240 100644
--- a/Sources/HttpResponse.swift
+++ b/XCode/Sources/HttpResponse.swift
@@ -77,6 +77,7 @@ public enum HttpResponseBody {
}
}
+// swiftlint:disable cyclomatic_complexity
public enum HttpResponse {
case switchProtocols([String: String], (Socket) -> Void)
@@ -89,30 +90,30 @@ public enum HttpResponse {
func statusCode() -> Int {
switch self {
- case .switchProtocols(_, _) : return 101
- case .ok(_) : return 200
+ case .switchProtocols : return 101
+ case .ok : return 200
case .created : return 201
case .accepted : return 202
case .movedPermanently : return 301
case .movedTemporarily : return 307
- case .badRequest(_) : return 400
+ case .badRequest : return 400
case .unauthorized : return 401
case .forbidden : return 403
case .notFound : return 404
case .internalServerError : return 500
- case .raw(let code, _ , _, _) : return code
+ case .raw(let code, _, _, _) : return code
}
}
func reasonPhrase() -> String {
switch self {
- case .switchProtocols(_, _) : return "Switching Protocols"
- case .ok(_) : return "OK"
+ case .switchProtocols : return "Switching Protocols"
+ case .ok : return "OK"
case .created : return "Created"
case .accepted : return "Accepted"
case .movedPermanently : return "Moved Permanently"
case .movedTemporarily : return "Moved Temporarily"
- case .badRequest(_) : return "Bad Request"
+ case .badRequest : return "Bad Request"
case .unauthorized : return "Unauthorized"
case .forbidden : return "Forbidden"
case .notFound : return "Not Found"
@@ -122,7 +123,7 @@ public enum HttpResponse {
}
func headers() -> [String: String] {
- var headers = ["Server" : "Swifter \(HttpServer.VERSION)"]
+ var headers = ["Server": "Swifter \(HttpServer.VERSION)"]
switch self {
case .switchProtocols(let switchHeaders, _):
for (key, value) in switchHeaders {
@@ -130,8 +131,8 @@ public enum HttpResponse {
}
case .ok(let body):
switch body {
- case .json(_) : headers["Content-Type"] = "application/json"
- case .html(_) : headers["Content-Type"] = "text/html"
+ case .json: headers["Content-Type"] = "application/json"
+ case .html: headers["Content-Type"] = "text/html"
default:break
}
case .movedPermanently(let location):
@@ -140,8 +141,8 @@ public enum HttpResponse {
headers["Location"] = location
case .raw(_, _, let rawHeaders, _):
if let rawHeaders = rawHeaders {
- for (k, v) in rawHeaders {
- headers.updateValue(v, forKey: k)
+ for (key, value) in rawHeaders {
+ headers.updateValue(value, forKey: key)
}
}
default:break
@@ -158,7 +159,7 @@ public enum HttpResponse {
}
}
- func socketSession() -> ((Socket) -> Void)? {
+ func socketSession() -> ((Socket) -> Void)? {
switch self {
case .switchProtocols(_, let handler) : return handler
default: return nil
@@ -177,7 +178,6 @@ public enum HttpResponse {
}
*/
-func ==(inLeft: HttpResponse, inRight: HttpResponse) -> Bool {
+func == (inLeft: HttpResponse, inRight: HttpResponse) -> Bool {
return inLeft.statusCode() == inRight.statusCode()
}
-
diff --git a/Sources/HttpRouter.swift b/XCode/Sources/HttpRouter.swift
similarity index 93%
rename from Sources/HttpRouter.swift
rename to XCode/Sources/HttpRouter.swift
index 5930f47f..093eb1e5 100644
--- a/Sources/HttpRouter.swift
+++ b/XCode/Sources/HttpRouter.swift
@@ -20,7 +20,7 @@ open class HttpRouter {
var isEndOfRoute: Bool = false
/// The closure to handle the route
- var handler: ((HttpRequest) -> HttpResponse)? = nil
+ var handler: ((HttpRequest) -> HttpResponse)?
}
private var rootNode = Node()
@@ -28,18 +28,18 @@ open class HttpRouter {
public func routes() -> [String] {
var routes = [String]()
for (_, child) in rootNode.nodes {
- routes.append(contentsOf: routesForNode(child));
+ routes.append(contentsOf: routesForNode(child))
}
return routes
}
private func routesForNode(_ node: Node, prefix: String = "") -> [String] {
var result = [String]()
- if let _ = node.handler {
+ if node.handler != nil {
result.append(prefix)
}
for (key, child) in node.nodes {
- result.append(contentsOf: routesForNode(child, prefix: prefix + "/" + key));
+ result.append(contentsOf: routesForNode(child, prefix: prefix + "/" + key))
}
return result
}
@@ -59,14 +59,14 @@ open class HttpRouter {
if let method = method {
let pathSegments = (method + "/" + stripQuery(path)).split("/")
var pathSegmentsGenerator = pathSegments.makeIterator()
- var params = [String:String]()
+ var params = [String: String]()
if let handler = findHandler(&rootNode, params: ¶ms, generator: &pathSegmentsGenerator) {
return (params, handler)
}
}
let pathSegments = ("*/" + stripQuery(path)).split("/")
var pathSegmentsGenerator = pathSegments.makeIterator()
- var params = [String:String]()
+ var params = [String: String]()
if let handler = findHandler(&rootNode, params: ¶ms, generator: &pathSegmentsGenerator) {
return (params, handler)
}
@@ -96,10 +96,11 @@ open class HttpRouter {
let pattern = generator.map { $0 }
let numberOfElements = pattern.count
- findHandler(&node, params: ¶ms, pattern: pattern , matchedNodes: &matchedRoutes, index: 0, count: numberOfElements)
+ findHandler(&node, params: ¶ms, pattern: pattern, matchedNodes: &matchedRoutes, index: 0, count: numberOfElements)
return matchedRoutes.first?.handler
}
+ // swiftlint:disable function_parameter_count
/// Find the handlers for a specified route
///
/// - Parameters:
diff --git a/Sources/HttpServer.swift b/XCode/Sources/HttpServer.swift
similarity index 88%
rename from Sources/HttpServer.swift
rename to XCode/Sources/HttpServer.swift
index 7c158074..fea6d9ec 100644
--- a/Sources/HttpServer.swift
+++ b/XCode/Sources/HttpServer.swift
@@ -29,8 +29,8 @@ public class HttpServer: HttpServerIO {
self.put = MethodRoute(method: "PUT", router: router)
}
- public var DELETE, PATCH, HEAD, POST, GET, PUT : MethodRoute
- public var delete, patch, head, post, get, put : MethodRoute
+ public var DELETE, PATCH, HEAD, POST, GET, PUT: MethodRoute
+ public var delete, patch, head, post, get, put: MethodRoute
public subscript(path: String) -> ((HttpRequest) -> HttpResponse)? {
set {
@@ -40,14 +40,14 @@ public class HttpServer: HttpServerIO {
}
public var routes: [String] {
- return router.routes();
+ return router.routes()
}
public var notFoundHandler: ((HttpRequest) -> HttpResponse)?
- public var middleware = Array<(HttpRequest) -> HttpResponse?>()
+ public var middleware = [(HttpRequest) -> HttpResponse?]()
- override public func dispatch(_ request: HttpRequest) -> ([String:String], (HttpRequest) -> HttpResponse) {
+ override public func dispatch(_ request: HttpRequest) -> ([String: String], (HttpRequest) -> HttpResponse) {
for layer in middleware {
if let response = layer(request) {
return ([:], { _ in response })
diff --git a/Sources/HttpServerIO.swift b/XCode/Sources/HttpServerIO.swift
similarity index 96%
rename from Sources/HttpServerIO.swift
rename to XCode/Sources/HttpServerIO.swift
index 215da739..e5b09550 100644
--- a/Sources/HttpServerIO.swift
+++ b/XCode/Sources/HttpServerIO.swift
@@ -14,7 +14,7 @@ public protocol HttpServerIODelegate: class {
public class HttpServerIO {
- public weak var delegate : HttpServerIODelegate?
+ public weak var delegate: HttpServerIODelegate?
private var socket = Socket(socketFileDescriptor: -1)
private var sockets = Set()
@@ -36,13 +36,12 @@ public class HttpServerIO {
#if !os(Linux)
OSAtomicCompareAndSwapInt(self.state.rawValue, state.rawValue, &stateValue)
#else
- //TODO - hehe :)
self.stateValue = state.rawValue
#endif
}
}
- public var operating: Bool { get { return self.state == .running } }
+ public var operating: Bool { return self.state == .running }
/// String representation of the IPv4 address to receive requests from.
/// It's only used when the server is started with `forceIPv4` option set to true.
@@ -199,6 +198,6 @@ public class HttpServerIO {
try writeClosure(context)
}
- return keepAlive && content.length != -1;
+ return keepAlive && content.length != -1
}
}
diff --git a/Sources/MimeTypes.swift b/XCode/Sources/MimeTypes.swift
similarity index 93%
rename from Sources/MimeTypes.swift
rename to XCode/Sources/MimeTypes.swift
index 36ee8925..204a262c 100644
--- a/Sources/MimeTypes.swift
+++ b/XCode/Sources/MimeTypes.swift
@@ -115,22 +115,22 @@ internal let mimeTypes = [
"avi": "video/x-msvideo"
]
-internal func MimeType(ext: String?) -> String {
- if ext != nil && mimeTypes.contains(where: { $0.0 == ext!.lowercased() }) {
- return mimeTypes[ext!.lowercased()]!
+internal func matchMimeType(extens: String?) -> String {
+ if extens != nil && mimeTypes.contains(where: { $0.0 == extens!.lowercased() }) {
+ return mimeTypes[extens!.lowercased()]!
}
return DEFAULT_MIME_TYPE
}
extension NSURL {
public func mimeType() -> String {
- return MimeType(ext: self.pathExtension)
+ return matchMimeType(extens: self.pathExtension)
}
}
extension NSString {
public func mimeType() -> String {
- return MimeType(ext: self.pathExtension)
+ return matchMimeType(extens: self.pathExtension)
}
}
@@ -139,5 +139,3 @@ extension String {
return (NSString(string: self)).mimeType()
}
}
-
-
diff --git a/Sources/Process.swift b/XCode/Sources/Process.swift
similarity index 78%
rename from Sources/Process.swift
rename to XCode/Sources/Process.swift
index 5b71ad1f..56d320b9 100644
--- a/Sources/Process.swift
+++ b/XCode/Sources/Process.swift
@@ -18,19 +18,19 @@ public class Process {
return UInt64(pthread_self())
#else
var tid: __uint64_t = 0
- pthread_threadid_np(nil, &tid);
+ pthread_threadid_np(nil, &tid)
return UInt64(tid)
#endif
}
- private static var signalsWatchers = Array<(Int32) -> Void>()
+ private static var signalsWatchers = [(Int32) -> Void]()
private static var signalsObserved = false
public static func watchSignals(_ callback: @escaping (Int32) -> Void) {
if !signalsObserved {
[SIGTERM, SIGHUP, SIGSTOP, SIGINT].forEach { item in
- signal(item) {
- signum in Process.signalsWatchers.forEach { $0(signum) }
+ signal(item) { signum in
+ Process.signalsWatchers.forEach { $0(signum) }
}
}
signalsObserved = true
diff --git a/Sources/Scopes.swift b/XCode/Sources/Scopes.swift
similarity index 56%
rename from Sources/Scopes.swift
rename to XCode/Sources/Scopes.swift
index d5a16845..537afcb0 100644
--- a/Sources/Scopes.swift
+++ b/XCode/Sources/Scopes.swift
@@ -5,333 +5,335 @@
// Copyright © 2014-2016 Damian Kołakowski. All rights reserved.
//
+// swiftlint:disable file_length
import Foundation
public func scopes(_ scope: @escaping Closure) -> ((HttpRequest) -> HttpResponse) {
- return { r in
- ScopesBuffer[Process.tid] = ""
+ return { _ in
+ scopesBuffer[Process.tid] = ""
scope()
return .raw(200, "OK", ["Content-Type": "text/html"], {
- try? $0.write([UInt8](("" + (ScopesBuffer[Process.tid] ?? "")).utf8))
+ try? $0.write([UInt8](("" + (scopesBuffer[Process.tid] ?? "")).utf8))
})
}
}
public typealias Closure = () -> Void
-public var idd: String? = nil
-public var dir: String? = nil
-public var rel: String? = nil
-public var rev: String? = nil
-public var alt: String? = nil
-public var forr: String? = nil
-public var src: String? = nil
-public var type: String? = nil
-public var href: String? = nil
-public var text: String? = nil
-public var abbr: String? = nil
-public var size: String? = nil
-public var face: String? = nil
-public var char: String? = nil
-public var cite: String? = nil
-public var span: String? = nil
-public var data: String? = nil
-public var axis: String? = nil
-public var Name: String? = nil
-public var name: String? = nil
-public var code: String? = nil
-public var link: String? = nil
-public var lang: String? = nil
-public var cols: String? = nil
-public var rows: String? = nil
-public var ismap: String? = nil
-public var shape: String? = nil
-public var style: String? = nil
-public var alink: String? = nil
-public var width: String? = nil
-public var rules: String? = nil
-public var align: String? = nil
-public var frame: String? = nil
-public var vlink: String? = nil
-public var deferr: String? = nil
-public var color: String? = nil
-public var media: String? = nil
-public var title: String? = nil
-public var scope: String? = nil
-public var classs: String? = nil
-public var value: String? = nil
-public var clear: String? = nil
-public var start: String? = nil
-public var label: String? = nil
-public var action: String? = nil
-public var height: String? = nil
-public var method: String? = nil
-public var acceptt: String? = nil
-public var object: String? = nil
-public var scheme: String? = nil
-public var coords: String? = nil
-public var usemap: String? = nil
-public var onblur: String? = nil
-public var nohref: String? = nil
-public var nowrap: String? = nil
-public var hspace: String? = nil
-public var border: String? = nil
-public var valign: String? = nil
-public var vspace: String? = nil
-public var onload: String? = nil
-public var target: String? = nil
-public var prompt: String? = nil
-public var onfocus: String? = nil
-public var enctype: String? = nil
-public var onclick: String? = nil
-public var onkeyup: String? = nil
-public var profile: String? = nil
-public var version: String? = nil
-public var onreset: String? = nil
-public var charset: String? = nil
-public var standby: String? = nil
-public var colspan: String? = nil
-public var charoff: String? = nil
-public var classid: String? = nil
-public var compact: String? = nil
-public var declare: String? = nil
-public var rowspan: String? = nil
-public var checked: String? = nil
-public var archive: String? = nil
-public var bgcolor: String? = nil
-public var content: String? = nil
-public var noshade: String? = nil
-public var summary: String? = nil
-public var headers: String? = nil
-public var onselect: String? = nil
-public var readonly: String? = nil
-public var tabindex: String? = nil
-public var onchange: String? = nil
-public var noresize: String? = nil
-public var disabled: String? = nil
-public var longdesc: String? = nil
-public var codebase: String? = nil
-public var language: String? = nil
-public var datetime: String? = nil
-public var selected: String? = nil
-public var hreflang: String? = nil
-public var onsubmit: String? = nil
-public var multiple: String? = nil
-public var onunload: String? = nil
-public var codetype: String? = nil
-public var scrolling: String? = nil
-public var onkeydown: String? = nil
-public var maxlength: String? = nil
-public var valuetype: String? = nil
-public var accesskey: String? = nil
-public var onmouseup: String? = nil
-public var autofocus: String? = nil
-public var onkeypress: String? = nil
-public var ondblclick: String? = nil
-public var onmouseout: String? = nil
-public var httpEquiv: String? = nil
-public var background: String? = nil
-public var onmousemove: String? = nil
-public var onmouseover: String? = nil
-public var cellpadding: String? = nil
-public var onmousedown: String? = nil
-public var frameborder: String? = nil
-public var marginwidth: String? = nil
-public var cellspacing: String? = nil
-public var placeholder: String? = nil
-public var marginheight: String? = nil
-public var acceptCharset: String? = nil
+public var idd: String?
+public var dir: String?
+public var rel: String?
+public var rev: String?
+public var alt: String?
+public var forr: String?
+public var src: String?
+public var type: String?
+public var href: String?
+public var text: String?
+public var abbr: String?
+public var size: String?
+public var face: String?
+public var char: String?
+public var cite: String?
+public var span: String?
+public var data: String?
+public var axis: String?
+public var Name: String?
+public var name: String?
+public var code: String?
+public var link: String?
+public var lang: String?
+public var cols: String?
+public var rows: String?
+public var ismap: String?
+public var shape: String?
+public var style: String?
+public var alink: String?
+public var width: String?
+public var rules: String?
+public var align: String?
+public var frame: String?
+public var vlink: String?
+public var deferr: String?
+public var color: String?
+public var media: String?
+public var title: String?
+public var scope: String?
+public var classs: String?
+public var value: String?
+public var clear: String?
+public var start: String?
+public var label: String?
+public var action: String?
+public var height: String?
+public var method: String?
+public var acceptt: String?
+public var object: String?
+public var scheme: String?
+public var coords: String?
+public var usemap: String?
+public var onblur: String?
+public var nohref: String?
+public var nowrap: String?
+public var hspace: String?
+public var border: String?
+public var valign: String?
+public var vspace: String?
+public var onload: String?
+public var target: String?
+public var prompt: String?
+public var onfocus: String?
+public var enctype: String?
+public var onclick: String?
+public var onkeyup: String?
+public var profile: String?
+public var version: String?
+public var onreset: String?
+public var charset: String?
+public var standby: String?
+public var colspan: String?
+public var charoff: String?
+public var classid: String?
+public var compact: String?
+public var declare: String?
+public var rowspan: String?
+public var checked: String?
+public var archive: String?
+public var bgcolor: String?
+public var content: String?
+public var noshade: String?
+public var summary: String?
+public var headers: String?
+public var onselect: String?
+public var readonly: String?
+public var tabindex: String?
+public var onchange: String?
+public var noresize: String?
+public var disabled: String?
+public var longdesc: String?
+public var codebase: String?
+public var language: String?
+public var datetime: String?
+public var selected: String?
+public var hreflang: String?
+public var onsubmit: String?
+public var multiple: String?
+public var onunload: String?
+public var codetype: String?
+public var scrolling: String?
+public var onkeydown: String?
+public var maxlength: String?
+public var valuetype: String?
+public var accesskey: String?
+public var onmouseup: String?
+public var autofocus: String?
+public var onkeypress: String?
+public var ondblclick: String?
+public var onmouseout: String?
+public var httpEquiv: String?
+public var background: String?
+public var onmousemove: String?
+public var onmouseover: String?
+public var cellpadding: String?
+public var onmousedown: String?
+public var frameborder: String?
+public var marginwidth: String?
+public var cellspacing: String?
+public var placeholder: String?
+public var marginheight: String?
+public var acceptCharset: String?
-public var inner: String? = nil
+public var inner: String?
-public func a(_ c: Closure) { element("a", c) }
-public func b(_ c: Closure) { element("b", c) }
-public func i(_ c: Closure) { element("i", c) }
-public func p(_ c: Closure) { element("p", c) }
-public func q(_ c: Closure) { element("q", c) }
-public func s(_ c: Closure) { element("s", c) }
-public func u(_ c: Closure) { element("u", c) }
+public func a(_ closure: Closure) { element("a", closure) }
+public func b(_ closure: Closure) { element("b", closure) }
+public func i(_ closure: Closure) { element("i", closure) }
+public func p(_ closure: Closure) { element("p", closure) }
+public func q(_ closure: Closure) { element("q", closure) }
+public func s(_ closure: Closure) { element("s", closure) }
+public func u(_ closure: Closure) { element("u", closure) }
-public func br(_ c: Closure) { element("br", c) }
-public func dd(_ c: Closure) { element("dd", c) }
-public func dl(_ c: Closure) { element("dl", c) }
-public func dt(_ c: Closure) { element("dt", c) }
-public func em(_ c: Closure) { element("em", c) }
-public func hr(_ c: Closure) { element("hr", c) }
-public func li(_ c: Closure) { element("li", c) }
-public func ol(_ c: Closure) { element("ol", c) }
-public func rp(_ c: Closure) { element("rp", c) }
-public func rt(_ c: Closure) { element("rt", c) }
-public func td(_ c: Closure) { element("td", c) }
-public func th(_ c: Closure) { element("th", c) }
-public func tr(_ c: Closure) { element("tr", c) }
-public func tt(_ c: Closure) { element("tt", c) }
-public func ul(_ c: Closure) { element("ul", c) }
+public func br(_ closure: Closure) { element("br", closure) }
+public func dd(_ closure: Closure) { element("dd", closure) }
+public func dl(_ closure: Closure) { element("dl", closure) }
+public func dt(_ closure: Closure) { element("dt", closure) }
+public func em(_ closure: Closure) { element("em", closure) }
+public func hr(_ closure: Closure) { element("hr", closure) }
+public func li(_ closure: Closure) { element("li", closure) }
+public func ol(_ closure: Closure) { element("ol", closure) }
+public func rp(_ closure: Closure) { element("rp", closure) }
+public func rt(_ closure: Closure) { element("rt", closure) }
+public func td(_ closure: Closure) { element("td", closure) }
+public func th(_ closure: Closure) { element("th", closure) }
+public func tr(_ closure: Closure) { element("tr", closure) }
+public func tt(_ closure: Closure) { element("tt", closure) }
+public func ul(_ closure: Closure) { element("ul", closure) }
-public func ul(_ collection: T, _ c: @escaping (T.Iterator.Element) -> Void) {
+public func ul(_ collection: T, _ closure: @escaping (T.Iterator.Element) -> Void) {
element("ul", {
for item in collection {
- c(item)
+ closure(item)
}
})
}
-public func h1(_ c: Closure) { element("h1", c) }
-public func h2(_ c: Closure) { element("h2", c) }
-public func h3(_ c: Closure) { element("h3", c) }
-public func h4(_ c: Closure) { element("h4", c) }
-public func h5(_ c: Closure) { element("h5", c) }
-public func h6(_ c: Closure) { element("h6", c) }
+public func h1(_ closure: Closure) { element("h1", closure) }
+public func h2(_ closure: Closure) { element("h2", closure) }
+public func h3(_ closure: Closure) { element("h3", closure) }
+public func h4(_ closure: Closure) { element("h4", closure) }
+public func h5(_ closure: Closure) { element("h5", closure) }
+public func h6(_ closure: Closure) { element("h6", closure) }
-public func bdi(_ c: Closure) { element("bdi", c) }
-public func bdo(_ c: Closure) { element("bdo", c) }
-public func big(_ c: Closure) { element("big", c) }
-public func col(_ c: Closure) { element("col", c) }
-public func del(_ c: Closure) { element("del", c) }
-public func dfn(_ c: Closure) { element("dfn", c) }
-public func dir(_ c: Closure) { element("dir", c) }
-public func div(_ c: Closure) { element("div", c) }
-public func img(_ c: Closure) { element("img", c) }
-public func ins(_ c: Closure) { element("ins", c) }
-public func kbd(_ c: Closure) { element("kbd", c) }
-public func map(_ c: Closure) { element("map", c) }
-public func nav(_ c: Closure) { element("nav", c) }
-public func pre(_ c: Closure) { element("pre", c) }
-public func rtc(_ c: Closure) { element("rtc", c) }
-public func sub(_ c: Closure) { element("sub", c) }
-public func sup(_ c: Closure) { element("sup", c) }
+public func bdi(_ closure: Closure) { element("bdi", closure) }
+public func bdo(_ closure: Closure) { element("bdo", closure) }
+public func big(_ closure: Closure) { element("big", closure) }
+public func col(_ closure: Closure) { element("col", closure) }
+public func del(_ closure: Closure) { element("del", closure) }
+public func dfn(_ closure: Closure) { element("dfn", closure) }
+public func dir(_ closure: Closure) { element("dir", closure) }
+public func div(_ closure: Closure) { element("div", closure) }
+public func img(_ closure: Closure) { element("img", closure) }
+public func ins(_ closure: Closure) { element("ins", closure) }
+public func kbd(_ closure: Closure) { element("kbd", closure) }
+public func map(_ closure: Closure) { element("map", closure) }
+public func nav(_ closure: Closure) { element("nav", closure) }
+public func pre(_ closure: Closure) { element("pre", closure) }
+public func rtc(_ closure: Closure) { element("rtc", closure) }
+public func sub(_ closure: Closure) { element("sub", closure) }
+public func sup(_ closure: Closure) { element("sup", closure) }
-public func varr(_ c: Closure) { element("var", c) }
-public func wbr(_ c: Closure) { element("wbr", c) }
-public func xmp(_ c: Closure) { element("xmp", c) }
+public func varr(_ closure: Closure) { element("var", closure) }
+public func wbr(_ closure: Closure) { element("wbr", closure) }
+public func xmp(_ closure: Closure) { element("xmp", closure) }
-public func abbr(_ c: Closure) { element("abbr", c) }
-public func area(_ c: Closure) { element("area", c) }
-public func base(_ c: Closure) { element("base", c) }
-public func body(_ c: Closure) { element("body", c) }
-public func cite(_ c: Closure) { element("cite", c) }
-public func code(_ c: Closure) { element("code", c) }
-public func data(_ c: Closure) { element("data", c) }
-public func font(_ c: Closure) { element("font", c) }
-public func form(_ c: Closure) { element("form", c) }
-public func head(_ c: Closure) { element("head", c) }
-public func html(_ c: Closure) { element("html", c) }
-public func link(_ c: Closure) { element("link", c) }
-public func main(_ c: Closure) { element("main", c) }
-public func mark(_ c: Closure) { element("mark", c) }
-public func menu(_ c: Closure) { element("menu", c) }
-public func meta(_ c: Closure) { element("meta", c) }
-public func nobr(_ c: Closure) { element("nobr", c) }
-public func ruby(_ c: Closure) { element("ruby", c) }
-public func samp(_ c: Closure) { element("samp", c) }
-public func span(_ c: Closure) { element("span", c) }
-public func time(_ c: Closure) { element("time", c) }
+public func abbr(_ closure: Closure) { element("abbr", closure) }
+public func area(_ closure: Closure) { element("area", closure) }
+public func base(_ closure: Closure) { element("base", closure) }
+public func body(_ closure: Closure) { element("body", closure) }
+public func cite(_ closure: Closure) { element("cite", closure) }
+public func code(_ closure: Closure) { element("code", closure) }
+public func data(_ closure: Closure) { element("data", closure) }
+public func font(_ closure: Closure) { element("font", closure) }
+public func form(_ closure: Closure) { element("form", closure) }
+public func head(_ closure: Closure) { element("head", closure) }
+public func html(_ closure: Closure) { element("html", closure) }
+public func link(_ closure: Closure) { element("link", closure) }
+public func main(_ closure: Closure) { element("main", closure) }
+public func mark(_ closure: Closure) { element("mark", closure) }
+public func menu(_ closure: Closure) { element("menu", closure) }
+public func meta(_ closure: Closure) { element("meta", closure) }
+public func nobr(_ closure: Closure) { element("nobr", closure) }
+public func ruby(_ closure: Closure) { element("ruby", closure) }
+public func samp(_ closure: Closure) { element("samp", closure) }
+public func span(_ closure: Closure) { element("span", closure) }
+public func time(_ closure: Closure) { element("time", closure) }
-public func aside(_ c: Closure) { element("aside", c) }
-public func audio(_ c: Closure) { element("audio", c) }
-public func blink(_ c: Closure) { element("blink", c) }
-public func embed(_ c: Closure) { element("embed", c) }
-public func frame(_ c: Closure) { element("frame", c) }
-public func image(_ c: Closure) { element("image", c) }
-public func input(_ c: Closure) { element("input", c) }
-public func label(_ c: Closure) { element("label", c) }
-public func meter(_ c: Closure) { element("meter", c) }
-public func param(_ c: Closure) { element("param", c) }
-public func small(_ c: Closure) { element("small", c) }
-public func style(_ c: Closure) { element("style", c) }
-public func table(_ c: Closure) { element("table", c) }
+public func aside(_ closure: Closure) { element("aside", closure) }
+public func audio(_ closure: Closure) { element("audio", closure) }
+public func blink(_ closure: Closure) { element("blink", closure) }
+public func embed(_ closure: Closure) { element("embed", closure) }
+public func frame(_ closure: Closure) { element("frame", closure) }
+public func image(_ closure: Closure) { element("image", closure) }
+public func input(_ closure: Closure) { element("input", closure) }
+public func label(_ closure: Closure) { element("label", closure) }
+public func meter(_ closure: Closure) { element("meter", closure) }
+public func param(_ closure: Closure) { element("param", closure) }
+public func small(_ closure: Closure) { element("small", closure) }
+public func style(_ closure: Closure) { element("style", closure) }
+public func table(_ closure: Closure) { element("table", closure) }
-public func table(_ collection: T, c: @escaping (T.Iterator.Element) -> Void) {
+public func table(_ collection: T, closure: @escaping (T.Iterator.Element) -> Void) {
element("table", {
for item in collection {
- c(item)
+ closure(item)
}
})
}
-public func tbody(_ c: Closure) { element("tbody", c) }
+public func tbody(_ closure: Closure) { element("tbody", closure) }
-public func tbody(_ collection: T, c: @escaping (T.Iterator.Element) -> Void) {
+public func tbody(_ collection: T, closure: @escaping (T.Iterator.Element) -> Void) {
element("tbody", {
for item in collection {
- c(item)
+ closure(item)
}
})
}
-public func tfoot(_ c: Closure) { element("tfoot", c) }
-public func thead(_ c: Closure) { element("thead", c) }
-public func title(_ c: Closure) { element("title", c) }
-public func track(_ c: Closure) { element("track", c) }
-public func video(_ c: Closure) { element("video", c) }
+public func tfoot(_ closure: Closure) { element("tfoot", closure) }
+public func thead(_ closure: Closure) { element("thead", closure) }
+public func title(_ closure: Closure) { element("title", closure) }
+public func track(_ closure: Closure) { element("track", closure) }
+public func video(_ closure: Closure) { element("video", closure) }
-public func applet(_ c: Closure) { element("applet", c) }
-public func button(_ c: Closure) { element("button", c) }
-public func canvas(_ c: Closure) { element("canvas", c) }
-public func center(_ c: Closure) { element("center", c) }
-public func dialog(_ c: Closure) { element("dialog", c) }
-public func figure(_ c: Closure) { element("figure", c) }
-public func footer(_ c: Closure) { element("footer", c) }
-public func header(_ c: Closure) { element("header", c) }
-public func hgroup(_ c: Closure) { element("hgroup", c) }
-public func iframe(_ c: Closure) { element("iframe", c) }
-public func keygen(_ c: Closure) { element("keygen", c) }
-public func legend(_ c: Closure) { element("legend", c) }
-public func object(_ c: Closure) { element("object", c) }
-public func option(_ c: Closure) { element("option", c) }
-public func output(_ c: Closure) { element("output", c) }
-public func script(_ c: Closure) { element("script", c) }
-public func select(_ c: Closure) { element("select", c) }
-public func shadow(_ c: Closure) { element("shadow", c) }
-public func source(_ c: Closure) { element("source", c) }
-public func spacer(_ c: Closure) { element("spacer", c) }
-public func strike(_ c: Closure) { element("strike", c) }
-public func strong(_ c: Closure) { element("strong", c) }
+public func applet(_ closure: Closure) { element("applet", closure) }
+public func button(_ closure: Closure) { element("button", closure) }
+public func canvas(_ closure: Closure) { element("canvas", closure) }
+public func center(_ closure: Closure) { element("center", closure) }
+public func dialog(_ closure: Closure) { element("dialog", closure) }
+public func figure(_ closure: Closure) { element("figure", closure) }
+public func footer(_ closure: Closure) { element("footer", closure) }
+public func header(_ closure: Closure) { element("header", closure) }
+public func hgroup(_ closure: Closure) { element("hgroup", closure) }
+public func iframe(_ closure: Closure) { element("iframe", closure) }
+public func keygen(_ closure: Closure) { element("keygen", closure) }
+public func legend(_ closure: Closure) { element("legend", closure) }
+public func object(_ closure: Closure) { element("object", closure) }
+public func option(_ closure: Closure) { element("option", closure) }
+public func output(_ closure: Closure) { element("output", closure) }
+public func script(_ closure: Closure) { element("script", closure) }
+public func select(_ closure: Closure) { element("select", closure) }
+public func shadow(_ closure: Closure) { element("shadow", closure) }
+public func source(_ closure: Closure) { element("source", closure) }
+public func spacer(_ closure: Closure) { element("spacer", closure) }
+public func strike(_ closure: Closure) { element("strike", closure) }
+public func strong(_ closure: Closure) { element("strong", closure) }
-public func acronym(_ c: Closure) { element("acronym", c) }
-public func address(_ c: Closure) { element("address", c) }
-public func article(_ c: Closure) { element("article", c) }
-public func bgsound(_ c: Closure) { element("bgsound", c) }
-public func caption(_ c: Closure) { element("caption", c) }
-public func command(_ c: Closure) { element("command", c) }
-public func content(_ c: Closure) { element("content", c) }
-public func details(_ c: Closure) { element("details", c) }
-public func elementt(_ c: Closure) { element("element", c) }
-public func isindex(_ c: Closure) { element("isindex", c) }
-public func listing(_ c: Closure) { element("listing", c) }
-public func marquee(_ c: Closure) { element("marquee", c) }
-public func noembed(_ c: Closure) { element("noembed", c) }
-public func picture(_ c: Closure) { element("picture", c) }
-public func section(_ c: Closure) { element("section", c) }
-public func summary(_ c: Closure) { element("summary", c) }
+public func acronym(_ closure: Closure) { element("acronym", closure) }
+public func address(_ closure: Closure) { element("address", closure) }
+public func article(_ closure: Closure) { element("article", closure) }
+public func bgsound(_ closure: Closure) { element("bgsound", closure) }
+public func caption(_ closure: Closure) { element("caption", closure) }
+public func command(_ closure: Closure) { element("command", closure) }
+public func content(_ closure: Closure) { element("content", closure) }
+public func details(_ closure: Closure) { element("details", closure) }
+public func elementt(_ closure: Closure) { element("element", closure) }
+public func isindex(_ closure: Closure) { element("isindex", closure) }
+public func listing(_ closure: Closure) { element("listing", closure) }
+public func marquee(_ closure: Closure) { element("marquee", closure) }
+public func noembed(_ closure: Closure) { element("noembed", closure) }
+public func picture(_ closure: Closure) { element("picture", closure) }
+public func section(_ closure: Closure) { element("section", closure) }
+public func summary(_ closure: Closure) { element("summary", closure) }
-public func basefont(_ c: Closure) { element("basefont", c) }
-public func colgroup(_ c: Closure) { element("colgroup", c) }
-public func datalist(_ c: Closure) { element("datalist", c) }
-public func fieldset(_ c: Closure) { element("fieldset", c) }
-public func frameset(_ c: Closure) { element("frameset", c) }
-public func menuitem(_ c: Closure) { element("menuitem", c) }
-public func multicol(_ c: Closure) { element("multicol", c) }
-public func noframes(_ c: Closure) { element("noframes", c) }
-public func noscript(_ c: Closure) { element("noscript", c) }
-public func optgroup(_ c: Closure) { element("optgroup", c) }
-public func progress(_ c: Closure) { element("progress", c) }
-public func template(_ c: Closure) { element("template", c) }
-public func textarea(_ c: Closure) { element("textarea", c) }
+public func basefont(_ closure: Closure) { element("basefont", closure) }
+public func colgroup(_ closure: Closure) { element("colgroup", closure) }
+public func datalist(_ closure: Closure) { element("datalist", closure) }
+public func fieldset(_ closure: Closure) { element("fieldset", closure) }
+public func frameset(_ closure: Closure) { element("frameset", closure) }
+public func menuitem(_ closure: Closure) { element("menuitem", closure) }
+public func multicol(_ closure: Closure) { element("multicol", closure) }
+public func noframes(_ closure: Closure) { element("noframes", closure) }
+public func noscript(_ closure: Closure) { element("noscript", closure) }
+public func optgroup(_ closure: Closure) { element("optgroup", closure) }
+public func progress(_ closure: Closure) { element("progress", closure) }
+public func template(_ closure: Closure) { element("template", closure) }
+public func textarea(_ closure: Closure) { element("textarea", closure) }
-public func plaintext(_ c: Closure) { element("plaintext", c) }
-public func javascript(_ c: Closure) { element("script", ["type": "text/javascript"], c) }
-public func blockquote(_ c: Closure) { element("blockquote", c) }
-public func figcaption(_ c: Closure) { element("figcaption", c) }
+public func plaintext(_ closure: Closure) { element("plaintext", closure) }
+public func javascript(_ closure: Closure) { element("script", ["type": "text/javascript"], closure) }
+public func blockquote(_ closure: Closure) { element("blockquote", closure) }
+public func figcaption(_ closure: Closure) { element("figcaption", closure) }
-public func stylesheet(_ c: Closure) { element("link", ["rel": "stylesheet", "type": "text/css"], c) }
+public func stylesheet(_ closure: Closure) { element("link", ["rel": "stylesheet", "type": "text/css"], closure) }
-public func element(_ node: String, _ c: Closure) { evaluate(node, [:], c) }
-public func element(_ node: String, _ attrs: [String: String?] = [:], _ c: Closure) { evaluate(node, attrs, c) }
+public func element(_ node: String, _ closure: Closure) { evaluate(node, [:], closure) }
+public func element(_ node: String, _ attrs: [String: String?] = [:], _ closure: Closure) { evaluate(node, attrs, closure) }
-var ScopesBuffer = [UInt64: String]()
+var scopesBuffer = [UInt64: String]()
-private func evaluate(_ node: String, _ attrs: [String: String?] = [:], _ c: Closure) {
+// swiftlint:disable cyclomatic_complexity function_body_length
+private func evaluate(_ node: String, _ attrs: [String: String?] = [:], _ closure: Closure) {
// Push the attributes.
@@ -583,19 +585,19 @@ private func evaluate(_ node: String, _ attrs: [String: String?] = [:], _ c: Clo
acceptCharset = nil
inner = nil
- ScopesBuffer[Process.tid] = (ScopesBuffer[Process.tid] ?? "") + "<" + node
+ scopesBuffer[Process.tid] = (scopesBuffer[Process.tid] ?? "") + "<" + node
// Save the current output before the nested scope evalutation.
- var output = ScopesBuffer[Process.tid] ?? ""
+ var output = scopesBuffer[Process.tid] ?? ""
// Clear the output buffer for the evalutation.
- ScopesBuffer[Process.tid] = ""
+ scopesBuffer[Process.tid] = ""
// Evaluate the nested scope.
- c()
+ closure()
// Render attributes set by the evalutation.
@@ -727,7 +729,7 @@ private func evaluate(_ node: String, _ attrs: [String: String?] = [:], _ c: Clo
mergedAttributes.updateValue(item.element.1, forKey: item.element.0)
}
- output = output + mergedAttributes.reduce("") { result, item in
+ output += mergedAttributes.reduce("") { result, item in
if let value = item.value {
return result + " \(item.key)=\"\(value)\""
} else {
@@ -736,10 +738,10 @@ private func evaluate(_ node: String, _ attrs: [String: String?] = [:], _ c: Clo
}
if let inner = inner {
- ScopesBuffer[Process.tid] = output + ">" + (inner) + "" + node + ">"
+ scopesBuffer[Process.tid] = output + ">" + (inner) + "" + node + ">"
} else {
- let current = ScopesBuffer[Process.tid] ?? ""
- ScopesBuffer[Process.tid] = output + ">" + current + "" + node + ">"
+ let current = scopesBuffer[Process.tid] ?? ""
+ scopesBuffer[Process.tid] = output + ">" + current + "" + node + ">"
}
// Pop the attributes.
diff --git a/Sources/Socket+File.swift b/XCode/Sources/Socket+File.swift
similarity index 91%
rename from Sources/Socket+File.swift
rename to XCode/Sources/Socket+File.swift
index 81f0c487..4381b9b2 100644
--- a/Sources/Socket+File.swift
+++ b/XCode/Sources/Socket+File.swift
@@ -8,6 +8,7 @@
import Foundation
#if os(iOS) || os(tvOS) || os (Linux)
+// swiftlint:disable type_name function_parameter_count
struct sf_hdtr { }
private func sendfileImpl(_ source: UnsafeMutablePointer, _ target: Int32, _: off_t, _: UnsafeMutablePointer, _: UnsafeMutablePointer, _: Int32) -> Int32 {
@@ -27,7 +28,7 @@ import Foundation
guard writeResult > 0 else {
return Int32(writeResult)
}
- writeCounter = writeCounter + writeResult
+ writeCounter += writeResult
}
}
}
@@ -35,7 +36,7 @@ import Foundation
extension Socket {
- public func writeFile(_ file: String.File) throws -> Void {
+ public func writeFile(_ file: String.File) throws {
var offset: off_t = 0
var sf: sf_hdtr = sf_hdtr()
@@ -49,5 +50,4 @@ extension Socket {
throw SocketError.writeFailed("sendfile: " + Errno.description())
}
}
-
}
diff --git a/Sources/Socket+Server.swift b/XCode/Sources/Socket+Server.swift
similarity index 96%
rename from Sources/Socket+Server.swift
rename to XCode/Sources/Socket+Server.swift
index 300712da..443bfbe8 100644
--- a/Sources/Socket+Server.swift
+++ b/XCode/Sources/Socket+Server.swift
@@ -9,6 +9,7 @@ import Foundation
extension Socket {
+ // swiftlint:disable function_body_length
/// - Parameters:
/// - listenAddress: String representation of the address the socket should accept
/// connections from. It should be in IPv4 format if forceIPv4 == true,
@@ -40,14 +41,14 @@ extension Socket {
sin_family: sa_family_t(AF_INET),
sin_port: port.bigEndian,
sin_addr: in_addr(s_addr: in_addr_t(0)),
- sin_zero:(0, 0, 0, 0, 0, 0, 0, 0))
+ sin_zero: (0, 0, 0, 0, 0, 0, 0, 0))
#else
var addr = sockaddr_in(
sin_len: UInt8(MemoryLayout.stride),
sin_family: UInt8(AF_INET),
sin_port: port.bigEndian,
sin_addr: in_addr(s_addr: in_addr_t(0)),
- sin_zero:(0, 0, 0, 0, 0, 0, 0, 0))
+ sin_zero: (0, 0, 0, 0, 0, 0, 0, 0))
#endif
if let address = listenAddress {
if address.withCString({ cstring in inet_pton(AF_INET, cstring, &addr.sin_addr) }) == 1 {
diff --git a/Sources/Socket.swift b/XCode/Sources/Socket.swift
similarity index 93%
rename from Sources/Socket.swift
rename to XCode/Sources/Socket.swift
index 54925356..0cc27aa9 100644
--- a/Sources/Socket.swift
+++ b/XCode/Sources/Socket.swift
@@ -21,12 +21,12 @@ public enum SocketError: Error {
case getSockNameFailed(String)
}
+// swiftlint: disable identifier_name
open class Socket: Hashable, Equatable {
let socketFileDescriptor: Int32
private var shutdown = false
-
public init(socketFileDescriptor: Int32) {
self.socketFileDescriptor = socketFileDescriptor
}
@@ -111,14 +111,14 @@ open class Socket: Hashable, Equatable {
var sent = 0
while sent < length {
#if os(Linux)
- let s = send(self.socketFileDescriptor, pointer + sent, Int(length - sent), Int32(MSG_NOSIGNAL))
+ let result = send(self.socketFileDescriptor, pointer + sent, Int(length - sent), Int32(MSG_NOSIGNAL))
#else
- let s = write(self.socketFileDescriptor, pointer + sent, Int(length - sent))
+ let result = write(self.socketFileDescriptor, pointer + sent, Int(length - sent))
#endif
- if s <= 0 {
+ if result <= 0 {
throw SocketError.writeFailed(Errno.description())
}
- sent += s
+ sent += result
}
}
@@ -195,11 +195,11 @@ open class Socket: Hashable, Equatable {
public func readLine() throws -> String {
var characters: String = ""
- var n: UInt8 = 0
+ var index: UInt8 = 0
repeat {
- n = try self.read()
- if n > Socket.CR { characters.append(Character(UnicodeScalar(n))) }
- } while n != Socket.NL
+ index = try self.read()
+ if index > Socket.CR { characters.append(Character(UnicodeScalar(index))) }
+ } while index != Socket.NL
return characters
}
@@ -228,9 +228,9 @@ open class Socket: Hashable, Equatable {
public class func close(_ socket: Int32) {
#if os(Linux)
- let _ = Glibc.close(socket)
+ _ = Glibc.close(socket)
#else
- let _ = Darwin.close(socket)
+ _ = Darwin.close(socket)
#endif
}
}
diff --git a/Sources/String+BASE64.swift b/XCode/Sources/String+BASE64.swift
similarity index 55%
rename from Sources/String+BASE64.swift
rename to XCode/Sources/String+BASE64.swift
index f0afa3ac..0f8ce533 100644
--- a/Sources/String+BASE64.swift
+++ b/XCode/Sources/String+BASE64.swift
@@ -7,7 +7,6 @@
import Foundation
-
extension String {
private static let CODES = [UInt8]("ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/=".utf8)
@@ -20,25 +19,25 @@ extension String {
var tmp: UInt8
for index in stride(from: 0, to: data.count, by: 3) {
let byte = data[index]
- tmp = (byte & 0xFC) >> 2;
+ tmp = (byte & 0xFC) >> 2
result.append(CODES[Int(tmp)])
- tmp = (byte & 0x03) << 4;
+ tmp = (byte & 0x03) << 4
if index + 1 < data.count {
- tmp |= (data[index + 1] & 0xF0) >> 4;
- result.append(CODES[Int(tmp)]);
- tmp = (data[index + 1] & 0x0F) << 2;
- if (index + 2 < data.count) {
- tmp |= (data[index + 2] & 0xC0) >> 6;
- result.append(CODES[Int(tmp)]);
- tmp = data[index + 2] & 0x3F;
- result.append(CODES[Int(tmp)]);
- } else {
- result.append(CODES[Int(tmp)]);
- result.append(contentsOf: [UInt8]("=".utf8));
+ tmp |= (data[index + 1] & 0xF0) >> 4
+ result.append(CODES[Int(tmp)])
+ tmp = (data[index + 1] & 0x0F) << 2
+ if index + 2 < data.count {
+ tmp |= (data[index + 2] & 0xC0) >> 6
+ result.append(CODES[Int(tmp)])
+ tmp = data[index + 2] & 0x3F
+ result.append(CODES[Int(tmp)])
+ } else {
+ result.append(CODES[Int(tmp)])
+ result.append(contentsOf: [UInt8]("=".utf8))
}
} else {
- result.append(CODES[Int(tmp)]);
- result.append(contentsOf: [UInt8]("==".utf8));
+ result.append(CODES[Int(tmp)])
+ result.append(contentsOf: [UInt8]("==".utf8))
}
}
return String(bytes: result, encoding: .utf8)
diff --git a/Sources/String+File.swift b/XCode/Sources/String+File.swift
similarity index 97%
rename from Sources/String+File.swift
rename to XCode/Sources/String+File.swift
index b4450022..65bdf88c 100644
--- a/Sources/String+File.swift
+++ b/XCode/Sources/String+File.swift
@@ -7,7 +7,6 @@
import Foundation
-
extension String {
public enum FileError: Error {
@@ -22,7 +21,7 @@ extension String {
self.pointer = pointer
}
- public func close() -> Void {
+ public func close() {
fclose(pointer)
}
@@ -47,7 +46,7 @@ extension String {
throw FileError.error(0)
}
- public func write(_ data: [UInt8]) throws -> Void {
+ public func write(_ data: [UInt8]) throws {
if data.count <= 0 {
return
}
@@ -89,7 +88,7 @@ extension String {
public func exists() throws -> Bool {
return try self.withStat {
- if let _ = $0 {
+ if $0 != nil {
return true
}
return false
diff --git a/Sources/String+Misc.swift b/XCode/Sources/String+Misc.swift
similarity index 84%
rename from Sources/String+Misc.swift
rename to XCode/Sources/String+Misc.swift
index fcfdd9cb..75c8876e 100644
--- a/Sources/String+Misc.swift
+++ b/XCode/Sources/String+Misc.swift
@@ -7,14 +7,13 @@
import Foundation
-
extension String {
public func unquote() -> String {
- var scalars = self.unicodeScalars;
+ var scalars = self.unicodeScalars
if scalars.first == "\"" && scalars.last == "\"" && scalars.count >= 2 {
- scalars.removeFirst();
- scalars.removeLast();
+ scalars.removeFirst()
+ scalars.removeLast()
return String(scalars)
}
return self
@@ -32,5 +31,4 @@ extension UnicodeScalar {
}
return nil
}
-
}
diff --git a/Sources/String+SHA1.swift b/XCode/Sources/String+SHA1.swift
similarity index 93%
rename from Sources/String+SHA1.swift
rename to XCode/Sources/String+SHA1.swift
index cf85ebf2..fe356701 100644
--- a/Sources/String+SHA1.swift
+++ b/XCode/Sources/String+SHA1.swift
@@ -7,7 +7,7 @@
import Foundation
-
+// swiftlint:disable identifier_name function_body_length
public struct SHA1 {
public static func hash(_ input: [UInt8]) -> [UInt8] {
@@ -51,15 +51,15 @@ public struct SHA1 {
// break chunk into sixteen 32-bit big-endian words w[i], 0 ≤ i ≤ 15
- for i in 0...15 {
- let value = chunk.withUnsafeBufferPointer({ UnsafePointer(OpaquePointer($0.baseAddress! + (i*4))).pointee})
+ for index in 0...15 {
+ let value = chunk.withUnsafeBufferPointer({ UnsafePointer(OpaquePointer($0.baseAddress! + (index*4))).pointee})
words.append(value.bigEndian)
}
// Extend the sixteen 32-bit words into eighty 32-bit words:
- for i in 16...79 {
- let value: UInt32 = ((words[i-3]) ^ (words[i-8]) ^ (words[i-14]) ^ (words[i-16]))
+ for index in 16...79 {
+ let value: UInt32 = ((words[index-3]) ^ (words[index-8]) ^ (words[index-14]) ^ (words[index-16]))
words.append(rotateLeft(value, 1))
}
diff --git a/Sources/WebSockets.swift b/XCode/Sources/WebSockets.swift
similarity index 86%
rename from Sources/WebSockets.swift
rename to XCode/Sources/WebSockets.swift
index 097c7752..3abeafa4 100644
--- a/Sources/WebSockets.swift
+++ b/XCode/Sources/WebSockets.swift
@@ -14,21 +14,22 @@ public func websocket(_ text: @escaping (WebSocketSession, String) -> Void,
return websocket(text: text, binary: binary, pong: pong)
}
+// swiftlint:disable function_body_length
public func websocket(
text: ((WebSocketSession, String) -> Void)? = nil,
binary: ((WebSocketSession, [UInt8]) -> Void)? = nil,
pong: ((WebSocketSession, [UInt8]) -> Void)? = nil,
connected: ((WebSocketSession) -> Void)? = nil,
disconnected: ((WebSocketSession) -> Void)? = nil) -> ((HttpRequest) -> HttpResponse) {
- return { r in
- guard r.hasTokenForHeader("upgrade", token: "websocket") else {
- return .badRequest(.text("Invalid value of 'Upgrade' header: \(r.headers["upgrade"] ?? "unknown")"))
+ return { request in
+ guard request.hasTokenForHeader("upgrade", token: "websocket") else {
+ return .badRequest(.text("Invalid value of 'Upgrade' header: \(request.headers["upgrade"] ?? "unknown")"))
}
- guard r.hasTokenForHeader("connection", token: "upgrade") else {
- return .badRequest(.text("Invalid value of 'Connection' header: \(r.headers["connection"] ?? "unknown")"))
+ guard request.hasTokenForHeader("connection", token: "upgrade") else {
+ return .badRequest(.text("Invalid value of 'Connection' header: \(request.headers["connection"] ?? "unknown")"))
}
- guard let secWebSocketKey = r.headers["sec-websocket-key"] else {
- return .badRequest(.text("Invalid value of 'Sec-Websocket-Key' header: \(r.headers["sec-websocket-key"] ?? "unknown")"))
+ guard let secWebSocketKey = request.headers["sec-websocket-key"] else {
+ return .badRequest(.text("Invalid value of 'Sec-Websocket-Key' header: \(request.headers["sec-websocket-key"] ?? "unknown")"))
}
let protocolSessionClosure: ((Socket) -> Void) = { socket in
let session = WebSocketSession(socket)
@@ -102,7 +103,6 @@ public func websocket(
if let handlePong = pong {
handlePong(session, frame.payload)
}
- break
}
}
@@ -147,7 +147,7 @@ public func websocket(
}
}
-public class WebSocketSession: Hashable, Equatable {
+public class WebSocketSession: Hashable, Equatable {
public enum WsError: Error { case unknownOpCode(String), unMaskedFrame(String), protocolError(String), invalidUTF8(String) }
public enum OpCode: UInt8 { case `continue` = 0x00, close = 0x08, ping = 0x09, pong = 0x0A, text = 0x01, binary = 0x02 }
@@ -173,15 +173,15 @@ public class WebSocketSession: Hashable, Equatable {
socket.close()
}
- public func writeText(_ text: String) -> Void {
+ public func writeText(_ text: String) {
self.writeFrame(ArraySlice(text.utf8), OpCode.text)
}
- public func writeBinary(_ binary: [UInt8]) -> Void {
+ public func writeBinary(_ binary: [UInt8]) {
self.writeBinary(ArraySlice(binary))
}
- public func writeBinary(_ binary: ArraySlice) -> Void {
+ public func writeBinary(_ binary: ArraySlice) {
self.writeFrame(binary, OpCode.binary)
}
@@ -206,25 +206,26 @@ public class WebSocketSession: Hashable, Equatable {
var encodedBytes = [UInt8]()
switch len {
case 0...125:
- encodedBytes.append(encodedLngth | UInt8(len));
+ encodedBytes.append(encodedLngth | UInt8(len))
case 126...UInt64(UINT16_MAX):
- encodedBytes.append(encodedLngth | 0x7E);
- encodedBytes.append(UInt8(len >> 8 & 0xFF));
- encodedBytes.append(UInt8(len >> 0 & 0xFF));
+ encodedBytes.append(encodedLngth | 0x7E)
+ encodedBytes.append(UInt8(len >> 8 & 0xFF))
+ encodedBytes.append(UInt8(len >> 0 & 0xFF))
default:
- encodedBytes.append(encodedLngth | 0x7F);
- encodedBytes.append(UInt8(len >> 56 & 0xFF));
- encodedBytes.append(UInt8(len >> 48 & 0xFF));
- encodedBytes.append(UInt8(len >> 40 & 0xFF));
- encodedBytes.append(UInt8(len >> 32 & 0xFF));
- encodedBytes.append(UInt8(len >> 24 & 0xFF));
- encodedBytes.append(UInt8(len >> 16 & 0xFF));
- encodedBytes.append(UInt8(len >> 08 & 0xFF));
- encodedBytes.append(UInt8(len >> 00 & 0xFF));
+ encodedBytes.append(encodedLngth | 0x7F)
+ encodedBytes.append(UInt8(len >> 56 & 0xFF))
+ encodedBytes.append(UInt8(len >> 48 & 0xFF))
+ encodedBytes.append(UInt8(len >> 40 & 0xFF))
+ encodedBytes.append(UInt8(len >> 32 & 0xFF))
+ encodedBytes.append(UInt8(len >> 24 & 0xFF))
+ encodedBytes.append(UInt8(len >> 16 & 0xFF))
+ encodedBytes.append(UInt8(len >> 08 & 0xFF))
+ encodedBytes.append(UInt8(len >> 00 & 0xFF))
}
return encodedBytes
}
+ // swiftlint:disable function_body_length
public func readFrame() throws -> Frame {
let frm = Frame()
let fst = try socket.read()
@@ -280,8 +281,8 @@ public class WebSocketSession: Hashable, Equatable {
let mask = [try socket.read(), try socket.read(), try socket.read(), try socket.read()]
//Read payload all at once, then apply mask (calling `socket.read` byte-by-byte is super slow).
frm.payload = try socket.read(length: Int(len))
- for i in 0.. Bool {
+public func == (webSocketSession1: WebSocketSession, webSocketSession2: WebSocketSession) -> Bool {
return webSocketSession1.socket == webSocketSession2.socket
}
diff --git a/XCode/Swifter.xcodeproj/project.pbxproj b/XCode/Swifter.xcodeproj/project.pbxproj
index 9d8d83b7..657944fe 100644
--- a/XCode/Swifter.xcodeproj/project.pbxproj
+++ b/XCode/Swifter.xcodeproj/project.pbxproj
@@ -24,6 +24,7 @@
043660E921FED51B00497989 /* SwifterTestsWebSocketSession.swift in Sources */ = {isa = PBXBuildFile; fileRef = 7C4785E81C71D15600A9FE73 /* SwifterTestsWebSocketSession.swift */; };
043660EA21FED51E00497989 /* IOSafetyTests.swift in Sources */ = {isa = PBXBuildFile; fileRef = 0858E7F31D68BB2600491CD1 /* IOSafetyTests.swift */; };
043660EB21FED52000497989 /* MimeTypesTests.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6A0D4511204E9988000A0726 /* MimeTypesTests.swift */; };
+ 047F1F02226AB9AD00909B95 /* XCTestManifests.swift in Sources */ = {isa = PBXBuildFile; fileRef = 7B912F49220507D00062C360 /* XCTestManifests.swift */; };
0858E7F81D68BC2600491CD1 /* PingServer.swift in Sources */ = {isa = PBXBuildFile; fileRef = 0858E7F61D68BC2600491CD1 /* PingServer.swift */; };
2659FC1A1DADC077003F3930 /* String+File.swift in Sources */ = {isa = PBXBuildFile; fileRef = 7C377E161D964B6A009C6148 /* String+File.swift */; };
269B47881D3AAAE20042D137 /* HttpResponse.swift in Sources */ = {isa = PBXBuildFile; fileRef = 7C76B6EF1D2C44F30030FC98 /* HttpResponse.swift */; };
@@ -344,8 +345,7 @@
7C377E161D964B6A009C6148 /* String+File.swift */,
6AE2FF702048011A00302EC4 /* MimeTypes.swift */,
);
- name = Sources;
- path = ../Sources;
+ path = Sources;
sourceTree = "";
};
7C839B6519422CFF003A6950 = {
@@ -526,6 +526,7 @@
7AE893E31C05127900A29F63 /* Frameworks */,
7AE893E41C05127900A29F63 /* Headers */,
7AE893E51C05127900A29F63 /* Resources */,
+ 047F1F00226AB51800909B95 /* Swiftlint */,
);
buildRules = (
);
@@ -734,6 +735,27 @@
};
/* End PBXResourcesBuildPhase section */
+/* Begin PBXShellScriptBuildPhase section */
+ 047F1F00226AB51800909B95 /* Swiftlint */ = {
+ isa = PBXShellScriptBuildPhase;
+ buildActionMask = 2147483647;
+ files = (
+ );
+ inputFileListPaths = (
+ );
+ inputPaths = (
+ );
+ name = Swiftlint;
+ outputFileListPaths = (
+ );
+ outputPaths = (
+ );
+ runOnlyForDeploymentPostprocessing = 0;
+ shellPath = /bin/sh;
+ shellScript = "if which swiftlint >/dev/null; then\n swiftlint lint --config ../.swiftlint.yml\nelse\n echo \"warning: SwiftLint not installed, download from https://github.com/realm/SwiftLint\"\nfi\n";
+ };
+/* End PBXShellScriptBuildPhase section */
+
/* Begin PBXSourcesBuildPhase section */
043660BE21FED34100497989 /* Sources */ = {
isa = PBXSourcesBuildPhase;
@@ -744,7 +766,7 @@
043660D221FED36800497989 /* IOSafetyTests.swift in Sources */,
043660D021FED35B00497989 /* SwifterTestsStringExtensions.swift in Sources */,
043660CD21FED35200497989 /* SwifterTestsHttpRouter.swift in Sources */,
- 542604AE226A33540065B874 /* XCTestManifests.swift in Sources */,
+ 047F1F02226AB9AD00909B95 /* XCTestManifests.swift in Sources */,
043660CE21FED35500497989 /* SwifterTestsHttpParser.swift in Sources */,
043660D521FED36C00497989 /* MimeTypesTests.swift in Sources */,
);
diff --git a/XCode/SwifterSampleiOS/AppDelegate.swift b/XCode/SwifterSampleiOS/AppDelegate.swift
index 7ea67f5b..6143fa29 100644
--- a/XCode/SwifterSampleiOS/AppDelegate.swift
+++ b/XCode/SwifterSampleiOS/AppDelegate.swift
@@ -12,7 +12,7 @@ import Swifter
class AppDelegate: UIResponder, UIApplicationDelegate {
var window: UIWindow?
- func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplication.LaunchOptionsKey : Any]? = nil) -> Bool {
+ func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplication.LaunchOptionsKey: Any]? = nil) -> Bool {
return true
}
}
diff --git a/XCode/Tests/IOSafetyTests.swift b/XCode/Tests/IOSafetyTests.swift
index 78a4234a..3e9e1984 100644
--- a/XCode/Tests/IOSafetyTests.swift
+++ b/XCode/Tests/IOSafetyTests.swift
@@ -36,8 +36,8 @@ class IOSafetyTests: XCTestCase {
}
}
server.stop()
- } catch let e {
- XCTFail("\(cpt): \(e)")
+ } catch let error {
+ XCTFail("\(cpt): \(error)")
}
}
}
diff --git a/XCode/Tests/MimeTypesTests.swift b/XCode/Tests/MimeTypesTests.swift
index b7b715ec..bad13e10 100644
--- a/XCode/Tests/MimeTypesTests.swift
+++ b/XCode/Tests/MimeTypesTests.swift
@@ -37,4 +37,3 @@ class MimeTypeTests: XCTestCase {
}
}
-
diff --git a/XCode/Tests/PingServer.swift b/XCode/Tests/PingServer.swift
index 909eddea..e07ad729 100644
--- a/XCode/Tests/PingServer.swift
+++ b/XCode/Tests/PingServer.swift
@@ -20,7 +20,7 @@ extension HttpServer {
}
}
-let defaultLocalhost = URL(string:"http://localhost:8080")!
+let defaultLocalhost = URL(string: "http://localhost:8080")!
// Client
extension URLSession {
@@ -61,7 +61,7 @@ extension URLSession {
}
func signalIfPongReceived(_ semaphore: DispatchSemaphore, hostURL: URL) {
- pingTask(hostURL: hostURL) { data, response, error in
+ pingTask(hostURL: hostURL) { _, response, _ in
if let httpResponse = response as? HTTPURLResponse, httpResponse.statusCode == 200 {
semaphore.signal()
} else {
diff --git a/XCode/Tests/SwifterTestsHttpParser.swift b/XCode/Tests/SwifterTestsHttpParser.swift
index 07b9588e..212f7754 100644
--- a/XCode/Tests/SwifterTestsHttpParser.swift
+++ b/XCode/Tests/SwifterTestsHttpParser.swift
@@ -18,8 +18,8 @@ class SwifterTestsHttpParser: XCTestCase {
/// Create an array to hold the read and write sockets that pipe creates
var fds = [Int32](repeating: 0, count: 2)
fds.withUnsafeMutableBufferPointer { ptr in
- let rv = pipe(ptr.baseAddress!)
- guard rv >= 0 else { fatalError("Pipe error!") }
+ let received = pipe(ptr.baseAddress!)
+ guard received >= 0 else { fatalError("Pipe error!") }
}
// Extract the read and write handles into friendly variables
@@ -50,64 +50,65 @@ class SwifterTestsHttpParser: XCTestCase {
}
}
+ // swiftlint:disable function_body_length
func testParser() {
let parser = HttpParser()
do {
- let _ = try parser.readHttpRequest(TestSocket(""))
+ _ = try parser.readHttpRequest(TestSocket(""))
XCTAssert(false, "Parser should throw an error if socket is empty.")
} catch { }
do {
- let _ = try parser.readHttpRequest(TestSocket("12345678"))
+ _ = try parser.readHttpRequest(TestSocket("12345678"))
XCTAssert(false, "Parser should throw an error if status line has single token.")
} catch { }
do {
- let _ = try parser.readHttpRequest(TestSocket("GET HTTP/1.0"))
+ _ = try parser.readHttpRequest(TestSocket("GET HTTP/1.0"))
XCTAssert(false, "Parser should throw an error if status line has not enough tokens.")
} catch { }
do {
- let _ = try parser.readHttpRequest(TestSocket("GET / HTTP/1.0"))
+ _ = try parser.readHttpRequest(TestSocket("GET / HTTP/1.0"))
XCTAssert(false, "Parser should throw an error if there is no next line symbol.")
} catch { }
do {
- let _ = try parser.readHttpRequest(TestSocket("GET / HTTP/1.0"))
+ _ = try parser.readHttpRequest(TestSocket("GET / HTTP/1.0"))
XCTAssert(false, "Parser should throw an error if there is no next line symbol.")
} catch { }
do {
- let _ = try parser.readHttpRequest(TestSocket("GET / HTTP/1.0\r"))
+ _ = try parser.readHttpRequest(TestSocket("GET / HTTP/1.0\r"))
XCTAssert(false, "Parser should throw an error if there is no next line symbol.")
} catch { }
do {
- let _ = try parser.readHttpRequest(TestSocket("GET / HTTP/1.0\n"))
+ _ = try parser.readHttpRequest(TestSocket("GET / HTTP/1.0\n"))
XCTAssert(false, "Parser should throw an error if there is no 'Content-Length' header.")
} catch { }
do {
- let _ = try parser.readHttpRequest(TestSocket("GET / HTTP/1.0\r\nContent-Length: 0\r\n\r\n"))
+ _ = try parser.readHttpRequest(TestSocket("GET / HTTP/1.0\r\nContent-Length: 0\r\n\r\n"))
} catch {
XCTAssert(false, "Parser should not throw any errors if there is a valid 'Content-Length' header.")
}
do {
- let _ = try parser.readHttpRequest(TestSocket("GET / HTTP/1.0\nContent-Length: 0\r\n\n"))
+ _ = try parser.readHttpRequest(TestSocket("GET / HTTP/1.0\nContent-Length: 0\r\n\n"))
} catch {
XCTAssert(false, "Parser should not throw any errors if there is a valid 'Content-Length' header.")
}
do {
- let _ = try parser.readHttpRequest(TestSocket("GET / HTTP/1.0\nContent-Length: 5\n\n12345"))
+ _ = try parser.readHttpRequest(TestSocket("GET / HTTP/1.0\nContent-Length: 5\n\n12345"))
} catch {
XCTAssert(false, "Parser should not throw any errors if there is a valid 'Content-Length' header.")
}
do {
- let _ = try parser.readHttpRequest(TestSocket("GET / HTTP/1.0\nContent-Length: 10\r\n\n"))
+ _ = try parser.readHttpRequest(TestSocket("GET / HTTP/1.0\nContent-Length: 10\r\n\n"))
XCTAssert(false, "Parser should throw an error if request' body is too short.")
} catch { }
@@ -148,21 +149,21 @@ class SwifterTestsHttpParser: XCTestCase {
XCTAssert(request.body == unicodeBytes, "Request body must be correct")
} catch { }
- var r = try? parser.readHttpRequest(TestSocket("GET /open?link=https://www.youtube.com/watch?v=D2cUBG4PnOA HTTP/1.0\nContent-Length: 10\n\n1234567890"))
+ var resp = try? parser.readHttpRequest(TestSocket("GET /open?link=https://www.youtube.com/watch?v=D2cUBG4PnOA HTTP/1.0\nContent-Length: 10\n\n1234567890"))
- XCTAssertEqual(r?.queryParams.filter({ $0.0 == "link"}).first?.1, "https://www.youtube.com/watch?v=D2cUBG4PnOA")
- XCTAssertEqual(r?.method, "GET", "Parser should extract HTTP method name from the status line.")
- XCTAssertEqual(r?.path, "/open?link=https://www.youtube.com/watch?v=D2cUBG4PnOA", "Parser should extract HTTP path value from the status line.")
- XCTAssertEqual(r?.headers["content-length"], "10", "Parser should extract Content-Length header value.")
+ XCTAssertEqual(resp?.queryParams.filter({ $0.0 == "link"}).first?.1, "https://www.youtube.com/watch?v=D2cUBG4PnOA")
+ XCTAssertEqual(resp?.method, "GET", "Parser should extract HTTP method name from the status line.")
+ XCTAssertEqual(resp?.path, "/open?link=https://www.youtube.com/watch?v=D2cUBG4PnOA", "Parser should extract HTTP path value from the status line.")
+ XCTAssertEqual(resp?.headers["content-length"], "10", "Parser should extract Content-Length header value.")
- r = try? parser.readHttpRequest(TestSocket("POST / HTTP/1.0\nContent-Length: 10\n\n1234567890"))
- XCTAssertEqual(r?.method, "POST", "Parser should extract HTTP method name from the status line.")
+ resp = try? parser.readHttpRequest(TestSocket("POST / HTTP/1.0\nContent-Length: 10\n\n1234567890"))
+ XCTAssertEqual(resp?.method, "POST", "Parser should extract HTTP method name from the status line.")
- r = try? parser.readHttpRequest(TestSocket("GET / HTTP/1.0\nHeader1: 1:1:34\nHeader2: 12345\nContent-Length: 0\n\n"))
- XCTAssertEqual(r?.headers["header1"], "1:1:34", "Parser should properly extract header name and value in case the value has ':' character.")
+ resp = try? parser.readHttpRequest(TestSocket("GET / HTTP/1.0\nHeader1: 1:1:34\nHeader2: 12345\nContent-Length: 0\n\n"))
+ XCTAssertEqual(resp?.headers["header1"], "1:1:34", "Parser should properly extract header name and value in case the value has ':' character.")
- r = try? parser.readHttpRequest(TestSocket("GET / HTTP/1.0\nHeader1: 1\nHeader2: 2\nContent-Length: 0\n\n"))
- XCTAssertEqual(r?.headers["header1"], "1", "Parser should extract multiple headers from the request.")
- XCTAssertEqual(r?.headers["header2"], "2", "Parser should extract multiple headers from the request.")
+ resp = try? parser.readHttpRequest(TestSocket("GET / HTTP/1.0\nHeader1: 1\nHeader2: 2\nContent-Length: 0\n\n"))
+ XCTAssertEqual(resp?.headers["header1"], "1", "Parser should extract multiple headers from the request.")
+ XCTAssertEqual(resp?.headers["header2"], "2", "Parser should extract multiple headers from the request.")
}
}
diff --git a/XCode/Tests/SwifterTestsHttpRouter.swift b/XCode/Tests/SwifterTestsHttpRouter.swift
index 6a863fbb..a9b80b38 100644
--- a/XCode/Tests/SwifterTestsHttpRouter.swift
+++ b/XCode/Tests/SwifterTestsHttpRouter.swift
@@ -15,7 +15,7 @@ class SwifterTestsHttpRouter: XCTestCase {
let router = HttpRouter()
- router.register(nil, path: "/", handler: { r in
+ router.register(nil, path: "/", handler: { _ in
return .ok(.html("OK"))
})
@@ -26,7 +26,7 @@ class SwifterTestsHttpRouter: XCTestCase {
let router = HttpRouter()
- router.register(nil, path: "/a/b/c/d", handler: { r in
+ router.register(nil, path: "/a/b/c/d", handler: { _ in
return .ok(.html("OK"))
})
@@ -41,7 +41,7 @@ class SwifterTestsHttpRouter: XCTestCase {
let router = HttpRouter()
- router.register(nil, path: "/a/*/c/d", handler: { r in
+ router.register(nil, path: "/a/*/c/d", handler: { _ in
return .ok(.html("OK"))
})
@@ -57,7 +57,7 @@ class SwifterTestsHttpRouter: XCTestCase {
let router = HttpRouter()
- router.register(nil, path: "/a/:arg1/:arg2/b/c/d/:arg3", handler: { r in
+ router.register(nil, path: "/a/:arg1/:arg2/b/c/d/:arg3", handler: { _ in
return .ok(.html("OK"))
})
@@ -73,7 +73,7 @@ class SwifterTestsHttpRouter: XCTestCase {
let router = HttpRouter()
- router.register(nil, path: "/a/**/e/f/g", handler: { r in
+ router.register(nil, path: "/a/**/e/f/g", handler: { _ in
return .ok(.html("OK"))
})
@@ -87,15 +87,14 @@ class SwifterTestsHttpRouter: XCTestCase {
let router = HttpRouter()
- router.register(nil, path: "/a/b/", handler: { r in
+ router.register(nil, path: "/a/b/", handler: { _ in
return .ok(.html("OK"))
})
- router.register(nil, path: "/a/b/:var", handler: { r in
+ router.register(nil, path: "/a/b/:var", handler: { _ in
return .ok(.html("OK"))
})
-
XCTAssertNil(router.route(nil, path: "/"))
XCTAssertNil(router.route(nil, path: "/a"))
XCTAssertNotNil(router.route(nil, path: "/a/b/"))
@@ -110,7 +109,7 @@ class SwifterTestsHttpRouter: XCTestCase {
let router = HttpRouter()
- router.register(nil, path: "/a/<>/^", handler: { r in
+ router.register(nil, path: "/a/<>/^", handler: { _ in
return .ok(.html("OK"))
})
XCTAssertNil(router.route(nil, path: "/"))
@@ -160,7 +159,7 @@ class SwifterTestsHttpRouter: XCTestCase {
let firstVariableRouteExpectation = expectation(description: "First Variable Route")
var foundFirstVariableRoute = false
- router.register("GET", path: "a/:id") { request in
+ router.register("GET", path: "a/:id") { _ in
foundFirstVariableRoute = true
firstVariableRouteExpectation.fulfill()
return HttpResponse.accepted
@@ -195,7 +194,7 @@ class SwifterTestsHttpRouter: XCTestCase {
let firstVariableRouteExpectation = expectation(description: "First Variable Route")
var foundFirstVariableRoute = false
- router.register("GET", path: "/a/:id") { request in
+ router.register("GET", path: "/a/:id") { _ in
foundFirstVariableRoute = true
firstVariableRouteExpectation.fulfill()
return HttpResponse.accepted
@@ -211,7 +210,7 @@ class SwifterTestsHttpRouter: XCTestCase {
let thirdVariableRouteExpectation = expectation(description: "Third Variable Route")
var foundThirdVariableRoute = false
- router.register("GET", path: "/a/:id/b") { request in
+ router.register("GET", path: "/a/:id/b") { _ in
foundThirdVariableRoute = true
thirdVariableRouteExpectation.fulfill()
return HttpResponse.accepted
@@ -244,7 +243,7 @@ class SwifterTestsHttpRouter: XCTestCase {
let firstVariableRouteExpectation = expectation(description: "First Variable Route")
var foundFirstVariableRoute = false
- router.register("GET", path: "/a/b/c/d/e") { request in
+ router.register("GET", path: "/a/b/c/d/e") { _ in
foundFirstVariableRoute = true
firstVariableRouteExpectation.fulfill()
return HttpResponse.accepted
diff --git a/XCode/Tests/SwifterTestsWebSocketSession.swift b/XCode/Tests/SwifterTestsWebSocketSession.swift
index 9607a798..360aec03 100644
--- a/XCode/Tests/SwifterTestsWebSocketSession.swift
+++ b/XCode/Tests/SwifterTestsWebSocketSession.swift
@@ -22,18 +22,19 @@ class SwifterTestsWebSocketSession: XCTestCase {
override func read() throws -> UInt8 {
if offset < content.count {
let value = self.content[offset]
- offset = offset + 1
+ offset += 1
return value
}
throw SocketError.recvFailed("")
}
}
+ // swiftlint:disable function_body_length
func testParser() {
do {
let session = WebSocketSession(TestSocket([0]))
- let _ = try session.readFrame()
+ _ = try session.readFrame()
XCTAssert(false, "Parser should throw an error if socket has not enough data for a frame.")
} catch {
XCTAssert(true, "Parser should throw an error if socket has not enough data for a frame.")
@@ -41,7 +42,7 @@ class SwifterTestsWebSocketSession: XCTestCase {
do {
let session = WebSocketSession(TestSocket([0b0000_0001, 0b0000_0000, 0, 0, 0, 0]))
- let _ = try session.readFrame()
+ _ = try session.readFrame()
XCTAssert(false, "Parser should not accept unmasked frames.")
} catch WebSocketSession.WsError.unMaskedFrame {
XCTAssert(true, "Parse should throw UnMaskedFrame error for unmasked message.")
@@ -85,30 +86,30 @@ class SwifterTestsWebSocketSession: XCTestCase {
let session = WebSocketSession(TestSocket([0b1000_1000, 0b1000_0000, 0, 0, 0, 0]))
let frame = try session.readFrame()
XCTAssertEqual(frame.opcode, WebSocketSession.OpCode.close, "Parser should accept Close opcode.")
- } catch let e {
- XCTAssert(false, "Parser should accept Close opcode without any errors. \(e)")
+ } catch let error {
+ XCTAssert(false, "Parser should accept Close opcode without any errors. \(error)")
}
do {
let session = WebSocketSession(TestSocket([0b1000_1001, 0b1000_0000, 0, 0, 0, 0]))
let frame = try session.readFrame()
XCTAssertEqual(frame.opcode, WebSocketSession.OpCode.ping, "Parser should accept Ping opcode.")
- } catch let e {
- XCTAssert(false, "Parser should accept Ping opcode without any errors. \(e)")
+ } catch let error {
+ XCTAssert(false, "Parser should accept Ping opcode without any errors. \(error)")
}
do {
let session = WebSocketSession(TestSocket([0b1000_1010, 0b1000_0000, 0, 0, 0, 0]))
let frame = try session.readFrame()
XCTAssertEqual(frame.opcode, WebSocketSession.OpCode.pong, "Parser should accept Pong opcode.")
- } catch let e {
- XCTAssert(false, "Parser should accept Pong opcode without any errors. \(e)")
+ } catch let error {
+ XCTAssert(false, "Parser should accept Pong opcode without any errors. \(error)")
}
for opcode in [3, 4, 5, 6, 7, 11, 12, 13, 14, 15] {
do {
let session = WebSocketSession(TestSocket([UInt8(opcode), 0b1000_0000, 0, 0, 0, 0]))
- let _ = try session.readFrame()
+ _ = try session.readFrame()
XCTAssert(false, "Parse should throw an error for unknown opcode: \(opcode)")
} catch WebSocketSession.WsError.unknownOpCode(_) {
XCTAssert(true, "Parse should throw UnknownOpCode error for unknown opcode.")