首页 > 解决方案 > AWS DynamoDB 给出了奇怪的 ResourceNotFoundException 但明确设置了区域

问题描述

我的 DynamoDB 区域明确定义如下:

const AWS = require('aws-sdk');

AWS.config.update({ region: process.env.TABLE_REGION });

const dynamodb = new AWS.DynamoDB.DocumentClient({ apiVersion: '2012-08-10', region: process.env.TABLE_REGION });

其中 process.env.TABLE_REGION 指的是我定义的区域。这可能看起来有点多余,但我一直在寻找“指定了错误的区域”的答案,而我似乎很清楚这里不是这种情况。

问题是,有时当我更新表(通常是数百个同时 PUT)时,我有时会收到 ResourceNotFoundException 消息“未找到请求的资源”。绝大多数的 PUT 都可以工作,只是偶尔的 PUT 不能。我认为这是某种限制消息,但我找不到任何支持使用异常的文档。此外,我的数据库容量在目标值范围内。

到底是怎么回事?这个问题使得处理大型上传几乎不可能,因为它们随机失败。我知道批量上传不能保证有效并且需要逻辑重试,但我的理解是单个请求应该始终有效。而且错误信息毫无意义;资源一直在原处。

帮助将不胜感激,谢谢。

编辑:

一些代码示例(有点难以总结/复制,因为脚本相当大,但会尽力而为)。这充其量只是伪代码;我应该指出,代码经过多次迭代,但结果是一样的。认为问题比简单地识别代码中的错误更为根本。此外,它经常起作用,只是偶尔不起作用:

此外,这些是 PUT。当我说“更新”表格时,我并不是很准确,更多的是“更改”表格,但更准确地说是“插入”。

const posts = [...];

const addPost = async ({ post }) => {
  await dynamodb.put({
      TableName: tableName,
      Item: {
          PartitionKey: organizationId + '-POST',
          SortKey: post.creationTime + '--' + post.id,
          ...post
      }
  }).promise();
};

const addAllPosts = async ({ sum = [], posts, index = 0 }) => {
  if (posts[index] === undefined) {
    await Promise.all(sum);

    return;
  }

  const post = posts[index];

  sum.push(addPost({ post }));

  if (sum.length === 300) {
    await Promise.all(sum);
    sum = undefined;
  } 

  await addAllPosts({ posts, sum, index: index + 1 });
};

await addAllPosts({ posts });

主要思想是我想批量插入不超过 300 个,所以我可以预测数据库写入单元。

完全错误:

它只是偶尔发生,但当它发生时,它当然会破坏一切:

{
    "errorType": "Runtime.UnhandledPromiseRejection",
    "errorMessage": "ResourceNotFoundException: Requested resource not found",
    "stack": [
        "Runtime.UnhandledPromiseRejection: ResourceNotFoundException: Requested resource not found",
        "    at process.on (/var/runtime/index.js:37:15)",
        "    at process.emit (events.js:198:13)",
        "    at process.EventEmitter.emit (domain.js:448:20)",
        "    at emitPromiseRejectionWarnings (internal/process/promises.js:119:20)",
        "    at process._tickCallback (internal/process/next_tick.js:69:34)"
    ],
    "reason": {
        "errorType": "ResourceNotFoundException",
        "errorMessage": "Requested resource not found",
        "code": "ResourceNotFoundException",
        "stack": [
            "ResourceNotFoundException: Requested resource not found",
            "    at Request.extractError (/var/task/node_modules/aws-sdk/lib/protocol/json.js:51:27)",
            "    at Request.callListeners (/var/task/node_modules/aws-sdk/lib/sequential_executor.js:106:20)",
            "    at Request.emit (/var/task/node_modules/aws-sdk/lib/sequential_executor.js:78:10)",
            "    at Request.emit (/var/task/node_modules/aws-sdk/lib/request.js:683:14)",
            "    at Request.transition (/var/task/node_modules/aws-sdk/lib/request.js:22:10)",
            "    at AcceptorStateMachine.runTo (/var/task/node_modules/aws-sdk/lib/state_machine.js:14:12)",
            "    at /var/task/node_modules/aws-sdk/lib/state_machine.js:26:10",
            "    at Request.<anonymous> (/var/task/node_modules/aws-sdk/lib/request.js:38:9)",
            "    at Request.<anonymous> (/var/task/node_modules/aws-sdk/lib/request.js:685:12)",
            "    at Request.callListeners (/var/task/node_modules/aws-sdk/lib/sequential_executor.js:116:18)"
        ],
        "message": "Requested resource not found",
        "time": "2019-09-23T23:22:54.784Z",
        "requestId": {redacted},
        "statusCode": 400,
        "retryable": false,
        "retryDelay": 3.7761727886367558
    },
    "promise": {}
}

标签: node.jsamazon-web-servicesamazon-dynamodbaws-sdk

解决方案


推荐阅读