在 Node.js AWS SDK 中配置区域

有人能解释一下如何用 Node.js 修复缺少的配置错误吗?我已经跟踪了 Aws 文档页面中的所有示例,但是无论如何我还是会得到这个错误。

{ [ConfigError: Missing region in config]
message: 'Missing region in config',
code: 'ConfigError',
time: Wed Jun 24 2015 21:39:58 GMT-0400 (EDT) }>{ thumbnail:
{ fieldname: 'thumbnail',
originalname: 'testDoc.pdf',
name: 'testDoc.pdf',
encoding: '7bit',
mimetype: 'application/pdf',
path: 'uploads/testDoc.pdf',
extension: 'pdf',
size: 24,
truncated: false,
buffer: null } }
POST / 200 81.530 ms - -

这是我的代码:

var express = require('express');
var router = express.Router();
var AWS = require('aws-sdk');
var dd = new AWS.DynamoDB();
var s3 = new AWS.S3();
var bucketName = 'my-bucket';


AWS.config.update({region:'us-east-1'});


(...)
145522 次浏览

改变陈述的顺序怎么样? 在实例化 s3和 dd 之前更新 AWS 配置

var AWS = require('aws-sdk');
AWS.config.update({region:'us-east-1'});


var dd = new AWS.DynamoDB();
var s3 = new AWS.S3();

我遇到过同样的问题“在配置中缺少区域”,在我的例子中,与 CLI 或 Python SDK 不同,Node SDK 不会从 ~\.aws\config文件中读取。

要解决这个问题,你有三个选择:

  1. 以编程方式(硬编码)配置它: AWS.config.update({region:'your-region'});

  2. 使用环境变量。当 CLI 使用 AWS_DEFAULT_REGION时,NodeSDK 使用 AWS_REGION

  3. 使用 AWS.config.loadFromPath('./config.json');从 JSON 文件加载

JSON 格式:

{
"accessKeyId": "akid",
"secretAccessKey": "secret",
"region": "us-east-1"
}

这可能不是正确的方法,但是我将所有的配置放在一个单独的 JSON 文件中。这确实解决了我的问题

为了加载 AWS 配置,我这样做:

var awsConfig = config.aws;
AWS.config.region = awsConfig.region;
AWS.config.credentials = {
accessKeyId: awsConfig.accessKeyId,
secretAccessKey: awsConfig.secretAccessKey
}

Aws 只是一个 JSON 文件。

您可以在创建 Dynamodb 连接时指定该区域(还没有尝试 s3,但它也应该可以工作)。

var AWS = require('aws-sdk');
var dd = new AWS.DynamoDB({'region': 'us-east-1'});

我也犯了同样的错误:

在做了很多试验之后,我决定采用以下方法:

选择一

  1. 只在本地系统设定 AWS_REGION环境变量至 us-east-1(例子)

对于 Linux:

Export AWS _ ACCESS _ KEY _ ID = AKIAIOSFODNN7EXAMPLE
Export AWS _ Secret T _ ACCESS _ KEY = wJalrXutnFEMI/K7MDeng/bPxRfiCYEXAMPLEKEY
Export AWS _ DEFAULT _ REGION = us-east-1出口 AWS _ DEFAULT _ REGION = us-east-1

适用于视窗
参见: < a href = “ https://docs.aws.amazon.com/cli/update/userguide/cli-configure-envvars.html”rel = “ norefrer”> https://docs.aws.amazon.com/cli/latest/userguide/cli-configure-envvars.html

  1. 现在,不需要为区域设置任何 lambda 变量
  2. 此外,不需要在代码中使用,例如:

    • AWS.config.update(...),这是 没有的要求
    • AWS.S3()等等,这些将工作没有任何问题。代替 S3,可以有任何法律服务

在极少数情况下,如果在代码中某处假定了某些默认值,并且您被迫发送区域,那么使用 {'region': process.env.AWS_REGION})


选择二

取代环境变量的另一种方法是 AWS CONFIG 文件:

在 Linux 上,你可以创建以下文件:

~/. aws/凭证

[default]
aws_access_key_id=AKIAIOSFODNN7EXAMPLE
aws_secret_access_key=wJalrXUtnFEMI/K7MDENG/bPxRfiCYEXAMPLEKEY

~/. aws/config

[default]
region=us-west-2
output=json

参见 https://docs.aws.amazon.com/cli/latest/userguide/cli-configure-files.html

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

//按以下方式分配 AWS 凭证:

AWS.config.update({
accessKeyId: 'asdjsadkskdskskdk',
secretAccessKey: 'sdsadsissdiidicdsi',
region: 'us-east-1'
});


var dd = new AWS.DynamoDB();
var s3 = new AWS.S3();

