|
|
|
@ -50,11 +50,15 @@ namespace Bit.Api.Test.Controllers
|
|
|
|
|
|
|
|
|
|
[Theory]
|
|
|
|
|
[BitAutoData]
|
|
|
|
|
public async Task CreateConnection_RequiresOwnerPermissions(SutProvider<OrganizationConnectionsController> sutProvider)
|
|
|
|
|
public async Task CreateConnection_CloudBillingSync_RequiresOwnerPermissions(SutProvider<OrganizationConnectionsController> sutProvider)
|
|
|
|
|
{
|
|
|
|
|
var exception = await Assert.ThrowsAsync<BadRequestException>(() => sutProvider.Sut.CreateConnection(null));
|
|
|
|
|
var model = new OrganizationConnectionRequestModel
|
|
|
|
|
{
|
|
|
|
|
Type = OrganizationConnectionType.CloudBillingSync,
|
|
|
|
|
};
|
|
|
|
|
var exception = await Assert.ThrowsAsync<BadRequestException>(() => sutProvider.Sut.CreateConnection(model));
|
|
|
|
|
|
|
|
|
|
Assert.Contains("Only the owner of an organization can create a connection.", exception.Message);
|
|
|
|
|
Assert.Contains($"You do not have permission to create a connection of type", exception.Message);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
[Theory]
|
|
|
|
@ -116,6 +120,7 @@ namespace Bit.Api.Test.Controllers
|
|
|
|
|
var typedModel = new OrganizationConnectionRequestModel<BillingSyncConfig>(model);
|
|
|
|
|
typedModel.ParsedConfig.CloudOrganizationId = cloudOrgId;
|
|
|
|
|
|
|
|
|
|
sutProvider.GetDependency<IGlobalSettings>().SelfHosted.Returns(true);
|
|
|
|
|
sutProvider.GetDependency<ICreateOrganizationConnectionCommand>().CreateAsync<BillingSyncConfig>(default)
|
|
|
|
|
.ReturnsForAnyArgs(typedModel.ToData(Guid.NewGuid()).ToEntity());
|
|
|
|
|
sutProvider.GetDependency<ICurrentContext>().OrganizationOwner(model.OrganizationId).Returns(true);
|
|
|
|
@ -143,17 +148,40 @@ namespace Bit.Api.Test.Controllers
|
|
|
|
|
|
|
|
|
|
var exception = await Assert.ThrowsAsync<BadRequestException>(() => sutProvider.Sut.UpdateConnection(default, null));
|
|
|
|
|
|
|
|
|
|
Assert.Contains("Only the owner of an organization can update a connection.", exception.Message);
|
|
|
|
|
Assert.Contains("You do not have permission to update this connection.", exception.Message);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
[Theory]
|
|
|
|
|
[BitMemberAutoData(nameof(ConnectionTypes))]
|
|
|
|
|
public async Task UpdateConnection_OnlyOneConnectionOfEachType(OrganizationConnectionType type,
|
|
|
|
|
[BitAutoData(OrganizationConnectionType.CloudBillingSync)]
|
|
|
|
|
public async Task UpdateConnection_BillingSync_OnlyOneConnectionOfEachType(OrganizationConnectionType type,
|
|
|
|
|
OrganizationConnection existing1, OrganizationConnection existing2, BillingSyncConfig config,
|
|
|
|
|
SutProvider<OrganizationConnectionsController> sutProvider)
|
|
|
|
|
{
|
|
|
|
|
existing1.Type = existing2.Type = type;
|
|
|
|
|
existing1.Config = JsonSerializer.Serialize(config);
|
|
|
|
|
var typedModel = RequestModelFromEntity(existing1);
|
|
|
|
|
var typedModel = RequestModelFromEntity<BillingSyncConfig>(existing1);
|
|
|
|
|
|
|
|
|
|
sutProvider.GetDependency<ICurrentContext>().OrganizationOwner(typedModel.OrganizationId).Returns(true);
|
|
|
|
|
|
|
|
|
|
var orgConnectionRepository = sutProvider.GetDependency<IOrganizationConnectionRepository>();
|
|
|
|
|
orgConnectionRepository.GetByIdAsync(existing1.Id).Returns(existing1);
|
|
|
|
|
orgConnectionRepository.GetByIdAsync(existing2.Id).Returns(existing2);
|
|
|
|
|
orgConnectionRepository.GetByOrganizationIdTypeAsync(typedModel.OrganizationId, type).Returns(new[] { existing1, existing2 });
|
|
|
|
|
|
|
|
|
|
var exception = await Assert.ThrowsAsync<BadRequestException>(() => sutProvider.Sut.UpdateConnection(existing1.Id, typedModel));
|
|
|
|
|
|
|
|
|
|
Assert.Contains($"The requested organization already has a connection of type {typedModel.Type}. Only one of each connection type may exist per organization.", exception.Message);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
[Theory]
|
|
|
|
|
[BitAutoData(OrganizationConnectionType.Scim)]
|
|
|
|
|
public async Task UpdateConnection_Scim_OnlyOneConnectionOfEachType(OrganizationConnectionType type,
|
|
|
|
|
OrganizationConnection existing1, OrganizationConnection existing2, ScimConfig config,
|
|
|
|
|
SutProvider<OrganizationConnectionsController> sutProvider)
|
|
|
|
|
{
|
|
|
|
|
existing1.Type = existing2.Type = type;
|
|
|
|
|
existing1.Config = JsonSerializer.Serialize(config);
|
|
|
|
|
var typedModel = RequestModelFromEntity<ScimConfig>(existing1);
|
|
|
|
|
|
|
|
|
|
sutProvider.GetDependency<ICurrentContext>().OrganizationOwner(typedModel.OrganizationId).Returns(true);
|
|
|
|
|
|
|
|
|
@ -161,7 +189,11 @@ namespace Bit.Api.Test.Controllers
|
|
|
|
|
.GetByIdAsync(existing1.Id)
|
|
|
|
|
.Returns(existing1);
|
|
|
|
|
|
|
|
|
|
sutProvider.GetDependency<IOrganizationConnectionRepository>().GetByOrganizationIdTypeAsync(typedModel.OrganizationId, type).Returns(new[] { existing1, existing2 });
|
|
|
|
|
sutProvider.GetDependency<ICurrentContext>().ManageScim(typedModel.OrganizationId).Returns(true);
|
|
|
|
|
|
|
|
|
|
sutProvider.GetDependency<IOrganizationConnectionRepository>()
|
|
|
|
|
.GetByOrganizationIdTypeAsync(typedModel.OrganizationId, type)
|
|
|
|
|
.Returns(new[] { existing1, existing2 });
|
|
|
|
|
|
|
|
|
|
var exception = await Assert.ThrowsAsync<BadRequestException>(() => sutProvider.Sut.UpdateConnection(existing1.Id, typedModel));
|
|
|
|
|
|
|
|
|
@ -180,11 +212,16 @@ namespace Bit.Api.Test.Controllers
|
|
|
|
|
});
|
|
|
|
|
updated.Config = JsonSerializer.Serialize(config);
|
|
|
|
|
updated.Id = existing.Id;
|
|
|
|
|
var model = RequestModelFromEntity(updated);
|
|
|
|
|
updated.Type = OrganizationConnectionType.CloudBillingSync;
|
|
|
|
|
var model = RequestModelFromEntity<BillingSyncConfig>(updated);
|
|
|
|
|
|
|
|
|
|
sutProvider.GetDependency<ICurrentContext>().OrganizationOwner(model.OrganizationId).Returns(true);
|
|
|
|
|
sutProvider.GetDependency<IOrganizationConnectionRepository>().GetByOrganizationIdTypeAsync(model.OrganizationId, model.Type).Returns(new[] { existing });
|
|
|
|
|
sutProvider.GetDependency<IUpdateOrganizationConnectionCommand>().UpdateAsync<BillingSyncConfig>(default).ReturnsForAnyArgs(updated);
|
|
|
|
|
sutProvider.GetDependency<IOrganizationConnectionRepository>()
|
|
|
|
|
.GetByOrganizationIdTypeAsync(model.OrganizationId, model.Type)
|
|
|
|
|
.Returns(new[] { existing });
|
|
|
|
|
sutProvider.GetDependency<IUpdateOrganizationConnectionCommand>()
|
|
|
|
|
.UpdateAsync<BillingSyncConfig>(default)
|
|
|
|
|
.ReturnsForAnyArgs(updated);
|
|
|
|
|
sutProvider.GetDependency<IOrganizationConnectionRepository>()
|
|
|
|
|
.GetByIdAsync(existing.Id)
|
|
|
|
|
.Returns(existing);
|
|
|
|
@ -211,7 +248,7 @@ namespace Bit.Api.Test.Controllers
|
|
|
|
|
var exception = await Assert.ThrowsAsync<BadRequestException>(() =>
|
|
|
|
|
sutProvider.Sut.GetConnection(connectionId, OrganizationConnectionType.CloudBillingSync));
|
|
|
|
|
|
|
|
|
|
Assert.Contains("Only the owner of an organization can retrieve a connection.", exception.Message);
|
|
|
|
|
Assert.Contains("You do not have permission to retrieve a connection of type", exception.Message);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
[Theory]
|
|
|
|
@ -221,7 +258,10 @@ namespace Bit.Api.Test.Controllers
|
|
|
|
|
{
|
|
|
|
|
connection.Config = JsonSerializer.Serialize(config);
|
|
|
|
|
|
|
|
|
|
sutProvider.GetDependency<IOrganizationConnectionRepository>().GetByOrganizationIdTypeAsync(connection.OrganizationId, connection.Type).Returns(new[] { connection });
|
|
|
|
|
sutProvider.GetDependency<IGlobalSettings>().SelfHosted.Returns(true);
|
|
|
|
|
sutProvider.GetDependency<IOrganizationConnectionRepository>()
|
|
|
|
|
.GetByOrganizationIdTypeAsync(connection.OrganizationId, connection.Type)
|
|
|
|
|
.Returns(new[] { connection });
|
|
|
|
|
sutProvider.GetDependency<ICurrentContext>().OrganizationOwner(connection.OrganizationId).Returns(true);
|
|
|
|
|
|
|
|
|
|
var expected = new OrganizationConnectionResponseModel(connection, typeof(BillingSyncConfig));
|
|
|
|
@ -247,7 +287,7 @@ namespace Bit.Api.Test.Controllers
|
|
|
|
|
|
|
|
|
|
var exception = await Assert.ThrowsAsync<BadRequestException>(() => sutProvider.Sut.DeleteConnection(connection.Id));
|
|
|
|
|
|
|
|
|
|
Assert.Contains("Only the owner of an organization can remove a connection.", exception.Message);
|
|
|
|
|
Assert.Contains("You do not have permission to remove this connection of type", exception.Message);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
[Theory]
|
|
|
|
@ -263,7 +303,8 @@ namespace Bit.Api.Test.Controllers
|
|
|
|
|
await sutProvider.GetDependency<IDeleteOrganizationConnectionCommand>().DeleteAsync(connection);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
private static OrganizationConnectionRequestModel<BillingSyncConfig> RequestModelFromEntity(OrganizationConnection entity)
|
|
|
|
|
private static OrganizationConnectionRequestModel<T> RequestModelFromEntity<T>(OrganizationConnection entity)
|
|
|
|
|
where T : new()
|
|
|
|
|
{
|
|
|
|
|
return new(new OrganizationConnectionRequestModel()
|
|
|
|
|
{
|
|
|
|
|