Repository navigation
Conversation
Drop the group parameter of DELETE /network-modifications, and the unused deletion of a whole group content: the modifications are found by id, in a group, nested in a composite or shared. Deleting a modification removes it from the loaded container holding it, and reads the content of the deleted composites in one query instead of one per level. Signed-off-by: Florent MILLOT <75525996+flomillot@users.noreply.github.com>
|
Important
This repository does not receive automatic reviews because it has fewer than 10 stars. ⚙️ Run configuration
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
Return early on an empty list instead of guarding each caller, read the composite ids straight from the deleted modifications, and check from outside whether a container content is loaded, so that an uninitialized proxy is not loaded by the check. Signed-off-by: Florent MILLOT <florent.millot_externe@rte-france.com>
Explain the PERSIST cascade that would cancel the deletion, split the container filter, and drop the replace composite test. Signed-off-by: Florent MILLOT <florent.millot_externe@rte-france.com>
Signed-off-by: Florent MILLOT <florent.millot_externe@rte-france.com>
Signed-off-by: Florent MILLOT <florent.millot_externe@rte-france.com>
Signed-off-by: Florent MILLOT <florent.millot_externe@rte-france.com>
…st it with the existing deletion test Signed-off-by: Florent MILLOT <florent.millot_externe@rte-france.com>
There was a problem hiding this comment.
🟡 Changes recommended
Deletion ordering can violate foreign keys, and late user validation can leave Elasticsearch inconsistent after rejected requests.
2 open issues
What changed in this PR
This PR makes modification deletion ID-based across groups, composites, and shared modifications, and extends directory-reference cleanup to nested content.
Changes:
- Removes group-scoped deletion parameters and ignores unknown IDs.
- Centralizes container cleanup and batches composite-descendant reads.
- Unlinks deleted references and updates API tests and query counts.
| File | Description |
|---|---|
| src/test/java/org/gridsuite/modification/server/utils/ApiUtils.java | Removes group-scoped deletion helpers. |
| src/test/java/org/gridsuite/modification/server/service/ModificationRepositoryTest.java | Updates deletion calls and query counts. |
| src/test/java/org/gridsuite/modification/server/service/ModificationIndexationTest.java | Updates service calls. |
| src/test/java/org/gridsuite/modification/server/modifications/tabularmodifications/TabularGeneratorModificationsTest.java | Adapts tabular deletion tests. |
| src/test/java/org/gridsuite/modification/server/modifications/tabularcreations/TabularGeneratorCreationsTest.java | Updates repository deletion call. |
| src/test/java/org/gridsuite/modification/server/ModificationControllerTest.java | Tests ID-based deletion and reference cleanup. |
| src/main/java/org/gridsuite/modification/server/service/NetworkModificationService.java | Adds transactional reference cleanup. |
| src/main/java/org/gridsuite/modification/server/service/DirectoryService.java | Tolerates missing elements when unlinking. |
| src/main/java/org/gridsuite/modification/server/repositories/NetworkModificationRepository.java | Centralizes subtree deletion and container cleanup. |
| src/main/java/org/gridsuite/modification/server/repositories/ModificationRepository.java | Adds descendant-entity query. |
| src/main/java/org/gridsuite/modification/server/NetworkModificationController.java | Updates deletion parameters and user forwarding. |
| src/main/java/org/gridsuite/modification/server/error/NetworkModificationExceptionHandler.java | Removes obsolete error mappings. |
| src/main/java/org/gridsuite/modification/server/error/ModificationBusinessErrorCode.java | Removes obsolete deletion errors. |
| src/main/java/org/gridsuite/modification/server/entities/AbstractModificationContainerEntity.java | Adds loaded-content detection. |
Review effort: Balanced
Signed-off-by: Florent MILLOT <florent.millot_externe@rte-france.com>
| if (deletedReferences.isEmpty()) { | ||
| return; | ||
| } | ||
| if (userId == null) { |
There was a problem hiding this comment.
Delete shared composite from gridexplore now fails with 400 error
(userId is missing in the endpoint header of explore-server)
There was a problem hiding this comment.
It works for me, userId is supposed to be propagated.
https://github.com/gridsuite/explore-server/blob/cf7b15ce9b16ef504ae572514dacd31fd45672f8/src/main/java/org/gridsuite/explore/server/config/RestClientConfig.java#L74
Maybe update your service ?
| deleteIndexedModificationGroups(groupUuids); | ||
| networkModificationRepository.deleteModificationGroups(groupUuids); | ||
| List<ModificationReferenceData> deletedReferences = networkModificationRepository.deleteModificationGroups(groupUuids); | ||
| removeDeletedElementReferences(deletedReferences, userId); |
There was a problem hiding this comment.
references deleted with one directory-server HTTP call inside Transactional method !?
There was a problem hiding this comment.
Yeah now that it's Transactional I should refactor this too, thanks
| @Transactional | ||
| public void deleteNetworkModifications(@NonNull List<UUID> modificationsUuids, String userId) { | ||
| List<ModificationReferenceData> deletedReferences = networkModificationRepository.deleteModifications(modificationsUuids); | ||
| removeDeletedElementReferences(deletedReferences, userId); |
There was a problem hiding this comment.
the same remark here (HTTP call inside DB transaction)
another remark : in this case if directory server returns 404 error for exemple ?
There was a problem hiding this comment.
…on is committed Signed-off-by: Florent MILLOT <florent.millot_externe@rte-france.com>
|
#943 (review) Could you fix Copilot’s feedback please @flomillot ? |
| @Query(""" | ||
| WITH descendants AS ( | ||
| SELECT m.id AS id FROM ModificationEntity m WHERE m.container.id IN (:containerIds) | ||
| UNION ALL |
There was a problem hiding this comment.
with Union All we can have duplicate ids. Shouldn't we use Union instead ?
There was a problem hiding this comment.
Based on findAllDescendantModificationIdsByContainerIds, that was already with UNION ALL, but your're right.
I change then both.
Also add a .distinct().
I answered, no fix needed |
Signed-off-by: Florent MILLOT <florent.millot_externe@rte-france.com>
…ications-by-list Signed-off-by: Florent MILLOT <florent.millot_externe@rte-france.com> # Conflicts: # src/main/java/org/gridsuite/modification/server/repositories/NetworkModificationRepository.java # src/test/java/org/gridsuite/modification/server/ModificationControllerTest.java
Signed-off-by: Florent MILLOT <florent.millot_externe@rte-france.com>
Signed-off-by: Florent MILLOT <florent.millot_externe@rte-france.com>
| .retrieve() | ||
| .toBodilessEntity(); | ||
| } catch (HttpClientErrorException.NotFound _) { | ||
| // the shared element is gone, and its references with it |
There was a problem hiding this comment.
What about here ? Log or throw ?
There was a problem hiding this comment.
Can add a log but I dont think its necessary
|
|
||
| @Transactional | ||
| public void deleteModificationGroups(List<UUID> groupUuids) { | ||
| public void deleteModificationGroups(List<UUID> groupUuids, String userId) { |
There was a problem hiding this comment.
here we remove the group in elasticsearch before the userId header check => the group could stay in the database with no index
=> too risky (I think we have a design issue here)
There was a problem hiding this comment.
Same problem everywhere in the repos
| /** | ||
| * After the commit, not to hold the deletion transaction during the calls to directory-server | ||
| */ | ||
| @TransactionalEventListener(phase = TransactionPhase.AFTER_COMMIT) |
There was a problem hiding this comment.
@TransactionalEventListener(phase = TransactionPhase.AFTER_COMMIT)
We haven’t used it anywhere else in the code, so we might need TL approval before introducing it here
| if (deletedReferences.isEmpty()) { | ||
| return; | ||
| } | ||
| if (userId == null) { |
There was a problem hiding this comment.
i'm not sure about this check here it seems too late it should be done up front maybe or by making the header required before any work starts
=> I don't know it seems a design prb with this userId check
There was a problem hiding this comment.
It's OK because I kept the Transactional, so everything is canceled (except ElasticSearch as you said). If I do it before, I need to do a recursive query in the DB just for that check.
| public ResponseEntity<Void> deleteStashedModificationFromGroups(@Parameter(description = "Group UUIDs") @RequestBody List<UUID> groupUuids, | ||
| @RequestHeader(HEADER_USER_ID) String userId) { | ||
| networkModificationService.deleteStashedModificationFromGroups(groupUuids); | ||
| networkModificationService.deleteStashedModificationFromGroups(groupUuids, userId); |
There was a problem hiding this comment.
deleteStashedModificationFromGroups +
removeElementReferences(groupUuid, userId) for each groupuuid ?
=> delete stashed and active modifications ?
There was a problem hiding this comment.
The links are deleted and it's a bug. It's cleaned and removed in #944.
| String.format("Some of these modifications %s (to be deleted) were not found", modificationsUuids), | ||
| Map.of("ids", modificationsUuids)); | ||
| @Transactional | ||
| public void deleteNetworkModifications(@NonNull List<UUID> modificationsUuids, String userId) { |
There was a problem hiding this comment.
MODIFICATIONS_NOT_FOUND and
MODIFICATION_WITH_GROUP_DELETION_FORBIDDEN are removed
=> deleting non existent modifications now returns 200 instead of 404, the group-deletion safe guard removed
=> The refacto changes the API behavior in my opinion
=> should be explicitly documented in the PR and validated with PO and TL maybe
There was a problem hiding this comment.
As said above I asked the TL before removing the group guard, it's validated.
Will be read by code owner anyway.
Its already in the PR description : "Unknown ids are ignored instead of answering 404 when none is found, like deleting an unknown group." So now both endpoint are coherent.
| WITH descendants AS ( | ||
| SELECT m.id AS id FROM ModificationEntity m WHERE m.container.id IN (:containerIds) | ||
| UNION ALL | ||
| UNION |
There was a problem hiding this comment.
UNION ALL changes to UNION why ?
| ) | ||
| SELECT m FROM ModificationEntity m JOIN descendants d ON m.id = d.id | ||
| """) | ||
| List<ModificationEntity> findAllDescendantModificationsByContainerIds(@Param("containerIds") Collection<UUID> containerIds); |
There was a problem hiding this comment.
it is seems the same or a duplicated query like findAllDescendantModificationIdsByContainerIds
There was a problem hiding this comment.
One return the entities, the other one only the IDs. It avoid a JOIN and a stream later on.
…ications-by-list Signed-off-by: Florent MILLOT <florent.millot_externe@rte-france.com> # Conflicts: # src/main/java/org/gridsuite/modification/server/repositories/NetworkModificationRepository.java
|




DELETE /network-modificationsnow takes only the ids of the modifications to delete: thegroupUuidparameter is removed, along with the deletion of a whole group content, which had no client. A modification is found by id whether it sits in a group, in a composite or is shared. Unknown ids are ignored instead of answering 404 when none is found, like deleting an unknown group.Deleting modifications now removes them from the loaded container holding them, instead of each caller doing it, and reads the content of the deleted composites in one query instead of two per level.
Deleting modifications, groups or stashed modifications, and replacing a composite content, now unlink the deleted modification references from directory-server, nested ones included. This fixes the references left in directory-server when they were deleted inside a composite, e.g. when deleting or replacing a shared composite. The references are unlinked once the deletion is committed, not to hold the transaction during the calls to directory-server.