1
0
mirror of https://github.com/bitwarden/server.git synced 2025-07-15 22:57:44 -05:00

[PM-18770] Convert Organization to Business Unit (#5610)

* [NO LOGIC] Rename MultiOrganizationEnterprise to BusinessUnit

* [Core] Add IMailService.SendBusinessUnitConversionInviteAsync

* [Core] Add BusinessUnitConverter

* [Admin] Add new permission

* [Admin] Add BusinessUnitConverterController

* [Admin] Add Convert to Business Unit button to Organization edit page

* [Api] Add OrganizationBillingController.SetupBusinessUnitAsync action

* [Multi] Propagate provider type to sync response

* [Multi] Put updates behind feature flag

* [Tests] BusinessUnitConverterTests

* Run dotnet format

* Fixing post-main merge compilation failure
This commit is contained in:
Alex Morask
2025-04-10 10:06:16 -04:00
committed by GitHub
parent d85807e94f
commit 54e7fac4d9
41 changed files with 1513 additions and 64 deletions

View File

@ -25,19 +25,19 @@ public static class BillingExtensions
public static bool IsBillable(this Provider provider) =>
provider is
{
Type: ProviderType.Msp or ProviderType.MultiOrganizationEnterprise,
Type: ProviderType.Msp or ProviderType.BusinessUnit,
Status: ProviderStatusType.Billable
};
public static bool IsBillable(this InviteOrganizationProvider inviteOrganizationProvider) =>
inviteOrganizationProvider is
{
Type: ProviderType.Msp or ProviderType.MultiOrganizationEnterprise,
Type: ProviderType.Msp or ProviderType.BusinessUnit,
Status: ProviderStatusType.Billable
};
public static bool SupportsConsolidatedBilling(this ProviderType providerType)
=> providerType is ProviderType.Msp or ProviderType.MultiOrganizationEnterprise;
=> providerType is ProviderType.Msp or ProviderType.BusinessUnit;
public static bool IsValidClient(this Organization organization)
=> organization is

View File

@ -0,0 +1,58 @@
using Bit.Core.AdminConsole.Entities;
using Bit.Core.AdminConsole.Entities.Provider;
using Bit.Core.AdminConsole.Enums.Provider;
using OneOf;
namespace Bit.Core.Billing.Services;
public interface IBusinessUnitConverter
{
/// <summary>
/// Finalizes the process of converting the <paramref name="organization"/> to a <see cref="ProviderType.BusinessUnit"/> by
/// saving all the necessary key provided by the client and updating the <paramref name="organization"/>'s subscription to a
/// provider subscription.
/// </summary>
/// <param name="organization">The organization to convert to a business unit.</param>
/// <param name="userId">The ID of the organization member who will be the provider admin.</param>
/// <param name="token">The token sent to the client as part of the <see cref="InitiateConversion"/> process.</param>
/// <param name="providerKey">The encrypted provider key used to enable the <see cref="ProviderUser"/>.</param>
/// <param name="organizationKey">The encrypted organization key used to enable the <see cref="ProviderOrganization"/>.</param>
/// <returns>The provider ID</returns>
Task<Guid> FinalizeConversion(
Organization organization,
Guid userId,
string token,
string providerKey,
string organizationKey);
/// <summary>
/// Begins the process of converting the <paramref name="organization"/> to a <see cref="ProviderType.BusinessUnit"/> by
/// creating all the necessary database entities and sending a setup invitation to the <paramref name="providerAdminEmail"/>.
/// </summary>
/// <param name="organization">The organization to convert to a business unit.</param>
/// <param name="providerAdminEmail">The email address of the organization member who will be the provider admin.</param>
/// <returns>Either the newly created provider ID or a list of validation failures.</returns>
Task<OneOf<Guid, List<string>>> InitiateConversion(
Organization organization,
string providerAdminEmail);
/// <summary>
/// Checks if the <paramref name="organization"/> has a business unit conversion in progress and, if it does, resends the
/// setup invitation to the provider admin.
/// </summary>
/// <param name="organization">The organization to convert to a business unit.</param>
/// <param name="providerAdminEmail">The email address of the organization member who will be the provider admin.</param>
Task ResendConversionInvite(
Organization organization,
string providerAdminEmail);
/// <summary>
/// Checks if the <paramref name="organization"/> has a business unit conversion in progress and, if it does, resets that conversion
/// by deleting all the database entities created as part of <see cref="InitiateConversion"/>.
/// </summary>
/// <param name="organization">The organization to convert to a business unit.</param>
/// <param name="providerAdminEmail">The email address of the organization member who will be the provider admin.</param>
Task ResetConversion(
Organization organization,
string providerAdminEmail);
}