Android 放大 Cognito Post 确认用户 Table 确认用户后不填充
Android Amplify Cognito Post Confirmation User Table not populating after user is confirmed
应用程序
Android 带有 Amplify 后端的 Studio 项目允许用户登录并查看一些个人资料信息。我想保留一个 DynamoDB 用户 table 来保存一些额外的数据。我希望根据用户采取的某些操作来更新 table, 但是 ,我真的很喜欢 Lambda 函数最初将用户添加到 table 的概念安全且无需我手动完成。
问题
调用了 Lambda 函数,但未将新用户添加到生成的 DynamoDB table。非常令人沮丧,因为我唯一的线索是无法解释的 CloudWatch 日志(如下所示)。
我上网查了一下,发现 this SO/GitHub 问题,这和我的很相似,只是我没有 amplify update auth
并在那里设置了 Post 确认触发器或在 Cognito 中添加任何群组。我在执行 amplify push
命令时没有出现循环依赖错误。
更新
在我的桌面网络浏览器中使用 Cognito Hosted UI 时,我得到了相同的结果。亚马逊在他们的文档中发布的 Lambda 函数肯定没有缺陷吗?
我需要的
关于为什么用户数据可能无法进入 DynamoDB 的一般指导 table。我应该尝试模仿上面 linked post 的 OP 吗?我是否遗漏了一些中间步骤?
任何帮助都很棒,如果他们愿意提供帮助,我非常乐意提供更多资源。
谢谢。
我做了什么
amplify init
和 amplify config
amplify add auth
遵循 these 说明。
- 在 AWS 控制台中,我设置了 Cognito Hosted UI 让用户注册和登录。效果很好。
amplify add api
遵循 these 说明。这是 schema.graphql 文件:
type User @model @auth(rules: [{ allow: owner }]) {
id: ID!
name: String
email: String
}
amplify add function
按照相同的说明 - 这是 index.js 文件:
/* Amplify Params - DO NOT EDIT
API_TBCPAPI_GRAPHQLAPIIDOUTPUT
API_TBCPAPI_USERTABLE_ARN
API_TBCPAPI_USERTABLE_NAME
ENV
REGION
Amplify Params - DO NOT EDIT */
var aws = require('aws-sdk');
var ddb = new aws.DynamoDB();
exports.handler = async (event, context) => {
let date = new Date();
if (event.request.userAttributes.sub) {
let params = {
Item: {
'id': {S: event.request.userAttributes.sub},
'__typename': {S: 'User'},
'name': {S: event.request.userAttributes.name},
'email': {S: event.request.userAttributes.email},
'createdAt': {S: date.toISOString()},
'updatedAt': {S: date.toISOString()},
},
TableName: process.env.API_TBCPAPI_USERTABLE_NAME
};
// Call DynamoDB
try {
await ddb.putItem(params).promise()
console.log("Success");
} catch (err) {
console.log("Error", err);
}
console.log("Success: Everything executed correctly");
context.done(null, event);
} else {
// Nothing to do, the user's email ID is unknown
console.log("Error: Nothing was written to DynamoDB");
context.done(null, event);
}
};
我很小心地编辑了正确的 DynamoDB table 名称。
amplify push
没有错误。
- 在 AWS Cognito 控制台中,我从下拉列表中手动选择了 Post Confirmation Lambda。保存无误。
amplify pull
以确保我已完成更改(不确定是否需要)。
- 运行 应用程序,在托管 UI 中创建了一个用户,通过电子邮件代码确认,登录并返回到应用程序。
- 去检查 DynamoDB table 并且在用户 table 中没有条目。无赖。
- 去检查Lambda监视器,它显示了1次调用,成功率为100%。 (我不敢苟同)
- 跟随 link 到 CloudWatch Logs,发现了这个:
2021-05-27T15:47:26.024Z c6d8ddfc-1f67-4bc9-b01c-1b89b91f0abc INFO Error ValidationException: Supplied AttributeValue is empty, must contain exactly one of the supported datatypes
at Request.extractError (/var/runtime/node_modules/aws-sdk/lib/protocol/json.js:52:27)
at Request.callListeners (/var/runtime/node_modules/aws-sdk/lib/sequential_executor.js:106:20)
at Request.emit (/var/runtime/node_modules/aws-sdk/lib/sequential_executor.js:78:10)
at Request.emit (/var/runtime/node_modules/aws-sdk/lib/request.js:688:14)
at Request.transition (/var/runtime/node_modules/aws-sdk/lib/request.js:22:10)
at AcceptorStateMachine.runTo (/var/runtime/node_modules/aws-sdk/lib/state_machine.js:14:12)
at /var/runtime/node_modules/aws-sdk/lib/state_machine.js:26:10
at Request.<anonymous> (/var/runtime/node_modules/aws-sdk/lib/request.js:38:9)
at Request.<anonymous> (/var/runtime/node_modules/aws-sdk/lib/request.js:690:12)
at Request.callListeners (/var/runtime/node_modules/aws-sdk/lib/sequential_executor.js:116:18) {
code: 'ValidationException',
time: 2021-05-27T15:47:25.983Z,
requestId: 'BRRPE7CIIAGD1H28DVO7UEGISVVV4KQNSO5AEMVJF66Q9ASUAAJG',
statusCode: 400,
retryable: false,
retryDelay: 22.42081554987443
}
而不是调用 context.done(null, event)
只是 return 事件 return event
。
问题是当您使用异步函数时,return 值包含在承诺中。如果没有 return,您的承诺将解析为未定义,这显然未通过验证。
Lambda 运行时设置为 Node.js 14.x,我将其切换为 12.x 以查看这是否会改变任何内容(也许 AWS 文档在他们的描述中并不完全准确说明)。
无论如何这似乎对我有用,我将一个用户加载到我的 DynamoDB table。
更新
好吧,这不是 Lambda 运行时...出于某种原因,如果我删除 index.js 文件中的姓名、电子邮件和日期属性,那么它将成功地将用户放入数据库中.我一定是做了那个改变,推送,然后改变了运行时。
更新 2
问题是 event.request.userAttributes.name
是空的,它旁边的 || 'no name'
起到了此处评论中建议的作用。电子邮件地址实际上工作正常。
老实说,用户名和电子邮件足以用于初始条目。我可以添加以后需要的任何属性。我将只使用 Kotlin,省去尝试调试的麻烦 JavaScript.
希望这对尝试导航的其他人有所帮助 these docs for Android。
谢谢。
应用程序
Android 带有 Amplify 后端的 Studio 项目允许用户登录并查看一些个人资料信息。我想保留一个 DynamoDB 用户 table 来保存一些额外的数据。我希望根据用户采取的某些操作来更新 table, 但是 ,我真的很喜欢 Lambda 函数最初将用户添加到 table 的概念安全且无需我手动完成。
问题
调用了 Lambda 函数,但未将新用户添加到生成的 DynamoDB table。非常令人沮丧,因为我唯一的线索是无法解释的 CloudWatch 日志(如下所示)。
我上网查了一下,发现 this SO/GitHub 问题,这和我的很相似,只是我没有 amplify update auth
并在那里设置了 Post 确认触发器或在 Cognito 中添加任何群组。我在执行 amplify push
命令时没有出现循环依赖错误。
更新
在我的桌面网络浏览器中使用 Cognito Hosted UI 时,我得到了相同的结果。亚马逊在他们的文档中发布的 Lambda 函数肯定没有缺陷吗?
我需要的
关于为什么用户数据可能无法进入 DynamoDB 的一般指导 table。我应该尝试模仿上面 linked post 的 OP 吗?我是否遗漏了一些中间步骤?
任何帮助都很棒,如果他们愿意提供帮助,我非常乐意提供更多资源。
谢谢。
我做了什么
amplify init
和amplify config
amplify add auth
遵循 these 说明。- 在 AWS 控制台中,我设置了 Cognito Hosted UI 让用户注册和登录。效果很好。
amplify add api
遵循 these 说明。这是 schema.graphql 文件:
type User @model @auth(rules: [{ allow: owner }]) {
id: ID!
name: String
email: String
}
amplify add function
按照相同的说明 - 这是 index.js 文件:
/* Amplify Params - DO NOT EDIT
API_TBCPAPI_GRAPHQLAPIIDOUTPUT
API_TBCPAPI_USERTABLE_ARN
API_TBCPAPI_USERTABLE_NAME
ENV
REGION
Amplify Params - DO NOT EDIT */
var aws = require('aws-sdk');
var ddb = new aws.DynamoDB();
exports.handler = async (event, context) => {
let date = new Date();
if (event.request.userAttributes.sub) {
let params = {
Item: {
'id': {S: event.request.userAttributes.sub},
'__typename': {S: 'User'},
'name': {S: event.request.userAttributes.name},
'email': {S: event.request.userAttributes.email},
'createdAt': {S: date.toISOString()},
'updatedAt': {S: date.toISOString()},
},
TableName: process.env.API_TBCPAPI_USERTABLE_NAME
};
// Call DynamoDB
try {
await ddb.putItem(params).promise()
console.log("Success");
} catch (err) {
console.log("Error", err);
}
console.log("Success: Everything executed correctly");
context.done(null, event);
} else {
// Nothing to do, the user's email ID is unknown
console.log("Error: Nothing was written to DynamoDB");
context.done(null, event);
}
};
我很小心地编辑了正确的 DynamoDB table 名称。
amplify push
没有错误。- 在 AWS Cognito 控制台中,我从下拉列表中手动选择了 Post Confirmation Lambda。保存无误。
amplify pull
以确保我已完成更改(不确定是否需要)。- 运行 应用程序,在托管 UI 中创建了一个用户,通过电子邮件代码确认,登录并返回到应用程序。
- 去检查 DynamoDB table 并且在用户 table 中没有条目。无赖。
- 去检查Lambda监视器,它显示了1次调用,成功率为100%。 (我不敢苟同)
- 跟随 link 到 CloudWatch Logs,发现了这个:
2021-05-27T15:47:26.024Z c6d8ddfc-1f67-4bc9-b01c-1b89b91f0abc INFO Error ValidationException: Supplied AttributeValue is empty, must contain exactly one of the supported datatypes
at Request.extractError (/var/runtime/node_modules/aws-sdk/lib/protocol/json.js:52:27)
at Request.callListeners (/var/runtime/node_modules/aws-sdk/lib/sequential_executor.js:106:20)
at Request.emit (/var/runtime/node_modules/aws-sdk/lib/sequential_executor.js:78:10)
at Request.emit (/var/runtime/node_modules/aws-sdk/lib/request.js:688:14)
at Request.transition (/var/runtime/node_modules/aws-sdk/lib/request.js:22:10)
at AcceptorStateMachine.runTo (/var/runtime/node_modules/aws-sdk/lib/state_machine.js:14:12)
at /var/runtime/node_modules/aws-sdk/lib/state_machine.js:26:10
at Request.<anonymous> (/var/runtime/node_modules/aws-sdk/lib/request.js:38:9)
at Request.<anonymous> (/var/runtime/node_modules/aws-sdk/lib/request.js:690:12)
at Request.callListeners (/var/runtime/node_modules/aws-sdk/lib/sequential_executor.js:116:18) {
code: 'ValidationException',
time: 2021-05-27T15:47:25.983Z,
requestId: 'BRRPE7CIIAGD1H28DVO7UEGISVVV4KQNSO5AEMVJF66Q9ASUAAJG',
statusCode: 400,
retryable: false,
retryDelay: 22.42081554987443
}
而不是调用 context.done(null, event)
只是 return 事件 return event
。
问题是当您使用异步函数时,return 值包含在承诺中。如果没有 return,您的承诺将解析为未定义,这显然未通过验证。
Lambda 运行时设置为 Node.js 14.x,我将其切换为 12.x 以查看这是否会改变任何内容(也许 AWS 文档在他们的描述中并不完全准确说明)。
无论如何这似乎对我有用,我将一个用户加载到我的 DynamoDB table。
更新
好吧,这不是 Lambda 运行时...出于某种原因,如果我删除 index.js 文件中的姓名、电子邮件和日期属性,那么它将成功地将用户放入数据库中.我一定是做了那个改变,推送,然后改变了运行时。
更新 2
问题是 event.request.userAttributes.name
是空的,它旁边的 || 'no name'
起到了此处评论中建议的作用。电子邮件地址实际上工作正常。
老实说,用户名和电子邮件足以用于初始条目。我可以添加以后需要的任何属性。我将只使用 Kotlin,省去尝试调试的麻烦 JavaScript.
希望这对尝试导航的其他人有所帮助 these docs for Android。
谢谢。