ASP.NET Core에서 개발 하는 동안 앱 암호의 안전한 저장소Safe storage of app secrets during development in ASP.NET Core

Rick Anderson, 김 Roth, 및 Scott AddieBy Rick Anderson, Daniel Roth, and Scott Addie

이 문서 코드 나가기를 비밀을 유지 하려면 개발에서 암호 관리자 도구를 사용 하는 방법을 보여줍니다.This document shows how you can use the Secret Manager tool in development to keep secrets out of your code. 가장 중요 한 점은 소스 코드에서 암호 또는 기타 중요 한 데이터를 저장 하지 않으며 해야 하 고 개발 및 테스트 모드에서 프로덕션 암호를 사용 하지 않아야 합니다.The most important point is you should never store passwords or other sensitive data in source code, and you shouldn't use production secrets in development and test mode. 대신 사용할 수 있습니다는 구성 시스템 환경 변수에서 이러한 값을 읽거나 암호 관리자를 사용 하 여 저장 된 값에서 도구입니다.You can instead use the configuration system to read these values from environment variables or from values stored using the Secret Manager tool. 암호 관리자 도구에서 소스 제어에 체크 인 되 고 중요 한 데이터를 방지할 수 있습니다.The Secret Manager tool helps prevent sensitive data from being checked into source control. 구성 시스템이이 문서에 설명 된 비밀 관리자 도구와 함께 저장 된 암호를 읽을 수 있습니다.The configuration system can read secrets stored with the Secret Manager tool described in this article.

암호 관리자 도구 개발에만 사용 됩니다.The Secret Manager tool is used only in development. 와 Azure 테스트 및 프로덕션 비밀을 보호할 수는 Microsoft Azure Key Vault 구성 공급자입니다.You can safeguard Azure test and production secrets with the Microsoft Azure Key Vault configuration provider. 참조 Azure 키 자격 증명 모음 구성 공급자 자세한 정보에 대 한 합니다.See Azure Key Vault configuration provider for more information.

환경 변수Environment variables

에 로컬 구성 파일 또는 코드에서 앱 암호를 저장 하지 않도록 하려면 환경 변수에서 암호를 저장 합니다.To avoid storing app secrets in code or in local configuration files, you store secrets in environment variables. 설정할 수 있습니다는 구성 프레임 워크를 호출 하 여 환경 변수에서 값을 읽을 AddEnvironmentVariables합니다.You can setup the configuration framework to read values from environment variables by calling AddEnvironmentVariables. 그런 다음 환경 변수를 사용 하 여 모든 이전에 지정 된 구성 소스에 대 한 구성 값을 재정의 합니다.You can then use environment variables to override configuration values for all previously specified configuration sources.

예를 들어, 개별 사용자 계정으로 새 ASP.NET Core 웹 앱을 만들면 기본 연결 문자열을 추가 되는 appsettings.json 키를 사용 하 여 프로젝트의 파일 DefaultConnection합니다.For example, if you create a new ASP.NET Core web app with individual user accounts, it will add a default connection string to the appsettings.json file in the project with the key DefaultConnection. 기본 연결 문자열에는 사용자 모드에서 실행 되 고 암호가 필요 하지 않습니다는 LocalDB를 사용 하도록 설정 되어 있습니다.The default connection string is setup to use LocalDB, which runs in user mode and doesn't require a password. 테스트 또는 프로덕션 서버에 응용 프로그램을 배포할 때 재정의할 수 있습니다는 DefaultConnection 테스트 또는 프로덕션 데이터베이스에 대 한 연결 문자열 (잠재적으로 중요 한 자격 증명)을 포함 하는 환경 변수 설정을 사용 하 여 키 값 서버입니다.When you deploy your application to a test or production server, you can override the DefaultConnection key value with an environment variable setting that contains the connection string (potentially with sensitive credentials) for a test or production database server.

경고

환경 변수는 일반적으로 일반 텍스트로 저장 되며 암호화 되지 않습니다.Environment variables are generally stored in plain text and are not encrypted. 컴퓨터 또는 프로세스가 손상 된 환경 변수 신뢰할 수 없는 당사자가 액세스할 수 있습니다.If the machine or process is compromised, then environment variables can be accessed by untrusted parties. 여전히 사용자 비밀 정보를 공개 하지 않도록 추가 조치가 필요할 수 있습니다.Additional measures to prevent disclosure of user secrets may still be required.

