1
0
mirror of https://github.com/bitwarden/server.git synced 2024-12-22 16:57:36 +01:00

enable default appsettings for self hosted installs (#1263)

* enable default appsettings for self hosted installs

* change setters to use arrow functions

* fix tests

* fix global settings ref
This commit is contained in:
Kyle Spearrin 2021-04-09 09:48:43 -04:00 committed by GitHub
parent c1ceeace95
commit 83e68bce06
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
16 changed files with 373 additions and 82 deletions

View File

@ -11,6 +11,7 @@ namespace Bit.Admin
{
Host
.CreateDefaultBuilder(args)
.ConfigureCustomAppConfiguration(args)
.ConfigureWebHostDefaults(webBuilder =>
{
webBuilder.ConfigureKestrel(o =>

View File

@ -0,0 +1,20 @@
{
"globalSettings": {
"baseServiceUri": {
"vault": null,
"api": null,
"identity": null,
"admin": null,
"notifications": null,
"sso": null,
"portal": null,
"internalNotifications": null,
"internalAdmin": null,
"internalIdentity": null,
"internalApi": null,
"internalVault": null,
"internalSso": null,
"internalPortal": null
}
}
}

View File

@ -13,6 +13,7 @@ namespace Bit.Api
{
Host
.CreateDefaultBuilder(args)
.ConfigureCustomAppConfiguration(args)
.ConfigureWebHostDefaults(webBuilder =>
{
webBuilder.UseStartup<Startup>();

View File

@ -0,0 +1,20 @@
{
"globalSettings": {
"baseServiceUri": {
"vault": null,
"api": null,
"identity": null,
"admin": null,
"notifications": null,
"sso": null,
"portal": null,
"internalNotifications": null,
"internalAdmin": null,
"internalIdentity": null,
"internalApi": null,
"internalVault": null,
"internalSso": null,
"internalPortal": null
}
}
}

View File

@ -1,18 +1,36 @@
using System;
using Bit.Core.Enums;
namespace Bit.Core.Settings
{
public class GlobalSettings : IGlobalSettings
{
private string _logDirectory;
private string _licenseDirectory;
public GlobalSettings()
{
BaseServiceUri = new BaseServiceUriSettings(this);
Attachment = new FileStorageSettings(this, "attchments", "attchments");
Send = new FileStorageSettings(this, "attchments/send", "attchments/send");
DataProtection = new DataProtectionSettings(this);
}
public bool SelfHosted { get; set; }
public virtual string KnownProxies { get; set; }
public virtual string SiteName { get; set; }
public virtual string StripeApiKey { get; set; }
public virtual string ProjectName { get; set; }
public virtual string LogDirectory { get; set; }
public virtual string LogDirectory
{
get => BuildDirectory(_logDirectory, "/logs");
set => _logDirectory = value;
}
public virtual long? LogRollBySizeLimit { get; set; }
public virtual string LicenseDirectory { get; set; }
public virtual string LicenseDirectory
{
get => BuildDirectory(_licenseDirectory, "/core/licenses");
set => _licenseDirectory = value;
}
public string LicenseCertificatePassword { get; set; }
public virtual string PushRelayBaseUri { get; set; }
public virtual string InternalIdentityKey { get; set; }
@ -23,17 +41,17 @@ namespace Bit.Core.Settings
public virtual int OrganizationInviteExpirationHours { get; set; } = 120; // 5 days
public virtual string EventGridKey { get; set; }
public virtual InstallationSettings Installation { get; set; } = new InstallationSettings();
public virtual BaseServiceUriSettings BaseServiceUri { get; set; } = new BaseServiceUriSettings();
public virtual BaseServiceUriSettings BaseServiceUri { get; set; }
public virtual SqlSettings SqlServer { get; set; } = new SqlSettings();
public virtual SqlSettings PostgreSql { get; set; } = new SqlSettings();
public virtual MailSettings Mail { get; set; } = new MailSettings();
public virtual ConnectionStringSettings Storage { get; set; } = new ConnectionStringSettings();
public virtual ConnectionStringSettings Events { get; set; } = new ConnectionStringSettings();
public virtual NotificationsSettings Notifications { get; set; } = new NotificationsSettings();
public virtual IFileStorageSettings Attachment { get; set; } = new FileStorageSettings();
public virtual FileStorageSettings Send { get; set; } = new FileStorageSettings();
public virtual IFileStorageSettings Attachment { get; set; }
public virtual FileStorageSettings Send { get; set; }
public virtual IdentityServerSettings IdentityServer { get; set; } = new IdentityServerSettings();
public virtual DataProtectionSettings DataProtection { get; set; } = new DataProtectionSettings();
public virtual DataProtectionSettings DataProtection { get; set; }
public virtual DocumentDbSettings DocumentDb { get; set; } = new DocumentDbSettings();
public virtual SentrySettings Sentry { get; set; } = new SentrySettings();
public virtual SyslogSettings Syslog { get; set; } = new SyslogSettings();
@ -47,21 +65,137 @@ namespace Bit.Core.Settings
public virtual AppleIapSettings AppleIap { get; set; } = new AppleIapSettings();
public virtual SsoSettings Sso { get; set; } = new SsoSettings();
public string BuildExternalUri(string explicitValue, string name)
{
if (!string.IsNullOrWhiteSpace(explicitValue))
{
return explicitValue;
}
if (!SelfHosted)
{
return null;
}
return string.Format("{0}/{1}", BaseServiceUri.Vault, name);
}
public string BuildInternalUri(string explicitValue, string name)
{
if (!string.IsNullOrWhiteSpace(explicitValue))
{
return explicitValue;
}
if (!SelfHosted)
{
return null;
}
return string.Format("http://{0}:5000", name);
}
public string BuildDirectory(string explicitValue, string appendedPath)
{
if (!string.IsNullOrWhiteSpace(explicitValue))
{
return explicitValue;
}
if (!SelfHosted)
{
return null;
}
return string.Concat("/etc/bitwarden", appendedPath);
}
public class BaseServiceUriSettings
{
private readonly GlobalSettings _globalSettings;
private string _api;
private string _identity;
private string _admin;
private string _notifications;
private string _sso;
private string _portal;
private string _internalApi;
private string _internalIdentity;
private string _internalAdmin;
private string _internalNotifications;
private string _internalSso;
private string _internalVault;
private string _internalPortal;
public BaseServiceUriSettings(GlobalSettings globalSettings)
{
_globalSettings = globalSettings;
}
public string Vault { get; set; }
public string VaultWithHash => $"{Vault}/#";
public string Api { get; set; }
public string Identity { get; set; }
public string Admin { get; set; }
public string Notifications { get; set; }
public string Sso { get; set; }
public string InternalNotifications { get; set; }
public string InternalAdmin { get; set; }
public string InternalIdentity { get; set; }
public string InternalApi { get; set; }
public string InternalVault { get; set; }
public string InternalSso { get; set; }
public string Api
{
get => _globalSettings.BuildExternalUri(_api, "api");
set => _api = value;
}
public string Identity
{
get => _globalSettings.BuildExternalUri(_identity, "identity");
set => _identity = value;
}
public string Admin
{
get => _globalSettings.BuildExternalUri(_admin, "admin");
set => _admin = value;
}
public string Notifications
{
get => _globalSettings.BuildExternalUri(_notifications, "notifications");
set => _notifications = value;
}
public string Sso
{
get => _globalSettings.BuildExternalUri(_sso, "sso");
set => _sso = value;
}
public string Portal
{
get => _globalSettings.BuildExternalUri(_portal, "portal");
set => _portal = value;
}
public string InternalNotifications
{
get => _globalSettings.BuildInternalUri(_internalNotifications, "notifications");
set => _internalNotifications = value;
}
public string InternalAdmin
{
get => _globalSettings.BuildInternalUri(_internalAdmin, "admin");
set => _internalAdmin = value;
}
public string InternalIdentity
{
get => _globalSettings.BuildInternalUri(_internalIdentity, "identity");
set => _internalIdentity = value;
}
public string InternalApi
{
get => _globalSettings.BuildInternalUri(_internalApi, "api");
set => _internalApi = value;
}
public string InternalVault
{
get => _globalSettings.BuildInternalUri(_internalVault, "web");
set => _internalVault = value;
}
public string InternalSso
{
get => _globalSettings.BuildInternalUri(_internalSso, "sso");
set => _internalSso = value;
}
public string InternalPortal
{
get => _globalSettings.BuildInternalUri(_internalPortal, "portal");
set => _internalPortal = value;
}
}
public class SqlSettings
@ -73,29 +207,20 @@ namespace Bit.Core.Settings
public string ConnectionString
{
get => _connectionString;
set
{
_connectionString = value.Trim('"');
}
set => _connectionString = value.Trim('"');
}
public string ReadOnlyConnectionString
{
get => string.IsNullOrWhiteSpace(_readOnlyConnectionString) ?
_connectionString : _readOnlyConnectionString;
set
{
_readOnlyConnectionString = value.Trim('"');
}
set => _readOnlyConnectionString = value.Trim('"');
}
public string JobSchedulerConnectionString
{
get => _jobSchedulerConnectionString;
set
{
_jobSchedulerConnectionString = value.Trim('"');
}
set => _jobSchedulerConnectionString = value.Trim('"');
}
}
@ -106,27 +231,43 @@ namespace Bit.Core.Settings
public string ConnectionString
{
get => _connectionString;
set
{
_connectionString = value.Trim('"');
}
set => _connectionString = value.Trim('"');
}
}
public class FileStorageSettings : IFileStorageSettings
{
private readonly GlobalSettings _globalSettings;
private readonly string _urlName;
private readonly string _directoryName;
private string _connectionString;
private string _baseDirectory;
private string _baseUrl;
public FileStorageSettings(GlobalSettings globalSettings, string urlName, string directoryName)
{
_globalSettings = globalSettings;
_urlName = urlName;
_directoryName = directoryName;
}
public string ConnectionString
{
get => _connectionString;
set
set => _connectionString = value.Trim('"');
}
public string BaseDirectory
{
_connectionString = value.Trim('"');
get => _globalSettings.BuildDirectory(_baseDirectory, string.Concat("/core/", _directoryName));
set => _baseDirectory = value;
}
public string BaseUrl
{
get => _globalSettings.BuildExternalUri(_baseUrl, _urlName);
set => _baseUrl = value;
}
public string BaseDirectory { get; set; }
public string BaseUrl { get; set; }
}
public class MailSettings
@ -157,9 +298,22 @@ namespace Bit.Core.Settings
public class DataProtectionSettings
{
private readonly GlobalSettings _globalSettings;
private string _directory;
public DataProtectionSettings(GlobalSettings globalSettings)
{
_globalSettings = globalSettings;
}
public string CertificateThumbprint { get; set; }
public string CertificatePassword { get; set; }
public string Directory { get; set; }
public string Directory
{
get => _globalSettings.BuildDirectory(_directory, "/core/aspnet-dataprotection");
set => _directory = value;
}
}
public class DocumentDbSettings
@ -228,10 +382,7 @@ namespace Bit.Core.Settings
public string ConnectionString
{
get => _connectionString;
set
{
_connectionString = value.Trim('"');
}
set => _connectionString = value.Trim('"');
}
public string HubName { get; set; }
}
@ -265,9 +416,15 @@ namespace Bit.Core.Settings
public class InstallationSettings
{
private string _identityUri;
public Guid Id { get; set; }
public string Key { get; set; }
public string IdentityUri { get; set; }
public string IdentityUri
{
get => string.IsNullOrWhiteSpace(_identityUri) ? "https://identity.bitwarden.com" : _identityUri;
set => _identityUri = value;
}
}
public class AmazonSettings

View File

@ -0,0 +1,44 @@
using System;
using System.Reflection;
using Microsoft.Extensions.Configuration;
using Microsoft.Extensions.Hosting;
namespace Bit.Core.Utilities
{
public static class HostBuilderExtensions
{
public static IHostBuilder ConfigureCustomAppConfiguration(this IHostBuilder hostBuilder, string[] args)
{
// Reload app configuration with SelfHosted overrides.
return hostBuilder.ConfigureAppConfiguration((hostingContext, config) =>
{
if (Environment.GetEnvironmentVariable("globalSettings__selfHosted")?.ToLower() != "true")
{
return;
}
var env = hostingContext.HostingEnvironment;
config.AddJsonFile("appsettings.json", optional: true, reloadOnChange: true)
.AddJsonFile($"appsettings.{env.EnvironmentName}.json", optional: true, reloadOnChange: true)
.AddJsonFile("appsettings.SelfHosted.json", optional: true, reloadOnChange: true);
if (env.IsDevelopment())
{
var appAssembly = Assembly.Load(new AssemblyName(env.ApplicationName));
if (appAssembly != null)
{
config.AddUserSecrets(appAssembly, optional: true);
}
}
config.AddEnvironmentVariables();
if (args != null)
{
config.AddCommandLine(args);
}
});
}
}
}

View File

@ -12,6 +12,7 @@ namespace Bit.Events
{
Host
.CreateDefaultBuilder(args)
.ConfigureCustomAppConfiguration(args)
.ConfigureWebHostDefaults(webBuilder =>
{
webBuilder.UseStartup<Startup>();

View File

@ -0,0 +1,20 @@
{
"globalSettings": {
"baseServiceUri": {
"vault": null,
"api": null,
"identity": null,
"admin": null,
"notifications": null,
"sso": null,
"portal": null,
"internalNotifications": null,
"internalAdmin": null,
"internalIdentity": null,
"internalApi": null,
"internalVault": null,
"internalSso": null,
"internalPortal": null
}
}
}

View File

@ -12,6 +12,7 @@ namespace Bit.Identity
{
Host
.CreateDefaultBuilder(args)
.ConfigureCustomAppConfiguration(args)
.ConfigureWebHostDefaults(webBuilder =>
{
webBuilder.UseStartup<Startup>();

View File

@ -0,0 +1,20 @@
{
"globalSettings": {
"baseServiceUri": {
"vault": null,
"api": null,
"identity": null,
"admin": null,
"notifications": null,
"sso": null,
"portal": null,
"internalNotifications": null,
"internalAdmin": null,
"internalIdentity": null,
"internalApi": null,
"internalVault": null,
"internalSso": null,
"internalPortal": null
}
}
}

View File

@ -11,6 +11,7 @@ namespace Bit.Notifications
{
Host
.CreateDefaultBuilder(args)
.ConfigureCustomAppConfiguration(args)
.ConfigureWebHostDefaults(webBuilder =>
{
webBuilder.UseStartup<Startup>();

View File

@ -0,0 +1,20 @@
{
"globalSettings": {
"baseServiceUri": {
"vault": null,
"api": null,
"identity": null,
"admin": null,
"notifications": null,
"sso": null,
"portal": null,
"internalNotifications": null,
"internalAdmin": null,
"internalIdentity": null,
"internalApi": null,
"internalVault": null,
"internalSso": null,
"internalPortal": null
}
}
}

View File

@ -0,0 +1,16 @@
using AutoFixture;
namespace Bit.Core.Test.AutoFixture
{
internal class GlobalSettings : ICustomization
{
public void Customize(IFixture fixture)
{
fixture.Customize<Settings.GlobalSettings>(composer => composer
.Without(s => s.BaseServiceUri)
.Without(s => s.Attachment)
.Without(s => s.Send)
.Without(s => s.DataProtection));
}
}
}

View File

@ -1,4 +1,4 @@
using System;
using System;
using System.Collections.Generic;
using AutoFixture;
using AutoFixture.Kernel;
@ -21,7 +21,7 @@ namespace Bit.Core.Test.AutoFixture
public SutProvider(IFixture fixture)
{
_dependencies = new Dictionary<Type, Dictionary<string, object>>();
_fixture = (fixture ?? new Fixture()).WithAutoNSubstitutions();
_fixture = (fixture ?? new Fixture()).WithAutoNSubstitutions().Customize(new GlobalSettings());
_constructorParameterRelay = new ConstructorParameterRelay<TSut>(this, _fixture);
_fixture.Customizations.Add(_constructorParameterRelay);
}

View File

@ -43,7 +43,7 @@ namespace Bit.Core.Test.Services
var ssoConfigRepo = Substitute.For<ISsoConfigRepository>();
var ssoUserRepo = Substitute.For<ISsoUserRepository>();
var referenceEventService = Substitute.For<IReferenceEventService>();
var globalSettings = Substitute.For<GlobalSettings>();
var globalSettings = Substitute.For<Settings.GlobalSettings>();
var taxRateRepository = Substitute.For<ITaxRateRepository>();
var orgService = new OrganizationService(orgRepo, orgUserRepo, collectionRepo, userRepo,
@ -105,7 +105,7 @@ namespace Bit.Core.Test.Services
var ssoConfigRepo = Substitute.For<ISsoConfigRepository>();
var ssoUserRepo = Substitute.For<ISsoUserRepository>();
var referenceEventService = Substitute.For<IReferenceEventService>();
var globalSettings = Substitute.For<GlobalSettings>();
var globalSettings = Substitute.For<Settings.GlobalSettings>();
var taxRateRepo = Substitute.For<ITaxRateRepository>();
var orgService = new OrganizationService(orgRepo, orgUserRepo, collectionRepo, userRepo,

View File

@ -23,21 +23,7 @@ namespace Bit.Setup
["ASPNETCORE_ENVIRONMENT"] = "Production",
["globalSettings__selfHosted"] = "true",
["globalSettings__baseServiceUri__vault"] = "http://localhost",
["globalSettings__baseServiceUri__api"] = "http://localhost/api",
["globalSettings__baseServiceUri__identity"] = "http://localhost/identity",
["globalSettings__baseServiceUri__admin"] = "http://localhost/admin",
["globalSettings__baseServiceUri__sso"] = "http://localhost/sso",
["globalSettings__baseServiceUri__portal"] = "http://localhost/portal",
["globalSettings__baseServiceUri__notifications"] = "http://localhost/notifications",
["globalSettings__baseServiceUri__internalNotifications"] = "http://notifications:5000",
["globalSettings__baseServiceUri__internalAdmin"] = "http://admin:5000",
["globalSettings__baseServiceUri__internalIdentity"] = "http://identity:5000",
["globalSettings__baseServiceUri__internalApi"] = "http://api:5000",
["globalSettings__baseServiceUri__internalVault"] = "http://web:5000",
["globalSettings__baseServiceUri__internalSso"] = "http://sso:5000",
["globalSettings__baseServiceUri__internalPortal"] = "http://portal:5000",
["globalSettings__pushRelayBaseUri"] = "https://push.bitwarden.com",
["globalSettings__installation__identityUri"] = "https://identity.bitwarden.com",
};
_mssqlValues = new Dictionary<string, string>
{
@ -89,23 +75,8 @@ namespace Bit.Setup
_globalOverrideValues = new Dictionary<string, string>
{
["globalSettings__baseServiceUri__vault"] = _context.Config.Url,
["globalSettings__baseServiceUri__api"] = $"{_context.Config.Url}/api",
["globalSettings__baseServiceUri__identity"] = $"{_context.Config.Url}/identity",
["globalSettings__baseServiceUri__admin"] = $"{_context.Config.Url}/admin",
["globalSettings__baseServiceUri__notifications"] = $"{_context.Config.Url}/notifications",
["globalSettings__baseServiceUri__sso"] = $"{_context.Config.Url}/sso",
["globalSettings__baseServiceUri__portal"] = $"{_context.Config.Url}/portal",
["globalSettings__sqlServer__connectionString"] = $"\"{dbConnectionString}\"",
["globalSettings__identityServer__certificatePassword"] = _context.Install?.IdentityCertPassword,
["globalSettings__attachment__baseDirectory"] = $"{_context.OutputDir}/core/attachments",
["globalSettings__attachment__baseUrl"] = $"{_context.Config.Url}/attachments",
["globalSettings__send__baseDirectory"] = $"{_context.OutputDir}/core/attachments/send",
["globalSettings__send__baseUrl"] = $"{_context.Config.Url}/attachments/send",
["globalSettings__dataProtection__directory"] = $"{_context.OutputDir}/core/aspnet-dataprotection",
["globalSettings__logDirectory"] = $"{_context.OutputDir}/logs",
["globalSettings__logRollBySizeLimit"] = string.Empty,
["globalSettings__syslog__destination"] = string.Empty,
["globalSettings__licenseDirectory"] = $"{_context.OutputDir}/core/licenses",
["globalSettings__internalIdentityKey"] = _context.Stub ? "RANDOM_IDENTITY_KEY" :
Helpers.SecureRandomString(64, alpha: true, numeric: true),
["globalSettings__oidcIdentityClientKey"] = _context.Stub ? "RANDOM_IDENTITY_KEY" :
@ -134,8 +105,6 @@ namespace Bit.Setup
_mssqlOverrideValues = new Dictionary<string, string>
{
["ACCEPT_EULA"] = "Y",
["MSSQL_PID"] = "Express",
["SA_PASSWORD"] = dbPassword,
};
}