具有 AWS4 和混合身份验证类型(UserPools 和 IAM)的 AppSync
AppSync with AWS4 and mixed authentication type (UserPools and IAM)
我定义了 AppSync GraphQL API。 API 使用 Cognito UserPools 作为主要身份验证。这部分工作正常。
我正在尝试使用 axios
和 aws4
执行来自 Nodejs Lambda 函数的请求。我试图命中的突变是在我的模式中配置这样的东西(省略大部分模式):
AppSyncSchema:
Type: AWS::AppSync::GraphQLSchema
Properties:
ApiId: !GetAtt MyApi.ApiId
Definition: |
type Something {
someId: ID!
}
input SomethingInput {
someId: ID!
}
type Mutation {
doSomething(input: SomethingInput!): Something @aws_iam
}
我已将 Lambda 函数执行角色配置为具有 appsync:GraphQL
权限:
"Action": [
"appsync:GraphQL"
],
"Resource": "arn:aws:appsync:eu-west-2:xxxx:apis/yyyy/*",
"Effect": "Allow",
"Sid": "AllowAppSyncExecution"
从不同的在线文章中,我整理了一些请求,然后我的 Nodejs Typescript 函数将尝试执行:
const doSomething = `mutation doSomething($input: SomethingInput!) {
doSomething(input: $input) {
someId
}
}`;
const data = {
operationName: 'doSomething',
query: doSomething,
variables: {
input: { someId: 'abc' },
},
};
const body = JSON.stringify(data);
const signOptions = {
method: 'POST',
url: 'https://zzzz.appsync-api.eu-west-2.amazonaws.com/graphql,
host: 'zzzz.appsync-api.eu-west-2.amazonaws.com',
path: '/graphql',
region: process.env.AWS_REGION,
service: 'appsync',
headers: {
'content-type': 'application/json',
},
body, // used by aws4
data, // used by axios
};
const creds = {
accessKeyId: process.env.AWS_ACCESS_KEY_ID,
secretAccessKey: process.env.AWS_SECRET_ACCESS_KEY,
sessionToken: process.env.AWS_SESSION_TOKEN,
};
const signed = aws4.sign(signOptions, creds);
delete signed.headers.Host;
delete signed.headers['Content-Length'];
console.log(signed);
console.log('Got signed headers');
try {
await axios(signed);
} catch (err) {
console.error('Fialed to execute AppSync request', err);
throw err;
}
我总是收到 Request failed with status code 401
回复。 AppSync 日志没有透露更多信息:
{
"logType": "RequestSummary",
"requestId": "11111111",
"graphQLAPIId": "some id",
"statusCode": 401,
"latency": 7079000
}
我在正确配置时遗漏了什么?是否需要添加一些内容以允许 AWS IAM 仅针对特定的变更,或者您是否发现我尝试执行请求的方式有任何问题?
这些是我参考的文章:
manually-triggering-appsync-apollo-subscriptions
calling-amazon-api-gateway-authenticated-methods-with-axios-and-aws4
成功了。我必须向 AWS::AppSync::GraphQLApi
添加额外的身份验证提供程序。在 CloudFormation 中,这看起来像是一个额外的 属性:
Type: AWS::AppSync::GraphQLApi
Properties:
Name: !Ref MyApi
AuthenticationType: AMAZON_COGNITO_USER_POOLS
UserPoolConfig:
UserPoolId: !Ref MyPool
AwsRegion: !Ref MyRegion
DefaultAction: ALLOW
AdditionalAuthenticationProviders:
- AuthenticationType: AWS_IAM
完成这项工作后,我收到了来自 AppSync GraphQL 的响应,但它包含响应对象中所有字段的 GraphQL 错误:
Not Authorized to access someId on type Something
为了解决这个问题,我还必须在 GraphQL 模式中允许 IAM 使用此类型:
type Something @aws_cognito_user_pools @aws_iam {
someId: ID!
}
我定义了 AppSync GraphQL API。 API 使用 Cognito UserPools 作为主要身份验证。这部分工作正常。
我正在尝试使用 axios
和 aws4
执行来自 Nodejs Lambda 函数的请求。我试图命中的突变是在我的模式中配置这样的东西(省略大部分模式):
AppSyncSchema:
Type: AWS::AppSync::GraphQLSchema
Properties:
ApiId: !GetAtt MyApi.ApiId
Definition: |
type Something {
someId: ID!
}
input SomethingInput {
someId: ID!
}
type Mutation {
doSomething(input: SomethingInput!): Something @aws_iam
}
我已将 Lambda 函数执行角色配置为具有 appsync:GraphQL
权限:
"Action": [
"appsync:GraphQL"
],
"Resource": "arn:aws:appsync:eu-west-2:xxxx:apis/yyyy/*",
"Effect": "Allow",
"Sid": "AllowAppSyncExecution"
从不同的在线文章中,我整理了一些请求,然后我的 Nodejs Typescript 函数将尝试执行:
const doSomething = `mutation doSomething($input: SomethingInput!) {
doSomething(input: $input) {
someId
}
}`;
const data = {
operationName: 'doSomething',
query: doSomething,
variables: {
input: { someId: 'abc' },
},
};
const body = JSON.stringify(data);
const signOptions = {
method: 'POST',
url: 'https://zzzz.appsync-api.eu-west-2.amazonaws.com/graphql,
host: 'zzzz.appsync-api.eu-west-2.amazonaws.com',
path: '/graphql',
region: process.env.AWS_REGION,
service: 'appsync',
headers: {
'content-type': 'application/json',
},
body, // used by aws4
data, // used by axios
};
const creds = {
accessKeyId: process.env.AWS_ACCESS_KEY_ID,
secretAccessKey: process.env.AWS_SECRET_ACCESS_KEY,
sessionToken: process.env.AWS_SESSION_TOKEN,
};
const signed = aws4.sign(signOptions, creds);
delete signed.headers.Host;
delete signed.headers['Content-Length'];
console.log(signed);
console.log('Got signed headers');
try {
await axios(signed);
} catch (err) {
console.error('Fialed to execute AppSync request', err);
throw err;
}
我总是收到 Request failed with status code 401
回复。 AppSync 日志没有透露更多信息:
{
"logType": "RequestSummary",
"requestId": "11111111",
"graphQLAPIId": "some id",
"statusCode": 401,
"latency": 7079000
}
我在正确配置时遗漏了什么?是否需要添加一些内容以允许 AWS IAM 仅针对特定的变更,或者您是否发现我尝试执行请求的方式有任何问题?
这些是我参考的文章:
manually-triggering-appsync-apollo-subscriptions
calling-amazon-api-gateway-authenticated-methods-with-axios-and-aws4
成功了。我必须向 AWS::AppSync::GraphQLApi
添加额外的身份验证提供程序。在 CloudFormation 中,这看起来像是一个额外的 属性:
Type: AWS::AppSync::GraphQLApi
Properties:
Name: !Ref MyApi
AuthenticationType: AMAZON_COGNITO_USER_POOLS
UserPoolConfig:
UserPoolId: !Ref MyPool
AwsRegion: !Ref MyRegion
DefaultAction: ALLOW
AdditionalAuthenticationProviders:
- AuthenticationType: AWS_IAM
完成这项工作后,我收到了来自 AppSync GraphQL 的响应,但它包含响应对象中所有字段的 GraphQL 错误:
Not Authorized to access someId on type Something
为了解决这个问题,我还必须在 GraphQL 模式中允许 IAM 使用此类型:
type Something @aws_cognito_user_pools @aws_iam {
someId: ID!
}