-
Notifications
You must be signed in to change notification settings - Fork 5
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
EES-4046: Add functionality to delete draft releases #5224
Conversation
...tatistics.Admin/Security/AuthorizationHandlers/DeleteSpecificReleaseAuthorizationHandlers.cs
Outdated
Show resolved
Hide resolved
// and associated item in releaseVersion.Publication.ReleaseSeries will also not be orphaned | ||
// so no need to remove them. | ||
|
||
releaseVersion.SoftDeleted = true; | ||
_context.ReleaseVersions.Update(releaseVersion); | ||
|
||
var roles = await _context | ||
.UserReleaseRoles | ||
.AsQueryable() | ||
.Where(r => r.ReleaseVersionId == releaseVersionId) | ||
.ToListAsync(); | ||
roles.ForEach(r => r.SoftDeleted = true); | ||
_context.UpdateRange(roles); | ||
|
||
var invites = await _context | ||
.UserReleaseInvites | ||
.AsQueryable() | ||
.Where(r => r.ReleaseVersionId == releaseVersionId) | ||
.ToListAsync(); | ||
invites.ForEach(r => r.SoftDeleted = true); | ||
_context.UpdateRange(invites); | ||
|
||
var methodologiesScheduledWithRelease = | ||
GetMethodologiesScheduledWithRelease(releaseVersionId); | ||
|
||
// TODO EES-2747 - this should be looked at to see how best to reuse similar "set to draft" logic | ||
// in MethodologyApprovalService. | ||
methodologiesScheduledWithRelease.ForEach(m => | ||
if (!releaseVersion.Amendment && releaseVersion.ApprovalStatus == ReleaseApprovalStatus.Draft) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think with DeleteSpecificReleaseAuthorizationHandler
set up as it is, it's possible for a BAU user to delete an original release that is currently set to HigherLevelReview
, and when they do it'll end up calling SoftDeleteForAmendment
. Although fixing that should probably happen in the auth handler, not here.
I think I'd remove the ApprovalStatus check in this if
. I'd rely on CheckCanDeleteReleaseVersion
to prevent any approved release from ever making it this far, and so there is no reason to check it again here.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Removing this causes a ReleaseServiceTest
to fail because it doesn't (by design) go through the authorisation handler. I'd argue that the check should remain as this is re-usable business logic, i.e. even though one of the implementations includes the restriction already, there's a chance that another implementation might not.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
My thought is that if we're checking the approval status here and not relying on CheckCanDeleteReleaseVersion
, for consistency we will also want to check it for all the preceeding OnSuccessDo
s.
We could do something like this instead:
.OnSuccess(_userService.CheckCanDeleteReleaseVersion)
.OnSuccessDo(releaseVersion =>
{
if (releaseVersion.ApprovalStatus != ReleaseApprovalStatus.Draft)
{
throw new Exception("Can only delete draft releases");
}
})
.OnSuccessDo(async () => await _processorClient.BulkDeleteDataSetVersions(releaseVersionId))
[....]
Then the approval status is ensured across all the method calls we do, not just the final removal of the release version itself.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'm still keen on removing the approval status check here - although I will accept moving it higher up. My personal opinion is that this check is redundant - for better or worse, we haven't generally kept business logic separate.
If we wanted this logic to work without the permission check so it could function as reusable business logic, I believe the logic is currently wrong. Without the permission check, it is possible to remove cache/data/general files of an approved release. And while the database entries wouldn't be removed for an approved release, they would be soft deleted.
So I'm personally inclined to remove the check entirely, but if you want this code to function as reusable business logic, then I think we need to check it's a draft release first - before calling BulkDeleteDataSetVersions
, DeleteCacheFolderAsync
, etc. - like the code sample I gave in the previous comment.
src/GovUk.Education.ExploreEducationStatistics.Admin/Services/ReleaseService.cs
Show resolved
Hide resolved
src/GovUk.Education.ExploreEducationStatistics.Admin/Services/ReleaseService.cs
Show resolved
Hide resolved
src/GovUk.Education.ExploreEducationStatistics.Admin/Services/ReleaseService.cs
Show resolved
Hide resolved
src/GovUk.Education.ExploreEducationStatistics.Admin/Services/ReleaseService.cs
Outdated
Show resolved
Hide resolved
src/GovUk.Education.ExploreEducationStatistics.Admin/Services/ReleaseService.cs
Show resolved
Hide resolved
src/GovUk.Education.ExploreEducationStatistics.Admin/Services/ReleaseService.cs
Show resolved
Hide resolved
Might want a frontender to give the frontend parts a look. |
9348558
to
11e8219
Compare
3e610b6
to
fd10db2
Compare
// and associated item in releaseVersion.Publication.ReleaseSeries will also not be orphaned | ||
// so no need to remove them. | ||
|
||
releaseVersion.SoftDeleted = true; | ||
_context.ReleaseVersions.Update(releaseVersion); | ||
|
||
var roles = await _context | ||
.UserReleaseRoles | ||
.AsQueryable() | ||
.Where(r => r.ReleaseVersionId == releaseVersionId) | ||
.ToListAsync(); | ||
roles.ForEach(r => r.SoftDeleted = true); | ||
_context.UpdateRange(roles); | ||
|
||
var invites = await _context | ||
.UserReleaseInvites | ||
.AsQueryable() | ||
.Where(r => r.ReleaseVersionId == releaseVersionId) | ||
.ToListAsync(); | ||
invites.ForEach(r => r.SoftDeleted = true); | ||
_context.UpdateRange(invites); | ||
|
||
var methodologiesScheduledWithRelease = | ||
GetMethodologiesScheduledWithRelease(releaseVersionId); | ||
|
||
// TODO EES-2747 - this should be looked at to see how best to reuse similar "set to draft" logic | ||
// in MethodologyApprovalService. | ||
methodologiesScheduledWithRelease.ForEach(m => | ||
if (!releaseVersion.Amendment && releaseVersion.ApprovalStatus == ReleaseApprovalStatus.Draft) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'm still keen on removing the approval status check here - although I will accept moving it higher up. My personal opinion is that this check is redundant - for better or worse, we haven't generally kept business logic separate.
If we wanted this logic to work without the permission check so it could function as reusable business logic, I believe the logic is currently wrong. Without the permission check, it is possible to remove cache/data/general files of an approved release. And while the database entries wouldn't be removed for an approved release, they would be soft deleted.
So I'm personally inclined to remove the check entirely, but if you want this code to function as reusable business logic, then I think we need to check it's a draft release first - before calling BulkDeleteDataSetVersions
, DeleteCacheFolderAsync
, etc. - like the code sample I gave in the previous comment.
fd10db2
to
5ed7831
Compare
5ed7831
to
ba89f85
Compare
This PR adds the functionality for BAU users to delete draft releases which have not yet been approved. This allows users to tidy up clutter within the Admin portal, database and storage by removing entities which are no longer necessary.
This functionality has been merged with the existing code to "cancel" (i.e. soft-delete) release amendments, the difference being that non-amendment drafts are removed using a hard-delete.
To avoid over-complicating the existing method with additional conditional trees, some of the code has been split into private sub-functions, primarily for readability, but also for potential future expansion/reusability.