/** * ============================================================================= * * ORCID (R) Open Source * http://orcid.org * * Copyright (c) 2012-2014 ORCID, Inc. * Licensed under an MIT-Style License (MIT) * http://orcid.org/open-source-license * * This copyright and license information (including a link to the full license) * shall be included in its entirety in all copies or substantial portion of * the software. * * ============================================================================= */ package org.orcid.persistence.dao; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertFalse; import static org.junit.Assert.assertNull; import static org.junit.Assert.assertTrue; import java.text.MessageFormat; import java.util.ArrayList; import java.util.Arrays; import java.util.List; import javax.annotation.Resource; import org.apache.commons.lang.RandomStringUtils; import org.junit.After; import org.junit.Before; import org.junit.Test; import org.junit.runner.RunWith; import org.orcid.utils.solr.entities.OrcidSolrDocument; import org.orcid.utils.solr.entities.OrcidSolrResult; import org.orcid.utils.solr.entities.OrcidSolrResults; import org.orcid.test.OrcidJUnit4ClassRunner; import org.springframework.test.context.ContextConfiguration; @RunWith(OrcidJUnit4ClassRunner.class) @ContextConfiguration(locations = { "classpath:test-orcid-persistence-context.xml" }) /** * Integration tests for Solr Daos. * In particular these are used to test that query strings return the Orcids that are expected from SOLR. * You may need to compare the queries given in the test methods below with those of the SearchOrcidFormToQueryMapperTest. * * @author jamesb * @See SearchOrcidFormToQueryMapperTest * */ public class SolrDaoTest { @Resource private SolrDao solrDao; private String firstOrcid = "1234-5678"; private String secondOrcid = "5677-1235"; private List<String> orcidsToDelete; @Before public void initOrcid() { orcidsToDelete = new ArrayList<String>(); orcidsToDelete.add(firstOrcid); orcidsToDelete.add(secondOrcid); } @After public void deleteOrcid() { solrDao.removeOrcids(orcidsToDelete); } @Test public void searchByOrcid() throws Exception { OrcidSolrResult firstOrcidResult = solrDao.findByOrcid(firstOrcid); assertNull(firstOrcidResult); OrcidSolrDocument secondOrcid = buildAndPersistSecondOrcid(); OrcidSolrDocument firstOrcid = buildAndPersistFirstOrcid(); firstOrcidResult = solrDao.findByOrcid(firstOrcid.getOrcid()); assertFalse(secondOrcid.getOrcid().equals(firstOrcidResult.getOrcid())); assertEquals("1234-5678", firstOrcidResult.getOrcid()); } @Test public void queryStringSearchPatent() throws Exception { OrcidSolrDocument firstOrcid = buildAndPersistFirstOrcid(); String patentQueryString = "patent-numbers:Elec-hammer01X%3A"; OrcidSolrResults orcidSolrResults = solrDao.findByDocumentCriteria(patentQueryString, null, null); List<OrcidSolrResult> solrResultsList = orcidSolrResults.getResults(); assertTrue(solrResultsList.size() == 1); assertEquals(firstOrcid.getOrcid(), solrResultsList.get(0).getOrcid()); } @Test public void queryStringSearchGrant() throws Exception { OrcidSolrDocument secondOrcid = buildAndPersistSecondOrcid(); String patentQueryString = "grant-numbers:grant-number02X%3A"; OrcidSolrResults orcidSolrResults = solrDao.findByDocumentCriteria(patentQueryString, null, null); List<OrcidSolrResult> solrResultsList = orcidSolrResults.getResults(); assertTrue(solrResultsList.size() == 1); assertEquals(secondOrcid.getOrcid(), solrResultsList.get(0).getOrcid()); } @Test public void queryStringSearchFamilyNameGivenName() throws Exception { OrcidSolrResult orcidSolrDocument = solrDao.findByOrcid(firstOrcid); assertNull(orcidSolrDocument); orcidSolrDocument = solrDao.findByOrcid(secondOrcid); assertNull(orcidSolrDocument); OrcidSolrDocument profile1 = new OrcidSolrDocument(); profile1.setOrcid(firstOrcid); profile1.setFamilyName("Bass"); profile1.setGivenNames("Teddy"); OrcidSolrDocument profile2 = new OrcidSolrDocument(); profile2.setOrcid(secondOrcid); profile2.setFamilyName("Bass"); profile2.setGivenNames("Terry"); solrDao.persist(profile1); solrDao.persist(profile2); String familyNameGivenNameQuery = "given-names:teddy AND family-name:bass"; OrcidSolrResults orcidSolrResults = solrDao.findByDocumentCriteria(familyNameGivenNameQuery, null, null); List<OrcidSolrResult> solrResultsList = orcidSolrResults.getResults(); assertTrue(solrResultsList.size() == 1); assertEquals(firstOrcid, solrResultsList.get(0).getOrcid()); String familyNameQueryRelaxed = "given-names:te* AND family-name:Bass"; solrResultsList = solrDao.findByDocumentCriteria(familyNameQueryRelaxed, null, null).getResults(); assertTrue(solrResultsList.size() == 2); assertEquals(firstOrcid, solrResultsList.get(0).getOrcid()); assertEquals(secondOrcid, solrResultsList.get(1).getOrcid()); } @Test public void queryFieldWithExclusions() throws Exception { buildAndPersistFirstOrcid(); buildAndPersistSecondOrcid(); String givenNameQueryString = "given-names:Given"; List<OrcidSolrResult> solrResults = solrDao.findByDocumentCriteria(givenNameQueryString, null, null).getResults(); assertTrue(solrResults.size() == 2); String givenNameWithExclusionsQueryString = MessageFormat.format("given-names:Given -orcid: {0}", new Object[] { secondOrcid }); solrResults = solrDao.findByDocumentCriteria(givenNameWithExclusionsQueryString, null, null).getResults(); assertTrue(solrResults.size() == 1 && solrResults.get(0).getOrcid().equals(firstOrcid)); } @Test public void queryFieldWithKeyword() throws Exception { buildAndPersistFirstOrcid(); OrcidSolrDocument secondDoc = buildSupplementaryOrcid(); String subjectKeyword1 = "Advanced Muppetry"; String subjectKeyword2 = "Basic Muppetry"; secondDoc.setOrcid(secondOrcid); secondDoc.setKeywords(Arrays.asList(subjectKeyword1, subjectKeyword2)); persistOrcid(secondDoc); String familyNameKeywordsQueryString = "given-names:given AND keyword:basic"; List<OrcidSolrResult> solrResults = solrDao.findByDocumentCriteria(familyNameKeywordsQueryString, null, null).getResults(); assertTrue(solrResults.size() == 1); OrcidSolrResult result = solrResults.get(0); assertEquals(secondOrcid, result.getOrcid()); familyNameKeywordsQueryString = "given-names:given AND keyword:advanced"; solrResults = solrDao.findByDocumentCriteria(familyNameKeywordsQueryString, null, null).getResults(); assertTrue(solrResults.size() == 1); result = solrResults.get(0); assertEquals(secondOrcid, result.getOrcid()); } @Test public void queryFieldWeyword() throws Exception { buildAndPersistFirstOrcid(); OrcidSolrDocument secondDoc = buildSupplementaryOrcid(); String subjectKeyword1 = "Advanced Muppetry"; String subjectKeyword2 = "Basic Muppetry"; secondDoc.setOrcid(secondOrcid); secondDoc.setKeywords(Arrays.asList(subjectKeyword1, subjectKeyword2)); persistOrcid(secondDoc); String familyNameKeywordsQueryString = "given-names:given AND keyword:basic"; List<OrcidSolrResult> solrResults = solrDao.findByDocumentCriteria(familyNameKeywordsQueryString, null, null).getResults(); assertTrue(solrResults.size() == 1); OrcidSolrResult result = solrResults.get(0); assertEquals(secondOrcid, result.getOrcid()); familyNameKeywordsQueryString = "given-names:given AND keyword:advanced"; solrResults = solrDao.findByDocumentCriteria(familyNameKeywordsQueryString, null, null).getResults(); assertTrue(solrResults.size() == 1); result = solrResults.get(0); assertEquals(secondOrcid, result.getOrcid()); } @Test public void queryFieldWithBoostAndExclusions() throws Exception { OrcidSolrDocument firstOrcidDoc = buildFirstOrcid(); firstOrcidDoc.setOrcid(firstOrcid); firstOrcidDoc.setFamilyName("James"); OrcidSolrDocument secondOrcidDoc = buildSupplementaryOrcid(); secondOrcidDoc.setOrcid(secondOrcid); secondOrcidDoc.setGivenNames("James"); OrcidSolrDocument thirdOrcidDoc = buildSupplementaryOrcid(); thirdOrcidDoc.setFamilyName("James"); thirdOrcidDoc.setOrcid(RandomStringUtils.randomAlphabetic(9)); persistOrcid(firstOrcidDoc); persistOrcid(secondOrcidDoc); persistOrcid(thirdOrcidDoc); String familyNameGivenNameQuery = "{!edismax qf='family-name^1.0 given-names^2.0'}James"; List<OrcidSolrResult> solrResults = solrDao.findByDocumentCriteria(familyNameGivenNameQuery, null, null).getResults(); assertTrue(solrResults.size() == 3); OrcidSolrResult givenNameMatch = solrResults.get(0); assertTrue(secondOrcid.equals(givenNameMatch.getOrcid()) && givenNameMatch.getRelevancyScore() > 1); OrcidSolrResult familyNameMatch1 = solrResults.get(1); OrcidSolrResult familyNameMatch2 = solrResults.get(2); assertTrue(familyNameMatch1.getRelevancyScore() < 1.0); assertTrue(familyNameMatch2.getRelevancyScore() < 1.0); String familyNameGivenNameQueryWithExclude = familyNameGivenNameQuery + " -orcid:" + thirdOrcidDoc.getOrcid(); solrResults = solrDao.findByDocumentCriteria(familyNameGivenNameQueryWithExclude, null, null).getResults(); assertTrue(solrResults.size() == 2); givenNameMatch = solrResults.get(0); assertTrue(givenNameMatch.getOrcid().equals(secondOrcid)); assertTrue(givenNameMatch.getRelevancyScore() > 1); familyNameMatch1 = solrResults.get(1); assertTrue(familyNameMatch1.getOrcid().equals(firstOrcid)); assertTrue(familyNameMatch1.getRelevancyScore() < 1); } @Test public void queryFieldWithBoost() throws Exception { OrcidSolrDocument firstOrcidDoc = buildFirstOrcid(); firstOrcidDoc.setOrcid(firstOrcid); firstOrcidDoc.setFamilyName("James"); OrcidSolrDocument secondOrcidDoc = buildSupplementaryOrcid(); secondOrcidDoc.setOrcid(secondOrcid); secondOrcidDoc.setGivenNames("James"); solrDao.persist(firstOrcidDoc); solrDao.persist(secondOrcidDoc); String familyNameGivenNameQuery = "{!edismax qf='family-name^1.0 given-names^2.0'}James"; List<OrcidSolrResult> solrResults = solrDao.findByDocumentCriteria(familyNameGivenNameQuery, null, null).getResults(); assertTrue(solrResults.size() == 2); assertTrue(solrResults.get(0).getOrcid().equals(secondOrcid)); assertTrue(solrResults.get(1).getOrcid().equals(firstOrcid)); } @Test public void queryStringSearchFamilyNameGivenNameTenRows() throws Exception { int numRecordsToCreate = 10; List<String> orcidsToGetStored = new ArrayList<String>(); for (int i = 0; i < numRecordsToCreate; i++) { OrcidSolrDocument orcidSolrDocument = buildSupplementaryOrcid(); orcidSolrDocument.setGivenNames(RandomStringUtils.randomAscii(20)); // format of orcid irrelevant to solr - just need to make them // different orcidSolrDocument.setOrcid(RandomStringUtils.randomAscii(20)); orcidsToGetStored.add(orcidSolrDocument.getOrcid()); persistOrcid(orcidSolrDocument); } String familyNameOnlyQuery = "family-name:Family Name"; List<OrcidSolrResult> solrResults = solrDao.findByDocumentCriteria(familyNameOnlyQuery, null, null).getResults(); assertTrue(solrResults.size() == 10); familyNameOnlyQuery = "{!start=0 rows=5} family-name:Family Name"; solrResults = solrDao.findByDocumentCriteria(familyNameOnlyQuery, null, null).getResults(); assertTrue(solrResults.size() == 5); } @Test public void queryStringWithTextFieldSpansAllFields() throws Exception { buildAndPersistFirstOrcid(); buildAndPersistSecondOrcid(); String orcidQueryString = "text=1234\\-5678"; List<OrcidSolrResult> solrResults = solrDao.findByDocumentCriteria(orcidQueryString, null, null).getResults(); assertTrue(solrResults.size() == 1); String givenNameQueryString = "text=Given"; solrResults = solrDao.findByDocumentCriteria(givenNameQueryString, null, null).getResults(); assertTrue(solrResults.size() == 2); String familyNameQueryString = "text=Smith"; solrResults = solrDao.findByDocumentCriteria(familyNameQueryString, null, null).getResults(); assertTrue(solrResults.size() == 1 && solrResults.get(0).getOrcid().equals(firstOrcid)); String patentsQueryString = "text=Elec-hammer01X%3A"; solrResults = solrDao.findByDocumentCriteria(patentsQueryString, null, null).getResults(); assertTrue(solrResults.size() == 1 && solrResults.get(0).getOrcid().equals(firstOrcid)); String grantQueryString = "text=Grant-number02X%3A"; solrResults = solrDao.findByDocumentCriteria(grantQueryString, null, null).getResults(); assertTrue(solrResults.size() == 1 && solrResults.get(0).getOrcid().equals(secondOrcid)); String creditNameQueryString = "text=Credit"; solrResults = solrDao.findByDocumentCriteria(creditNameQueryString, null, null).getResults(); assertTrue(solrResults.size() == 1 && solrResults.get(0).getOrcid().equals(secondOrcid)); String otherNamesQueryString = "text=Other"; solrResults = solrDao.findByDocumentCriteria(otherNamesQueryString, null, null).getResults(); assertTrue(solrResults.size() == 1 && solrResults.get(0).getOrcid().equals(secondOrcid)); String doiQueryString = "text=id2"; solrResults = solrDao.findByDocumentCriteria(doiQueryString, null, null).getResults(); assertTrue(solrResults.size() == 1 && solrResults.get(0).getOrcid().equals(secondOrcid)); String worksTitlesQueryString = "text=Work Title 1"; solrResults = solrDao.findByDocumentCriteria(worksTitlesQueryString, null, null).getResults(); assertTrue(solrResults.size() == 1 && solrResults.get(0).getOrcid().equals(secondOrcid)); String emailQueryString = "text=stan@ficitional.co.uk"; solrResults = solrDao.findByDocumentCriteria(emailQueryString, null, null).getResults(); assertTrue(solrResults.size() == 1 && solrResults.get(0).getOrcid().equals(secondOrcid)); } private OrcidSolrDocument buildAndPersistFirstOrcid() { OrcidSolrDocument firstDocument = buildFirstOrcid(); firstDocument.setOrcid(firstOrcid); persistOrcid(firstDocument); return firstDocument; } private OrcidSolrDocument buildFirstOrcid() { OrcidSolrDocument testDoc = new OrcidSolrDocument(); testDoc.setOrcid(firstOrcid); testDoc.setGivenNames("Given Name of Person"); testDoc.setFamilyName("Smith"); testDoc.setPatentNumbers(Arrays.asList(new String[] { "Elec-hammer01X:" })); return testDoc; } private OrcidSolrDocument buildAndPersistSecondOrcid() { OrcidSolrDocument secondDoc = buildSupplementaryOrcid(); secondDoc.setOrcid(secondOrcid); persistOrcid(secondDoc); return secondDoc; } private OrcidSolrDocument buildSupplementaryOrcid() { OrcidSolrDocument secondOrcidDoc = new OrcidSolrDocument(); secondOrcidDoc.setCreditName("Credit Name"); secondOrcidDoc.addEmailAddress("stan@ficitional.co.uk"); secondOrcidDoc.setFamilyName("Family Name"); secondOrcidDoc.setGivenNames("Given Names"); secondOrcidDoc.setDigitalObjectIds(Arrays.asList(new String[] { "id1", "id2" })); secondOrcidDoc.setOtherNames(Arrays.asList(new String[] { "Other Name 1", "Other Name 2" })); secondOrcidDoc.setWorkTitles(Arrays.asList(new String[] { "Work Title 1", "Work Title 2" })); secondOrcidDoc.setGrantNumbers(Arrays.asList(new String[] { "Grant-number02X:" })); return secondOrcidDoc; } private void persistOrcid(OrcidSolrDocument orcidSolrDocument) { orcidsToDelete.add(orcidSolrDocument.getOrcid()); solrDao.persist(orcidSolrDocument); } }