Swift Auth0 访问代码导致未经授权的访问,但 Auth0 日志中没有任何内容

Swift Auth0 access code results in unauthorized access but nothing in Auth0 logs

我有一个受 Auth0 保护的 nestJS 后端。通过在授权 header (Authorization: Bearer ACCESS_TOKEN)

中包含访问令牌,我能够从 react-admin 成功访问后端

但是,当我尝试从 Swift iOS 应用程序访问相同的后端时,我似乎遇到了问题。我已经按照 Auth0 教程进行操作,并且能够确认用户成功登录和访问用户个人资料。但是,当我尝试向 nestJS 后端发出请求时,我收到 401 Unauthorized 错误。有趣的是,Auth0 日志中没有任何记录。

Link 到 Auth0 教程:https://auth0.com/docs/quickstart/native/ios-swift/04-calling-apis

let path = "\(baseURL)\(endpoint.rawValue)"
        
guard let url = URL(string: path)
else { preconditionFailure("Bad URL") }
        
var headers: [String:String] = [:]
headers["Content-Type"] = "application/json"
        
// if access token is set then set Authorization headers
if (accessToken != nil) {
    headers["Authorization"] = "Bearer \(accessToken!)"
    print("Bearer \(accessToken!)")
}
        
var request = URLRequest(url: url)
request.httpMethod = "\(method)"
request.allHTTPHeaderFields = headers
        
// check if body exists
if (body != nil) {
    request.httpBody = body!
}

let dataTask = URLSession.shared.dataTask(with: request) {
    (data, response, error) in
    guard error == nil
    else { completion(.failure(.serverError)); return }
            
    do {
        guard let data = data
        else { completion(.failure(.serverError)); return }
                
        guard let object : [[String: AnyObject]] = try JSONSerialization.object(with: data) as? [[String: AnyObject]]
        else {
            print("Unable to convert from data")
            return
        }
        
        guard let json = try? JSONSerialization.data(withJSONObject: object, options: .prettyPrinted)
        else {
            print("Unable to prettify")
            return
        }

        guard let jsonString = String(data: json, encoding: .utf8)
        else {
            print("Unable to convert to string")
            return
        }
                
         print("JSON: \(jsonString)")
                
         completion(Result.success(object))
     } catch {
         completion(Result.failure(.parsingError))
     }
}
dataTask.resume()

baseURL 是一个指向我的 nestJS 后端的字符串。 endpoint 是端点的枚举,例如 \user

使用 Proxyman,我能够确认端点被正确的 headers 击中。截图如下。

此外,使用邮递员我能够成功登录并发出对受保护数据的获取请求。截图如下。

对可能的原因有什么想法吗?让我知道是否应该添加任何其他详细信息。

更新 我解码了成功的 (react-admin) 和不成功的 (iOS) JWT 令牌并注意到以下差异:

成功的 JWT 中的

aud 包含一组受众,其中包括在 Auth0 上注册的 API 以及 auth0 端点 https://xxxxx.us.auth0.com/userinfo

azp 仅出现在成功的 JWT 中并且包含我的 clientID

aud中不成功的token包含clientID

scopepermissions 不成功的令牌缺失。

Ps。也发布在 Auth0 社区 https://community.auth0.com/t/access-token-when-obtained-from-ios-results-in-401-unauthorized-while-from-react-admin-is-ok/71115

问题是 audience 是在从 react-admin 请求访问令牌时设置的,而我没有将其包含在 swift 登录实现中。

解码 jwt.io 上的 JWT 和后续线程得出了这个结论。 https://community.auth0.com/t/access-token-too-short-jwt-malformed/9169/11?u=kennethphough

在以下代码中添加受众导致返回正确的 jwt 并成功访问后端。

Auth0
    .authentication()
    .login(
        usernameOrEmail: self.email,
        password: self.password,
        realm: "Username-Password-Authentication",
        audience: "<YOUR_AUDIENCE>",     // <- This is what I forgot
        scope: "openid profile email"
)