AWS iOS SDK Cognito开发人员authentication(Swift)

我很难弄清楚如何将我的服务器(通过AWS)提供的开发人员凭证返回给示例身份提供者。

看来我需要在ExampleIdentityProvider类的refresh方法中同步执行此操作。 我正在使用AFNetworking发出请求,但它是一个asynchronousGET请求。 我怎样才能做到这一点我的IdentityProvider刷新方法同步?

以下是在Swift中:

 class ExampleIdentityProvider: AWSAbstractIdentityProvider { var newToken: String! override var token: String { get { return newToken } set { newToken = newValue } } override func getIdentityId() -> BFTask! { if self.identityId != nil { return BFTask(result: self.identityId) }else{ return BFTask(result: nil).continueWithBlock({ (task) -> AnyObject! in if self.identityId == nil { return self.refresh() } return BFTask(result: self.identityId) }) } } override func refresh() -> BFTask! { return BFTask(result: nil).continueWithBlock({ (task) -> AnyObject! in let result = AFNETWORKING REQUEST FOR CREDENTIALS TO MY SERVER self.identityId = result.identityId self.token = result.token return BFTask(result: self.identityId) }) } } 

我相信我已经弄清楚了。 我需要利用BFTask来完成处理后台任务。

对于使用Cognito进行开发人员身份validation的人员,他们可能有类似的设置,我就是这么做的:

 class ExampleAppIdentityProvider: AWSAbstractCognitoIdentityProvider { var _token: String! var _logins: [ NSObject : AnyObject ]! // Header stuff you may not need but I use for auth with my server let acceptHeader = "application/vnd.exampleapp-api+json;version=1;" let authHeader = "Token token=" let userDefaults = NSUserDefaults.standardUserDefaults() let authToken = self.userDefaults.valueForKey("authentication_token") as String // End point that my server gives amazon identityId and tokens to authorized users let url = "https://api.myapp.com/api/amazon_id/" override var token: String { get { return _token } } override var logins: [ NSObject : AnyObject ]! { get { return _logins } set { _logins = newValue } } override func getIdentityId() -> BFTask! { if self.identityId != nil { return BFTask(result: self.identityId) }else{ return BFTask(result: nil).continueWithBlock({ (task) -> AnyObject! in if self.identityId == nil { return self.refresh() } return BFTask(result: self.identityId) }) } } override func refresh() -> BFTask! { let task = BFTaskCompletionSource() let request = AFHTTPRequestOperationManager() request.requestSerializer.setValue(self.acceptHeader, forHTTPHeaderField: "ACCEPT") request.requestSerializer.setValue(self.authHeader+authToken, forHTTPHeaderField: "AUTHORIZATION") request.GET(self.url, parameters: nil, success: { (request: AFHTTPRequestOperation!, response: AnyObject!) -> Void in // The following 3 lines are required as referenced here: http://stackoverflow.com/a/26741208/535363 var tmp = NSMutableDictionary() tmp.setObject("temp", forKey: "ExampleApp") self.logins = tmp // Get the properties from my server response let properties: NSDictionary = response.objectForKey("properties") as NSDictionary let amazonId = properties.objectForKey("amazon_identity") as String let amazonToken = properties.objectForKey("token") as String // Set the identityId and token for the ExampleAppIdentityProvider self.identityId = amazonId self._token = amazonToken task.setResult(response) }, failure: { (request: AFHTTPRequestOperation!, error: NSError!) -> Void in task.setError(error) }) return task.task } } 

并通过执行ExampleAppIdentityProvider来初始化:

  let identityProvider = ExampleAppIdentityProvider() let credentialsProvider = AWSCognitoCredentialsProvider(regionType: AWSRegionType.USEast1, identityProvider: identityProvider, unauthRoleArn: GlobalVariables.cognitoUnauthRoleArn, authRoleArn: GlobalVariables.cognitoAuthRoleArn) let defaultServiceConfiguration = AWSServiceConfiguration(region: .USEast1, credentialsProvider: credentialsProvider) AWSServiceManager.defaultServiceManager().defaultServiceConfiguration = defaultServiceConfiguration let transferManager = AWSS3TransferManager.defaultS3TransferManager() let uploadRequest = AWSS3TransferManagerUploadRequest() uploadRequest.bucket = GlobalVariables.awsBucket uploadRequest.key = "\(GlobalVariables.environment)/uploads/users/\(userId)/\(type)/\(timestamp)/original.jpg" uploadRequest.ACL = .AuthenticatedRead uploadRequest.body = tmpFileUrl // Upload file let task = transferManager.upload(uploadRequest) 

我用全局环境variables创build了一个名为GlobalVariablesstruct ,这个variables包含了bucketunAuthRoleArnauthRoleArn等等的值。当然,你不需要这样做,但是我提到它,以防有人感到困惑。

您可以生成自定义类进行authenticationauthentication

 import AWSS3 import AWSCore import Alamofire //This variable is store aws credential token var cachedLogin : NSDictionary? final class AmazonIdentityProvider : AWSCognitoCredentialsProviderHelper{ // Handles getting the login override func logins() -> AWSTask<NSDictionary> { guard let cachedLoginObj = cachedLogin else { return getCredentials().continueWith(block: { (credentialTask) -> AWSTask<NSDictionary> in guard let credential = credentialTask.result else { return AWSTask(result: nil) } self.setCognitoTokenKey(credential: credential) return AWSTask(result: cachedLogin) }) as! AWSTask<NSDictionary> } return AWSTask(result: cachedLoginObj) } // Handles getting a token from the server override func token() -> AWSTask<NSString> { return getCredentials().continueWith(block: { (credentialTask) -> AWSTask<NSString> in guard let credential = credentialTask.result else { return AWSTask(result: nil) } self.setCognitoTokenKey(credential: credential) return AWSTask(result: credential.token as NSString) }) as! AWSTask<NSString> } // Handles getting the identity id override func getIdentityId() -> AWSTask<NSString> { return getCredentials().continueWith(block: { (credentialTask) -> AWSTask<NSString> in guard let credential = credentialTask.result else { return AWSTask(result: nil) } self.setCognitoTokenKey(credential: credential) return AWSTask(result: credential.identityId as NSString) }) as! AWSTask<NSString> } //This method is used to AWS Token set func setCognitoTokenKey(credential : AmazonCognitoCredential){ let login: NSDictionary = ["cognito-identity.amazonaws.com": credential.token] cachedLogin = login self.identityId = credential.identityId } // Gets credentials from server func getCredentials() -> AWSTask<AmazonCognitoCredential> { let tokenRequest = AWSTaskCompletionSource<AmazonCognitoCredential>() getAwsToken { (isSuccess, error, credentials) in if isSuccess { tokenRequest.set(result: credentials) } else { tokenRequest.set(error: error!) } } return tokenRequest.task } typealias CompletionBlock = (_ success:Bool,_ errorMassage:Error?,_ responce:AmazonCognitoCredential?) -> Void func getAwsToken(complitionBlock : @escaping CompletionBlock) { //Your server token code } /// AmazonCognito credential custom class final class AmazonCognitoCredential { let token: String let identityId: String init(token: String, identityId: String) { self.token = token self.identityId = identityId } } 

你可以在应用程序委托中使用

 func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplicationLaunchOptionsKey: Any]?) -> Bool { AWSDDLog.sharedInstance.logLevel = .all let identityProvider = AmazonIdentityProvider() let credentialsProvider = AWSCognitoCredentialsProvider(regionType: .USEast1, unauthRoleArn: CognitoRoleUnauth, authRoleArn: CognitoRoleAuth, identityProvider: identityProvider) let configuration = AWSServiceConfiguration(region: .USWest2, credentialsProvider: credentialsProvider) AWSServiceManager.default().defaultServiceConfiguration = configuration let task = identityProvider.getIdentityId() task.continueWith { (task:AWSTask) -> Any? in if (task.error != nil ) { print("\(String(describing: task.error))") } else { print("Task result: \(String(describing: task.result))") } return nil } return true }