mirror of
https://github.com/bitwarden/server.git
synced 2025-06-14 23:10:48 -05:00
Moved user license out of user service
This commit is contained in:
parent
ad47990b3f
commit
82fe94de6b
@ -5,6 +5,7 @@ using Bit.Admin.Models;
|
||||
using Bit.Admin.Utilities;
|
||||
using Bit.Core.AdminConsole.Entities;
|
||||
using Bit.Core.AdminConsole.Repositories;
|
||||
using Bit.Core.Billing.Licenses.Queries;
|
||||
using Bit.Core.Entities;
|
||||
using Bit.Core.Models.BitStripe;
|
||||
using Bit.Core.OrganizationFeatures.OrganizationLicenses.Interfaces;
|
||||
@ -25,6 +26,7 @@ public class ToolsController : Controller
|
||||
private readonly GlobalSettings _globalSettings;
|
||||
private readonly IOrganizationRepository _organizationRepository;
|
||||
private readonly ICloudGetOrganizationLicenseQuery _cloudGetOrganizationLicenseQuery;
|
||||
private readonly IGetUserLicenseQuery _getUserLicenseQuery;
|
||||
private readonly IUserService _userService;
|
||||
private readonly ITransactionRepository _transactionRepository;
|
||||
private readonly IInstallationRepository _installationRepository;
|
||||
@ -38,6 +40,7 @@ public class ToolsController : Controller
|
||||
GlobalSettings globalSettings,
|
||||
IOrganizationRepository organizationRepository,
|
||||
ICloudGetOrganizationLicenseQuery cloudGetOrganizationLicenseQuery,
|
||||
IGetUserLicenseQuery getUserLicenseQuery,
|
||||
IUserService userService,
|
||||
ITransactionRepository transactionRepository,
|
||||
IInstallationRepository installationRepository,
|
||||
@ -50,6 +53,7 @@ public class ToolsController : Controller
|
||||
_globalSettings = globalSettings;
|
||||
_organizationRepository = organizationRepository;
|
||||
_cloudGetOrganizationLicenseQuery = cloudGetOrganizationLicenseQuery;
|
||||
_getUserLicenseQuery = getUserLicenseQuery;
|
||||
_userService = userService;
|
||||
_transactionRepository = transactionRepository;
|
||||
_installationRepository = installationRepository;
|
||||
@ -326,7 +330,7 @@ public class ToolsController : Controller
|
||||
}
|
||||
else if (user != null)
|
||||
{
|
||||
var license = await _userService.GenerateLicenseAsync(user, null, model.Version);
|
||||
var license = await _getUserLicenseQuery.GetLicenseAsync(user, null, model.Version);
|
||||
var ms = new MemoryStream();
|
||||
ms.Seek(0, SeekOrigin.Begin);
|
||||
await JsonSerializer.SerializeAsync(ms, license, JsonHelpers.Indented);
|
||||
|
@ -4,6 +4,7 @@ using Bit.Api.Models.Request.Accounts;
|
||||
using Bit.Api.Models.Response;
|
||||
using Bit.Api.Utilities;
|
||||
using Bit.Core.Auth.UserFeatures.TwoFactorAuth.Interfaces;
|
||||
using Bit.Core.Billing.Licenses.Queries;
|
||||
using Bit.Core.Billing.Models;
|
||||
using Bit.Core.Billing.Services;
|
||||
using Bit.Core.Exceptions;
|
||||
@ -20,6 +21,7 @@ namespace Bit.Api.Billing.Controllers;
|
||||
[Authorize("Application")]
|
||||
public class AccountsController(
|
||||
IUserService userService,
|
||||
IGetUserLicenseQuery getUserLicenseQuery,
|
||||
ITwoFactorIsEnabledQuery twoFactorIsEnabledQuery) : Controller
|
||||
{
|
||||
[HttpPost("premium")]
|
||||
@ -82,12 +84,12 @@ public class AccountsController(
|
||||
if (!globalSettings.SelfHosted && user.Gateway != null)
|
||||
{
|
||||
var subscriptionInfo = await paymentService.GetSubscriptionAsync(user);
|
||||
var license = await userService.GenerateLicenseAsync(user, subscriptionInfo);
|
||||
var license = await getUserLicenseQuery.GetLicenseAsync(user, subscriptionInfo);
|
||||
return new SubscriptionResponseModel(user, subscriptionInfo, license);
|
||||
}
|
||||
else if (!globalSettings.SelfHosted)
|
||||
{
|
||||
var license = await userService.GenerateLicenseAsync(user);
|
||||
var license = await getUserLicenseQuery.GetLicenseAsync(user);
|
||||
return new SubscriptionResponseModel(user, license);
|
||||
}
|
||||
else
|
||||
@ -133,8 +135,6 @@ public class AccountsController(
|
||||
return new PaymentResponseModel { Success = true, PaymentIntentClientSecret = result };
|
||||
}
|
||||
|
||||
|
||||
|
||||
[HttpPost("license")]
|
||||
[SelfHosted(SelfHostedOnly = true)]
|
||||
public async Task PostLicenseAsync(LicenseRequestModel model)
|
||||
|
@ -1,11 +1,11 @@
|
||||
using Bit.Core.AdminConsole.OrganizationFeatures.OrganizationConnections.Interfaces;
|
||||
using Bit.Core.Billing.Licenses.Queries;
|
||||
using Bit.Core.Context;
|
||||
using Bit.Core.Exceptions;
|
||||
using Bit.Core.Models.Api.OrganizationLicenses;
|
||||
using Bit.Core.Models.Business;
|
||||
using Bit.Core.OrganizationFeatures.OrganizationLicenses.Interfaces;
|
||||
using Bit.Core.Repositories;
|
||||
using Bit.Core.Services;
|
||||
using Bit.Core.Utilities;
|
||||
using Microsoft.AspNetCore.Authorization;
|
||||
using Microsoft.AspNetCore.Mvc;
|
||||
@ -18,7 +18,7 @@ namespace Bit.Api.Controllers;
|
||||
public class LicensesController : Controller
|
||||
{
|
||||
private readonly IUserRepository _userRepository;
|
||||
private readonly IUserService _userService;
|
||||
private readonly IGetUserLicenseQuery _getUserLicenseQuery;
|
||||
private readonly IOrganizationRepository _organizationRepository;
|
||||
private readonly ICloudGetOrganizationLicenseQuery _cloudGetOrganizationLicenseQuery;
|
||||
private readonly IValidateBillingSyncKeyCommand _validateBillingSyncKeyCommand;
|
||||
@ -26,14 +26,14 @@ public class LicensesController : Controller
|
||||
|
||||
public LicensesController(
|
||||
IUserRepository userRepository,
|
||||
IUserService userService,
|
||||
IGetUserLicenseQuery getUserLicenseQuery,
|
||||
IOrganizationRepository organizationRepository,
|
||||
ICloudGetOrganizationLicenseQuery cloudGetOrganizationLicenseQuery,
|
||||
IValidateBillingSyncKeyCommand validateBillingSyncKeyCommand,
|
||||
ICurrentContext currentContext)
|
||||
{
|
||||
_userRepository = userRepository;
|
||||
_userService = userService;
|
||||
_getUserLicenseQuery = getUserLicenseQuery;
|
||||
_organizationRepository = organizationRepository;
|
||||
_cloudGetOrganizationLicenseQuery = cloudGetOrganizationLicenseQuery;
|
||||
_validateBillingSyncKeyCommand = validateBillingSyncKeyCommand;
|
||||
@ -54,7 +54,7 @@ public class LicensesController : Controller
|
||||
throw new BadRequestException("Invalid license key.");
|
||||
}
|
||||
|
||||
var license = await _userService.GenerateLicenseAsync(user, null);
|
||||
var license = await _getUserLicenseQuery.GetLicenseAsync(user, null);
|
||||
return license;
|
||||
}
|
||||
|
||||
|
@ -10,6 +10,10 @@ using Bit.Core.Billing.Tax.Services.Implementations;
|
||||
|
||||
namespace Bit.Core.Billing.Extensions;
|
||||
|
||||
using Bit.Core.Billing.Licenses.Queries;
|
||||
using Bit.Core.Billing.Licenses.Queries.Implementations;
|
||||
using Bit.Core.OrganizationFeatures.OrganizationLicenses;
|
||||
using Bit.Core.OrganizationFeatures.OrganizationLicenses.Interfaces;
|
||||
using Microsoft.Extensions.DependencyInjection;
|
||||
|
||||
public static class ServiceCollectionExtensions
|
||||
@ -27,5 +31,14 @@ public static class ServiceCollectionExtensions
|
||||
services.AddLicenseServices();
|
||||
services.AddPricingClient();
|
||||
services.AddTransient<IPreviewTaxAmountCommand, PreviewTaxAmountCommand>();
|
||||
services.AddOrganizationLicenseCommandsQueries();
|
||||
}
|
||||
|
||||
private static void AddOrganizationLicenseCommandsQueries(this IServiceCollection services)
|
||||
{
|
||||
services.AddScoped<ICloudGetOrganizationLicenseQuery, CloudGetOrganizationLicenseQuery>();
|
||||
services.AddScoped<ISelfHostedGetOrganizationLicenseQuery, SelfHostedGetOrganizationLicenseQuery>();
|
||||
services.AddScoped<IUpdateOrganizationLicenseCommand, UpdateOrganizationLicenseCommand>();
|
||||
services.AddScoped<IGetUserLicenseQuery, GetUserLicenseQuery>();
|
||||
}
|
||||
}
|
||||
|
@ -0,0 +1,9 @@
|
||||
using Bit.Core.Entities;
|
||||
using Bit.Core.Models.Business;
|
||||
|
||||
namespace Bit.Core.Billing.Licenses.Queries;
|
||||
|
||||
public interface IGetUserLicenseQuery
|
||||
{
|
||||
Task<UserLicense> GetLicenseAsync(User user, SubscriptionInfo subscriptionInfo = null, int? version = null);
|
||||
}
|
@ -0,0 +1,60 @@
|
||||
using Bit.Core.Billing.Licenses.Extensions;
|
||||
using Bit.Core.Entities;
|
||||
using Bit.Core.Enums;
|
||||
using Bit.Core.Exceptions;
|
||||
using Bit.Core.Models.Business;
|
||||
using Bit.Core.Services;
|
||||
|
||||
namespace Bit.Core.Billing.Licenses.Queries.Implementations;
|
||||
|
||||
public class GetUserLicenseQuery : IGetUserLicenseQuery
|
||||
{
|
||||
private readonly IPaymentService _paymentService;
|
||||
private readonly ILicensingService _licensingService;
|
||||
|
||||
public GetUserLicenseQuery(
|
||||
IPaymentService paymentService,
|
||||
ILicensingService licensingService)
|
||||
{
|
||||
_paymentService = paymentService;
|
||||
_licensingService = licensingService;
|
||||
}
|
||||
|
||||
public async Task<UserLicense> GetLicenseAsync(User user, SubscriptionInfo subscriptionInfo = null, int? version = null)
|
||||
{
|
||||
if (user == null)
|
||||
{
|
||||
throw new NotFoundException();
|
||||
}
|
||||
|
||||
if (subscriptionInfo == null && user.Gateway != null)
|
||||
{
|
||||
subscriptionInfo = await _paymentService.GetSubscriptionAsync(user);
|
||||
}
|
||||
|
||||
var issued = DateTime.UtcNow;
|
||||
|
||||
var userLicense = new UserLicense
|
||||
{
|
||||
Version = version.GetValueOrDefault(1),
|
||||
LicenseType = LicenseType.User,
|
||||
LicenseKey = user.LicenseKey,
|
||||
Id = user.Id,
|
||||
Name = user.Name,
|
||||
Email = user.Email,
|
||||
Premium = user.Premium,
|
||||
MaxStorageGb = user.MaxStorageGb,
|
||||
Issued = issued,
|
||||
Expires = user.CalculateFreshExpirationDate(subscriptionInfo),
|
||||
Refresh = user.CalculateFreshRefreshDate(subscriptionInfo),
|
||||
Trial = user.IsTrialing(subscriptionInfo)
|
||||
};
|
||||
|
||||
// Hash is included in Signature, and so must be initialized before signing
|
||||
userLicense.Hash = Convert.ToBase64String(userLicense.ComputeHash());
|
||||
userLicense.Signature = Convert.ToBase64String(_licensingService.SignLicense(userLicense));
|
||||
userLicense.Token = await _licensingService.CreateUserTokenAsync(user, subscriptionInfo);
|
||||
|
||||
return userLicense;
|
||||
}
|
||||
}
|
@ -1,8 +1,5 @@
|
||||
using System.Text.Json.Serialization;
|
||||
using Bit.Core.Billing.Licenses.Attributes;
|
||||
using Bit.Core.Billing.Licenses.Extensions;
|
||||
using Bit.Core.Entities;
|
||||
using Bit.Core.Services;
|
||||
|
||||
namespace Bit.Core.Models.Business;
|
||||
|
||||
@ -11,45 +8,6 @@ public class UserLicense : BaseLicense
|
||||
public UserLicense()
|
||||
{ }
|
||||
|
||||
public UserLicense(User user, SubscriptionInfo subscriptionInfo, ILicensingService licenseService,
|
||||
int? version = null)
|
||||
{
|
||||
LicenseType = Enums.LicenseType.User;
|
||||
LicenseKey = user.LicenseKey;
|
||||
Id = user.Id;
|
||||
Name = user.Name;
|
||||
Email = user.Email;
|
||||
Version = version.GetValueOrDefault(1);
|
||||
Premium = user.Premium;
|
||||
MaxStorageGb = user.MaxStorageGb;
|
||||
Issued = DateTime.UtcNow;
|
||||
Expires = user.CalculateFreshExpirationDate(subscriptionInfo);
|
||||
Refresh = user.CalculateFreshRefreshDate(subscriptionInfo);
|
||||
Trial = user.IsTrialing(subscriptionInfo);
|
||||
|
||||
Hash = Convert.ToBase64String(this.ComputeHash());
|
||||
Signature = Convert.ToBase64String(licenseService.SignLicense(this));
|
||||
}
|
||||
|
||||
public UserLicense(User user, ILicensingService licenseService, int? version = null)
|
||||
{
|
||||
LicenseType = Enums.LicenseType.User;
|
||||
LicenseKey = user.LicenseKey;
|
||||
Id = user.Id;
|
||||
Name = user.Name;
|
||||
Email = user.Email;
|
||||
Version = version.GetValueOrDefault(1);
|
||||
Premium = user.Premium;
|
||||
MaxStorageGb = user.MaxStorageGb;
|
||||
Issued = DateTime.UtcNow;
|
||||
Expires = user.CalculateFreshExpirationDate(null);
|
||||
Refresh = user.CalculateFreshRefreshDate(null);
|
||||
Trial = user.IsTrialing(null);
|
||||
|
||||
Hash = Convert.ToBase64String(this.ComputeHash());
|
||||
Signature = Convert.ToBase64String(licenseService.SignLicense(this));
|
||||
}
|
||||
|
||||
[LicenseVersion(1)]
|
||||
public string Email { get; set; }
|
||||
|
||||
@ -65,6 +23,4 @@ public class UserLicense : BaseLicense
|
||||
{
|
||||
get => Version == 1;
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
@ -22,8 +22,6 @@ using Bit.Core.AdminConsole.OrganizationFeatures.OrganizationUsers.RestoreUser.v
|
||||
using Bit.Core.Models.Business.Tokenables;
|
||||
using Bit.Core.OrganizationFeatures.OrganizationCollections;
|
||||
using Bit.Core.OrganizationFeatures.OrganizationCollections.Interfaces;
|
||||
using Bit.Core.OrganizationFeatures.OrganizationLicenses;
|
||||
using Bit.Core.OrganizationFeatures.OrganizationLicenses.Interfaces;
|
||||
using Bit.Core.OrganizationFeatures.OrganizationSponsorships.FamiliesForEnterprise;
|
||||
using Bit.Core.OrganizationFeatures.OrganizationSponsorships.FamiliesForEnterprise.Cloud;
|
||||
using Bit.Core.OrganizationFeatures.OrganizationSponsorships.FamiliesForEnterprise.Interfaces;
|
||||
@ -56,7 +54,6 @@ public static class OrganizationServiceCollectionExtensions
|
||||
services.AddOrganizationApiKeyCommandsQueries();
|
||||
services.AddOrganizationCollectionCommands();
|
||||
services.AddOrganizationGroupCommands();
|
||||
services.AddOrganizationLicenseCommandsQueries();
|
||||
services.AddOrganizationDomainCommandsQueries();
|
||||
services.AddOrganizationSignUpCommands();
|
||||
services.AddOrganizationDeleteCommands();
|
||||
@ -154,13 +151,6 @@ public static class OrganizationServiceCollectionExtensions
|
||||
services.AddScoped<IUpdateGroupCommand, UpdateGroupCommand>();
|
||||
}
|
||||
|
||||
private static void AddOrganizationLicenseCommandsQueries(this IServiceCollection services)
|
||||
{
|
||||
services.AddScoped<ICloudGetOrganizationLicenseQuery, CloudGetOrganizationLicenseQuery>();
|
||||
services.AddScoped<ISelfHostedGetOrganizationLicenseQuery, SelfHostedGetOrganizationLicenseQuery>();
|
||||
services.AddScoped<IUpdateOrganizationLicenseCommand, UpdateOrganizationLicenseCommand>();
|
||||
}
|
||||
|
||||
private static void AddOrganizationDomainCommandsQueries(this IServiceCollection services)
|
||||
{
|
||||
services.AddScoped<ICreateOrganizationDomainCommand, CreateOrganizationDomainCommand>();
|
||||
|
@ -68,8 +68,7 @@ public interface IUserService
|
||||
Task EnablePremiumAsync(Guid userId, DateTime? expirationDate);
|
||||
Task DisablePremiumAsync(Guid userId, DateTime? expirationDate);
|
||||
Task UpdatePremiumExpirationAsync(Guid userId, DateTime? expirationDate);
|
||||
Task<UserLicense> GenerateLicenseAsync(User user, SubscriptionInfo subscriptionInfo = null,
|
||||
int? version = null);
|
||||
|
||||
Task<bool> CheckPasswordAsync(User user, string password);
|
||||
/// <summary>
|
||||
/// Checks if the user has access to premium features, either through a personal subscription or through an organization.
|
||||
|
@ -1183,30 +1183,6 @@ public class UserService : UserManager<User>, IUserService, IDisposable
|
||||
}
|
||||
}
|
||||
|
||||
public async Task<UserLicense> GenerateLicenseAsync(
|
||||
User user,
|
||||
SubscriptionInfo subscriptionInfo = null,
|
||||
int? version = null)
|
||||
{
|
||||
if (user == null)
|
||||
{
|
||||
throw new NotFoundException();
|
||||
}
|
||||
|
||||
if (subscriptionInfo == null && user.Gateway != null)
|
||||
{
|
||||
subscriptionInfo = await _paymentService.GetSubscriptionAsync(user);
|
||||
}
|
||||
|
||||
var userLicense = subscriptionInfo == null
|
||||
? new UserLicense(user, _licenseService)
|
||||
: new UserLicense(user, subscriptionInfo, _licenseService);
|
||||
|
||||
userLicense.Token = await _licenseService.CreateUserTokenAsync(user, subscriptionInfo);
|
||||
|
||||
return userLicense;
|
||||
}
|
||||
|
||||
public override async Task<bool> CheckPasswordAsync(User user, string password)
|
||||
{
|
||||
if (user == null)
|
||||
|
Loading…
x
Reference in New Issue
Block a user