引言
互聯網每隔一段時間就會爆出 【某程序猿在代碼托管平台上傳了公司機密配置信息,導致公司核心數據被黑客獲取或修改】, 一茬又一茬背鍋俠層出不窮。拯救自我
軟件工程理論早以加粗字體給出 經典原則:Never store production passwords or other sensitive data in source code
頭腦風暴
.Net Framework
原配置節 <configuration> <appSettings file="appsecrets.config"> <add key="FtpUserId" value="test_userid" /> <add key="FtpPwd" value="test-pwd"> </appSettings> </configuration>
外置配置文件 <?xml version="1.0" encoding="utf-8" ?> <appSettings> <add key="FtpUrl" value="sftp.rategain.com" /> <add key="FtpUserId" value="RateGain_M&C" /> <add key="FtpPwd" value="RateGain@123" /> <add key="RemotePath" value="/M&C/" /> <!--路徑 /M&C/ 需要轉義--> </appSettings>
var hostBuilder = WebHost.CreateDefaultBuilder(args) .ConfigureAppConfiguration((context, builder) => { builder.AddJsonFile($"appsettings.secrets.json", optional: true); if (context.HostingEnvironment.IsDevelopment()) { builder.AddUserSecrets<Startup>(true); } builder.AddEnvironmentVariables(); }) .UseStartup<Startup>();
據此思路,可將敏感信息交由其他組件托管,.NetCore開發者還有其他3種實踐:
- 適用於Dev的Secrets manager tool 托管
ASP.NETCore 在開發環境下保存密鑰的方式,總體思路是使用一個匿名GUID引用存儲在系統文件夾下的同名配置Json。
- 適用於Azure雲的 Azure Key Vault 托管
https://azure.microsoft.com/en-us/resources/samples/key-vault-dotnet-core-quickstart/
- 適用於General Deploy的環境變量托管
下面對環境變量方式分離敏感信息做進一步說明。
環境變量托管
環境變量能在進程創建時被導入/注入,因此可作為一種敏感信息分離的思路, 環境變量來自三個級別 :系統、用戶、進程。
介紹幾種修改環境變量的方式:
①Windows-CMD命令行: setx命令, 注意該方式設置的環境變量需要在新的CMD界面上才能驗證生效。
②系統控制面板-我的電腦-屬性-高級設置-環境變量
以上兩種形式均為在ASP.NET Core進程啟動時導入系統環境變量,
③在Visual Studio launchsettings.json設定進程啟動時注入環境變量

{ "iisSettings": { "windowsAuthentication": false, "anonymousAuthentication": true, "iisExpress": { "applicationUrl": "http://localhost:11761/", "sslPort": 0 } }, "profiles": { "IIS Express": { "commandName": "IISExpress", "launchBrowser": true, "environmentVariables": { "ASPNETCORE_ENVIRONMENT": "Development" } }, "JumpServer": { "commandName": "Project", "launchBrowser": true, "applicationUrl": "http://localhost:5020", "environmentVariables": { "ASPNETCORE_ENVIRONMENT": "production" , "ASPNETCORE_URLS": "http://localhost:5020" } } } }
④在VScode launchsettings.json設定進程啟動時注入環境變量

{ "version": "0.2.0", "configurations": [ { "name": ".NET Core Launch (web)", "type": "coreclr", "request": "launch", "preLaunchTask": "build", "program": "${workspaceRoot}/bin/Debug/netcoreapp1.0/TestApp.dll", "args": [], "cwd": "${workspaceRoot}", "stopAtEntry": false, "launchBrowser": { "enabled": true, "args": "${auto-detect-url}", "windows": { "command": "cmd.exe", "args": "/C start ${auto-detect-url}" }, "osx": { "command": "open" }, "linux": { "command": "xdg-open" } }, "env": { "ASPNETCORE_ENVIRONMENT": "Development" }, "sourceFileMap": { "/Views": "${workspaceRoot}/Views" } } ] }
⑤ 在進程啟動時通過命令行參數注入,這種方式嚴格來說並不屬於環境變量方式,是一種參數配置。
public static IWebHost BuildWebHost(string[] args) { var webHostBuilder = WebHost.CreateDefaultBuilder(args) .ConfigureAppConfiguration((hostingContext, configBuilder) => { // 啟用命令行參數配置 configBuilder.AddCommandLine(args)
.AddEnvironmentVariables(); if (hostingContext.HostingEnvironment.IsDevelopment()) configBuilder.AddUserSecrets<Startup>(true); }) .ConfigureLogging((hostingContext, logging) => { logging.AddAzureWebAppDiagnostics(); }) .UseStartup<Startup>(); return webHostBuilder.Build(); }
--------------
dotnet run --environment "development"
⑥ 若使用IIS托管AspNetCore,可在IIS的配置編輯器新增/重寫環境變量

在.NetCore生產部署實踐中,比較常用的方式是使用獨立的appsettings.secrets.json或環境變量來分離敏感信息。
掌握這些,.Net程序猿應該就不會因為在git上傳機密信息而背鍋了。
~~~~~~~~~更多方式,歡迎大家留言補充。~~~~