我的 iOS 应用程序检查 iCloud 帐户状态,然后使用以下方法请求 iCloud WebToken:
@objc static func fetchWebAuthToken ( _ apiToken : String, _ callback : @escaping CCallbackFunctionWithBoolAndString )
{
let fetchAuthorization = CKFetchWebAuthTokenOperation(apiToken: apiToken)
fetchAuthorization.fetchWebAuthTokenCompletionBlock = { webToken, error in
guard let webToken = webToken, error == nil else {
callback ( false, "[SWIFT] fetchWebAuthToken() error. " + (error?.localizedDescription ?? ""));
return;
}
let encodedWebToken = token.addingPercentEncoding (
withAllowedCharacters: CharacterSet(charactersIn: "+/=").inverted
) ?? token
callback ( true, encodedWebToken );
return;
}
CKContainer.default().privateCloudDatabase.add(fetchAuthorization);
}
一切正常,并返回格式正确的 Web 令牌。
然后,我获取该 Web 令牌,并使用 Postman 形成请求(删除了确切的值):
https://api.apple-cloudkit.com/database/1/iCloud.com.[my container]/development/private/users/caller?ckAPIToken=[development container token]&ckWebAuthToken=[web token]
回应是:
{
"uuid": "[abc]",
"serverErrorCode": "ACCESS_DENIED",
"reason": "private db access disabled for this account"
}
如果我改为请求公共数据库,我会得到有效且正确的响应:
https://api.apple-cloudkit.com/database/1/iCloud.com.[my container]/development/public/users/caller?ckAPIToken=[development container token]&ckWebAuthToken=[web token]
{
"userRecordName": "_[user id]",
"nameComponents": {
"givenName": "[First Name]",
"familyName": "[Surname]"
}
}
所以,这里有两个问题。
1)如果我在代码中为私有数据库请求 Web 令牌,为什么它只允许我与公共数据库交互?感觉就像它提供了一个仅对公共数据库有效的 Web 令牌,而不管我将操作添加到哪个数据库。
2)像这样针对公共数据库验证用户的安全隐患是什么?令牌应在 30 分钟内过期,这在这方面有所帮助。
为了证明 Web 令牌对私有数据库有效,我在 Dashboard 中更新了“登录回调”,复制了生成的 ckWebAuthToken 并能够通过 PostMan 访问私有数据库,因此这没有问题。似乎问题完全在于从 iOS 代码返回的 Web 令牌。