问题
I have a simple iOS app that uploads to s3. I'm trying unauth all around- even though ideally I want to do Facebook.
2 IAM Roles (created using the wizard). The IAM auth policy (for unauth role):
{
"Version": "2012-10-17",
"Statement": [{
"Action": [
"mobileanalytics:PutEvents",
"cognito-sync:*"
],
"Effect": "Allow",
"Resource": [
"*"
]
},
{
"Effect": "Allow",
"Action": [
"s3:PutObject",
"s3:GetObject",
"s3:DeleteObject"
],
"Resource": "arn:aws:s3:::[mybucketname]/*"
}
]
}
My constants.h file (scrubbed):
#define AWSID @"[12 digit num]"
#define PoolID @"us-east-1:[long id number]"
#define CRUnauth @"arn:aws:iam::[id num]:role/Cognito_Auth_DefaultRole"
#define CRAuth @"arn:aws:iam::[id num]:role/Cognito_auth_DefaultRole"
My appDelegate.m file has this:
credentialsProvider = [AWSCognitoCredentialsProvider credentialsWithRegionType:AWSRegionUSEast1 accountId:AWSID identityPoolId:PoolID unauthRoleArn:CRUnauth authRoleArn:nil];
AWSServiceConfiguration *configuration = [AWSServiceConfiguration configurationWithRegion:AWSRegionSAEast1
credentialsProvider:credentialsProvider];
[AWSServiceManager defaultServiceManager].defaultServiceConfiguration = configuration;
I made credentialsProvider a property since I need to add the Facebook login at some point.
I'm simply uploading a bundle image to test this. In my viewController:
if([app.fb_token length] > 0){
app.credentialsProvider.logins = @{ @(AWSCognitoLoginProviderKeyFacebook): app.fb_token };
}
AWSS3TransferManager *transferManager = [AWSS3TransferManager defaultS3TransferManager];
UIImage *image = [UIImage imageNamed:@"yayDot"];
NSArray *paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory,
NSUserDomainMask, YES);
NSString *documentsDirectory = [paths objectAtIndex:0];
NSString* path = [documentsDirectory stringByAppendingPathComponent:
@"yayDot.png" ];
NSData* data = UIImagePNGRepresentation(image);
[data writeToFile:path atomically:YES];
AWSS3TransferManagerUploadRequest *uploadRequest = [AWSS3TransferManagerUploadRequest new];
uploadRequest.body = [NSURL URLWithString:path];
uploadRequest.key = @"yayDot.png";
uploadRequest.bucket = thebucket;
[AWSLogger defaultLogger].logLevel = AWSLogLevelVerbose;
[[transferManager upload:uploadRequest] continueWithBlock:^id(BFTask *task) {
// Do something with the response
NSLog(@"result: %@", task.result);
return nil;
}];
Full error:
AWSURLResponseSerialization.m line:258 | -[AWSXMLResponseSerializer responseObjectForResponse:originalRequest:currentRequest:data:error:] | Response header: [{
"Content-Length" = 299;
"Content-Type" = "text/xml";
Date = "Tue, 27 Jan 2015 18:54:17 GMT";
"x-amzn-RequestId" = "xxxxx";
}]
2015-01-27 10:54:18.052 AWSiOSSDKv2 [Verbose] AWSURLResponseSerialization.m line:263 | -[AWSXMLResponseSerializer responseObjectForResponse:originalRequest:currentRequest:data:error:] | Response body: [<ErrorResponse xmlns="https://sts.amazonaws.com/doc/2011-06-15/">
<Error>
<Type>Sender</Type>
<Code>AccessDenied</Code>
<Message>Not authorized to perform sts:AssumeRoleWithWebIdentity</Message>
</Error>
<RequestId>xxxxx</RequestId>
</ErrorResponse>
]
2015-01-27 10:54:18.059 lookyloo[20024:332664] AWSiOSSDKv2 [Error] AWSCredentialsProvider.m line:587 | __40-[AWSCognitoCredentialsProvider refresh]_block_invoke356 | Unable to refresh. Error is [Error Domain=com.amazonaws.AWSSTSErrorDomain Code=0 "The operation couldn’t be completed. (com.amazonaws.AWSSTSErrorDomain error 0.)" UserInfo=0x7d936310 {Type=Sender, Message=Not authorized to perform sts:AssumeRoleWithWebIdentity, __text=(
"\n ",
"\n ",
"\n ",
"\n "
), Code=AccessDenied}]
回答1:
looking at your code, it looks like you were using the "Auth" role arn:aws:iam::[id num]:role/Cognito_Auth_DefaultRole
as your unauth role. By default Amazon Cognito creates roles that only trust the specific kind of access (unauthenticated and authenticated), hence the sts error when trying with unauthenticated access. This blog post goes over trust policies and understanding how Cognito uses them.
Switching to the simplified constructor should have fixed this for you, unless you also made the same association inside of the AWS console. Associating your roles in the console allows you to not embed your roles inside your application.
Also, if you want to use a bucket outside of the "US Standard" region, you would need to change this line:
AWSServiceConfiguration *configuration = [AWSServiceConfiguration configurationWithRegion:AWSRegionSAEast1
credentialsProvider:credentialsProvider];
To reflect the region where the bucket resides.
来源:https://stackoverflow.com/questions/28178541/not-authorized-to-perform-stsassumerolewithwebidentity-aws-s3-cognito-auth-fail