Commit f7520765 authored by Piotr Gawron's avatar Piotr Gawron
Browse files

filter by includedCompartmentIds did not work

parent 6c89a8f1
Pipeline #50762 failed with stage
in 63 minutes and 18 seconds
...@@ -8,9 +8,10 @@ minerva (16.0.5) stable; urgency=medium ...@@ -8,9 +8,10 @@ minerva (16.0.5) stable; urgency=medium
* Bug fix: some old maps could not be removed (#1607) * Bug fix: some old maps could not be removed (#1607)
* Bug fix: concurency issue when exporting to CellDesigner - minerva could * Bug fix: concurency issue when exporting to CellDesigner - minerva could
crash when there were two exports running in parallel (#1598) crash when there were two exports running in parallel (#1598)
* Bug fix: fetching elements filtered by includedCompartmentIds using REST
API did not work (#1614)
-- Piotr Gawron <piotr.gawron@uni.lu> Mon, 13 Dec 2021 15:00:00 +0200 -- Piotr Gawron <piotr.gawron@uni.lu> Thu, 16 Dec 2021 11:00:00 +0200
minerva (16.0.4) stable; urgency=high minerva (16.0.4) stable; urgency=high
* Bug fix: security fix in log4j2 zero day exploit * Bug fix: security fix in log4j2 zero day exploit
......
package lcsb.mapviewer.api.projects.models.bioEntities.elements; package lcsb.mapviewer.api.projects.models.bioEntities.elements;
import java.util.*; import java.util.ArrayList;
import java.util.Arrays;
import java.util.HashMap;
import java.util.LinkedHashSet;
import java.util.List;
import java.util.Map;
import java.util.Objects;
import java.util.Set;
import java.util.TreeMap;
import org.apache.logging.log4j.LogManager; import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger; import org.apache.logging.log4j.Logger;
...@@ -15,8 +23,24 @@ import lcsb.mapviewer.model.map.BioEntity; ...@@ -15,8 +23,24 @@ import lcsb.mapviewer.model.map.BioEntity;
import lcsb.mapviewer.model.map.compartment.Compartment; import lcsb.mapviewer.model.map.compartment.Compartment;
import lcsb.mapviewer.model.map.layout.graphics.Glyph; import lcsb.mapviewer.model.map.layout.graphics.Glyph;
import lcsb.mapviewer.model.map.model.ModelData; import lcsb.mapviewer.model.map.model.ModelData;
import lcsb.mapviewer.model.map.species.*; import lcsb.mapviewer.model.map.species.AntisenseRna;
import lcsb.mapviewer.model.map.species.field.*; import lcsb.mapviewer.model.map.species.Element;
import lcsb.mapviewer.model.map.species.Gene;
import lcsb.mapviewer.model.map.species.Protein;
import lcsb.mapviewer.model.map.species.Rna;
import lcsb.mapviewer.model.map.species.Species;
import lcsb.mapviewer.model.map.species.field.AbstractSiteModification;
import lcsb.mapviewer.model.map.species.field.BindingRegion;
import lcsb.mapviewer.model.map.species.field.CodingRegion;
import lcsb.mapviewer.model.map.species.field.ModificationResidue;
import lcsb.mapviewer.model.map.species.field.ModificationSite;
import lcsb.mapviewer.model.map.species.field.ProteinBindingDomain;
import lcsb.mapviewer.model.map.species.field.RegulatoryRegion;
import lcsb.mapviewer.model.map.species.field.Residue;
import lcsb.mapviewer.model.map.species.field.StructuralState;
import lcsb.mapviewer.model.map.species.field.Structure;
import lcsb.mapviewer.model.map.species.field.TranscriptionSite;
import lcsb.mapviewer.model.map.species.field.UniprotRecord;
import lcsb.mapviewer.persist.dao.map.species.ElementProperty; import lcsb.mapviewer.persist.dao.map.species.ElementProperty;
import lcsb.mapviewer.services.QueryException; import lcsb.mapviewer.services.QueryException;
import lcsb.mapviewer.services.interfaces.IElementService; import lcsb.mapviewer.services.interfaces.IElementService;
...@@ -33,13 +57,13 @@ public class ElementsRestImpl extends BaseRestImpl { ...@@ -33,13 +57,13 @@ public class ElementsRestImpl extends BaseRestImpl {
private Logger logger = LogManager.getLogger(); private Logger logger = LogManager.getLogger();
@Autowired @Autowired
public ElementsRestImpl(IElementService elementService, IModelService modelService) { public ElementsRestImpl(final IElementService elementService, final IModelService modelService) {
this.elementService = elementService; this.elementService = elementService;
this.modelService = modelService; this.modelService = modelService;
} }
public List<Map<String, Object>> getElements(String projectId, String id, String columns, String mapId, public List<Map<String, Object>> getElements(final String projectId, final String id, final String columns, final String mapId,
String type, String includedCompartmentIds, String excludedCompartmentIds) final String type, final String includedCompartmentIds, final String excludedCompartmentIds)
throws QueryException { throws QueryException {
Set<Integer> ids = new LinkedHashSet<>(); Set<Integer> ids = new LinkedHashSet<>();
if (!id.equals("")) { if (!id.equals("")) {
...@@ -87,8 +111,8 @@ public class ElementsRestImpl extends BaseRestImpl { ...@@ -87,8 +111,8 @@ public class ElementsRestImpl extends BaseRestImpl {
return result; return result;
} }
private boolean matchIncludedExcludedCompartments(Element element, Set<Compartment> includedCompartments, private boolean matchIncludedExcludedCompartments(final Element element, final Set<Compartment> includedCompartments,
Set<Compartment> excludedCompartments) { final Set<Compartment> excludedCompartments) {
boolean matchIncluded = true; boolean matchIncluded = true;
boolean matchExcluded = false; boolean matchExcluded = false;
...@@ -102,11 +126,11 @@ public class ElementsRestImpl extends BaseRestImpl { ...@@ -102,11 +126,11 @@ public class ElementsRestImpl extends BaseRestImpl {
return matchIncluded && !matchExcluded; return matchIncluded && !matchExcluded;
} }
private boolean matchCompartments(Element element, Set<Compartment> compartmentList) { private boolean matchCompartments(final Element element, final Set<Compartment> compartmentList) {
boolean isInside = false; boolean isInside = false;
if (element != null) { if (element != null) {
for (Compartment compartment : compartmentList) { for (Compartment compartment : compartmentList) {
if (compartment.contains(element) && element.getModel().getId().equals(compartment.getModel().getId())) { if (compartment.contains(element) && Objects.equals(element.getModelData().getId(), compartment.getModelData().getId())) {
isInside = true; isInside = true;
} }
} }
...@@ -114,7 +138,7 @@ public class ElementsRestImpl extends BaseRestImpl { ...@@ -114,7 +138,7 @@ public class ElementsRestImpl extends BaseRestImpl {
return isInside; return isInside;
} }
private Set<Compartment> getCompartments(String includedCompartmentIds, List<Element> elements) { private Set<Compartment> getCompartments(final String includedCompartmentIds, final List<Element> elements) {
Set<Compartment> includedCompartments = new LinkedHashSet<>(); Set<Compartment> includedCompartments = new LinkedHashSet<>();
int count = 0; int count = 0;
if (!includedCompartmentIds.isEmpty()) { if (!includedCompartmentIds.isEmpty()) {
...@@ -134,131 +158,131 @@ public class ElementsRestImpl extends BaseRestImpl { ...@@ -134,131 +158,131 @@ public class ElementsRestImpl extends BaseRestImpl {
return includedCompartments; return includedCompartments;
} }
private Map<String, Object> preparedElement(Element element, Set<String> columnsSet) { private Map<String, Object> preparedElement(final Element element, final Set<String> columnsSet) {
Map<String, Object> result = new TreeMap<>(); Map<String, Object> result = new TreeMap<>();
for (String string : columnsSet) { for (String string : columnsSet) {
String column = string.toLowerCase(); String column = string.toLowerCase();
Object value = null; Object value = null;
switch (column) { switch (column) {
case "id": case "id":
case "idobject": case "idobject":
value = element.getId(); value = element.getId();
break; break;
case "modelid": case "modelid":
value = element.getModelData().getId(); value = element.getModelData().getId();
break; break;
case "elementid": case "elementid":
value = element.getElementId(); value = element.getElementId();
break; break;
case "name": case "name":
value = element.getName(); value = element.getName();
break; break;
case "type": case "type":
value = element.getStringType(); value = element.getStringType();
break; break;
case "symbol": case "symbol":
value = element.getSymbol(); value = element.getSymbol();
break; break;
case "fullname": case "fullname":
value = element.getFullName(); value = element.getFullName();
break; break;
case "abbreviation": case "abbreviation":
value = element.getAbbreviation(); value = element.getAbbreviation();
break; break;
case "compartmentid": case "compartmentid":
if (element.getCompartment() != null) { if (element.getCompartment() != null) {
value = element.getCompartment().getId(); value = element.getCompartment().getId();
}
break;
case "complexid":
if (element instanceof Species) {
if (((Species) element).getComplex() != null) {
value = ((Species) element).getComplex().getId();
} }
} break;
break; case "complexid":
case "initialconcentration": if (element instanceof Species) {
if (element instanceof Species) { if (((Species) element).getComplex() != null) {
value = ((Species) element).getInitialConcentration(); value = ((Species) element).getComplex().getId();
} }
break; }
case "initialamount": break;
if (element instanceof Species) { case "initialconcentration":
value = ((Species) element).getInitialAmount(); if (element instanceof Species) {
} value = ((Species) element).getInitialConcentration();
break; }
case "boundarycondition": break;
if (element instanceof Species) { case "initialamount":
value = ((Species) element).isBoundaryCondition(); if (element instanceof Species) {
} value = ((Species) element).getInitialAmount();
break; }
case "constant": break;
if (element instanceof Species) { case "boundarycondition":
value = ((Species) element).isConstant(); if (element instanceof Species) {
} value = ((Species) element).isBoundaryCondition();
break; }
case "hypothetical": break;
if (element instanceof Species) { case "constant":
value = ((Species) element).isHypothetical(); if (element instanceof Species) {
} value = ((Species) element).isConstant();
break; }
case "activity": break;
if (element instanceof Species) { case "hypothetical":
value = ((Species) element).getActivity(); if (element instanceof Species) {
} value = ((Species) element).isHypothetical();
break; }
case "references": break;
value = createAnnotations(element.getMiriamData()); case "activity":
break; if (element instanceof Species) {
case "synonyms": value = ((Species) element).getActivity();
value = element.getSynonyms(); }
break; break;
case "homomultimer": case "references":
if (element instanceof Species) { value = createAnnotations(element.getMiriamData());
value = ((Species) element).getHomodimer(); break;
} else { case "synonyms":
value = null; value = element.getSynonyms();
} break;
break; case "homomultimer":
case "formula": if (element instanceof Species) {
value = element.getFormula(); value = ((Species) element).getHomodimer();
break; } else {
case "notes": value = null;
value = element.getNotes(); }
break; break;
case "other": case "formula":
value = getOthersForElement(element); value = element.getFormula();
break; break;
case "formersymbols": case "notes":
value = element.getFormerSymbols(); value = element.getNotes();
break; break;
case "hierarchyvisibilitylevel": case "other":
value = element.getVisibilityLevel(); value = getOthersForElement(element);
break; break;
case "transparencylevel": case "formersymbols":
value = element.getTransparencyLevel(); value = element.getFormerSymbols();
break; break;
case "linkedsubmodel": case "hierarchyvisibilitylevel":
if (element.getSubmodel() != null) { value = element.getVisibilityLevel();
value = element.getSubmodel().getSubmodel().getId(); break;
} case "transparencylevel":
break; value = element.getTransparencyLevel();
case "bounds": break;
value = createBounds(element.getX(), element.getY(), element.getZ(), element.getWidth(), element.getHeight()); case "linkedsubmodel":
break; if (element.getSubmodel() != null) {
case "glyph": value = element.getSubmodel().getSubmodel().getId();
value = createGlyph(element.getGlyph()); }
break; break;
default: case "bounds":
value = "Unknown column"; value = createBounds(element.getX(), element.getY(), element.getZ(), element.getWidth(), element.getHeight());
break; break;
case "glyph":
value = createGlyph(element.getGlyph());
break;
default:
value = "Unknown column";
break;
} }
result.put(string, value); result.put(string, value);
} }
return result; return result;
} }
private Map<String, Object> createGlyph(Glyph glyph) { private Map<String, Object> createGlyph(final Glyph glyph) {
if (glyph == null) { if (glyph == null) {
return null; return null;
} else { } else {
...@@ -268,7 +292,7 @@ public class ElementsRestImpl extends BaseRestImpl { ...@@ -268,7 +292,7 @@ public class ElementsRestImpl extends BaseRestImpl {
} }
} }
protected Map<String, Object> getOthersForElement(Element element) { protected Map<String, Object> getOthersForElement(final Element element) {
Map<String, Object> result = new TreeMap<>(); Map<String, Object> result = new TreeMap<>();
List<Map<String, Object>> modifications = new ArrayList<>(); List<Map<String, Object>> modifications = new ArrayList<>();
StructuralState structuralState = null; StructuralState structuralState = null;
...@@ -287,7 +311,7 @@ public class ElementsRestImpl extends BaseRestImpl { ...@@ -287,7 +311,7 @@ public class ElementsRestImpl extends BaseRestImpl {
modifications = getModifications(gene.getModificationResidues()); modifications = getModifications(gene.getModificationResidues());
} }
if (element instanceof Species) { if (element instanceof Species) {
Species species= (Species) element; Species species = (Species) element;
structures = getStructures(species.getUniprots()); structures = getStructures(species.getUniprots());
structuralState = species.getStructuralState(); structuralState = species.getStructuralState();
} }
...@@ -302,7 +326,7 @@ public class ElementsRestImpl extends BaseRestImpl { ...@@ -302,7 +326,7 @@ public class ElementsRestImpl extends BaseRestImpl {
return result; return result;
} }
private List<Map<String, Object>> getModifications(List<? extends ModificationResidue> elements) { private List<Map<String, Object>> getModifications(final List<? extends ModificationResidue> elements) {
List<Map<String, Object>> result = new ArrayList<>(); List<Map<String, Object>> result = new ArrayList<>();
for (ModificationResidue region : elements) { for (ModificationResidue region : elements) {
Map<String, Object> row = new TreeMap<>(); Map<String, Object> row = new TreeMap<>();
...@@ -342,7 +366,7 @@ public class ElementsRestImpl extends BaseRestImpl { ...@@ -342,7 +366,7 @@ public class ElementsRestImpl extends BaseRestImpl {
return result; return result;
} }
private Map<String, Object> getStructures(Set<UniprotRecord> uniprots) { private Map<String, Object> getStructures(final Set<UniprotRecord> uniprots) {
Map<String, Object> result = new TreeMap<>(); Map<String, Object> result = new TreeMap<>();
for (UniprotRecord uniprotRec : uniprots) { for (UniprotRecord uniprotRec : uniprots) {
Set<Object> structs = new LinkedHashSet<>(); Set<Object> structs = new LinkedHashSet<>();
...@@ -354,7 +378,7 @@ public class ElementsRestImpl extends BaseRestImpl { ...@@ -354,7 +378,7 @@ public class ElementsRestImpl extends BaseRestImpl {
return result; return result;
} }
private Map<String, Object> createBounds(Double x, Double y, Integer z, Double width, Double height) { private Map<String, Object> createBounds(final Double x, final Double y, final Integer z, final Double width, final Double height) {
Map<String, Object> result = new TreeMap<>(); Map<String, Object> result = new TreeMap<>();
result.put("x", x); result.put("x", x);
result.put("y", y); result.put("y", y);
...@@ -397,7 +421,7 @@ public class ElementsRestImpl extends BaseRestImpl { ...@@ -397,7 +421,7 @@ public class ElementsRestImpl extends BaseRestImpl {
return result; return result;
} }
private Set<String> createElementColumnSet(String columns) { private Set<String> createElementColumnSet(final String columns) {
Set<String> columnsSet = new LinkedHashSet<>(); Set<String> columnsSet = new LinkedHashSet<>();
if (columns.equals("")) { if (columns.equals("")) {
columnsSet.addAll(getAvailableElementColumns()); columnsSet.addAll(getAvailableElementColumns());
......
package lcsb.mapviewer.web; package lcsb.mapviewer.web;
import static org.springframework.restdocs.mockmvc.MockMvcRestDocumentation.documentationConfiguration; import static org.springframework.restdocs.mockmvc.MockMvcRestDocumentation.documentationConfiguration;
import static org.springframework.restdocs.request.RequestDocumentation.*; import static org.springframework.restdocs.request.RequestDocumentation.parameterWithName;
import static org.springframework.restdocs.request.RequestDocumentation.pathParameters;
import static org.springframework.restdocs.request.RequestDocumentation.requestParameters;
import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.post; import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.post;
import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.status; import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.status;
...@@ -10,8 +12,14 @@ import java.io.ByteArrayInputStream; ...@@ -10,8 +12,14 @@ import java.io.ByteArrayInputStream;
import java.io.IOException; import java.io.IOException;
import java.nio.file.Files; import java.nio.file.Files;
import java.nio.file.Paths; import java.nio.file.Paths;
import java.util.*; import java.util.Arrays;
import java.util.concurrent.*; import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.concurrent.Callable;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.Future;
import java.util.function.Supplier; import java.util.function.Supplier;
import javax.annotation.PostConstruct; import javax.annotation.PostConstruct;
...@@ -22,7 +30,9 @@ import org.apache.commons.lang3.StringUtils; ...@@ -22,7 +30,9 @@ import org.apache.commons.lang3.StringUtils;
import org.apache.logging.log4j.LogManager; import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger; import org.apache.logging.log4j.Logger;
import org.apache.logging.log4j.core.LogEvent; import org.apache.logging.log4j.core.LogEvent;
import org.junit.*; import org.junit.After;
import org.junit.Before;
import org.junit.Rule;
import org.springframework.beans.factory.annotation.Autowired; import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.mock.web.MockHttpSession; import org.springframework.mock.web.MockHttpSession;
import org.springframework.restdocs.JUnitRestDocumentation; import org.springframework.restdocs.JUnitRestDocumentation;
...@@ -41,20 +51,44 @@ import org.springframework.test.web.servlet.setup.MockMvcBuilders; ...@@ -41,20 +51,44 @@ import org.springframework.test.web.servlet.setup.MockMvcBuilders;
import org.springframework.web.context.WebApplicationContext; import org.springframework.web.context.WebApplicationContext;
import lcsb.mapviewer.api.projects.chemicals.ChemicalRestImpl; import lcsb.mapviewer.api.projects.chemicals.ChemicalRestImpl;
import lcsb.mapviewer.common.*; import lcsb.mapviewer.common.MinervaLoggerAppender;
import lcsb.mapviewer.common.TextFileUtils;
import lcsb.mapviewer.common.UnitTestFailedWatcher;
import lcsb.mapviewer.converter.ColorSchemaReader; import lcsb.mapviewer.converter.ColorSchemaReader;
import lcsb.mapviewer.converter.zip.ZipEntryFileFactory; import lcsb.mapviewer.converter.zip.ZipEntryFileFactory;
import lcsb.mapviewer.model.*; import lcsb.mapviewer.model.Project;
import lcsb.mapviewer.model.ProjectLogEntry;
import lcsb.mapviewer.model.ProjectLogEntryType;
import lcsb.mapviewer.model.ProjectStatus;
import lcsb.mapviewer.model.cache.UploadedFileEntry; import lcsb.mapviewer.model.cache.UploadedFileEntry;
import lcsb.mapviewer.model.graphics.*; import lcsb.mapviewer.model.graphics.HorizontalAlign;
import lcsb.mapviewer.model.map.*; import lcsb.mapviewer.model.graphics.PolylineData;
import lcsb.mapviewer.model.map.kinetics.*; import lcsb.mapviewer.model.graphics.VerticalAlign;
import lcsb.mapviewer.model.map.layout.*; import lcsb.mapviewer.model.map.Comment;
import lcsb.mapviewer.model.map.MiriamData;
import lcsb.mapviewer.model.map.MiriamType;
import lcsb.mapviewer.model.map.OverviewImage;
import lcsb.mapviewer.model.map.compartment.Compartment;
import lcsb.mapviewer.model.map.compartment.SquareCompartment;
import lcsb.mapviewer.model.map.kinetics.SbmlFunction;
import lcsb.mapviewer.model.map.kinetics.SbmlParameter;
import lcsb.mapviewer.model.map.kinetics.SbmlUnit;
import lcsb.mapviewer.model.map.layout.ProjectBackground;
import lcsb.mapviewer.model.map.layout.ProjectBackgroundImageLayer;
import lcsb.mapviewer.model.map.layout.ProjectBackgroundStatus;
import lcsb.mapviewer.model.map.layout.graphics.Glyph; import lcsb.mapviewer.model.map.layout.graphics.Glyph;
import lcsb.mapviewer.model.map.model.*; import lcsb.mapviewer.model.map.model.ModelData;
import lcsb.mapviewer.model.map.reaction.*; import lcsb.mapviewer.model.map.model.ModelSubmodelConnection;