From dfdb80c2502db365d432931d3e406e08ca9e355d Mon Sep 17 00:00:00 2001 From: Tanner Nelson Date: Thu, 16 Feb 2017 18:02:18 +0100 Subject: [PATCH] token + cleanup --- .../Authentication/Credentials/Custom.swift | 6 ---- .../Credentials/Identifier.swift | 33 ----------------- .../Authentication/Credentials/Token.swift | 35 +++++++++++-------- .../Authentication/Header/Authorization.swift | 8 ++--- Sources/Authentication/Header/Basic.swift | 13 ++++--- Sources/Authentication/Header/Bearer.swift | 6 ++-- Sources/Authentication/User/User.swift | 3 -- Tests/AuthenticationTests/ExampleTests.swift | 5 --- .../Utilities/AuthUser.swift | 12 ------- 9 files changed, 33 insertions(+), 88 deletions(-) delete mode 100644 Sources/Authentication/Credentials/Custom.swift delete mode 100644 Sources/Authentication/Credentials/Identifier.swift delete mode 100644 Sources/Authentication/User/User.swift diff --git a/Sources/Authentication/Credentials/Custom.swift b/Sources/Authentication/Credentials/Custom.swift deleted file mode 100644 index 87bcd47..0000000 --- a/Sources/Authentication/Credentials/Custom.swift +++ /dev/null @@ -1,6 +0,0 @@ -// MARK: Authenticatable - -public protocol CustomAuthenticatable: Authenticatable { - /// Returns the user matching the custom credential. - static func authenticate(custom: Crendentials) throws -> Self -} diff --git a/Sources/Authentication/Credentials/Identifier.swift b/Sources/Authentication/Credentials/Identifier.swift deleted file mode 100644 index 5629a6f..0000000 --- a/Sources/Authentication/Credentials/Identifier.swift +++ /dev/null @@ -1,33 +0,0 @@ -// MARK: Data structure - -import Node - -public struct Identifier: Crendentials { - let id: Node - - public init(id: Node) { - self.id = id - } -} - -// MARK: Authenticatable - -public protocol IdentifierAuthenticatable { - /// Return the user with the supplied id. - static func authenticate(_: Identifier) throws -> Self -} - - -// MARK: Entity conformance - -import Fluent - -extension IdentifierAuthenticatable where Self: Entity { - public static func authenticate(_ id: Identifier) throws -> Self { - guard let match = try Self.find(id.id) else { - throw AuthenticationError.invalidCredentials - } - - return match - } -} diff --git a/Sources/Authentication/Credentials/Token.swift b/Sources/Authentication/Credentials/Token.swift index d503018..759e20b 100644 --- a/Sources/Authentication/Credentials/Token.swift +++ b/Sources/Authentication/Credentials/Token.swift @@ -12,19 +12,17 @@ public struct Token: Crendentials { public protocol TokenAuthenticatable: Authenticatable { /// The token entity that contains a foreign key - /// pointer to the user table - associatedtype TokenType: TokenProtocol + /// pointer to the user table (or on the user table itself) + associatedtype TokenType /// Returns the user matching the supplied token. - static func authenticate(_: Token) throws -> Self -} + static func authenticate(_ token: Token) throws -> Self -public protocol TokenProtocol { + /// The column under which the tokens are stored static var tokenKey: String { get } - static func findUser(for: Token) throws -> U } -extension TokenProtocol { +extension TokenAuthenticatable { public static var tokenKey: String { return "token" } @@ -34,20 +32,27 @@ extension TokenProtocol { import Fluent -extension TokenAuthenticatable where Self: Entity { +extension TokenAuthenticatable where Self: Entity, Self.TokenType: Entity { public static func authenticate(_ token: Token) throws -> Self { - return try TokenType.findUser(for: token) + guard let user = try Self.query() + .join(Self.TokenType.self) + .filter(Self.TokenType.self, tokenKey, token.string) + .first() + else { + throw AuthenticationError.invalidCredentials + } + + return user } } -extension TokenProtocol where Self: Entity { - public static func findUser(for token: Token) throws -> U { - guard let user = try U.query() - .join(self) - .filter(self, tokenKey, token.string) +extension TokenAuthenticatable where Self: Entity, Self.TokenType: Entity, Self.TokenType == Self { + public static func authenticate(_ token: Token) throws -> Self { + guard let user = try Self.query() + .filter(tokenKey, token.string) .first() else { - throw AuthenticationError.invalidCredentials + throw AuthenticationError.invalidCredentials } return user diff --git a/Sources/Authentication/Header/Authorization.swift b/Sources/Authentication/Header/Authorization.swift index 78cb620..38cedb9 100644 --- a/Sources/Authentication/Header/Authorization.swift +++ b/Sources/Authentication/Header/Authorization.swift @@ -1,7 +1,7 @@ -public struct Authorization { - public let header: String +public struct AuthorizationHeader { + public let string: String - public init(header: String) { - self.header = header + public init(string: String) { + self.string = string } } diff --git a/Sources/Authentication/Header/Basic.swift b/Sources/Authentication/Header/Basic.swift index cc386d9..946ff13 100644 --- a/Sources/Authentication/Header/Basic.swift +++ b/Sources/Authentication/Header/Basic.swift @@ -1,22 +1,21 @@ import Core -extension Authorization { +extension AuthorizationHeader { public var basic: Password? { - guard let range = header.range(of: "Basic ") else { + guard let range = string.range(of: "Basic ") else { return nil } - let token = header.substring(from: range.upperBound) - + let token = string.substring(from: range.upperBound) let decodedToken = token.makeBytes().base64Decoded.string guard let separatorRange = decodedToken.range(of: ":") else { return nil } - let apiKeyID = decodedToken.substring(to: separatorRange.lowerBound) - let apiKeySecret = decodedToken.substring(from: separatorRange.upperBound) + let username = decodedToken.substring(to: separatorRange.lowerBound) + let password = decodedToken.substring(from: separatorRange.upperBound) - return Password(username: apiKeyID, password: apiKeySecret) + return Password(username: username, password: password) } } diff --git a/Sources/Authentication/Header/Bearer.swift b/Sources/Authentication/Header/Bearer.swift index 6fff8de..b1364e7 100644 --- a/Sources/Authentication/Header/Bearer.swift +++ b/Sources/Authentication/Header/Bearer.swift @@ -1,10 +1,10 @@ -extension Authorization { +extension AuthorizationHeader { public var bearer: Token? { - guard let range = header.range(of: "Bearer ") else { + guard let range = string.range(of: "Bearer ") else { return nil } - let token = header.substring(from: range.upperBound) + let token = string.substring(from: range.upperBound) return Token(string: token) } } diff --git a/Sources/Authentication/User/User.swift b/Sources/Authentication/User/User.swift deleted file mode 100644 index e63c601..0000000 --- a/Sources/Authentication/User/User.swift +++ /dev/null @@ -1,3 +0,0 @@ -import Fluent - -// public protocol User: Entity {} diff --git a/Tests/AuthenticationTests/ExampleTests.swift b/Tests/AuthenticationTests/ExampleTests.swift index dc2f34b..2f49f17 100644 --- a/Tests/AuthenticationTests/ExampleTests.swift +++ b/Tests/AuthenticationTests/ExampleTests.swift @@ -10,12 +10,7 @@ class ExampleTests: XCTestCase { func testExample() throws { do { - let id = Identifier(id: Node.string("5")) let token = Token(string: "5") - - let user1 = try AuthUser.authenticate(id) - XCTAssertEqual(user1.name, "5") - let user2 = try AuthUser.authenticate(token) XCTAssertEqual(user2.name, "6") } catch { diff --git a/Tests/AuthenticationTests/Utilities/AuthUser.swift b/Tests/AuthenticationTests/Utilities/AuthUser.swift index ad190a9..86b234d 100644 --- a/Tests/AuthenticationTests/Utilities/AuthUser.swift +++ b/Tests/AuthenticationTests/Utilities/AuthUser.swift @@ -31,12 +31,6 @@ final class AuthUser: Entity { } } -extension AuthUser: IdentifierAuthenticatable { - static func authenticate(_ id: Identifier) throws -> Self { - return self.init(name: "5") - } -} - extension AuthUser: TokenAuthenticatable { typealias TokenType = AuthUser @@ -44,9 +38,3 @@ extension AuthUser: TokenAuthenticatable { return self.init(name: "6") } } - -extension AuthUser: TokenProtocol { - static var tokenKey: String { - return "" - } -}