如果使用 AWS CLI,则可能在 ~/中定义了一个默认区域。Aws/config.不幸的是,默认情况下 AWS SDK for JavaScript 不会加载它。要加载它,请定义 env var

AWS_SDK_LOAD_CONFIG=1

参见 https://github.com/aws/aws-sdk-js/pull/1391

您可以创建一个公共模块,并根据需要的区域使用它

var AWS = require('aws-sdk')


module.exports = {
getClient: function(region) {
AWS.config.update({ region: region })
return new AWS.S3()
}
}

然后把它当作,

 var s3Client = s3.getClient(config.region)

其思想是在实例化 s3之前更新 AWS 配置

我已经通过您的代码,这里您连接到 AWS 服务之前设置的区域,所以我建议您更新该区域,然后连接到服务或创建实例的服务如下-

var express = require('express');
var router = express.Router();
var AWS = require('aws-sdk');
AWS.config.update({region:'us-east-1'});


var dd = new AWS.DynamoDB();
var s3 = new AWS.S3();
var bucketName = 'my-bucket';

最佳实践是利用亚马逊认知身份池。

创建一个 IAM 策略,该策略定义对所需资源的访问权限(最小访问权限)

然后创建一个 Amazon 认证身份池,允许未经身份验证的身份。 然后将您创建的 IAM 策略附加到标识池的未经身份验证角色。

一旦设置完成,您可以使用以下代码:

   AWS.config.region = 'us-east-1';
AWS.config.credentials = new AWS.CognitoIdentityCredentials({
IdentityPoolId: 'IdentityPoolIdHere',
});

Amazon Cognoto 假设在未经身份验证的身份中指定的 IAM 角色,在后台使用 Amazon STS,然后使用 IAM 角色的附加 IAM 策略中定义的具有可访问性的临时凭证填充配置。

对于上面的注释,您可以通过添加以下内容,从本地全局配置文件 ~ ./aws/config 运行它:

process.env.AWS_SDK_LOAD_CONFIG="true";

这将加载您的本地全局配置文件,并使用您所在的任何凭据/帐户,这在迭代多个帐户/角色时非常方便。

我知道我已经迟到很久了,但是我有一个额外的解决办法。

直接向每个资源传递凭据可能是值得的。

let lambda = AWS.Lambda({region: "us-east-1"});
let credentials = new AWS.SharedIniFileCredentials({
profile: PROFILE_NAME,
});


lambda.config.credentials = credentials;

您可以在项目目录中解决这个问题。

  1. npm i -D dotenv.
  2. 在项目的根目录中创建 .env文件。
  3. 在那个 .env文件中设置环境变量 AWS_SDK_LOAD_CONFIG=1
  4. 在配置到 DynamoDB 的连接的同一个文件中的 const {config} = require("dotenv");
  5. 在你之前。

另外,正如前面提到的,问题是 Node 不能从 aws.config 文件中获取数据

我很惊讶这个还没有被发布到这里。

不需要用 AWS.config.update()设置区域,您可以使用

const s3 = new AWS.S3({
region: "eu-central-1",
});

使其具体到实例。

var AWS = require("aws-sdk");


AWS.config.getCredentials(function(err) {
if (err) console.log(err.stack);
// credentials not loaded
else {
console.log("Access key:", AWS.config.credentials.accessKeyId);
}
});

在我的例子中,我试图在 本教程之后的 React.JS 应用程序中使用它。

我需要将配置数据移动到调用 DocumentClient的同一个文件中,而不是将配置放在 index.js文件中。

create a common module and use it based on the region you want to


var AWS = require('aws-sdk')


module.exports = {
getClient: function(region) {
AWS.config.update({ region: region })
return new AWS.S3()
}
}




----------------------------------------------------
And then you can use the following .




var s3Client = s3.getClient(config.region)

现在是2022年,这是谷歌 “配置中缺少的区域”排名第一的搜索结果。

对于那些在结合使用 AWS Node SDK 和概要文件(即 ~/.aws/config~/.aws/credentials)时出现此错误的用户,解决方案是加载概要文件名的凭据(通过 共享文件凭证 ) , 属性分别获取配置文件名的区域 @ aws-sdk/share-ini-file-loader .

也就是说。

import AWS from "aws-sdk";
import { loadSharedConfigFiles } from "@aws-sdk/shared-ini-file-loader";


const profileName = "default"; // change this to whatever profile name you want


loadSharedConfigFiles().then((awsConfig) => {
// console.log(awsConfig);
const region = awsConfig?.configFile?.[profileName]?.region;


const credentials = new AWS.SharedIniFileCredentials({
profile: profileName,
});


// now use the credentials and the profile's region however you want
const pinpoint = new AWS.Pinpoint({
credentials: credentials,
region: region,
});
pinpoint.getApps({}, function (err, data) {
if (err) console.log(err, err.stack); // an error occurred
else console.log(data); // successful response
});
});