mirror of
https://github.com/bitwarden/server
synced 2025-12-29 14:43:39 +00:00
[PM-24279] Add vnext policy endpoint (#6253)
This commit is contained in:
@@ -18,7 +18,7 @@ internal class PolicyUpdateCustomization(PolicyType type, bool enabled) : ICusto
|
||||
}
|
||||
}
|
||||
|
||||
public class PolicyUpdateAttribute(PolicyType type, bool enabled = true) : CustomizeAttribute
|
||||
public class PolicyUpdateAttribute(PolicyType type = PolicyType.FreeFamiliesSponsorshipPolicy, bool enabled = true) : CustomizeAttribute
|
||||
{
|
||||
public override ICustomization GetCustomization(ParameterInfo parameter)
|
||||
{
|
||||
|
||||
@@ -10,7 +10,6 @@ using Bit.Core.Services;
|
||||
using Bit.Core.Test.AdminConsole.AutoFixture;
|
||||
using Bit.Test.Common.AutoFixture;
|
||||
using Bit.Test.Common.AutoFixture.Attributes;
|
||||
using Microsoft.Extensions.Logging;
|
||||
using NSubstitute;
|
||||
using Xunit;
|
||||
|
||||
@@ -22,9 +21,10 @@ public class OrganizationDataOwnershipPolicyValidatorTests
|
||||
private const string _defaultUserCollectionName = "Default";
|
||||
|
||||
[Theory, BitAutoData]
|
||||
public async Task OnSaveSideEffectsAsync_FeatureFlagDisabled_DoesNothing(
|
||||
[PolicyUpdate(PolicyType.OrganizationDataOwnership)] PolicyUpdate policyUpdate,
|
||||
[Policy(PolicyType.OrganizationDataOwnership, false)] Policy currentPolicy,
|
||||
public async Task ExecuteSideEffectsAsync_FeatureFlagDisabled_DoesNothing(
|
||||
[PolicyUpdate(PolicyType.OrganizationDataOwnership, false)] PolicyUpdate policyUpdate,
|
||||
[Policy(PolicyType.OrganizationDataOwnership, false)] Policy postUpdatedPolicy,
|
||||
[Policy(PolicyType.OrganizationDataOwnership, false)] Policy previousPolicyState,
|
||||
SutProvider<OrganizationDataOwnershipPolicyValidator> sutProvider)
|
||||
{
|
||||
// Arrange
|
||||
@@ -32,95 +32,102 @@ public class OrganizationDataOwnershipPolicyValidatorTests
|
||||
.IsEnabled(FeatureFlagKeys.CreateDefaultLocation)
|
||||
.Returns(false);
|
||||
|
||||
var policyRequest = new SavePolicyModel(policyUpdate, null, new OrganizationModelOwnershipPolicyModel(_defaultUserCollectionName));
|
||||
|
||||
// Act
|
||||
await sutProvider.Sut.OnSaveSideEffectsAsync(policyUpdate, currentPolicy);
|
||||
await sutProvider.Sut.ExecuteSideEffectsAsync(policyRequest, postUpdatedPolicy, previousPolicyState);
|
||||
|
||||
// Assert
|
||||
await sutProvider.GetDependency<ICollectionRepository>()
|
||||
.DidNotReceive()
|
||||
.UpsertDefaultCollectionsAsync(Arg.Any<Guid>(), Arg.Any<List<Guid>>(), Arg.Any<string>());
|
||||
.UpsertDefaultCollectionsAsync(Arg.Any<Guid>(), Arg.Any<IEnumerable<Guid>>(), Arg.Any<string>());
|
||||
}
|
||||
|
||||
[Theory, BitAutoData]
|
||||
public async Task OnSaveSideEffectsAsync_PolicyAlreadyEnabled_DoesNothing(
|
||||
[PolicyUpdate(PolicyType.OrganizationDataOwnership)] PolicyUpdate policyUpdate,
|
||||
[Policy(PolicyType.OrganizationDataOwnership, true)] Policy currentPolicy,
|
||||
public async Task ExecuteSideEffectsAsync_PolicyAlreadyEnabled_DoesNothing(
|
||||
[PolicyUpdate(PolicyType.OrganizationDataOwnership, true)] PolicyUpdate policyUpdate,
|
||||
[Policy(PolicyType.OrganizationDataOwnership, true)] Policy postUpdatedPolicy,
|
||||
[Policy(PolicyType.OrganizationDataOwnership, true)] Policy previousPolicyState,
|
||||
SutProvider<OrganizationDataOwnershipPolicyValidator> sutProvider)
|
||||
{
|
||||
// Arrange
|
||||
currentPolicy.OrganizationId = policyUpdate.OrganizationId;
|
||||
policyUpdate.Enabled = true;
|
||||
postUpdatedPolicy.OrganizationId = policyUpdate.OrganizationId;
|
||||
previousPolicyState.OrganizationId = policyUpdate.OrganizationId;
|
||||
|
||||
sutProvider.GetDependency<IFeatureService>()
|
||||
.IsEnabled(FeatureFlagKeys.CreateDefaultLocation)
|
||||
.Returns(true);
|
||||
|
||||
var policyRequest = new SavePolicyModel(policyUpdate, null, new OrganizationModelOwnershipPolicyModel(_defaultUserCollectionName));
|
||||
|
||||
// Act
|
||||
await sutProvider.Sut.OnSaveSideEffectsAsync(policyUpdate, currentPolicy);
|
||||
await sutProvider.Sut.ExecuteSideEffectsAsync(policyRequest, postUpdatedPolicy, previousPolicyState);
|
||||
|
||||
// Assert
|
||||
await sutProvider.GetDependency<ICollectionRepository>()
|
||||
.DidNotReceive()
|
||||
.UpsertDefaultCollectionsAsync(Arg.Any<Guid>(), Arg.Any<List<Guid>>(), Arg.Any<string>());
|
||||
.UpsertDefaultCollectionsAsync(Arg.Any<Guid>(), Arg.Any<IEnumerable<Guid>>(), Arg.Any<string>());
|
||||
}
|
||||
|
||||
[Theory, BitAutoData]
|
||||
public async Task OnSaveSideEffectsAsync_PolicyBeingDisabled_DoesNothing(
|
||||
public async Task ExecuteSideEffectsAsync_PolicyBeingDisabled_DoesNothing(
|
||||
[PolicyUpdate(PolicyType.OrganizationDataOwnership, false)] PolicyUpdate policyUpdate,
|
||||
[Policy(PolicyType.OrganizationDataOwnership, true)] Policy currentPolicy,
|
||||
[Policy(PolicyType.OrganizationDataOwnership, false)] Policy postUpdatedPolicy,
|
||||
[Policy(PolicyType.OrganizationDataOwnership)] Policy previousPolicyState,
|
||||
SutProvider<OrganizationDataOwnershipPolicyValidator> sutProvider)
|
||||
{
|
||||
// Arrange
|
||||
currentPolicy.OrganizationId = policyUpdate.OrganizationId;
|
||||
previousPolicyState.OrganizationId = policyUpdate.OrganizationId;
|
||||
postUpdatedPolicy.OrganizationId = policyUpdate.OrganizationId;
|
||||
|
||||
sutProvider.GetDependency<IFeatureService>()
|
||||
.IsEnabled(FeatureFlagKeys.CreateDefaultLocation)
|
||||
.Returns(true);
|
||||
|
||||
var policyRequest = new SavePolicyModel(policyUpdate, null, new OrganizationModelOwnershipPolicyModel(_defaultUserCollectionName));
|
||||
|
||||
// Act
|
||||
await sutProvider.Sut.OnSaveSideEffectsAsync(policyUpdate, currentPolicy);
|
||||
await sutProvider.Sut.ExecuteSideEffectsAsync(policyRequest, postUpdatedPolicy, previousPolicyState);
|
||||
|
||||
// Assert
|
||||
await sutProvider.GetDependency<ICollectionRepository>()
|
||||
.DidNotReceive()
|
||||
.UpsertDefaultCollectionsAsync(Arg.Any<Guid>(), Arg.Any<List<Guid>>(), Arg.Any<string>());
|
||||
.UpsertDefaultCollectionsAsync(Arg.Any<Guid>(), Arg.Any<IEnumerable<Guid>>(), Arg.Any<string>());
|
||||
}
|
||||
|
||||
[Theory, BitAutoData]
|
||||
public async Task OnSaveSideEffectsAsync_WhenNoUsersExist_ShouldLogError(
|
||||
[PolicyUpdate(PolicyType.OrganizationDataOwnership)] PolicyUpdate policyUpdate,
|
||||
[Policy(PolicyType.OrganizationDataOwnership, false)] Policy currentPolicy,
|
||||
public async Task ExecuteSideEffectsAsync_WhenNoUsersExist_DoNothing(
|
||||
[PolicyUpdate(PolicyType.OrganizationDataOwnership, true)] PolicyUpdate policyUpdate,
|
||||
[Policy(PolicyType.OrganizationDataOwnership, true)] Policy postUpdatedPolicy,
|
||||
[Policy(PolicyType.OrganizationDataOwnership, false)] Policy previousPolicyState,
|
||||
OrganizationDataOwnershipPolicyRequirementFactory factory)
|
||||
{
|
||||
// Arrange
|
||||
currentPolicy.OrganizationId = policyUpdate.OrganizationId;
|
||||
policyUpdate.Enabled = true;
|
||||
postUpdatedPolicy.OrganizationId = policyUpdate.OrganizationId;
|
||||
previousPolicyState.OrganizationId = policyUpdate.OrganizationId;
|
||||
|
||||
var policyRepository = ArrangePolicyRepositoryWithOutUsers();
|
||||
var policyRepository = ArrangePolicyRepository([]);
|
||||
var collectionRepository = Substitute.For<ICollectionRepository>();
|
||||
var logger = Substitute.For<ILogger<OrganizationDataOwnershipPolicyValidator>>();
|
||||
|
||||
var sut = ArrangeSut(factory, policyRepository, collectionRepository, logger);
|
||||
var sut = ArrangeSut(factory, policyRepository, collectionRepository);
|
||||
var policyRequest = new SavePolicyModel(policyUpdate, null, new OrganizationModelOwnershipPolicyModel(_defaultUserCollectionName));
|
||||
|
||||
// Act
|
||||
await sut.OnSaveSideEffectsAsync(policyUpdate, currentPolicy);
|
||||
await sut.ExecuteSideEffectsAsync(policyRequest, postUpdatedPolicy, previousPolicyState);
|
||||
|
||||
// Assert
|
||||
await collectionRepository
|
||||
.DidNotReceive()
|
||||
.UpsertDefaultCollectionsAsync(
|
||||
Arg.Any<Guid>(),
|
||||
Arg.Any<List<Guid>>(),
|
||||
Arg.Any<IEnumerable<Guid>>(),
|
||||
Arg.Any<string>());
|
||||
|
||||
const string expectedErrorMessage = "No UserOrganizationIds found for";
|
||||
|
||||
logger.Received(1).Log(
|
||||
LogLevel.Error,
|
||||
Arg.Any<EventId>(),
|
||||
Arg.Is<object>(o => (o.ToString() ?? "").Contains(expectedErrorMessage)),
|
||||
Arg.Any<Exception>(),
|
||||
Arg.Any<Func<object, Exception?, string>>());
|
||||
await policyRepository
|
||||
.Received(1)
|
||||
.GetPolicyDetailsByOrganizationIdAsync(
|
||||
policyUpdate.OrganizationId,
|
||||
PolicyType.OrganizationDataOwnership);
|
||||
}
|
||||
|
||||
public static IEnumerable<object?[]> ShouldUpsertDefaultCollectionsTestCases()
|
||||
@@ -133,13 +140,13 @@ public class OrganizationDataOwnershipPolicyValidatorTests
|
||||
object?[] WithExistingPolicy()
|
||||
{
|
||||
var organizationId = Guid.NewGuid();
|
||||
var policyUpdate = new PolicyUpdate
|
||||
var postUpdatedPolicy = new Policy
|
||||
{
|
||||
OrganizationId = organizationId,
|
||||
Type = PolicyType.OrganizationDataOwnership,
|
||||
Enabled = true
|
||||
};
|
||||
var currentPolicy = new Policy
|
||||
var previousPolicyState = new Policy
|
||||
{
|
||||
Id = Guid.NewGuid(),
|
||||
OrganizationId = organizationId,
|
||||
@@ -149,51 +156,53 @@ public class OrganizationDataOwnershipPolicyValidatorTests
|
||||
|
||||
return new object?[]
|
||||
{
|
||||
policyUpdate,
|
||||
currentPolicy
|
||||
postUpdatedPolicy,
|
||||
previousPolicyState
|
||||
};
|
||||
}
|
||||
|
||||
object?[] WithNoExistingPolicy()
|
||||
{
|
||||
var policyUpdate = new PolicyUpdate
|
||||
var postUpdatedPolicy = new Policy
|
||||
{
|
||||
OrganizationId = new Guid(),
|
||||
Type = PolicyType.OrganizationDataOwnership,
|
||||
Enabled = true
|
||||
};
|
||||
|
||||
const Policy currentPolicy = null;
|
||||
const Policy previousPolicyState = null;
|
||||
|
||||
return new object?[]
|
||||
{
|
||||
policyUpdate,
|
||||
currentPolicy
|
||||
postUpdatedPolicy,
|
||||
previousPolicyState
|
||||
};
|
||||
}
|
||||
}
|
||||
[Theory, BitAutoData]
|
||||
[Theory]
|
||||
[BitMemberAutoData(nameof(ShouldUpsertDefaultCollectionsTestCases))]
|
||||
public async Task OnSaveSideEffectsAsync_WithRequirements_ShouldUpsertDefaultCollections(
|
||||
public async Task ExecuteSideEffectsAsync_WithRequirements_ShouldUpsertDefaultCollections(
|
||||
Policy postUpdatedPolicy,
|
||||
Policy? previousPolicyState,
|
||||
[PolicyUpdate(PolicyType.OrganizationDataOwnership)] PolicyUpdate policyUpdate,
|
||||
[Policy(PolicyType.OrganizationDataOwnership, false)] Policy? currentPolicy,
|
||||
[OrganizationPolicyDetails(PolicyType.OrganizationDataOwnership)] IEnumerable<OrganizationPolicyDetails> orgPolicyDetails,
|
||||
OrganizationDataOwnershipPolicyRequirementFactory factory)
|
||||
{
|
||||
// Arrange
|
||||
foreach (var policyDetail in orgPolicyDetails)
|
||||
var orgPolicyDetailsList = orgPolicyDetails.ToList();
|
||||
foreach (var policyDetail in orgPolicyDetailsList)
|
||||
{
|
||||
policyDetail.OrganizationId = policyUpdate.OrganizationId;
|
||||
}
|
||||
|
||||
var policyRepository = ArrangePolicyRepository(orgPolicyDetails);
|
||||
var policyRepository = ArrangePolicyRepository(orgPolicyDetailsList);
|
||||
var collectionRepository = Substitute.For<ICollectionRepository>();
|
||||
var logger = Substitute.For<ILogger<OrganizationDataOwnershipPolicyValidator>>();
|
||||
|
||||
var sut = ArrangeSut(factory, policyRepository, collectionRepository, logger);
|
||||
var sut = ArrangeSut(factory, policyRepository, collectionRepository);
|
||||
var policyRequest = new SavePolicyModel(policyUpdate, null, new OrganizationModelOwnershipPolicyModel(_defaultUserCollectionName));
|
||||
|
||||
// Act
|
||||
await sut.OnSaveSideEffectsAsync(policyUpdate, currentPolicy);
|
||||
await sut.ExecuteSideEffectsAsync(policyRequest, postUpdatedPolicy, previousPolicyState);
|
||||
|
||||
// Assert
|
||||
await collectionRepository
|
||||
@@ -204,9 +213,40 @@ public class OrganizationDataOwnershipPolicyValidatorTests
|
||||
_defaultUserCollectionName);
|
||||
}
|
||||
|
||||
private static IPolicyRepository ArrangePolicyRepositoryWithOutUsers()
|
||||
private static IEnumerable<object?[]> WhenDefaultCollectionsDoesNotExistTestCases()
|
||||
{
|
||||
return ArrangePolicyRepository([]);
|
||||
yield return [new OrganizationModelOwnershipPolicyModel(null)];
|
||||
yield return [new OrganizationModelOwnershipPolicyModel("")];
|
||||
yield return [new OrganizationModelOwnershipPolicyModel(" ")];
|
||||
yield return [new EmptyMetadataModel()];
|
||||
}
|
||||
[Theory]
|
||||
[BitMemberAutoData(nameof(WhenDefaultCollectionsDoesNotExistTestCases))]
|
||||
public async Task ExecuteSideEffectsAsync_WhenDefaultCollectionNameIsInvalid_DoesNothing(
|
||||
IPolicyMetadataModel metadata,
|
||||
[PolicyUpdate(PolicyType.OrganizationDataOwnership)] PolicyUpdate policyUpdate,
|
||||
[Policy(PolicyType.OrganizationDataOwnership, true)] Policy postUpdatedPolicy,
|
||||
[Policy(PolicyType.OrganizationDataOwnership, false)] Policy previousPolicyState,
|
||||
SutProvider<OrganizationDataOwnershipPolicyValidator> sutProvider)
|
||||
{
|
||||
// Arrange
|
||||
postUpdatedPolicy.OrganizationId = policyUpdate.OrganizationId;
|
||||
previousPolicyState.OrganizationId = policyUpdate.OrganizationId;
|
||||
policyUpdate.Enabled = true;
|
||||
|
||||
sutProvider.GetDependency<IFeatureService>()
|
||||
.IsEnabled(FeatureFlagKeys.CreateDefaultLocation)
|
||||
.Returns(true);
|
||||
|
||||
var policyRequest = new SavePolicyModel(policyUpdate, null, metadata);
|
||||
|
||||
// Act
|
||||
await sutProvider.Sut.ExecuteSideEffectsAsync(policyRequest, postUpdatedPolicy, previousPolicyState);
|
||||
|
||||
// Assert
|
||||
await sutProvider.GetDependency<ICollectionRepository>()
|
||||
.DidNotReceive()
|
||||
.UpsertDefaultCollectionsAsync(Arg.Any<Guid>(), Arg.Any<IEnumerable<Guid>>(), Arg.Any<string>());
|
||||
}
|
||||
|
||||
private static IPolicyRepository ArrangePolicyRepository(IEnumerable<OrganizationPolicyDetails> policyDetails)
|
||||
@@ -222,17 +262,15 @@ public class OrganizationDataOwnershipPolicyValidatorTests
|
||||
private static OrganizationDataOwnershipPolicyValidator ArrangeSut(
|
||||
OrganizationDataOwnershipPolicyRequirementFactory factory,
|
||||
IPolicyRepository policyRepository,
|
||||
ICollectionRepository collectionRepository,
|
||||
ILogger<OrganizationDataOwnershipPolicyValidator> logger = null!)
|
||||
ICollectionRepository collectionRepository)
|
||||
{
|
||||
logger ??= Substitute.For<ILogger<OrganizationDataOwnershipPolicyValidator>>();
|
||||
|
||||
var featureService = Substitute.For<IFeatureService>();
|
||||
featureService
|
||||
.IsEnabled(FeatureFlagKeys.CreateDefaultLocation)
|
||||
.Returns(true);
|
||||
|
||||
var sut = new OrganizationDataOwnershipPolicyValidator(policyRepository, collectionRepository, [factory], featureService, logger);
|
||||
var sut = new OrganizationDataOwnershipPolicyValidator(policyRepository, collectionRepository, [factory], featureService);
|
||||
return sut;
|
||||
}
|
||||
|
||||
|
||||
@@ -1,7 +1,5 @@
|
||||
using Bit.Core.AdminConsole.Entities;
|
||||
using Bit.Core.AdminConsole.Enums;
|
||||
using Bit.Core.AdminConsole.Enums;
|
||||
using Bit.Core.AdminConsole.Models.Data.Organizations.Policies;
|
||||
using Bit.Core.AdminConsole.OrganizationFeatures.Policies.Models;
|
||||
using Bit.Core.AdminConsole.OrganizationFeatures.Policies.PolicyRequirements;
|
||||
using Bit.Core.AdminConsole.OrganizationFeatures.Policies.PolicyValidators;
|
||||
using Bit.Core.AdminConsole.Repositories;
|
||||
@@ -161,20 +159,6 @@ public class TestOrganizationPolicyValidator : OrganizationPolicyValidator
|
||||
{
|
||||
}
|
||||
|
||||
public override PolicyType Type => PolicyType.TwoFactorAuthentication;
|
||||
|
||||
public override IEnumerable<PolicyType> RequiredPolicies => [];
|
||||
|
||||
public override Task<string> ValidateAsync(PolicyUpdate policyUpdate, Policy? currentPolicy)
|
||||
{
|
||||
return Task.FromResult("");
|
||||
}
|
||||
|
||||
public override Task OnSaveSideEffectsAsync(PolicyUpdate policyUpdate, Policy? currentPolicy)
|
||||
{
|
||||
return Task.CompletedTask;
|
||||
}
|
||||
|
||||
public async Task<IEnumerable<T>> TestGetUserPolicyRequirementsByOrganizationIdAsync<T>(Guid organizationId, PolicyType policyType)
|
||||
where T : IPolicyRequirement
|
||||
{
|
||||
|
||||
@@ -94,8 +94,8 @@ public class SavePolicyCommandTests
|
||||
Substitute.For<IEventService>(),
|
||||
Substitute.For<IPolicyRepository>(),
|
||||
[new FakeSingleOrgPolicyValidator(), new FakeSingleOrgPolicyValidator()],
|
||||
Substitute.For<TimeProvider>()
|
||||
));
|
||||
Substitute.For<TimeProvider>(),
|
||||
Substitute.For<IPostSavePolicySideEffect>()));
|
||||
Assert.Contains("Duplicate PolicyValidator for SingleOrg policy", exception.Message);
|
||||
}
|
||||
|
||||
@@ -281,6 +281,85 @@ public class SavePolicyCommandTests
|
||||
await AssertPolicyNotSavedAsync(sutProvider);
|
||||
}
|
||||
|
||||
[Theory, BitAutoData]
|
||||
public async Task VNextSaveAsync_OrganizationDataOwnershipPolicy_ExecutesPostSaveSideEffects(
|
||||
[PolicyUpdate(PolicyType.OrganizationDataOwnership)] PolicyUpdate policyUpdate,
|
||||
[Policy(PolicyType.OrganizationDataOwnership, false)] Policy currentPolicy)
|
||||
{
|
||||
// Arrange
|
||||
var sutProvider = SutProviderFactory();
|
||||
var savePolicyModel = new SavePolicyModel(policyUpdate, null, new EmptyMetadataModel());
|
||||
|
||||
currentPolicy.OrganizationId = policyUpdate.OrganizationId;
|
||||
sutProvider.GetDependency<IPolicyRepository>()
|
||||
.GetByOrganizationIdTypeAsync(policyUpdate.OrganizationId, policyUpdate.Type)
|
||||
.Returns(currentPolicy);
|
||||
|
||||
ArrangeOrganization(sutProvider, policyUpdate);
|
||||
sutProvider.GetDependency<IPolicyRepository>()
|
||||
.GetManyByOrganizationIdAsync(policyUpdate.OrganizationId)
|
||||
.Returns([currentPolicy]);
|
||||
|
||||
// Act
|
||||
var result = await sutProvider.Sut.VNextSaveAsync(savePolicyModel);
|
||||
|
||||
// Assert
|
||||
await sutProvider.GetDependency<IPolicyRepository>()
|
||||
.Received(1)
|
||||
.UpsertAsync(result);
|
||||
|
||||
await sutProvider.GetDependency<IEventService>()
|
||||
.Received(1)
|
||||
.LogPolicyEventAsync(result, EventType.Policy_Updated);
|
||||
|
||||
await sutProvider.GetDependency<IPostSavePolicySideEffect>()
|
||||
.Received(1)
|
||||
.ExecuteSideEffectsAsync(savePolicyModel, result, currentPolicy);
|
||||
}
|
||||
|
||||
[Theory]
|
||||
[BitAutoData(PolicyType.SingleOrg)]
|
||||
[BitAutoData(PolicyType.TwoFactorAuthentication)]
|
||||
public async Task VNextSaveAsync_NonOrganizationDataOwnershipPolicy_DoesNotExecutePostSaveSideEffects(
|
||||
PolicyType policyType,
|
||||
Policy currentPolicy,
|
||||
[PolicyUpdate] PolicyUpdate policyUpdate)
|
||||
{
|
||||
// Arrange
|
||||
policyUpdate.Type = policyType;
|
||||
currentPolicy.Type = policyType;
|
||||
currentPolicy.OrganizationId = policyUpdate.OrganizationId;
|
||||
|
||||
|
||||
var sutProvider = SutProviderFactory();
|
||||
var savePolicyModel = new SavePolicyModel(policyUpdate, null, new EmptyMetadataModel());
|
||||
|
||||
sutProvider.GetDependency<IPolicyRepository>()
|
||||
.GetByOrganizationIdTypeAsync(policyUpdate.OrganizationId, policyUpdate.Type)
|
||||
.Returns(currentPolicy);
|
||||
|
||||
ArrangeOrganization(sutProvider, policyUpdate);
|
||||
sutProvider.GetDependency<IPolicyRepository>()
|
||||
.GetManyByOrganizationIdAsync(policyUpdate.OrganizationId)
|
||||
.Returns([currentPolicy]);
|
||||
|
||||
// Act
|
||||
var result = await sutProvider.Sut.VNextSaveAsync(savePolicyModel);
|
||||
|
||||
// Assert
|
||||
await sutProvider.GetDependency<IPolicyRepository>()
|
||||
.Received(1)
|
||||
.UpsertAsync(result);
|
||||
|
||||
await sutProvider.GetDependency<IEventService>()
|
||||
.Received(1)
|
||||
.LogPolicyEventAsync(result, EventType.Policy_Updated);
|
||||
|
||||
await sutProvider.GetDependency<IPostSavePolicySideEffect>()
|
||||
.DidNotReceiveWithAnyArgs()
|
||||
.ExecuteSideEffectsAsync(default!, default!, default!);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Returns a new SutProvider with the PolicyValidators registered in the Sut.
|
||||
/// </summary>
|
||||
@@ -289,6 +368,7 @@ public class SavePolicyCommandTests
|
||||
return new SutProvider<SavePolicyCommand>()
|
||||
.WithFakeTimeProvider()
|
||||
.SetDependency(policyValidators ?? [])
|
||||
.SetDependency(Substitute.For<IPostSavePolicySideEffect>())
|
||||
.Create();
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user