Reverse relationships support

This commit is contained in:
Fabio Sinibaldi 2022-10-25 13:03:14 +02:00
parent 39e09c436b
commit 2b40d4058a
1 changed files with 62 additions and 12 deletions

View File

@ -45,10 +45,7 @@ import org.gcube.application.geoportal.common.model.rest.ConfigurationException;
import org.gcube.application.geoportal.common.model.rest.QueryRequest;
import org.gcube.application.geoportal.common.model.rest.RegisterFileSetRequest;
import org.gcube.application.geoportal.common.model.rest.TempFile;
import org.gcube.application.geoportal.common.model.useCaseDescriptor.DataAccessPolicy;
import org.gcube.application.geoportal.common.model.useCaseDescriptor.Field;
import org.gcube.application.geoportal.common.model.useCaseDescriptor.HandlerDeclaration;
import org.gcube.application.geoportal.common.model.useCaseDescriptor.UseCaseDescriptor;
import org.gcube.application.geoportal.common.model.useCaseDescriptor.*;
import org.gcube.application.geoportal.common.utils.ContextUtils;
import org.gcube.application.geoportal.common.utils.StorageUtils;
import org.gcube.application.geoportal.service.engine.providers.PluginManager;
@ -304,8 +301,18 @@ public class ProfiledMongoManager extends MongoManager implements MongoManagerI<
@Override
public Project setRelation(String id, String relation, String targetUCD, String targetId) throws IOException, EventException, ProjectLockedException, ProjectNotFoundException, InvalidLockException, InvalidUserRoleException, UnauthorizedAccess, RegistrationException, ConfigurationException {
Project toUpdate=lock(id,"Set Relation");
Project toUpdate=lock(id,"Set Relation "+relation+" toward "+targetUCD+":"+targetId);
try{
log.info(getUseCaseDescriptor().getId()+":"+id+" setting relation "+relation+" toward "+targetUCD+":"+targetId);
// Check if relation is defined
String toSetReverseRelation=null;
List<RelationshipDefinition> existingDefinitions = getUseCaseDescriptor().getRelationshipDefinitions();
for(RelationshipDefinition def : existingDefinitions)
if(def.getId().equals(relation))
toSetReverseRelation =def.getReverseRelationId();
log.debug("{} reverse relation for {} is {}",getUseCaseDescriptor().getId(),relation,toSetReverseRelation);
// check if relation existing
List<Relationship> relations = toUpdate.getRelationshipsByName(relation);
if(!relations.isEmpty()){
@ -317,14 +324,26 @@ public class ProfiledMongoManager extends MongoManager implements MongoManagerI<
// check if target exists
ProfiledMongoManager otherManager = (targetUCD.equals(this.useCaseDescriptor.getId()))?this:new ProfiledMongoManager(targetUCD);
Project other = getByID(targetId);
// add relation
Relationship rel = new Relationship();
rel.setRelationshipName(relation);
rel.setTargetID(targetId);
rel.setTargetUCD(targetUCD);
toUpdate =onUpdate(toUpdate.addRelation(rel));
// set reverse relation
if(toSetReverseRelation!=null){
Relationship reverseRel = new Relationship();
reverseRel.setRelationshipName(toSetReverseRelation);
reverseRel.setTargetID(id);
reverseRel.setTargetUCD(getUseCaseDescriptor().getId());
log.info("Setting reverse relation {} ",reverseRel);
otherManager.lock(other.getId(),"Setting reverse relation "+reverseRel);
other.addRelation(reverseRel);
otherManager.unlockAndUpdate(other);
}
return unlockAndUpdate(toUpdate);
}catch(Throwable t){
log.error("Unexpected exception ",t);
@ -335,21 +354,52 @@ public class ProfiledMongoManager extends MongoManager implements MongoManagerI<
@Override
public Project deleteRelation(String id, String relation, String targetUCD, String targetId) throws IOException, EventException, ProjectLockedException, ProjectNotFoundException, InvalidLockException, InvalidUserRoleException, UnauthorizedAccess, RegistrationException, ConfigurationException {
log.debug("Delete relation {}:{}--{}-->{}:{} ",getUseCaseDescriptor().getId(),id,relation,targetUCD,targetId);
log.info("Delete relation {}:{}--{}-->{}:{} ",getUseCaseDescriptor().getId(),id,relation,targetUCD,targetId);
Project toUpdate=lock(id,"Delete Relation");
try{
// SET target UCD to present UCD as default
final String toUseTargetUCD = (targetUCD == null || targetUCD.equals(""))? getUseCaseDescriptor().getId():targetUCD;
String toDeleteReverseRelation=null;
List<RelationshipDefinition> existingDefinitions = getUseCaseDescriptor().getRelationshipDefinitions();
for(RelationshipDefinition def : existingDefinitions)
if(def.getId().equals(relation))
toDeleteReverseRelation =def.getReverseRelationId();
log.debug("{} reverse relation for {} is {}",getUseCaseDescriptor().getId(),relation,toDeleteReverseRelation);
// check if relation existing
List<Relationship> relations = toUpdate.getRelationships();
if(relations!=null && !relations.isEmpty()){
int beforeSize = relations.size();
toUpdate.getRelationships().removeIf(r ->
r.getRelationshipName().equals(relation)&&
r.getTargetUCD().equals(toUseTargetUCD)&&
r.getTargetID().equals(targetId));
ArrayList<Relationship> toRemove = new ArrayList<>();
for(Relationship r : toUpdate.getRelationships()){
if(r.getRelationshipName().equals(relation)&&
r.getTargetUCD().equals(toUseTargetUCD)&&
r.getTargetID().equals(targetId)){
// set to be remove
log.debug("Removing {} ",r);
toRemove.add(r);
// delete reverse relation
if(toDeleteReverseRelation!=null){
log.debug("Removing reverse of {} ",r);
ProfiledMongoManager otherManager = (targetUCD.equals(this.useCaseDescriptor.getId()))?this:new ProfiledMongoManager(targetUCD);
Project other = getByID(targetId);
otherManager.lock(other.getId(),"Remove reverse relation "+toDeleteReverseRelation + " toward "+getUseCaseDescriptor().getId()+":"+id);
final String finalToDeleteReverseRelation = toDeleteReverseRelation;
other.getRelationships().removeIf(revRel ->revRel.getRelationshipName().equals(finalToDeleteReverseRelation)&&
revRel.getTargetID().equals(id)&&revRel.getTargetUCD().equals(getUseCaseDescriptor().getId()));
otherManager.unlockAndUpdate(other);
}
}
}
toUpdate.getRelationships().removeAll(toRemove);
// update only if something changed
if(toUpdate.getRelationships().size()!=beforeSize) {
log.debug("Removed {} relations from {} ",(toUpdate.getRelationships().size()!=beforeSize),id);