Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 2 additions & 2 deletions Sources/Logto/Core/LogtoCore+Fetch.swift
Original file line number Diff line number Diff line change
Expand Up @@ -46,7 +46,7 @@ public extension LogtoCore {
struct CodeTokenResponse: Codable, Equatable {
public let accessToken: String
public let refreshToken: String?
public let idToken: String
public let idToken: String?
public let scope: String
public let expiresIn: Int64
}
Expand Down Expand Up @@ -80,7 +80,7 @@ public extension LogtoCore {

struct RefreshTokenTokenResponse: Codable, Equatable {
public let accessToken: String
public let refreshToken: String
public let refreshToken: String?
public let idToken: String?
public let scope: String
public let expiresIn: Int64
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,10 @@ extension LogtoClient {
)

accessTokenMap[key] = accessToken
self.refreshToken = response.refreshToken

response.refreshToken.map {
self.refreshToken = $0
}

response.idToken.map {
self.idToken = $0
Expand Down
14 changes: 8 additions & 6 deletions Sources/LogtoClient/LogtoClient/LogtoClient+SignIn.swift
Original file line number Diff line number Diff line change
Expand Up @@ -30,12 +30,14 @@ extension LogtoClient {
let response = try await session.start()
let jwks = try await fetchJwkSet()

try LogtoUtilities.verifyIdToken(
response.idToken,
issuer: oidcConfig.issuer,
clientId: logtoConfig.appId,
jwks: jwks
)
try response.idToken.map {
try LogtoUtilities.verifyIdToken(
$0,
issuer: oidcConfig.issuer,
clientId: logtoConfig.appId,
jwks: jwks
)
}

idToken = response.idToken
refreshToken = response.refreshToken
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -35,6 +35,27 @@ extension LogtoClientTests {

XCTAssertEqual(tokens[0], "123")
XCTAssertEqual(tokens[1], "456")
XCTAssertEqual(client.refreshToken, "789")
XCTAssertEqual(client.idToken, "abc")
}

func testGetAccessTokenByRefreshTokenWithoutRefreshAndIdTokenReturned() async throws {
NetworkSessionMock.shared.tokenRequestCount = 0

let client = buildClient(withOidcEndpoint: "/oidc_config:good:no_refresh")
client.idToken = "baz"
client.refreshToken = "bar"
client.accessTokenMap[client.buildAccessTokenKey(for: "resource1")] = AccessToken(
token: "foo",
scope: "",
expiresAt: Date().timeIntervalSince1970 - 1
)

let token = try await client.getAccessToken(for: "resource1")

XCTAssertEqual(token, "123")
XCTAssertEqual(client.refreshToken, "bar")
XCTAssertEqual(client.idToken, "baz")
}

func testGetAccessTokenUnalbeToFetchOidcConfig() async throws {
Expand Down
21 changes: 21 additions & 0 deletions Tests/LogtoMock/NetworkSessionMock.swift
Original file line number Diff line number Diff line change
Expand Up @@ -33,6 +33,18 @@ public class NetworkSessionMock: NetworkSession {
"issuer": "http://localhost:443/oidc"
}
""".utf8), nil)
case "oidc_config:good:no_refresh":
return (Data("""
{
"authorization_endpoint": "https://logto.dev/auth:good",
"token_endpoint": "https://logto.dev/token:good:no_refresh",
"end_session_endpoint": "https://logto.dev/end:good",
"revocation_endpoint": "https://logto.dev/revoke:good",
"userinfo_endpoint": "https://logto.dev/user",
"jwks_uri": "https://logto.dev/jwks:good",
"issuer": "http://localhost:443/oidc"
}
""".utf8), nil)
case "oidc_config:bad":
return (Data("""
{
Expand Down Expand Up @@ -86,6 +98,15 @@ public class NetworkSessionMock: NetworkSession {
"expires_in": 123
}
""".utf8), nil)
case "token:good:no_refresh":
return (Data("""
{
"access_token": "123",
"token_type": "jwt",
"scope": "",
"expires_in": 123
}
""".utf8), nil)
case "revoke:good":
return (nil, nil)
default:
Expand Down