암호 관리자Secret Manager

암호 관리자 도구는 프로젝트 트리 외부의 개발 작업에 대 한 중요 한 데이터를 저장합니다.The Secret Manager tool stores sensitive data for development work outside of your project tree. 암호 관리자 도구는에 대 한 기밀 정보를 사용할 수 있는 프로젝트 도구는 .NET Core 개발 중 프로젝트.The Secret Manager tool is a project tool that can be used to store secrets for a .NET Core project during development. 암호 관리자 도구를 사용 특정 프로젝트와 앱 암호를 연결 하 고 여러 프로젝트 간에 공유할 수 있습니다.With the Secret Manager tool, you can associate app secrets with a specific project and share them across multiple projects.

경고

암호 관리자 도구 저장 된 암호를 암호화 하지 않습니다 하 고 신뢰할 수 있는 저장소로 처리 되지 해야 합니다.The Secret Manager tool does not encrypt the stored secrets and should not be treated as a trusted store. 개발 용도로입니다.It is for development purposes only. 키와 값은 사용자 프로필 디렉터리에는 JSON 구성 파일에 저장 됩니다.The keys and values are stored in a JSON configuration file in the user profile directory.

암호 관리자 도구를 설치합니다.Installing the Secret Manager tool

솔루션 탐색기에서 프로젝트를 마우스 오른쪽 단추로 클릭 하 고 선택 편집 <project_name>.csproj 상황에 맞는 메뉴입니다.Right-click the project in Solution Explorer, and select Edit <project_name>.csproj from the context menu. 강조 표시 된 줄을 추가 .csproj 파일과 연결 된 NuGet 패키지를 복원 하려면 저장:Add the highlighted line to the .csproj file, and save to restore the associated NuGet package:

<Project Sdk="Microsoft.NET.Sdk.Web">
  <PropertyGroup>
    <TargetFramework>netcoreapp2.0</TargetFramework>
  </PropertyGroup>
  <ItemGroup>
    <PackageReference Include="Microsoft.AspNetCore.All" Version="2.0.0" />
  </ItemGroup>
  <ItemGroup>
    <DotNetCliToolReference Include="Microsoft.VisualStudio.Web.CodeGeneration.Tools" Version="2.0.0" />
    <DotNetCliToolReference Include="Microsoft.Extensions.SecretManager.Tools" Version="2.0.0" />
  </ItemGroup>
</Project>

솔루션 탐색기에서 프로젝트를 다시 마우스 오른쪽 단추로 클릭 하 고 선택 관리 사용자의 비밀 상황에 맞는 메뉴입니다.Right-click the project in Solution Explorer again, and select Manage User Secrets from the context menu. 이 제스처를 새로 추가 UserSecretsId 내에서 노드는 PropertyGroup.csproj 다음 샘플에 강조 표시 된 대로 파일:This gesture adds a new UserSecretsId node within a PropertyGroup of the .csproj file, as highlighted in the following sample:

<Project Sdk="Microsoft.NET.Sdk.Web">
  <PropertyGroup>
    <TargetFramework>netcoreapp2.0</TargetFramework>
    <UserSecretsId>User-Secret-ID</UserSecretsId>
  </PropertyGroup>
  <ItemGroup>
    <PackageReference Include="Microsoft.AspNetCore.All" Version="2.0.0" />
  </ItemGroup>
  <ItemGroup>
    <DotNetCliToolReference Include="Microsoft.VisualStudio.Web.CodeGeneration.Tools" Version="2.0.0" />
    <DotNetCliToolReference Include="Microsoft.Extensions.SecretManager.Tools" Version="2.0.0" />
  </ItemGroup>
</Project>

수정 된 저장 .csproj 파일도 열립니다는 secrets.json 파일 텍스트 편집기에서.Saving the modified .csproj file also opens a secrets.json file in the text editor. 내용을 대체는 secrets.json 를 다음 코드로 파일:Replace the contents of the secrets.json file with the following code:

{
    "MySecret": "ValueOfMySecret"
}

구성을 통해 사용자의 비밀 정보에 액세스Accessing user secrets via configuration

