1
0
mirror of https://github.com/bitwarden/server.git synced 2025-06-30 15:42:48 -05:00

[PM-20064] Add cascade deletion for cipher with tasks (#5690)

* add cascade deletion for cipher tasks

* add migrations for cascade delete on ciphers and security tasks

* remove trailing comma

* add SQL migration for PasswordHealthReportApplication

- Allow cascade delete when an organization is deleted
This commit is contained in:
Nick Krantz
2025-04-23 13:16:29 -05:00
committed by GitHub
parent 90d831d9ef
commit 6809709628
22 changed files with 19009 additions and 8 deletions

View File

@ -1,6 +1,7 @@
using System.Text.Json;
using Bit.Core.AdminConsole.Entities;
using Bit.Core.AdminConsole.Repositories;
using Bit.Core.Billing.Enums;
using Bit.Core.Entities;
using Bit.Core.Enums;
using Bit.Core.Models.Data;
@ -912,4 +913,59 @@ public class CipherRepositoryTests
Assert.Equal(CipherType.SecureNote, updatedCipher1.Type);
Assert.Equal("new_attachments", updatedCipher2.Attachments);
}
[DatabaseTheory, DatabaseData]
public async Task DeleteCipherWithSecurityTaskAsync_Works(
IOrganizationRepository organizationRepository,
ICipherRepository cipherRepository,
ISecurityTaskRepository securityTaskRepository)
{
var organization = await organizationRepository.CreateAsync(new Organization
{
Name = "Test Org",
PlanType = PlanType.EnterpriseAnnually,
Plan = "Test Plan",
BillingEmail = ""
});
var cipher1 = new Cipher { Type = CipherType.Login, OrganizationId = organization.Id, Data = "", };
await cipherRepository.CreateAsync(cipher1);
var cipher2 = new Cipher { Type = CipherType.Login, OrganizationId = organization.Id, Data = "", };
await cipherRepository.CreateAsync(cipher2);
var tasks = new List<SecurityTask>
{
new()
{
OrganizationId = organization.Id,
CipherId = cipher1.Id,
Status = SecurityTaskStatus.Pending,
Type = SecurityTaskType.UpdateAtRiskCredential,
},
new()
{
OrganizationId = organization.Id,
CipherId = cipher2.Id,
Status = SecurityTaskStatus.Completed,
Type = SecurityTaskType.UpdateAtRiskCredential,
}
};
await securityTaskRepository.CreateManyAsync(tasks);
// Delete cipher with pending security task
await cipherRepository.DeleteAsync(cipher1);
var deletedCipher1 = await cipherRepository.GetByIdAsync(cipher1.Id);
Assert.Null(deletedCipher1);
// Delete cipher with completed security task
await cipherRepository.DeleteAsync(cipher2);
var deletedCipher2 = await cipherRepository.GetByIdAsync(cipher2.Id);
Assert.Null(deletedCipher2);
}
}