Dor*_*hez 9 .net amazon-web-services aws-sdk .net-core asp.net-core-webapi
我必须调试一个关于 .net Core 和 AWS 的现有项目。我们的项目在我们的 AWS 实例上运行良好,但我们无法在本地运行该项目。
首先,我们收到了 AmazonServiceException:无法找到凭证,但现在我们收到了消息:AmazonClientException:未配置 RegionEndpoint 或 ServiceURL。我觉得这样更好。
我们的配置: 在我们的应用程序中,我们有 3 个 appsettings.{env.EnvironmentName}.json(开发、本地和生产)。我们知道VS默认使用开发文件。在我们的开发 appsettings 文件中,我们没有 AWS 对象,但在本地 appsettings 文件中,我们只有:
"AWS": {
"Region": "ap-southeast-2"
}
Run Code Online (Sandbox Code Playgroud)
我们没有任何 web.config 或其他 json 配置文件。
我们尝试将凭证文件创建为:
[name of my IAM profile]
aws_access_key_id=accesskey
aws_secret_access_key=secretkey
region=ap-southeast-2
Run Code Online (Sandbox Code Playgroud)
但是我们没有找到如何使用它。
我们还尝试使用 dotnet core run 命令运行该项目,并将一些环境变量指定为:
export AWS_Region=ap-southeast-2
export AWS_ACCESS_KEY_ID=id
export AWS_SECRET_ACCESS_KEY=secret
export AWS_SESSION_TOKEN=token
export
AWS_CREDENTIAL_FILE=/Users/user/Developer/exemple/nameproject/G$
Run Code Online (Sandbox Code Playgroud)
但同样的错误。
程序.cs文件:
var host = new WebHostBuilder()
.UseKestrel(options => options.AddServerHeader = false)
.UseContentRoot(Directory.GetCurrentDirectory())
.UseIISIntegration()
.UseStartup<Startup>()
.UseUrls("http://*:9000")
.CaptureStartupErrors(true)
.Build();
host.Run();
Run Code Online (Sandbox Code Playgroud)
启动文件(第一个函数):
public Startup(IHostingEnvironment env) {
// Configuration override https://docs.microsoft.com/en-us/aspnet/core/fundamentals/configuration
var builder = new ConfigurationBuilder()
.SetBasePath(env.ContentRootPath)
.AddJsonFile($"appsettings.{env.EnvironmentName}.json", false, true)
.AddEnvironmentVariables();
Configuration = builder.Build();
// Shared startup configurator
CommonStartup = new CommonStartup(env, Configuration);
}
Run Code Online (Sandbox Code Playgroud)
这是我们的问题: 我们项目的凭据在哪里或如何配置?
预先感谢您的回答。
小智 7
我找到了一种仅使用appsettings.json 文件中的值来配置 AWS 凭证的方法。我将在下面详细说明,以防它对某人有所帮助。小心!这不是 AWS 推荐的方式,我只是需要它来满足这个特定的用例。
在此示例中,我需要 AWS 凭证(访问密钥 ID 和访问密钥)以及区域,以及我需要的 SQS 队列客户端的一些其他配置。该应用程序是一个 .Net 5 Worker Service(它具有开箱即用的依赖项注入和配置文件设置,就像 ASP.Net Core Web 应用程序一样)。
这是 appsettings.json 文件:
{
"AwsSqsConfiguration": {
"AWSAccessKey": "ACCESSKEYID",
"AWSSecretKey": "SECRETKEY",
"AWSRegion": "us-west-2",
"AWSQueueUrl": "https://sqs.us-east-1.amazonaws.com/rest-of-queue-url",
"AWSQueueServiceUrl": "http://sqs.us-east-1.amazonaws.com"
},
"Logging": {
"LogLevel": {
"Default": "Information",
"Microsoft": "Warning",
"Microsoft.Hosting.Lifetime": "Information"
}
}
}
Run Code Online (Sandbox Code Playgroud)
以下是配置部分“AwsSqsConfiguration”的相应 C# 9 记录:
public record AwsSqsConfiguration (
string AWSAccessKey = null,
string AWSSecretKey = null,
string AWSRegion = null,
string AWSQueueUrl = null,
string AWSQueueServiceUrl = null);
Run Code Online (Sandbox Code Playgroud)
这是 Program.cs 类(类似于 ASP.Net Core Web 应用程序的 Startup.cs 类)。请注意使用Amazon.Runtime.BasicAWSCredentials传入访问密钥和秘密密钥:
using Amazon.Extensions.NETCore.Setup;
using Amazon.SQS;
using Microsoft.Extensions.Configuration;
using Microsoft.Extensions.DependencyInjection;
using Microsoft.Extensions.Hosting;
using PlatformDeploymentService.Core.Factories;
using PlatformDeploymentService.Core.Interfaces;
using PlatformDeploymentService.Core.Models.Configuration;
using PlatformDeploymentService.Core.Services;
namespace PlatformDeploymentService.WorkerService
{
public class Program
{
public static void Main(string[] args)
{
CreateHostBuilder(args).Build().Run();
}
public static IHostBuilder CreateHostBuilder(string[] args) =>
Host.CreateDefaultBuilder(args)
.ConfigureAppConfiguration((hostingContext, configuration) => {
configuration.Sources.Clear();
IHostEnvironment env = hostingContext.HostingEnvironment;
configuration
.SetBasePath(env.ContentRootPath)
.AddJsonFile("appsettings.json", optional: true, reloadOnChange: true)
.AddJsonFile($"appsettings.{env.EnvironmentName}.json", true, true)
.AddEnvironmentVariables();
})
.ConfigureServices((hostContext, services) =>
{
services.AddHostedService<Worker>();
var awsSqsConfiguration = new AwsSqsConfiguration();
hostContext.Configuration.GetSection(nameof(AwsSqsConfiguration)).Bind(awsSqsConfiguration);
AWSOptions awsOptions = new AWSOptions
{
Credentials = new Amazon.Runtime.BasicAWSCredentials(awsSqsConfiguration.AWSAccessKey, awsSqsConfiguration.AWSSecretKey),
Region = Amazon.RegionEndpoint.GetBySystemName(awsSqsConfiguration.AWSRegion)
};
services.AddDefaultAWSOptions(awsOptions);
services.AddSingleton<IAmazonSQS>(sp => new AmazonSQSClient(awsOptions.Credentials, new AmazonSQSConfig { ServiceURL = awsSqsConfiguration.AWSQueueServiceUrl }));
});
}
}
Run Code Online (Sandbox Code Playgroud)
以及该 Program.cs 类中使用的 Nuget 包的包引用:
<ItemGroup>
<PackageReference Include="AWSSDK.Extensions.NETCore.Setup" Version="3.3.101" />
<PackageReference Include="Microsoft.Extensions.Hosting" Version="5.0.0" />
<PackageReference Include="Microsoft.VisualStudio.Azure.Containers.Tools.Targets" Version="1.10.9" />
</ItemGroup>
Run Code Online (Sandbox Code Playgroud)
然后,只要您需要 SQS 客户端对消息进行排队或其他任何操作,您就会在构造函数中收到一个 IAmazonSQS 实例,以便依赖项注入可以注入它。
参考:
在 AWS 中,您可以创建一个 IAM 角色并将其配置为只能访问它需要的资源(S3 读/写、SES 等)。然后,您可以将此角色附加到 EC2 实例。
如果您使用的是 AWS 开发工具包,请使用以下内容:
services.AddDefaultAWSOptions(Configuration.GetAWSOptions());
services.AddAWSService<IAmazonS3>();
Run Code Online (Sandbox Code Playgroud)
它会自动为您处理权限。
对于本地开发,您可能想要使用凭证文件。在您中,appsettings.Local.json
您将有一个类似于此的设置:
"AWS": {
"Profile": "myprofilename",
"Region": "eu-west-1",
"ProfilesLocation": "C:\\Credentials.txt"
}
Run Code Online (Sandbox Code Playgroud)
您可能希望将凭据文件存储在项目之外,以免意外将其签入源代码管理。
Credentials.txt 看起来像:
[myprofilename]
aws_access_key_id=MY_ACCESS_KEY
aws_secret_access_key=MY_ACCESS_SECRET
Run Code Online (Sandbox Code Playgroud)
设置环境
您可能希望位于服务器上的代码对于每个环境都相同——它使部署和其他任务变得更加容易。您可以通过使用 Parameter Store 存储每个 AWS 环境的所有配置来实现这一点。
我这样做的方法是在 EC2 实例上使用“标签”来指定环境名称。然后我使用标签从 Parameter Store 获取正确的配置。
在您的情况下,标签将是environment=development
或environment=production
商店中的参数名称/键应与您要覆盖的 JSON appsettings 文件中的属性名称相匹配。
它们看起来类似于:
/开发/ConnectionStrings/数据库 /development/MySettingGroup/MySetting /生产/ConnectionStrings/数据库 /生产/我的设置组/我的设置
我已经向 github 添加了一些代码来检查标签和参数等 - 如果它在本地运行,它默认为“LocalDevelopment”的环境名称(这是我使用的约定 - 所以你需要将其更改为“Local”)并加载正确的 appsettings 文件。
https://github.com/secretorange/aws-aspnetcore-environment-startup
您需要在项目中使用的文件在这里:
https://github.com/secretorange/aws-aspnetcore-environment-startup/tree/master/AWSBoot/Boot
使用BootHelper
您的启动代码看起来与此类似:
public static IWebHost BuildWebHost()
{
// ===================================
// Get the boot config from the server
// ===================================
var bootConfig = Task.Run(() => BootHelper.GetConfig()).Result;
var webHost = new WebHostBuilder()
.UseKestrel()
.UseContentRoot(Directory.GetCurrentDirectory())
.ConfigureAppConfiguration((context, config) =>
{
// !!! IMPORTANT !!!
// Set the environment from boot config
context.HostingEnvironment.EnvironmentName = bootConfig.Environment;
config.AddJsonFile("appsettings.json", optional: true)
.AddJsonFile($"appsettings.{context.HostingEnvironment.EnvironmentName}.json", optional: true);
// !!! IMPORTANT !!!
// If there are any parameters from the server
// then we'll use them to override anything in the JSON files
config.AddInMemoryCollection(bootConfig.Parameters);
})
.UseIISIntegration()
.UseStartup<Startup>()
.Build();
return webHost;
}
Run Code Online (Sandbox Code Playgroud)
AWS 中的 IAM 角色需要附加策略以授予对标签和参数等的访问权限。它们将类似于:
{
"Version": "2012-10-17",
"Statement": [
{
"Sid": "VisualEditor0",
"Effect": "Allow",
"Action": [
"ec2:DescribeInstances",
"tag:GetResources",
"tag:GetTagValues",
"tag:GetTagKeys"
],
"Resource": "*"
}
]
}
{
"Version": "2012-10-17",
"Statement": [
{
"Sid": "VisualEditor0",
"Effect": "Allow",
"Action": "ssm:GetParametersByPath",
"Resource": [
"arn:aws:ssm:YOUR_ARN_HERE:parameter/development",
"arn:aws:ssm:YOUR_ARN_HERE:parameter/development/*"
]
}
]
}
Run Code Online (Sandbox Code Playgroud)
设置似乎有点麻烦 - 但是一旦它开始运行,这意味着您可以轻松地将所有秘密置于源代码控制之外,并且只需创建一个新标签和参数即可创建一个新环境(例如 Staging) . 无需更改代码。
如果你愿意,你可以保留一些配置appsettings.Production.json
- 这只是意味着如果你想创建一个新环境,你需要创建一个新的 JSON 文件并部署新代码等。如果所有环境信息都是在 AWS(即参数存储)中。
我的目标是.net Core 2.0而不是1.1,并且还在VS中添加环境变量(ASPNETCORE_ENVIRONMENT、AWS_SECRET_ACCESS_KEY、AWS_ACCESS_KEY_ID、AWS_DEFAULT_REGION)并且它有效!
感谢您的帮助拉杰什。
但如果有人知道为什么它现在有效,请提前感谢您在这里写下您的答案。
归档时间: |
|
查看次数: |
15887 次 |
最近记录: |