구성 시스템을 통해 보안 관리자 암호에 액세스 합니다.You access Secret Manager secrets through the configuration system. 추가 Microsoft.Extensions.Configuration.UserSecrets 패키지 및 실행 dotnet restore합니다.Add the Microsoft.Extensions.Configuration.UserSecrets package and run dotnet restore.

사용자 암호 구성 소스를 추가 Startup 메서드:Add the user secrets configuration source to the Startup method:

using Microsoft.AspNetCore.Builder;
using Microsoft.AspNetCore.Hosting;
using Microsoft.AspNetCore.Http;
using Microsoft.Extensions.Configuration;
using Microsoft.Extensions.DependencyInjection;

namespace UserSecrets
{
    public class Startup
    {
        string _testSecret = null;
        public Startup(IHostingEnvironment env)
        {
            var builder = new ConfigurationBuilder();

            if (env.IsDevelopment())
            {
                builder.AddUserSecrets<Startup>();
            }

            Configuration = builder.Build();
        }

        public IConfigurationRoot Configuration { get; }

        public void ConfigureServices(IServiceCollection services)
        {
            _testSecret = Configuration["MySecret"];
        }

        public void Configure(IApplicationBuilder app)
        {
            var result = string.IsNullOrEmpty(_testSecret) ? "Null" : "Not Null";
            app.Run(async (context) =>
            {
                await context.Response.WriteAsync($"Secret is {result}");
            });
        }
    }
}

구성 API 통해 사용자의 비밀을 액세스할 수 있습니다.You can access user secrets via the configuration API:

using Microsoft.AspNetCore.Builder;
using Microsoft.AspNetCore.Hosting;
using Microsoft.AspNetCore.Http;
using Microsoft.Extensions.Configuration;
using Microsoft.Extensions.DependencyInjection;

namespace UserSecrets
{
    public class Startup
    {
        string _testSecret = null;
        public Startup(IHostingEnvironment env)
        {
            var builder = new ConfigurationBuilder();

            if (env.IsDevelopment())
            {
                builder.AddUserSecrets<Startup>();
            }

            Configuration = builder.Build();
        }

        public IConfigurationRoot Configuration { get; }

        public void ConfigureServices(IServiceCollection services)
        {
            _testSecret = Configuration["MySecret"];
        }

        public void Configure(IApplicationBuilder app)
        {
            var result = string.IsNullOrEmpty(_testSecret) ? "Null" : "Not Null";
            app.Run(async (context) =>
            {
                await context.Response.WriteAsync($"Secret is {result}");
            });
        }
    }
}

암호 관리자 도구 작동 방식How the Secret Manager tool works

암호 관리자 도구 값을 저장 하는 위치와 방법을 같은 구현 세부 정보를 추상화 합니다.The Secret Manager tool abstracts away the implementation details, such as where and how the values are stored. 이러한 구현 정보를 알 필요 없이 도구를 사용할 수 있습니다.You can use the tool without knowing these implementation details. 현재 버전의 값에 저장 됩니다는 JSON 사용자 프로필 디렉터리에 구성 파일:In the current version, the values are stored in a JSON configuration file in the user profile directory:

  • Windows:%APPDATA%\microsoft\UserSecrets\<userSecretsId>\secrets.jsonWindows: %APPDATA%\microsoft\UserSecrets\<userSecretsId>\secrets.json

  • Linux:~/.microsoft/usersecrets/<userSecretsId>/secrets.jsonLinux: ~/.microsoft/usersecrets/<userSecretsId>/secrets.json

  • Mac:~/.microsoft/usersecrets/<userSecretsId>/secrets.jsonMac: ~/.microsoft/usersecrets/<userSecretsId>/secrets.json

userSecretsId 에 지정 된 값에서 가져온 .csproj 파일입니다.The value of userSecretsId comes from the value specified in .csproj file.

이러한 구현 정보 변경 될 수 있으므로 위치 또는 보안 관리자 도구와 함께 저장 된 데이터의 형식에 의존 하는 코드를 작성 하지 말아야 합니다.You should not write code that depends on the location or format of the data saved with the Secret Manager tool, as these implementation details might change. 예를 들어 비밀 값은 현재 하지 오늘 암호화 되지만 언젠가 수 있습니다.For example, the secret values are currently not encrypted today, but could be someday.

추가 리소스Additional Resources