Commit 7e59bea6 authored by Piotr Gawron's avatar Piotr Gawron
Browse files

Merge branch 'search-by-synonyms-in-chembl' into 'devel_13.1.x'

Search by synonyms in chembl

See merge request minerva/core!885
parents 90fad475 d4db2a49
Pipeline #12952 canceled with stage
in 6 minutes and 4 seconds
minerva (13.1.4) stable; urgency=medium
* Bug fix:search by drugs didn't check synonyms in chembl database
-- Piotr Gawron <piotr.gawron@uni.lu> Wed, 21 Aug 2019 17:00:00 +0200
minerva (13.1.3) stable; urgency=medium
* Bug fix: refreshing list of projects or list of users doesn't change active
page (#870)
......
......@@ -64,6 +64,11 @@ public class ChEMBLParser extends DrugAnnotation implements IExternalService {
*/
private static final String DRUG_NAME_API_URL = "https://www.ebi.ac.uk/chembl/api/data/molecule?pref_name__exact=";
/**
* Url that access data of drug identified by name.
*/
private static final String DRUG_SYNONYM_API_URL = "https://www.ebi.ac.uk/chembl/api/data/molecule?molecule_synonyms__molecule_synonym__iexact=";
/**
* Url that access target by identifier.
*/
......@@ -366,29 +371,22 @@ public class ChEMBLParser extends DrugAnnotation implements IExternalService {
String page = getWebPageContent(accessUrl);
Document document = XmlParser.getXmlDocumentFromString(page);
Node response = XmlParser.getNode("response", document.getChildNodes());
Node molecules = XmlParser.getNode("molecules", response.getChildNodes());
NodeList list = molecules.getChildNodes();
for (int i = 0; i < list.getLength(); i++) {
Node node = list.item(i);
if (node.getNodeType() == Node.ELEMENT_NODE) {
if (node.getNodeName().equalsIgnoreCase("molecule")) {
if (drug == null) {
drug = parseDrug(node);
} else {
logger.warn("More drugs than one found for query: " + query);
}
}
}
List<Drug> drugs = extractDrugsFromDocument(document);
if (drugs.size()==0) {
accessUrl = DRUG_SYNONYM_API_URL + name;
page = getWebPageContent(accessUrl);
document = XmlParser.getXmlDocumentFromString(page);
drugs = extractDrugsFromDocument(document);
}
if (drugs.size()>1) {
logger.warn("More drugs than one found for query: " + query);
}
if (drug == null) {
if (drugs.size() == 0) {
return null;
}
setCacheValue(query, getDrugSerializer().objectToString(drug));
return drug;
setCacheValue(query, getDrugSerializer().objectToString(drugs.get(0)));
return drugs.get(0);
} catch (IOException e) {
throw new DrugSearchException("Problem with accessing CHEMBL database", e);
} catch (InvalidXmlSchemaException e) {
......@@ -396,6 +394,24 @@ public class ChEMBLParser extends DrugAnnotation implements IExternalService {
}
}
private List<Drug> extractDrugsFromDocument(Document document) throws DrugSearchException {
List<Drug> result = new ArrayList<>();
Node response = XmlParser.getNode("response", document.getChildNodes());
Node molecules = XmlParser.getNode("molecules", response.getChildNodes());
NodeList list = molecules.getChildNodes();
for (int i = 0; i < list.getLength(); i++) {
Node node = list.item(i);
if (node.getNodeType() == Node.ELEMENT_NODE) {
if (node.getNodeName().equalsIgnoreCase("molecule")) {
result.add(parseDrug(node));
}
}
}
return result;
}
/**
* Parse xml node repesenting drug and returns drug with information obtained
* from there and other places in chembl API.
......
package lcsb.mapviewer.annotation.services;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertNotNull;
import static org.junit.Assert.assertNull;
import static org.junit.Assert.assertTrue;
import static org.junit.Assert.fail;
import static org.mockito.ArgumentMatchers.any;
import static org.mockito.ArgumentMatchers.anyString;
import static org.mockito.ArgumentMatchers.nullable;
import static org.junit.Assert.*;
import static org.mockito.ArgumentMatchers.*;
import static org.mockito.Mockito.when;
import java.io.IOException;
import java.util.ArrayList;
import java.util.List;
import java.util.Set;
import java.util.*;
import org.apache.log4j.Logger;
import org.junit.Test;
......@@ -23,22 +14,11 @@ import org.springframework.beans.factory.annotation.Autowired;
import org.w3c.dom.Node;
import lcsb.mapviewer.annotation.AnnotationTestFunctions;
import lcsb.mapviewer.annotation.cache.GeneralCacheInterface;
import lcsb.mapviewer.annotation.cache.PermanentDatabaseLevelCacheInterface;
import lcsb.mapviewer.annotation.cache.SourceNotAvailable;
import lcsb.mapviewer.annotation.cache.WebPageDownloader;
import lcsb.mapviewer.annotation.cache.XmlSerializer;
import lcsb.mapviewer.annotation.data.Drug;
import lcsb.mapviewer.annotation.data.Target;
import lcsb.mapviewer.annotation.data.TargetType;
import lcsb.mapviewer.annotation.services.annotators.AnnotatorException;
import lcsb.mapviewer.annotation.services.annotators.HgncAnnotator;
import lcsb.mapviewer.annotation.services.annotators.UniprotAnnotator;
import lcsb.mapviewer.annotation.services.annotators.UniprotSearchException;
import lcsb.mapviewer.annotation.cache.*;
import lcsb.mapviewer.annotation.data.*;
import lcsb.mapviewer.annotation.services.annotators.*;
import lcsb.mapviewer.common.exception.InvalidArgumentException;
import lcsb.mapviewer.model.map.MiriamData;
import lcsb.mapviewer.model.map.MiriamRelationType;
import lcsb.mapviewer.model.map.MiriamType;
import lcsb.mapviewer.model.map.*;
public class ChEMBLParserTest extends AnnotationTestFunctions {
Logger logger = Logger.getLogger(ChEMBLParserTest.class);
......@@ -349,7 +329,8 @@ public class ChEMBLParserTest extends AnnotationTestFunctions {
try {
chemblParser.setCache(null);
WebPageDownloader mockDownloader = Mockito.mock(WebPageDownloader.class);
when(mockDownloader.getFromNetwork(anyString(), anyString(), nullable(String.class))).thenThrow(new IOException());
when(mockDownloader.getFromNetwork(anyString(), anyString(), nullable(String.class)))
.thenThrow(new IOException());
chemblParser.setWebPageDownloader(mockDownloader);
chemblParser.getTargetFromId(new MiriamData(MiriamType.CHEMBL_TARGET, "water"));
fail("Exception expected");
......@@ -411,7 +392,8 @@ public class ChEMBLParserTest extends AnnotationTestFunctions {
try {
chemblParser.setCache(null);
WebPageDownloader mockDownloader = Mockito.mock(WebPageDownloader.class);
when(mockDownloader.getFromNetwork(anyString(), anyString(), nullable(String.class))).thenReturn("<target><unk/></target>");
when(mockDownloader.getFromNetwork(anyString(), anyString(), nullable(String.class)))
.thenReturn("<target><unk/></target>");
chemblParser.setWebPageDownloader(mockDownloader);
chemblParser.getTargetFromId(new MiriamData(MiriamType.CHEMBL_TARGET, "water"));
assertEquals(1, getWarnings().size());
......@@ -842,7 +824,8 @@ public class ChEMBLParserTest extends AnnotationTestFunctions {
// simulate problem with downloading
WebPageDownloader mockDownloader = Mockito.mock(WebPageDownloader.class);
when(mockDownloader.getFromNetwork(anyString(), anyString(), nullable(String.class))).thenThrow(new IOException());
when(mockDownloader.getFromNetwork(anyString(), anyString(), nullable(String.class)))
.thenThrow(new IOException());
chemblParser.setWebPageDownloader(mockDownloader);
chemblParser.refreshCacheQuery("http://google.pl/");
fail("Exception expected");
......@@ -866,7 +849,8 @@ public class ChEMBLParserTest extends AnnotationTestFunctions {
// simulate problem with downloading
WebPageDownloader mockDownloader = Mockito.mock(WebPageDownloader.class);
when(mockDownloader.getFromNetwork(anyString(), anyString(), nullable(String.class))).thenThrow(new IOException());
when(mockDownloader.getFromNetwork(anyString(), anyString(), nullable(String.class)))
.thenThrow(new IOException());
chemblParser.setWebPageDownloader(mockDownloader);
chemblParser.getDrugsByChemblTarget(new MiriamData());
......@@ -920,7 +904,8 @@ public class ChEMBLParserTest extends AnnotationTestFunctions {
// simulate problem with downloading
WebPageDownloader mockDownloader = Mockito.mock(WebPageDownloader.class);
when(mockDownloader.getFromNetwork(anyString(), anyString(), nullable(String.class))).thenThrow(new IOException());
when(mockDownloader.getFromNetwork(anyString(), anyString(), nullable(String.class)))
.thenThrow(new IOException());
chemblParser.setWebPageDownloader(mockDownloader);
chemblParser.refreshCacheQuery(query);
fail("Exception expected");
......@@ -949,7 +934,8 @@ public class ChEMBLParserTest extends AnnotationTestFunctions {
WebPageDownloader downloader = chemblParser.getWebPageDownloader();
try {
WebPageDownloader mockDownloader = Mockito.mock(WebPageDownloader.class);
when(mockDownloader.getFromNetwork(anyString(), anyString(), nullable(String.class))).thenThrow(new IOException());
when(mockDownloader.getFromNetwork(anyString(), anyString(), nullable(String.class)))
.thenThrow(new IOException());
chemblParser.setWebPageDownloader(mockDownloader);
assertEquals(ExternalServiceStatusType.DOWN, chemblParser.getServiceStatus().getStatus());
} catch (Exception e) {
......@@ -984,9 +970,10 @@ public class ChEMBLParserTest extends AnnotationTestFunctions {
WebPageDownloader mockDownloader = Mockito.mock(WebPageDownloader.class);
// valid xml but with empty data
when(mockDownloader.getFromNetwork(anyString(), anyString(), nullable(String.class))).thenReturn("<response><molecules>"
+ "<molecule><pref_name/><max_phase/><molecule_chembl_id/><molecule_synonyms/></molecule>"
+ "</molecules><mechanisms/><molecule_forms/></response>");
when(mockDownloader.getFromNetwork(anyString(), anyString(), nullable(String.class)))
.thenReturn("<response><molecules>"
+ "<molecule><pref_name/><max_phase/><molecule_chembl_id/><molecule_synonyms/></molecule>"
+ "</molecules><mechanisms/><molecule_forms/></response>");
chemblParser.setWebPageDownloader(mockDownloader);
assertEquals(ExternalServiceStatusType.CHANGED, chemblParser.getServiceStatus().getStatus());
} catch (Exception e) {
......@@ -1043,7 +1030,8 @@ public class ChEMBLParserTest extends AnnotationTestFunctions {
try {
chemblParser.setCache(null);
WebPageDownloader mockDownloader = Mockito.mock(WebPageDownloader.class);
when(mockDownloader.getFromNetwork(anyString(), anyString(), nullable(String.class))).thenThrow(new IOException());
when(mockDownloader.getFromNetwork(anyString(), anyString(), nullable(String.class)))
.thenThrow(new IOException());
chemblParser.setWebPageDownloader(mockDownloader);
chemblParser.getTargetsByDrugId(new MiriamData(MiriamType.CHEMBL_COMPOUND, "123"));
fail("Exception expected");
......@@ -1063,7 +1051,8 @@ public class ChEMBLParserTest extends AnnotationTestFunctions {
try {
chemblParser.setCache(null);
WebPageDownloader mockDownloader = Mockito.mock(WebPageDownloader.class);
when(mockDownloader.getFromNetwork(anyString(), anyString(), nullable(String.class))).thenThrow(new IOException());
when(mockDownloader.getFromNetwork(anyString(), anyString(), nullable(String.class)))
.thenThrow(new IOException());
chemblParser.setWebPageDownloader(mockDownloader);
chemblParser.getDrugListByTarget(new MiriamData(MiriamType.UNIPROT, "O60391"));
fail("Exception expected");
......@@ -1165,7 +1154,8 @@ public class ChEMBLParserTest extends AnnotationTestFunctions {
try {
chemblParser.setCache(null);
WebPageDownloader mockDownloader = Mockito.mock(WebPageDownloader.class);
when(mockDownloader.getFromNetwork(anyString(), anyString(), nullable(String.class))).thenThrow(new IOException());
when(mockDownloader.getFromNetwork(anyString(), anyString(), nullable(String.class)))
.thenThrow(new IOException());
chemblParser.setWebPageDownloader(mockDownloader);
chemblParser.getDrugById(new MiriamData(MiriamType.CHEMBL_COMPOUND, ""));
fail("Exception expected");
......@@ -1199,7 +1189,8 @@ public class ChEMBLParserTest extends AnnotationTestFunctions {
try {
chemblParser.setCache(null);
WebPageDownloader mockDownloader = Mockito.mock(WebPageDownloader.class);
when(mockDownloader.getFromNetwork(anyString(), anyString(), nullable(String.class))).thenThrow(new IOException());
when(mockDownloader.getFromNetwork(anyString(), anyString(), nullable(String.class)))
.thenThrow(new IOException());
chemblParser.setWebPageDownloader(mockDownloader);
chemblParser.getTargetsForChildElements(new MiriamData());
fail("Exception expected");
......@@ -1253,4 +1244,16 @@ public class ChEMBLParserTest extends AnnotationTestFunctions {
}
}
@Test
public void testFindDrugBryBrandName() throws Exception {
try {
Drug drug = chemblParser.findDrug("picato");
assertNotNull(drug);
assertEquals("CHEMBL1863513", drug.getSources().get(0).getResource());
} catch (Exception e) {
e.printStackTrace();
throw e;
}
}
}
delete from cache_query_table where type in (select id from cache_type_table where class_name ='lcsb.mapviewer.annotation.services.ChEMBLParser');
package lcsb.mapviewer.services.search.drug;
import java.util.ArrayList;
import java.util.Collection;
import java.util.Collections;
import java.util.HashSet;
import java.util.List;
import java.util.Set;
import java.util.*;
import org.apache.log4j.Logger;
import org.springframework.beans.factory.annotation.Autowired;
......@@ -14,21 +9,14 @@ import org.springframework.transaction.annotation.Transactional;
import lcsb.mapviewer.annotation.data.Drug;
import lcsb.mapviewer.annotation.data.Target;
import lcsb.mapviewer.annotation.services.ChEMBLParser;
import lcsb.mapviewer.annotation.services.DrugSearchException;
import lcsb.mapviewer.annotation.services.DrugbankHTMLParser;
import lcsb.mapviewer.annotation.services.*;
import lcsb.mapviewer.annotation.services.annotators.AnnotatorException;
import lcsb.mapviewer.annotation.services.annotators.HgncAnnotator;
import lcsb.mapviewer.common.IProgressUpdater;
import lcsb.mapviewer.model.Project;
import lcsb.mapviewer.model.map.BioEntity;
import lcsb.mapviewer.model.map.MiriamData;
import lcsb.mapviewer.model.map.MiriamType;
import lcsb.mapviewer.model.map.*;
import lcsb.mapviewer.model.map.model.Model;
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.*;
import lcsb.mapviewer.model.map.statistics.SearchType;
import lcsb.mapviewer.services.interfaces.ISearchHistoryService;
import lcsb.mapviewer.services.search.DbSearchCriteria;
......@@ -185,9 +173,15 @@ public class DrugService extends DbSearchService implements IDrugService {
if (name.trim().equals("")) {
return null;
}
DrugAnnotation secondParser = chEMBLParser;
Drug drug = null;
try {
drug = drugBankParser.findDrug(name);
if (drug==null) {
drug = chEMBLParser.findDrug(name);
secondParser = drugBankParser;
}
if (drug != null) {
removeUnknownOrganisms(drug, searchCriteria.getOrganisms());
}
......@@ -201,13 +195,13 @@ public class DrugService extends DbSearchService implements IDrugService {
// * search for name
searchNames.add(name);
if (drug != null && drug.getName() != null) {
// * search for name of a drug in drugbanke
// * search for name of a drug in drugbank
searchNames.add(drug.getName());
// * search for all synonyms found in drugbank
// searchNames.addAll(drug.getSynonyms());
}
for (String string : searchNames) {
Drug drug2 = chEMBLParser.findDrug(string);
Drug drug2 = secondParser.findDrug(string);
if (drug2 != null) {
removeUnknownOrganisms(drug2, searchCriteria.getOrganisms());
// don't add drugs that were already found
......
......@@ -57,6 +57,17 @@ public class DrugServiceTest extends ServiceTestFunctions {
}
}
@Test
public void testGetIstodax() throws Exception {
try {
Drug drug = drugService.getByName("istodax", new DbSearchCriteria());
assertEquals(2, drug.getSources().size());
} catch (Exception e) {
e.printStackTrace();
throw e;
}
}
@Test
public void testGetTargets() throws Exception {
try {
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment