[英]AWS API gateway Cognito - How to fetch from react app
I try to add Cognito auth to an react app which calls an API gateway, too. 我尝试将Cognito auth添加到一个调用API网关的反应应用程序中。 I made it to have auth in the react app with: 我让它在反应应用程序中使用auth:
export default withAuthenticator(App);
But now I in addition want to make the API gateway secure with the same login. 但是现在我还想用同样的登录来保证API网关的安全。
Currently I get this error: 目前我收到此错误:
Access to fetch at '.../' from origin ' http://localhost:3000 ' has been blocked by CORS policy: Request header field access-control-allow-origin is not allowed by Access-Control-Allow-Headers in preflight response. 从“ http:// localhost:3000 ”获取“... /”的访问权限已被CORS策略阻止:Access-Control-Allow-Headers中不允许使用请求头字段access-control-allow-origin飞行前响应。
Tested different things I found online, but actually I haven't found what exactly I need to send as Authorization (Is token.sessionToken the right thing?) nor what the header needs in addition. 测试了我在网上找到的不同的东西,但实际上我还没有找到我需要发送什么作为授权(令牌.sessionToken正确的东西?)以及标头需要的内容。 The API call looks like this currently. API调用目前看起来像这样。
callAPI = async (url) => {
let token = await Amplify.Auth.currentCredentials();
console.log(token.sessionToken)
const apiurl = 'https...?url=' + url
const response = await fetch(apiurl, {
method: 'GET',
mode: 'cors',
headers: {
'Access-Control-Allow-Origin': '*',
'Access-Control-Allow-Methods': 'GET, POST, PUT, DELETE, PATCH',
'Access-Control-Allow-Headers': 'Origin, X-Requested-With, Content-Type, Accept, Authorization',
Authorization: token.sessionToken
},
})
const data = await response.json();
Serverless of the API gateway + corresponding lambda: 无服务器的API网关+对应的lambda:
resources:
...
Resources:
...
CognitoUserPool:
Type: AWS::Cognito::UserPool
Properties:
UserPoolName: ${self:service}_user_pool
MfaConfiguration: OFF
UsernameAttributes:
- email
Policies:
PasswordPolicy:
MinimumLength: 8
RequireLowercase: False
RequireNumbers: False
RequireSymbols: False
RequireUppercase: False
CognitoUserPoolClient:
Type: AWS::Cognito::UserPoolClient
Properties:
ClientName: ${self:service}_client
UserPoolId:
Ref: CognitoUserPool
ApiGatewayAuthorizer:
Type: AWS::ApiGateway::Authorizer
Properties:
Name: CognitoUserPool
Type: COGNITO_USER_POOLS
IdentitySource: method.request.header.Authorization
RestApiId:
Ref: ApiGatewayRestApi
ProviderARNs:
- Fn::GetAtt:
- CognitoUserPool
- Arn
CognitoIdentityPool:
Type: AWS::Cognito::IdentityPool
Properties:
IdentityPoolName: ${self:service}_identity_pool
AllowUnauthenticatedIdentities: false
CognitoIdentityProviders:
- ClientId:
Ref: CognitoUserPoolClient
ProviderName:
Fn::GetAtt: [CognitoUserPool, ProviderName]
CognitoIdentityPoolRoles:
Type: AWS::Cognito::IdentityPoolRoleAttachment
Properties:
IdentityPoolId:
Ref: CognitoIdentityPool
Roles:
authenticated:
Fn::GetAtt: [CognitoAuthRole, Arn]
unauthenticated:
Fn::GetAtt: [CognitoUnauthRole, Arn]
CognitoAuthRole:
Type: AWS::IAM::Role
Properties:
RoleName: appAuthRole
Path: /
AssumeRolePolicyDocument:
Version: "2012-10-17"
Statement:
- Effect: "Allow"
Principal:
Federated: "cognito-identity.amazonaws.com"
Action:
- "sts:AssumeRoleWithWebIdentity"
Condition:
StringEquals:
"cognito-identity.amazonaws.com:aud":
Ref: CognitoIdentityPool
"ForAnyValue:StringLike":
"cognito-identity.amazonaws.com:amr": authenticated
Policies:
- PolicyName: "CognitoAuthorizedPolicy"
PolicyDocument:
Version: "2012-10-17"
Statement:
- Effect: "Allow"
Action:
- "mobileanalytics:PutEvents"
- "cognito-sync:*"
- "cognito-identity:*"
Resource: "*"
- Effect: "Allow"
Action:
- "execute-api:Invoke"
Resource: "*"
CognitoUnauthRole:
Type: AWS::IAM::Role
Properties:
RoleName: appUnauthRole
Path: /
AssumeRolePolicyDocument:
Version: "2012-10-17"
Statement:
- Effect: "Allow"
Principal:
Federated: "cognito-identity.amazonaws.com"
Action:
- "sts:AssumeRoleWithWebIdentity"
Condition:
StringEquals:
"cognito-identity.amazonaws.com:aud":
Ref: CognitoIdentityPool
"ForAnyValue:StringLike":
"cognito-identity.amazonaws.com:amr": unauthenticated
Policies:
- PolicyName: "CognitoUnauthorizedPolicy"
PolicyDocument:
Version: "2012-10-17"
Statement:
- Effect: "Allow"
Action:
- "mobileanalytics:PutEvents"
- "cognito-sync:*"
- "cognito-identity:*"
Resource: "*"
... ...
functions:
ampstoryscreenshotsStep1:
handler: src/index.ampstoryscreenshotsStep1
events:
- http:
path: '{proxy+}'
method: get
cors: true
integration: lambda
authorizer:
type: COGNITO_USER_POOLS
authorizerId:
Ref: ApiGatewayAuthorizer
Would also be interesting to learn how to test this with postman? 学习如何用邮递员测试这个也很有趣?
Ok after checking docs + some test this is my solution. 检查文档+一些测试后确定这是我的解决方案。 This creates cognito user pool, identity pool and the auth for the api gateway 这为api网关创建了cognito用户池,标识池和auth
Serverless: 无服务器:
resources:
Resources:
...
CognitoUserPool:
Type: AWS::Cognito::UserPool
Properties:
UserPoolName: ${self:service}_user_pool
MfaConfiguration: OFF
Policies:
PasswordPolicy:
MinimumLength: 8
RequireLowercase: False
RequireNumbers: False
RequireSymbols: False
RequireUppercase: False
AutoVerifiedAttributes:
- email
CognitoUserPoolClient:
Type: AWS::Cognito::UserPoolClient
Properties:
ClientName: ${self:service}_client
UserPoolId:
Ref: CognitoUserPool
CognitoIdentityPool:
Type: AWS::Cognito::IdentityPool
Properties:
IdentityPoolName: ${self:service}_identity_pool
AllowUnauthenticatedIdentities: false
CognitoIdentityProviders:
- ClientId:
Ref: CognitoUserPoolClient
ProviderName:
Fn::GetAtt: [CognitoUserPool, ProviderName]
CognitoIdentityPoolRoles:
Type: AWS::Cognito::IdentityPoolRoleAttachment
Properties:
IdentityPoolId:
Ref: CognitoIdentityPool
Roles:
authenticated:
Fn::GetAtt: [CognitoAuthRole, Arn]
unauthenticated:
Fn::GetAtt: [CognitoUnauthRole, Arn]
CognitoAuthRole:
Type: AWS::IAM::Role
Properties:
RoleName: appAuthRole
Path: /
AssumeRolePolicyDocument:
Version: "2012-10-17"
Statement:
- Effect: "Allow"
Principal:
Federated: "cognito-identity.amazonaws.com"
Action:
- "sts:AssumeRoleWithWebIdentity"
Condition:
StringEquals:
"cognito-identity.amazonaws.com:aud":
Ref: CognitoIdentityPool
"ForAnyValue:StringLike":
"cognito-identity.amazonaws.com:amr": authenticated
Policies:
- PolicyName: "CognitoAuthorizedPolicy"
PolicyDocument:
Version: "2012-10-17"
Statement:
- Effect: "Allow"
Action:
- "mobileanalytics:PutEvents"
- "cognito-sync:*"
- "cognito-identity:*"
Resource: "*"
- Effect: "Allow"
Action:
- "execute-api:Invoke"
Resource: "*"
CognitoUnauthRole:
Type: AWS::IAM::Role
Properties:
RoleName: appUnauthRole
Path: /
AssumeRolePolicyDocument:
Version: "2012-10-17"
Statement:
- Effect: "Allow"
Principal:
Federated: "cognito-identity.amazonaws.com"
Action:
- "sts:AssumeRoleWithWebIdentity"
Condition:
StringEquals:
"cognito-identity.amazonaws.com:aud":
Ref: CognitoIdentityPool
"ForAnyValue:StringLike":
"cognito-identity.amazonaws.com:amr": unauthenticated
Policies:
- PolicyName: "CognitoUnauthorizedPolicy"
PolicyDocument:
Version: "2012-10-17"
Statement:
- Effect: "Allow"
Action:
- "mobileanalytics:PutEvents"
- "cognito-sync:*"
- "cognito-identity:*"
Resource: "*"
GatewayResponseDefault4XX:
Type: 'AWS::ApiGateway::GatewayResponse'
Properties:
ResponseParameters:
gatewayresponse.header.Access-Control-Allow-Origin: "'*'"
gatewayresponse.header.Access-Control-Allow-Headers: "'*'"
gatewayresponse.header.Access-Control-Allow-Methods: "'GET,PUT,OPTIONS'"
ResponseType: DEFAULT_4XX
RestApiId:
Ref: 'ApiGatewayRestApi'
GatewayResponseDefault5XX:
Type: 'AWS::ApiGateway::GatewayResponse'
Properties:
ResponseParameters:
gatewayresponse.header.Access-Control-Allow-Origin: "'*'"
gatewayresponse.header.Access-Control-Allow-Headers: "'*'"
gatewayresponse.header.Access-Control-Allow-Methods: "'GET,PUT,OPTIONS'"
ResponseType: DEFAULT_5XX
RestApiId:
Ref: 'ApiGatewayRestApi'
ApiGatewayAuthorizer:
DependsOn:
- ApiGatewayRestApi
Type: AWS::ApiGateway::Authorizer
Properties:
Name: cognito-authorizer
IdentitySource: method.request.header.Authorization
RestApiId:
Ref: ApiGatewayRestApi
Type: COGNITO_USER_POOLS
ProviderARNs:
- Fn::GetAtt: [CognitoUserPool, Arn]
functions:
ampstoryscreenshotsStep1:
handler: src/index.ampstoryscreenshotsStep1
events:
- http:
path: '{proxy+}'
method: get
cors: true
authorizer:
type: COGNITO_USER_POOLS
authorizerId:
Ref: ApiGatewayAuthorizer
The order here is important. 这里的顺序很重要。
I query like this: 我这样查询:
callAPI = async (url) => {
const user = await Amplify.Auth.currentAuthenticatedUser();
const token = user.signInUserSession.idToken.jwtToken;
const apiurl = config.apiGateway.URL + '/takescreenshots/?url=' + url
console.log(apiurl)
const response = await fetch(apiurl, {
method: 'GET',
headers: {
Authorization: token
},
})
const data = await response.json();
which just works if your signed in. 只有你登录后才能正常工作。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.