Project

General

Profile

« Previous | Next » 

Revision 5d806a70

Added by Andreas Müller over 13 years ago

Moving IPNI service to new package and adding new functionality.
Create BCI service

View differences:

.gitattributes
1238 1238
cdmlib-ext/src/main/java/eu/etaxonomy/cdm/ext/EditGeoService.java -text
1239 1239
cdmlib-ext/src/main/java/eu/etaxonomy/cdm/ext/EditGeoServiceUtilities.java -text
1240 1240
cdmlib-ext/src/main/java/eu/etaxonomy/cdm/ext/IEditGeoService.java -text
1241
cdmlib-ext/src/main/java/eu/etaxonomy/cdm/ext/IIpniService.java -text
1242
cdmlib-ext/src/main/java/eu/etaxonomy/cdm/ext/IpniService.java -text
1241
cdmlib-ext/src/main/java/eu/etaxonomy/cdm/ext/bci/BciService.java -text
1242
cdmlib-ext/src/main/java/eu/etaxonomy/cdm/ext/bci/IBciService.java -text
1243
cdmlib-ext/src/main/java/eu/etaxonomy/cdm/ext/ipni/IIpniService.java -text
1244
cdmlib-ext/src/main/java/eu/etaxonomy/cdm/ext/ipni/IIpniServiceConfigurator.java -text
1245
cdmlib-ext/src/main/java/eu/etaxonomy/cdm/ext/ipni/IpniService.java -text
1246
cdmlib-ext/src/main/java/eu/etaxonomy/cdm/ext/ipni/IpniServiceAuthorConfigurator.java -text
1247
cdmlib-ext/src/main/java/eu/etaxonomy/cdm/ext/ipni/IpniServiceConfiguratorBase.java -text
1248
cdmlib-ext/src/main/java/eu/etaxonomy/cdm/ext/ipni/IpniServiceNamesConfigurator.java -text
1249
cdmlib-ext/src/main/java/eu/etaxonomy/cdm/ext/ipni/IpniServicePublicationConfigurator.java -text
1243 1250
cdmlib-ext/src/site/site.xml -text
1244 1251
cdmlib-ext/src/test/java/eu/etaxonomy/cdm/ext/EditGeoServiceTest.java -text
1252
cdmlib-ext/src/test/java/eu/etaxonomy/cdm/ext/bci/BciServiceTest.java -text
1253
cdmlib-ext/src/test/java/eu/etaxonomy/cdm/ext/ipni/IpniServiceTest.java -text
1245 1254
cdmlib-ext/src/test/java/eu/etaxonomy/cdm/test/suite/CdmTestSuite.java -text
1246 1255
cdmlib-ext/src/test/java/eu/etaxonomy/cdm/test/unit/CdmUnitTestBase.java -text
1247 1256
cdmlib-ext/src/test/resources/eu/etaxonomy/cdm.datasources.xml -text
cdmlib-ext/src/main/java/eu/etaxonomy/cdm/ext/EditGeoService.java
38 38
@Service
39 39
@Transactional(readOnly=true)
40 40
public class EditGeoService implements IEditGeoService{
41
	public static final Logger logger = Logger.getLogger(EditGeoService.class);
41 42
	
42 43
	private static final String DEFAULT_BACK_LAYER = "tdwg4";
43 44

  
44
	public static final Logger logger = Logger.getLogger(EditGeoService.class);
45
	
46 45
	@Autowired
47 46
	private IDescriptionDao dao;
48 47
	@Autowired
cdmlib-ext/src/main/java/eu/etaxonomy/cdm/ext/IIpniService.java
1
// $Id$
2
/**
3
* Copyright (C) 2009 EDIT
4
* European Distributed Institute of Taxonomy 
5
* http://www.e-taxonomy.eu
6
* 
7
* The contents of this file are subject to the Mozilla Public License Version 1.1
8
* See LICENSE.TXT at the top of this package for the full license terms.
9
*/
10
package eu.etaxonomy.cdm.ext;
11

  
12
import java.util.List;
13
import java.util.UUID;
14

  
15
import eu.etaxonomy.cdm.api.application.ICdmApplicationConfiguration;
16
import eu.etaxonomy.cdm.model.agent.Person;
17
import eu.etaxonomy.cdm.model.common.ExtensionType;
18
import eu.etaxonomy.cdm.model.common.IdentifiableSource;
19
import eu.etaxonomy.cdm.model.name.BotanicalName;
20
import eu.etaxonomy.cdm.model.name.Rank;
21

  
22

  
23
/**
24
* Interface for queying IPNI via webservice ({@link http://www.uk.ipni.org/}). 
25
* Services are available for the plant name index, the autor index and the publication index.
26
* @author a.mueller
27
* @created Aug 16, 2010
28
* @version 1.0
29
 */
30
public interface IIpniService {
31

  
32
	// GENERAL
33
	public static String ID = "Id";
34
	public static String VERSION = "Version";
35
	
36
	//NAMES 
37
	public static final String FULL_NAME_WITHOUT_FAMILY_AND_AUTHORS = "Full name without family and authors";
38
	public static final String AUTHORS = "Authors";
39
	public static final String FAMILY = "Family";
40
	public static final String GENUS = "Genus";
41
	public static final String INFRA_GENUS = "Infra genus";
42
	public static final String SPECIES = "Species";
43
	public static final String INFRA_SPECIFIC = "Infra species";
44
	public static final String RANK = "Rank";
45
	public static final String BASIONYM_AUTHOR = "Basionym author";
46
	public static final String PUBLISHING_AUTHOR = "Publishing author";
47
	public static final String PUBLICATION = "Publication";
48
	public static final String PUBLICATION_YEAR_FULL = "Publication year full";
49
	public static final String NAME_STATUS = "Name status";
50
	public static final String REMARKS = "Remarks";
51
	public static final String BASIONYM = "Basionym";
52
	public static final String REPLACED_SYNONYM = "Replaced synonym";
53

  
54
	
55
	//AUTHORS
56
	
57
	public static final String STANDARD_FORM = "Standard Form";
58
	
59
	public static final String DEFAULT_AUTHOR_FORENAME = "Default author forename";
60
	public static final String DEFAULT_AUTHOR_SURNAME = "Default author surname";
61
	public static final String TAXON_GROUPS = "Taxon groups";
62
	public static final String DATES = "Dates";
63
	public static final String ALTERNATIVE_NAMES = "Alternative names";
64
	
65
	public static final String DEFAULT_AUTHOR_NAME = "Default author name";
66
	
67
	public static final String NAME_NOTES = "Name notes";
68
	public static final String NAME_SOURCE = "Name source";
69
	public static final String DATE_TYPE_CODE = "Date type code";
70
	public static final String DATE_TYPE_STRING = "Date type string";
71
	
72
	public static final String ALTERNATIVE_ABBREVIATIONS = "Alternative abbreviations";
73
	public static final String EXAMPLE_OF_NAME_PUBLISHED = "Example of name published";
74
	
75
	/**
76
	 * UUID for the reference representing the IPNI database:<BR/>
77
	 * 8b6d750f-c7e0-4180-afbf-aa4c50148813
78
	 */
79
	public static final UUID uuidIpni = UUID.fromString("8b6d750f-c7e0-4180-afbf-aa4c50148813");
80
	/**
81
	 * UUID for the extension type 'Alternative name':<BR/>
82
	 * eee99927-1f9f-4df2-9d8f-11746bf35c0c
83
	 */
84
	public static final UUID uuidAlternativeNames = UUID.fromString("eee99927-1f9f-4df2-9d8f-11746bf35c0c");
85
	
86

  
87
	public static final String AUTHOR_SERVICE_URL = "http://www.ipni.org/ipni/advAuthorSearch.do";
88
	public static final String SIMPLE_NAME_SERVICE_URL = "http://www.uk.ipni.org/ipni/simplePlantNameSearch.do";
89
	public static final String ADVANCED_NAME_SERVICE_URL = "http://www.uk.ipni.org/ipni/advPlantNameSearch.do";
90
	public static final String PUBLICATION_SERVICE_URL = "http://www.uk.ipni.org/ipni/pubXXX.do";
91
	
92
	
93
	 /**
94
	 * Enumeration of the four return delimited data formats provided by IPNI.<BR/>
95
	 * @see http://www.ipni.org/ipni/delimited_help.html
96
	 * @author a.mueller
97
	 */
98
	public enum DelimitedFormat{
99
		/** IPNI classic delimited format */
100
		 CLASSIC ("delimited-classic"),
101
		 /** IPNI minimal delimited format */
102
		 MINIMAL ("delimited-minimal"),
103
		 /** IPNI short delimited format */
104
		 SHORT ("delimited-short"),
105
		 /** IPNI extended delimited format */
106
		 EXTENDED ("delimited-extended");
107
		 
108
		 String parameter;
109
		 DelimitedFormat(String parameter){
110
			this.parameter = parameter; 
111
		 }
112
	 }
113
	
114
	/**
115
	 * Returns a list of persons (authors) defined by their abbreviation, surname, forename and/or isoCountry.
116
	 * The amount of data added to each person depends on the format and the database connection (appConfig).
117
	 * <BR/><BR/>
118
	 * The {@link DelimitedFormat#MINIMAL minimal}  and {@link DelimitedFormat#SHORT short} format returns the 
119
	 * <i>standard form</i> as the nomenclatural title, the <i>default author forename</i> as the firstname and
120
	 * the <i>default author surname</i> as the lastname of the returned {@link Person person} object. 
121
	 * The <i>id</i> and the <i>version</i> are added as {@link IdentifiableSource source} where the id is the id,
122
	 * the namespace is "Author" and the microcitation is the <i>version</i>. If an a database connection is passed
123
	 * (appConig is not <code>null</null>) the database is searched for an existing citation representing the IPNI
124
	 *  webservice. If not exists a new such reference with the given {@link #uuidIpni ipni uuid} is created and stored
125
	 *  in the database.<BR/>
126
	 *  If no database connection is passed a new reference is created each time with a random UUID to avoid duplicate
127
	 *  key problems when trying to save the returned objects.
128
	 *  <BR/><BR/>
129
	 * The {@link DelimitedFormat#EXTENDED minimal} format returns the same object as the {@link DelimitedFormat#SHORT short} format 
130
	 * but additionally the <i>date</i> is evaluated as lifespan.
131
	 * Also an extension of type
132
	 * {@link ExtensionType.INFORMAL_CATEGORY} is added for each semicolon separated part of the 'Alternative names' result.
133
	 * TODO make alternative name or alternative title an own ExtensionType
134
	 * <BR/><BR/>
135
	 * The {@link DelimitedFormat#CLASSIC classic} format at the moment returns the same object as the {@link DelimitedFormat#EXTENDED extended} format 
136
	 * as the remaining parameters are not yet implemented.
137
	 *  
138
	 * @param abbreviation
139
	 * @param surname
140
	 * @param forename
141
	 * @param isoCountry
142
	 * @param format 
143
	 * @param appConfig
144
	 * @return
145
	 */
146
	public List<Person> getAuthors(String abbreviation, String surname, String forename, String isoCountry, DelimitedFormat format, ICdmApplicationConfiguration appConfig);
147

  
148

  
149
	public List<BotanicalName> getNamesSimple(String wholeName, DelimitedFormat format , ICdmApplicationConfiguration appConfig);
150

  
151
	public List<BotanicalName> getNamesAdvanced(String family, String genus, String species, String infraFamily, 
152
			String infraGenus, String infraSpecies, String authorAbbrev, Boolean includePublicationAuthors, 
153
			Boolean includeBasionymAuthors,
154
			String publicationTitle,
155
			Boolean isAPNIRecord, 
156
			Boolean isGCIRecord, 
157
			Boolean isIKRecord,
158
			Rank rankToReturn,
159
			Boolean sortByFamily,
160
			DelimitedFormat format, 
161
			ICdmApplicationConfiguration appConfig);
162
	}
cdmlib-ext/src/main/java/eu/etaxonomy/cdm/ext/IpniService.java
1
// $Id$
2
/**
3
* Copyright (C) 2009 EDIT
4
* European Distributed Institute of Taxonomy 
5
* http://www.e-taxonomy.eu
6
* 
7
* The contents of this file are subject to the Mozilla Public License Version 1.1
8
* See LICENSE.TXT at the top of this package for the full license terms.
9
*/
10
package eu.etaxonomy.cdm.ext;
11

  
12
import java.io.BufferedReader;
13
import java.io.IOException;
14
import java.io.InputStream;
15
import java.io.InputStreamReader;
16
import java.net.HttpURLConnection;
17
import java.net.MalformedURLException;
18
import java.net.URL;
19
import java.util.ArrayList;
20
import java.util.HashMap;
21
import java.util.List;
22
import java.util.Map;
23

  
24
import org.apache.commons.lang.StringUtils;
25
import org.apache.log4j.Logger;
26
import org.springframework.stereotype.Component;
27

  
28
import eu.etaxonomy.cdm.api.application.ICdmApplicationConfiguration;
29
import eu.etaxonomy.cdm.common.CdmUtils;
30
import eu.etaxonomy.cdm.model.agent.Person;
31
import eu.etaxonomy.cdm.model.agent.Team;
32
import eu.etaxonomy.cdm.model.common.Annotation;
33
import eu.etaxonomy.cdm.model.common.AnnotationType;
34
import eu.etaxonomy.cdm.model.common.Extension;
35
import eu.etaxonomy.cdm.model.common.ExtensionType;
36
import eu.etaxonomy.cdm.model.common.IdentifiableEntity;
37
import eu.etaxonomy.cdm.model.common.Language;
38
import eu.etaxonomy.cdm.model.common.TimePeriod;
39
import eu.etaxonomy.cdm.model.name.BotanicalName;
40
import eu.etaxonomy.cdm.model.name.NomenclaturalCode;
41
import eu.etaxonomy.cdm.model.name.NomenclaturalStatus;
42
import eu.etaxonomy.cdm.model.name.NomenclaturalStatusType;
43
import eu.etaxonomy.cdm.model.name.Rank;
44
import eu.etaxonomy.cdm.model.name.TaxonNameBase;
45
import eu.etaxonomy.cdm.model.reference.ReferenceBase;
46
import eu.etaxonomy.cdm.model.reference.ReferenceFactory;
47
import eu.etaxonomy.cdm.strategy.exceptions.UnknownCdmTypeException;
48

  
49

  
50
/**
51
* @author a.mueller
52
* @created Aug 16, 2010
53
* @version 1.0
54
 *
55
 */
56
@Component
57
public class IpniService implements IIpniService{
58
	private static final Logger logger = Logger.getLogger(IpniService.class);
59
	
60
	 private enum ServiceType{
61
		 AUTHOR,
62
		 NAME,
63
		 PUBLICATION,
64
	 }
65
		
66
	 
67
//	private URL serviceUrl;
68
	 
69
// ******************************** CONSTRUCTOR **************************************
70
	   
71
	   
72
//	/**
73
//	 * Creates new instance of this factory and connects it to the given
74
//	 * CDM Community Stores access point.
75
//	 *
76
//	 * Typically, there is no need to instantiate this class.
77
//	 */
78
//	protected IpniService(URL webserviceUrl){
79
//		this.serviceUrl = webserviceUrl;
80
//	}
81

  
82
// ****************************** METHODS ****************************************************/	
83
	
84
	/**
85
	 *
86
	 * @param restRequest
87
	 * @return
88
	 */
89
	public List<Person> getAuthors(String abbreviation, String surname, String forename, String isoCountry, DelimitedFormat format , ICdmApplicationConfiguration appConfig){
90
		abbreviation = CdmUtils.Nz(abbreviation);
91
		surname = CdmUtils.Nz(surname);
92
		isoCountry = CdmUtils.Nz(isoCountry);
93
		forename = CdmUtils.Nz(forename);
94
		
95
		format = format == null ? getDefaultFormat() : format;
96
			
97
		String request = "find_abbreviation=" + abbreviation + 
98
						"&find_surname=" + surname + 
99
						"&find_isoCountry=" + isoCountry + 
100
						"&find_forename=" + forename +
101
						"&output_format=" + format.parameter;
102
		
103
		return (List)queryService(request, appConfig, getServiceUrl(IIpniService.AUTHOR_SERVICE_URL), ServiceType.AUTHOR);
104
	}
105
	       
106

  
107
	/**
108
	 *
109
	 * @param restRequest
110
	 * @return
111
	*/
112
	private List<? extends IdentifiableEntity> queryService(String request, ICdmApplicationConfiguration appConfig, URL serviceUrl, ServiceType serviceType){
113
		try {
114
            // create the request url
115
            URL newUrl = new URL(serviceUrl.getProtocol(),
116
                                                     serviceUrl.getHost(),
117
                                                     serviceUrl.getPort(),
118
                                                     serviceUrl.getPath() 
119
                                                     + "?" + request);
120
            // open a connection
121
            HttpURLConnection connection = (HttpURLConnection) newUrl.openConnection();
122
            // set the accept property to XML so we can use jdom to handle the content
123
            //connection.setRequestProperty("Accept", "text/xml");
124
   
125
           
126
            logger.info("Firing request for URL: " + newUrl);
127
                   
128
            int responseCode = connection.getResponseCode();
129
           
130
            // get the content at the resource
131
            InputStream content = (InputStream) connection.getContent();
132
           
133
            // build the result
134
            List<? extends IdentifiableEntity> result;
135
            if (serviceType.equals(ServiceType.AUTHOR)){
136
            	result = buildAuthorList(content, appConfig);
137
            }else if (serviceType.equals(ServiceType.NAME)){
138
            	result = buildNameList(content, appConfig);
139
            }else{
140
            	result = buildPublicationList(content, appConfig);
141
            }
142
            if(responseCode == HttpURLConnection.HTTP_OK){
143
                    return result;
144
            }else{
145
                //TODO error handling    
146
            	logger.error("No Http_OK");
147
            }
148
               
149
        } catch (IOException e) {
150
                logger.error("No content for request: " + request);
151
        }
152
       
153
        // error
154
        return null;
155
    }
156

  
157
	private List<ReferenceBase> buildPublicationList( InputStream content, ICdmApplicationConfiguration appConfig) {
158
		throw new RuntimeException("Publication service not yet implemented");
159
	}
160

  
161

  
162
	private List<BotanicalName> buildNameList( InputStream content, ICdmApplicationConfiguration appConfig) throws IOException {
163
		List<BotanicalName> result = new ArrayList<BotanicalName>(); 
164
		BufferedReader reader = new BufferedReader (new InputStreamReader(content));
165
		
166
		String headerLine = reader.readLine();
167
		Map<Integer, String> parameterMap = getAuthorParameterMap(headerLine);
168
		
169
		String line = reader.readLine();
170
		while (StringUtils.isNotBlank(line)){
171
			BotanicalName name = getNameFromLine(line,parameterMap, appConfig);
172
			result.add(name);
173
			line = reader.readLine();
174
		}
175

  
176
		return result;
177
	}
178

  
179

  
180
	private BotanicalName getNameFromLine(String line, Map<Integer, String> categoryMap, ICdmApplicationConfiguration appConfig) {
181
		//Id%Version%Standard form%Default author forename%Default author surname%Taxon groups%Dates%Alternative names
182
		String[] splits = line.split("%");
183
		Map<String, String> valueMap = new HashMap<String, String>();
184
		
185
		for (int i = 0; i < splits.length; i++){
186
			valueMap.put(categoryMap.get(i), splits[i]);
187
		}
188
		
189
		BotanicalName name = BotanicalName.NewInstance(null);
190
		
191
		//caches
192
		name.setNameCache(valueMap.get(FULL_NAME_WITHOUT_FAMILY_AND_AUTHORS), true);
193
		name.setAuthorshipCache(valueMap.get(AUTHORS), true);
194
		
195
		//epithets
196
		name.setGenusOrUninomial(valueMap.get(GENUS));
197
		name.setInfraGenericEpithet(valueMap.get(INFRA_GENUS));
198
		name.setSpecificEpithet(valueMap.get(SPECIES));
199
		name.setInfraSpecificEpithet(valueMap.get(INFRA_SPECIFIC));
200
		
201
		//rank
202
		try {
203
			String rankStr = nomalizeRank(valueMap.get(RANK));
204
			name.setRank(Rank.getRankByNameOrAbbreviation(rankStr, NomenclaturalCode.ICBN, true));
205
		} catch (UnknownCdmTypeException e) {
206
			logger.warn("Rank was unknown");
207
		}
208
		
209
		//authors
210
		name.setBasionymAuthorTeam(Team.NewTitledInstance(valueMap.get(BASIONYM_AUTHOR), valueMap.get(BASIONYM_AUTHOR)));
211
		name.setCombinationAuthorTeam(Team.NewTitledInstance(valueMap.get(PUBLISHING_AUTHOR), valueMap.get(PUBLISHING_AUTHOR)));
212
		
213
		//publication
214
		ReferenceBase ref = ReferenceFactory.newGeneric();
215
		ref.setTitleCache(valueMap.get(PUBLICATION));
216
		TimePeriod datePublished = TimePeriod.parseString(valueMap.get(PUBLICATION_YEAR_FULL));
217
		name.setNomenclaturalReference(ref);
218
		
219
		//name status
220
		NomenclaturalStatusType statusType = null;
221
		String statusString = valueMap.get(NAME_STATUS);
222
		if (StringUtils.isNotBlank(statusString)){
223
			try {
224
				statusType = NomenclaturalStatusType.getNomenclaturalStatusTypeByAbbreviation(statusString);
225
				NomenclaturalStatus nomStatus = NomenclaturalStatus.NewInstance(statusType);
226
				name.addStatus(nomStatus);
227
			} catch (UnknownCdmTypeException e) {
228
				logger.warn("Name status not recognized: " + statusString);
229
			}
230
		}
231
		
232
		//remarks
233
		String remarks = valueMap.get(REMARKS);
234
		Annotation annotation = Annotation.NewInstance(remarks, AnnotationType.EDITORIAL(), Language.ENGLISH());
235
		name.addAnnotation(annotation);
236
		
237
		//basionym
238
		BotanicalName basionym = BotanicalName.NewInstance(null);
239
		basionym.setTitleCache(valueMap.get(BASIONYM), true);
240
		name.addBasionym(basionym);
241
		
242
		//basionym
243
		BotanicalName replacedSynoynm = BotanicalName.NewInstance(null);
244
		replacedSynoynm.setTitleCache(valueMap.get(REPLACED_SYNONYM), true);
245
		name.addReplacedSynonym(replacedSynoynm, null, null, null);
246

  
247
		
248
		//source
249
		ReferenceBase citation = getIpniCitation(appConfig);
250
		name.addSource(valueMap.get(ID), "Name", citation, valueMap.get(VERSION));
251
		
252
		
253
//		//TODO Family, Infra family, Hybrid genus, Hybrid, Collation, Nomenclatural synonym, Distribution, Citation type
254

  
255
		
256
		return name;
257
	}
258

  
259

  
260
	private String nomalizeRank(String string) {
261
		String result = string.replace("spec.", "sp.");
262
		return result;
263
	}
264

  
265

  
266
	private List<Person> buildAuthorList(InputStream content, ICdmApplicationConfiguration appConfig) throws IOException {
267
		List<Person> result = new ArrayList<Person>(); 
268
		BufferedReader reader = new BufferedReader (new InputStreamReader(content));
269
		
270
		String headerLine = reader.readLine();
271
		Map<Integer, String> parameterMap = getAuthorParameterMap(headerLine);
272
		
273
		String line = reader.readLine();
274
		while (StringUtils.isNotBlank(line)){
275
			Person author = getAuthorFromLine(line,parameterMap, appConfig);
276
			result.add(author);
277
			line = reader.readLine();
278
		}
279

  
280
		return result;
281
	}
282

  
283

  
284

  
285
	private Map<Integer, String> getAuthorParameterMap(String headerLine) {
286
		Map<Integer, String> result = new HashMap<Integer, String>();
287
		String[] splits = headerLine.split("%");
288
		for (int i = 0; i < splits.length ; i ++){
289
			result.put(i, splits[i]);
290
		}
291
		return result;
292
	}
293

  
294

  
295
	private Person getAuthorFromLine(String line, Map<Integer, String> categoryMap, ICdmApplicationConfiguration appConfig) {
296
		//Id%Version%Standard form%Default author forename%Default author surname%Taxon groups%Dates%Alternative names
297
		String[] splits = line.split("%");
298
		Map<String, String> valueMap = new HashMap<String, String>();
299
		
300
		for (int i = 0; i < splits.length; i++){
301
			valueMap.put(categoryMap.get(i), splits[i]);
302
		}
303
		
304
		Person person = Person.NewInstance();
305
		
306
		person.setNomenclaturalTitle(valueMap.get(STANDARD_FORM));
307
		person.setFirstname(valueMap.get(DEFAULT_AUTHOR_FORENAME));
308
		person.setLastname(valueMap.get(DEFAULT_AUTHOR_SURNAME));
309
		
310
		ReferenceBase citation = getIpniCitation(appConfig);
311
		
312
		//id, version
313
		person.addSource(valueMap.get(ID), "Author", citation, valueMap.get(VERSION));
314
		
315
		//dates
316
		TimePeriod lifespan = TimePeriod.parseString(valueMap.get(DATES));
317
		person.setLifespan(lifespan);
318
		
319
		//alternative_names
320
		String alternativeNames = valueMap.get(ALTERNATIVE_NAMES);
321
		if (StringUtils.isNotBlank(alternativeNames)){
322
			String[] alternativeNameSplits = alternativeNames.split("%");
323
			for (String alternativeName : alternativeNameSplits){
324
				if (alternativeName.startsWith(">")){
325
					alternativeName = alternativeName.substring(1);
326
				}
327
				Extension.NewInstance(person, alternativeName, ExtensionType.INFORMAL_CATEGORY());
328
			}
329
		}
330
		
331
		//TODO taxonGroups
332
		
333
		return person;
334
	}
335

  
336
	
337
	private ReferenceBase getIpniCitation(ICdmApplicationConfiguration appConfig) {
338
		ReferenceBase ipniReference;
339
		if (appConfig != null){
340
			ipniReference = appConfig.getReferenceService().find(uuidIpni);
341
			if (ipniReference == null){
342
				ipniReference = getNewIpniReference();
343
				ipniReference.setUuid(uuidIpni);
344
				appConfig.getReferenceService().save(ipniReference);
345
			}
346
		}else{
347
			ipniReference = getNewIpniReference();
348
		}
349
		return ipniReference;
350
	}
351

  
352
	/**
353
	 * @return
354
	 */
355
	private ReferenceBase getNewIpniReference() {
356
		ReferenceBase ipniReference;
357
		ipniReference = ReferenceFactory.newDatabase();
358
		ipniReference.setTitleCache("The International Plant Names Index (IPNI)");
359
		return ipniReference;
360
	}
361

  
362

  
363
	/**
364
	 * @param parameter
365
	 */
366
	private String normalizeParameter(String parameter) {
367
		String result = CdmUtils.Nz(parameter).replace(" ", "+");
368
		return result;
369
	}
370

  
371
	/**
372
	 *
373
	 * @param restRequest
374
	 * @return
375
	 * @throws MalformedURLException 
376
	 */
377
	public List<BotanicalName> getNamesAdvanced(String family, String genus, String species, String infraFamily, 
378
			String infraGenus, String infraSpecies, String authorAbbrev, Boolean includePublicationAuthors, 
379
			Boolean includeBasionymAuthors,
380
			String publicationTitle,
381
			Boolean isAPNIRecord, 
382
			Boolean isGCIRecord, 
383
			Boolean isIKRecord,
384
			Rank rankToReturn,
385
			Boolean sortByFamily,
386
			DelimitedFormat format , 
387
			ICdmApplicationConfiguration appConfig) {
388
		
389
//		find_rankToReturn=all&output_format=normal&find_sortByFamily=on&find_sortByFamily=off&query_type=by_query&back_page=plantsearch
390
			
391
		family = normalizeParameter(family);
392
		genus = normalizeParameter(genus);
393
		species = normalizeParameter(species);
394
		infraFamily = normalizeParameter(infraFamily);
395
		infraGenus = normalizeParameter(infraGenus);
396
		infraSpecies = normalizeParameter(infraSpecies);
397
		authorAbbrev = normalizeParameter(authorAbbrev);
398

  
399
		publicationTitle = normalizeParameter(publicationTitle);
400
		
401
		format = format == null ? getDefaultFormat() : format;
402
		
403
		String request = 
404
				"find_family=" + family + 
405
				"&find_genus=" + genus + 
406
				"&find_species=" + species + 
407
				"&find_infrafamily=" + infraFamily +
408
				"&find_infragenus=" + infraGenus +
409
				"&find_infraspecies=" + infraSpecies +
410
				"&find_authorAbbrev=" + authorAbbrev +
411
				getBooleanParameter("&find_includePublicationAuthors=", includePublicationAuthors, "on", "off") +
412
				getBooleanParameter("&find_includeBasionymAuthors=", includePublicationAuthors, "on", "off") +
413
				getBooleanParameter("&find_find_isAPNIRecord=", includePublicationAuthors, "on", "false") +
414
				getBooleanParameter("&find_isGCIRecord=", includePublicationAuthors, "on", "false") +
415
				getBooleanParameter("&find_isIKRecord=", includePublicationAuthors, "on", "false") +
416
				
417
				
418
				"&find_publicationTitle=" + publicationTitle +
419
				"&output_format=" + format.parameter;
420
		
421
		return (List)queryService(request, appConfig, getServiceUrl(IIpniService.ADVANCED_NAME_SERVICE_URL), ServiceType.NAME);
422

  
423
			
424
	}
425

  
426
	
427
	private String getBooleanParameter(String urlParamString, Boolean booleanParameter, String trueString, String falseString) {
428
		String result;
429
		if (booleanParameter == null){
430
			result = getBooleanParameter(urlParamString, true, trueString, falseString) + getBooleanParameter(urlParamString, false, trueString, falseString); 
431
		}else if (booleanParameter == true){
432
			result = urlParamString + trueString;
433
		}else {
434
			result = urlParamString + falseString;
435
		}
436
		return result;
437
	}
438

  
439

  
440
	/**
441
	 *
442
	 * @param restRequest
443
	 * @return
444
	 */
445
	public List<BotanicalName> getNamesSimple(String wholeName, DelimitedFormat format , ICdmApplicationConfiguration appConfig){
446
		
447
		
448
//		query_type=by_query&back_page=query_ipni.html
449
		
450
		wholeName = normalizeParameter(wholeName);
451
		
452
		format = format == null ? getDefaultFormat() : format;
453
			
454
		String request = "find_wholeName=" + wholeName + 
455
						"&output_format=" + format.parameter;
456
		
457
		return (List)queryService(request, appConfig, getServiceUrl(IIpniService.SIMPLE_NAME_SERVICE_URL), ServiceType.NAME);
458
	}
459

  
460
	/**
461
	 *
462
	 * @param restRequest
463
	 * @return
464
	 */
465
	public List<ReferenceBase> getPublications(String wholeName, DelimitedFormat format , ICdmApplicationConfiguration appConfig){
466
		wholeName = normalizeParameter(wholeName);
467
		
468
		format = format == null ? getDefaultFormat() : format;
469
			
470
		String request = "find_wholeName=" + wholeName + 
471
						"&output_format=" + format.parameter;
472
		
473
		return (List)queryService(request, appConfig, getServiceUrl(IIpniService.PUBLICATION_SERVICE_URL), ServiceType.PUBLICATION);
474
	}
475

  
476
	
477
	
478
	/**
479
	 * @return
480
	 */
481
	private DelimitedFormat getDefaultFormat() {
482
		return DelimitedFormat.SHORT;
483
	}
484

  
485
	
486
	/**
487
	 * The service url
488
	 *
489
	 * @return the serviceUrl
490
	 */
491
	public URL getServiceUrl(String url) {
492
		URL serviceUrl;
493
		try {
494
			serviceUrl = new URL(url);
495
		} catch (MalformedURLException e) {
496
			throw new RuntimeException("This should not happen", e);
497
		}
498
		return serviceUrl;
499
	}
500

  
501
		
502
	
503
}
cdmlib-ext/src/main/java/eu/etaxonomy/cdm/ext/bci/BciService.java
1
// $Id$
2
/**
3
* Copyright (C) 2009 EDIT
4
* European Distributed Institute of Taxonomy 
5
* http://www.e-taxonomy.eu
6
* 
7
* The contents of this file are subject to the Mozilla Public License Version 1.1
8
* See LICENSE.TXT at the top of this package for the full license terms.
9
*/
10
package eu.etaxonomy.cdm.ext.bci;
11

  
12
import java.io.BufferedReader;
13
import java.io.IOException;
14
import java.io.InputStream;
15
import java.io.InputStreamReader;
16
import java.net.HttpURLConnection;
17
import java.net.MalformedURLException;
18
import java.net.URL;
19
import java.util.ArrayList;
20
import java.util.HashMap;
21
import java.util.List;
22
import java.util.Map;
23

  
24
import org.apache.commons.lang.StringUtils;
25
import org.apache.log4j.Logger;
26
import org.springframework.stereotype.Component;
27

  
28
import com.ibm.lsid.MalformedLSIDException;
29

  
30
import eu.etaxonomy.cdm.api.application.ICdmApplicationConfiguration;
31
import eu.etaxonomy.cdm.common.CdmUtils;
32
import eu.etaxonomy.cdm.model.agent.Person;
33
import eu.etaxonomy.cdm.model.agent.Team;
34
import eu.etaxonomy.cdm.model.common.Annotation;
35
import eu.etaxonomy.cdm.model.common.AnnotationType;
36
import eu.etaxonomy.cdm.model.common.Extension;
37
import eu.etaxonomy.cdm.model.common.ExtensionType;
38
import eu.etaxonomy.cdm.model.common.IdentifiableEntity;
39
import eu.etaxonomy.cdm.model.common.LSID;
40
import eu.etaxonomy.cdm.model.common.Language;
41
import eu.etaxonomy.cdm.model.common.TimePeriod;
42
import eu.etaxonomy.cdm.model.name.BotanicalName;
43
import eu.etaxonomy.cdm.model.name.NomenclaturalCode;
44
import eu.etaxonomy.cdm.model.name.NomenclaturalStatus;
45
import eu.etaxonomy.cdm.model.name.NomenclaturalStatusType;
46
import eu.etaxonomy.cdm.model.name.Rank;
47
import eu.etaxonomy.cdm.model.occurrence.Collection;
48
import eu.etaxonomy.cdm.model.reference.ReferenceBase;
49
import eu.etaxonomy.cdm.model.reference.ReferenceFactory;
50
import eu.etaxonomy.cdm.strategy.exceptions.UnknownCdmTypeException;
51

  
52

  
53
/**
54
* This service allows to query the Biodiversity collection index {@link http://www.biodiversitycollectionsindex.org}
55
* @author a.mueller
56
* @created Aug 16, 2010
57
* @version 1.0
58
 *
59
 */
60
@Component
61
public class BciService implements IBciService{
62
	private static final Logger logger = Logger.getLogger(BciService.class);
63
	
64
	 private enum ServiceType{
65
		 AUTHOR,
66
		 NAME,
67
		 PUBLICATION,
68
	 }
69
		
70
	 
71
//	private URL serviceUrl;
72
	 
73
// ******************************** CONSTRUCTOR **************************************
74
	   
75
	   
76
//	/**
77
//	 * Creates new instance of this factory and connects it to the given
78
//	 * CDM Community Stores access point.
79
//	 *
80
//	 * Typically, there is no need to instantiate this class.
81
//	 */
82
//	protected IpniService(URL webserviceUrl){
83
//		this.serviceUrl = webserviceUrl;
84
//	}
85

  
86
// ****************************** METHODS ****************************************************/	
87
	
88
	/**
89
	 *
90
	 * @param restRequest
91
	 * @return
92
	 */
93
	public List<Collection> getCollectionsByCode(String code, ICdmApplicationConfiguration appConfig){
94
		code = normalizeParameter(code);
95
		String request = code;
96
		
97
		return (List)queryService(request, appConfig, getServiceUrl(IBciService.LOOKUP_CODE_REST), ServiceType.AUTHOR);
98
	}
99
	       
100

  
101
	/**
102
	 *
103
	 * @param restRequest
104
	 * @return
105
	*/
106
	private List<? extends IdentifiableEntity> queryService(String request, ICdmApplicationConfiguration appConfig, URL serviceUrl, ServiceType serviceType){
107
		try {
108
            // create the request url
109
            URL newUrl = new URL(serviceUrl.getProtocol(),
110
                                                     serviceUrl.getHost(),
111
                                                     serviceUrl.getPort(),
112
                                                     serviceUrl.getPath() 
113
                                                     + "" + request);
114
            // open a connection
115
            HttpURLConnection connection = (HttpURLConnection) newUrl.openConnection();
116
            // set the accept property to XML so we can use jdom to handle the content
117
            //connection.setRequestProperty("Accept", "text/xml");
118
   
119
           
120
            logger.info("Firing request for URL: " + newUrl);
121
                   
122
            int responseCode = connection.getResponseCode();
123
           
124
            // get the content at the resource
125
            InputStream content = (InputStream) connection.getContent();
126
           
127
            // build the result
128
            List<? extends IdentifiableEntity> result;
129
            if (serviceType.equals(ServiceType.AUTHOR)){
130
            	result = buildCollectionList(content, appConfig);
131
            }else if (serviceType.equals(ServiceType.NAME)){
132
            	//
133
            	result = null;
134
            }else{
135
            	//
136
            	result = null;
137
            }
138
            if(responseCode == HttpURLConnection.HTTP_OK){
139
                    return result;
140
            }else if(responseCode == HttpURLConnection.HTTP_MULT_CHOICE){
141
                    return result;
142
            }else{
143
                //TODO error handling    
144
            	logger.error("No Http_OK");
145
            }
146
               
147
        } catch (IOException e) {
148
                logger.error("No content for request: " + request);
149
        }
150
       
151
        // error
152
        return null;
153
    }
154

  
155

  
156
	private List<Collection> buildCollectionList(InputStream content, ICdmApplicationConfiguration appConfig) throws IOException {
157
		List<Collection> result = new ArrayList<Collection>(); 
158
		BufferedReader reader = new BufferedReader (new InputStreamReader(content));
159
		
160
		String headerLine = reader.readLine();
161
		
162
		String line = reader.readLine();
163
		while (StringUtils.isNotBlank(line)){
164
			Collection collection = getCollectionFromLine(line, appConfig);
165
			result.add(collection);
166
			line = reader.readLine();
167
		}
168

  
169
		return result;
170
	}
171

  
172

  
173
	private Collection getCollectionFromLine(String line, ICdmApplicationConfiguration appConfig) {
174
		//urn:lsid:biocol.org:col:15727	http://biocol.org/urn:lsid:biocol.org:col:15727	University of Bergen Herbarium
175
		String[] splits = line.split("\t");  
176
		if (splits.length != 3){
177
			logger.warn("Unknwon BCI line format: " + line);
178
			return null;
179
		}
180
		String lsidString = splits[0]; 
181
		String urlString = splits[1]; 
182
		String collectionName = splits[2];
183
		
184
		Collection result = Collection.NewInstance();
185
		
186
		//LSID
187
		LSID lsid = null;
188
		try {
189
			lsid = new LSID(lsidString);
190
		} catch (MalformedLSIDException e) {
191
			logger.warn("Malformed LSID " + lsidString, e);
192
		}
193

  
194
		result.setLsid(lsid);
195
		String id = getCollectionId(lsid);
196
		
197
		result.setName(collectionName);
198
		
199
		//id, citation
200
		ReferenceBase citation = getBciCitation(appConfig);
201
		result.addSource(id, null, citation, null);
202
		
203
		
204
		return result;
205
	}
206

  
207
	
208
	private String getCollectionId(LSID lsid) {
209
		String result = lsid == null? null : lsid.getObject();
210
		return result;
211
	}
212

  
213

  
214
	private ReferenceBase getBciCitation(ICdmApplicationConfiguration appConfig) {
215
		ReferenceBase bciReference;
216
		if (appConfig != null){
217
			bciReference = appConfig.getReferenceService().find(uuidBci);
218
			if (bciReference == null){
219
				bciReference = getNewBciReference();
220
				bciReference.setUuid(uuidBci);
221
				appConfig.getReferenceService().save(bciReference);
222
			}
223
		}else{
224
			bciReference = getNewBciReference();
225
		}
226
		return bciReference;
227
	}
228

  
229
	/**
230
	 * @return
231
	 */
232
	private ReferenceBase getNewBciReference() {
233
		ReferenceBase bciReference;
234
		bciReference = ReferenceFactory.newDatabase();
235
		bciReference.setTitleCache("Biodiversity Collection Index (BCI))");
236
		return bciReference;
237
	}
238

  
239

  
240
	/**
241
	 * @param parameter
242
	 */
243
	private String normalizeParameter(String parameter) {
244
		String result = CdmUtils.Nz(parameter).replace(" ", "+");
245
		return result;
246
	}
247

  
248
	
249
	
250
	/**
251
	 * The service url
252
	 *
253
	 * @return the serviceUrl
254
	 */
255
	public URL getServiceUrl(String url) {
256
		URL serviceUrl;
257
		try {
258
			serviceUrl = new URL(url);
259
		} catch (MalformedURLException e) {
260
			throw new RuntimeException("This should not happen", e);
261
		}
262
		return serviceUrl;
263
	}
264

  
265
		
266
	
267
}
cdmlib-ext/src/main/java/eu/etaxonomy/cdm/ext/bci/IBciService.java
1
// $Id$
2
/**
3
* Copyright (C) 2009 EDIT
4
* European Distributed Institute of Taxonomy 
5
* http://www.e-taxonomy.eu
6
* 
7
* The contents of this file are subject to the Mozilla Public License Version 1.1
8
* See LICENSE.TXT at the top of this package for the full license terms.
9
*/
10
package eu.etaxonomy.cdm.ext.bci;
11

  
12
import java.net.URL;
13
import java.util.List;
14
import java.util.UUID;
15

  
16
import eu.etaxonomy.cdm.api.application.ICdmApplicationConfiguration;
17
import eu.etaxonomy.cdm.model.occurrence.Collection;
18

  
19

  
20
/**
21
* Interface for queying the Biodiversity Collection Index  via webservices ({@link http://www.biodiversitycollectionsindex.org}). 
22
* @author a.mueller
23
* @created Aug 18, 2010
24
* @version 1.0
25
 */
26
public interface IBciService {
27

  
28

  
29
	/**
30
	 * UUID for the reference representing the IPNI database:<BR/>
31
	 * 8b6d750f-c7e0-4180-afbf-aa4c50148813
32
	 */
33
	public static final UUID uuidBci = UUID.fromString("34aa4989-eb5e-4eef-9c9b-080f055ac15c");
34

  
35
	public static final String LOOKUP_CODE_REST = "http://www.biocol.org/rest/lookup/code/";
36

  
37
	
38
	/**
39
	 * Returns a list of collections collection code.
40
	 *  
41
	 * @param code
42
	 * @param appConfig
43
	 * @return
44
	 */
45
	public List<Collection> getCollectionsByCode(String code, ICdmApplicationConfiguration appConfig);
46
	
47
	public URL getServiceUrl(String url);
48

  
49
}
cdmlib-ext/src/main/java/eu/etaxonomy/cdm/ext/ipni/IIpniService.java
1
// $Id$
2
/**
3
* Copyright (C) 2009 EDIT
4
* European Distributed Institute of Taxonomy 
5
* http://www.e-taxonomy.eu
6
* 
7
* The contents of this file are subject to the Mozilla Public License Version 1.1
8
* See LICENSE.TXT at the top of this package for the full license terms.
9
*/
10
package eu.etaxonomy.cdm.ext.ipni;
11

  
12
import java.net.URL;
13
import java.util.List;
14
import java.util.UUID;
15

  
16
import eu.etaxonomy.cdm.api.application.ICdmApplicationConfiguration;
17
import eu.etaxonomy.cdm.ext.ipni.IpniService.IpniRank;
18
import eu.etaxonomy.cdm.model.agent.Person;
19
import eu.etaxonomy.cdm.model.common.ExtensionType;
20
import eu.etaxonomy.cdm.model.common.IdentifiableSource;
21
import eu.etaxonomy.cdm.model.name.BotanicalName;
22
import eu.etaxonomy.cdm.model.name.Rank;
23
import eu.etaxonomy.cdm.model.reference.ReferenceBase;
24

  
25

  
26
/**
27
* Interface for queying IPNI via webservice ({@link http://www.uk.ipni.org/}). 
28
* Services are available for the plant name index, the autor index and the publication index.
29
* @author a.mueller
30
* @created Aug 16, 2010
31
* @version 1.0
32
 */
33
public interface IIpniService {
34

  
35

  
36
	
37
	/**
38
	 * UUID for the reference representing the IPNI database:<BR/>
39
	 * 8b6d750f-c7e0-4180-afbf-aa4c50148813
40
	 */
41
	public static final UUID uuidIpni = UUID.fromString("8b6d750f-c7e0-4180-afbf-aa4c50148813");
42

  
43
	/**
44
	 * UUID for the extension type 'Alternative name':<BR/>
45
	 * eee99927-1f9f-4df2-9d8f-11746bf35c0c
46
	 */
47
	public static final UUID uuidAlternativeNames = UUID.fromString("eee99927-1f9f-4df2-9d8f-11746bf35c0c");
48
	
49

  
50
	public static final String AUTHOR_SERVICE_URL = "http://www.ipni.org/ipni/advAuthorSearch.do";
51
	public static final String SIMPLE_NAME_SERVICE_URL = "http://www.uk.ipni.org/ipni/simplePlantNameSearch.do";
52
	public static final String ADVANCED_NAME_SERVICE_URL = "http://www.uk.ipni.org/ipni/advPlantNameSearch.do";
53
	public static final String PUBLICATION_SERVICE_URL = "http://www.uk.ipni.org/ipni/advPublicationSearch.do";
54
	
55
	
56
	 /**
57
	 * Enumeration of the four return delimited data formats provided by IPNI.<BR/>
58
	 * @see http://www.ipni.org/ipni/delimited_help.html
59
	 * @author a.mueller
60
	 */
61
	public enum DelimitedFormat{
62
		/** IPNI classic delimited format */
63
		 CLASSIC ("delimited-classic"),
64
		 /** IPNI minimal delimited format */
65
		 MINIMAL ("delimited-minimal"),
66
		 /** IPNI short delimited format */
67
		 SHORT ("delimited-short"),
68
		 /** IPNI extended delimited format */
69
		 EXTENDED ("delimited-extended");
70
		 
71
		 String parameter;
72
		 DelimitedFormat(String parameter){
73
			this.parameter = parameter; 
74
		 }
75
	 }
76
	
77
	/**
78
	 * Returns a list of persons (authors) defined by their abbreviation, surname, forename and/or isoCountry.
79
	 * The amount of data added to each person depends on the format and the database connection (appConfig).
80
	 * <BR/><BR/>
81
	 * The {@link DelimitedFormat#MINIMAL minimal}  and {@link DelimitedFormat#SHORT short} format returns the 
82
	 * <i>standard form</i> as the nomenclatural title, the <i>default author forename</i> as the firstname and
83
	 * the <i>default author surname</i> as the lastname of the returned {@link Person person} object. 
84
	 * The <i>id</i> and the <i>version</i> are added as {@link IdentifiableSource source} where the id is the id,
85
	 * the namespace is "Author" and the microcitation is the <i>version</i>. If an a database connection is passed
86
	 * (appConig is not <code>null</null>) the database is searched for an existing citation representing the IPNI
87
	 *  webservice. If not exists a new such reference with the given {@link #uuidIpni ipni uuid} is created and stored
88
	 *  in the database.<BR/>
89
	 *  If no database connection is passed a new reference is created each time with a random UUID to avoid duplicate
90
	 *  key problems when trying to save the returned objects.
91
	 *  <BR/><BR/>
92
	 * The {@link DelimitedFormat#EXTENDED minimal} format returns the same object as the {@link DelimitedFormat#SHORT short} format 
93
	 * but additionally the <i>date</i> is evaluated as lifespan.
94
	 * Also an extension of type
95
	 * {@link ExtensionType.INFORMAL_CATEGORY} is added for each semicolon separated part of the 'Alternative names' result.
96
	 * TODO make alternative name or alternative title an own ExtensionType
97
	 * <BR/><BR/>
98
	 * The {@link DelimitedFormat#CLASSIC classic} format at the moment returns the same object as the {@link DelimitedFormat#EXTENDED extended} format 
99
	 * as the remaining parameters are not yet implemented.
100
	 *  
101
	 * @param abbreviation
102
	 * @param surname
103
	 * @param forename
104
	 * @param isoCountry
105
	 * @param format 
106
	 * @param appConfig
107
	 * @return
108
	 */
109
	public List<Person> getAuthors(String abbreviation, String surname, String forename, String isoCountry, ICdmApplicationConfiguration appConfig, IpniServiceAuthorConfigurator config);
110

  
111

  
112
	/**
113
	 * Returns a list of names matching the wholeName parameter according to the IPNI Quick search function.
114
	 * See {@link http://www.uk.ipni.org/sample_searches.html#name_quick} for further explanation about the IPNI Quick search.
115
	 * <BR/><BR/>
116
	 * The format parameter defines the depth of the data returned. See {@link http://www.ipni.org/ipni/delimited_help.html} for further
117
	 * information on the supported data formats.
118
	 * <BR/>
119
	 * Please be aware that not all data returned by IPNI are transformed into CDM data as some of the data types are not available in the
120
	 * CDM and some types are just not yet implemented.
121
	 *  
122
	 * @param wholeName
123
	 * @param format
124
	 * @param appConfig
125
	 * @return
126
	 */
127
	public List<BotanicalName> getNamesSimple(String wholeName, ICdmApplicationConfiguration services, IpniServiceNamesConfigurator config);
128

  
129
	
130
	/**
131
	 * Returns a list of names matching the relevant parameters according to the IPNI full search function.
132
	 * See {http://www.uk.ipni.org/sample_searches.html#name_full} for further explanation about the IPNI Full search.
133
	 * <BR/><BR/>
134
	 * The format parameter defines the depth of the data returned. See {@link http://www.ipni.org/ipni/delimited_help.html} for further
135
	 * information on the supported data formats.
136
	 * <BR/>
137
	 * Please be aware that not all data returned by IPNI are transformed into CDM data as some of the data types are not available in the
138
	 * CDM and some types are just not yet implemented.
139
	 *  
140
	 * @param family
141
	 * @param genus
142
	 * @param species
143
	 * @param infraFamily
144
	 * @param infraGenus
145
	 * @param infraSpecies
146
	 * @param authorAbbrev
147
	 * @param includePublicationAuthors
148
	 * @param includeBasionymAuthors
149
	 * @param publicationTitle
150
	 * @param isAPNIRecord
151
	 * @param isGCIRecord
152
	 * @param isIKRecord
153
	 * @param rankToReturn
154
	 * @param sortByFamily
155
	 * @param format
156
	 * @param appConfig
157
	 * @return List of botanical names returned by the IPNI web service.
158
	 */
159
	public List<BotanicalName> getNamesAdvanced(String family, String genus, String species, String infraFamily, 
160
			String infraGenus, String infraSpecies, String authorAbbrev, Boolean includePublicationAuthors, 
161
			Boolean includeBasionymAuthors,
162
			String publicationTitle,
163
			Boolean isAPNIRecord, 
164
			Boolean isGCIRecord, 
165
			Boolean isIKRecord,
166
			IpniRank ipniRankToReturn,
167
			Boolean sortByFamily,
168
			IpniServiceNamesConfigurator config,
169
			ICdmApplicationConfiguration appConfig);
170

  
171
	/**
172
	 * As {@link #getNamesAdvanced(String, String, String, String, String, String, String, Boolean, Boolean, String, Boolean, Boolean, Boolean, IpniRank, Boolean, IpniServiceNamesConfigurator, ICdmApplicationConfiguration)}
173
	 * but using CDM Rank instead of IpniRank. The CDM Rank is transformed into an IpniRank so it returns all
174
	 * names that are in the same IpniRange as the CDM rank. Therefore when using CDM rank 'variety' also a 
175
	 * 'subspecies' may be returned as 'variety' and 'subspecies' are within the same IpniRange 'Infraspecific'.  
176
	 * 
177
	 * @param family
178
	 * @param genus
179
	 * @param species
180
	 * @param infraFamily
181
	 * @param infraGenus
182
	 * @param infraSpecies
183
	 * @param authorAbbrev
184
	 * @param includePublicationAuthors
185
	 * @param includeBasionymAuthors
186
	 * @param publicationTitle
187
	 * @param isAPNIRecord
188
	 * @param isGCIRecord
189
	 * @param isIKRecord
190
	 * @param rankToReturn
191
	 * @param sortByFamily
192
	 * @param format
193
	 * @param appConfig
194
	 * @return List of botanical names returned by the IPNI web service.
195
	 */
196
	public List<BotanicalName> getNamesAdvanced(String family, String genus, String species, String infraFamily, 
197
			String infraGenus, String infraSpecies, String authorAbbrev, Boolean includePublicationAuthors, 
198
			Boolean includeBasionymAuthors,
199
			String publicationTitle,
200
			Boolean isAPNIRecord, 
201
			Boolean isGCIRecord, 
202
			Boolean isIKRecord,
203
			Rank rankRangeToReturn,
204
			Boolean sortByFamily,
205
			IpniServiceNamesConfigurator config,
206
			ICdmApplicationConfiguration appConfig);
207
	
208
	/**
209
	 * Returns a list of publications matching the title and/or the abbreviation parameter according to the IPNI Publication search function.
210
	 * See {@link http://www.uk.ipni.org/sample_searches.html#publication_examples} for further explanation about the IPNI Publication search.
211
	 * <BR/><BR/>
212
	  * Please be aware that not all data returned by IPNI are transformed into CDM data as some of the data types are not available in the
213
	 * CDM and some types are just not yet implemented.
214
	 *  
215
	 * @param title
216
	 * @param abbreviation
217
	 * @param appConfig
218
	 * @return
219
	 */
220
	public List<ReferenceBase> getPublications(String title, String abbreviation, ICdmApplicationConfiguration appConfig, IpniServicePublicationConfigurator config);
221

  
222
	public URL getServiceUrl(String url);
223
}
cdmlib-ext/src/main/java/eu/etaxonomy/cdm/ext/ipni/IIpniServiceConfigurator.java
1
package eu.etaxonomy.cdm.ext.ipni;
2

  
3
import eu.etaxonomy.cdm.ext.ipni.IIpniService.DelimitedFormat;
4

  
5
public interface IIpniServiceConfigurator {
6
	
7
	/**
8
	 * The IPNI delimited data format to use. See {@link http://www.ipni.org/ipni/delimited_help.html} for 
9
	 * further information on the delimited data format.
10
	 * <BR/><BR/>
11
	 * NOTE: Not all services support all formats.
12
	 */
13
	public DelimitedFormat getFormat();
14
	
15
	/**
16
	 * @see #getFormat()
17
	 * @param format
18
	 */
19
	public void setFormat(DelimitedFormat format);
20

  
21
}
cdmlib-ext/src/main/java/eu/etaxonomy/cdm/ext/ipni/IpniService.java
1
// $Id$
2
/**
3
* Copyright (C) 2009 EDIT
4
* European Distributed Institute of Taxonomy 
5
* http://www.e-taxonomy.eu
6
* 
7
* The contents of this file are subject to the Mozilla Public License Version 1.1
8
* See LICENSE.TXT at the top of this package for the full license terms.
9
*/
10
package eu.etaxonomy.cdm.ext.ipni;
11

  
12
import java.io.BufferedReader;
13
import java.io.IOException;
14
import java.io.InputStream;
15
import java.io.InputStreamReader;
16
import java.net.HttpURLConnection;
17
import java.net.MalformedURLException;
18
import java.net.URL;
19
import java.util.ArrayList;
20
import java.util.HashMap;
21
import java.util.List;
22
import java.util.Map;
23

  
24
import org.apache.commons.lang.StringUtils;
25
import org.apache.log4j.Logger;
26
import org.springframework.stereotype.Component;
27

  
28
import eu.etaxonomy.cdm.api.application.ICdmApplicationConfiguration;
29
import eu.etaxonomy.cdm.common.CdmUtils;
30
import eu.etaxonomy.cdm.ext.ipni.IIpniService.DelimitedFormat;
31
import eu.etaxonomy.cdm.model.agent.Person;
32
import eu.etaxonomy.cdm.model.agent.Team;
33
import eu.etaxonomy.cdm.model.common.Annotation;
34
import eu.etaxonomy.cdm.model.common.AnnotationType;
35
import eu.etaxonomy.cdm.model.common.Extension;
36
import eu.etaxonomy.cdm.model.common.ExtensionType;
37
import eu.etaxonomy.cdm.model.common.IdentifiableEntity;
38
import eu.etaxonomy.cdm.model.common.Language;
39
import eu.etaxonomy.cdm.model.common.TimePeriod;
40
import eu.etaxonomy.cdm.model.name.BotanicalName;
41
import eu.etaxonomy.cdm.model.name.NomenclaturalCode;
42
import eu.etaxonomy.cdm.model.name.NomenclaturalStatus;
43
import eu.etaxonomy.cdm.model.name.NomenclaturalStatusType;
44
import eu.etaxonomy.cdm.model.name.Rank;
45
import eu.etaxonomy.cdm.model.reference.ReferenceBase;
46
import eu.etaxonomy.cdm.model.reference.ReferenceFactory;
47
import eu.etaxonomy.cdm.strategy.exceptions.UnknownCdmTypeException;
48

  
49

  
50
/**
51
* @author a.mueller
52
* @created Aug 16, 2010
53
* @version 1.0
54
 *
55
 */
56
@Component
57
public class IpniService implements IIpniService{
58
	private static final Logger logger = Logger.getLogger(IpniService.class);
59
	
60
	// GENERAL
61
	public static String ID = "Id";
62
	public static String VERSION = "Version";
63
	public static final String REMARKS = "Remarks";
64
	
65
	//NAMES 
66
	public static final String FULL_NAME_WITHOUT_FAMILY_AND_AUTHORS = "Full name without family and authors";
67
	public static final String AUTHORS = "Authors";
68
	public static final String FAMILY = "Family";
69
	public static final String GENUS = "Genus";
70
	public static final String INFRA_GENUS = "Infra genus";
71
	public static final String SPECIES = "Species";
72
	public static final String INFRA_SPECIFIC = "Infra species";
73
	public static final String RANK = "Rank";
74
	public static final String BASIONYM_AUTHOR = "Basionym author";
75
	public static final String PUBLISHING_AUTHOR = "Publishing author";
76
	public static final String PUBLICATION = "Publication";
77
	public static final String PUBLICATION_YEAR_FULL = "Publication year full";
78
	public static final String NAME_STATUS = "Name status";
79
	public static final String BASIONYM = "Basionym";
80
	public static final String REPLACED_SYNONYM = "Replaced synonym";
81

  
82
	
83
	//AUTHORS
84
	
85
	public static final String STANDARD_FORM = "Standard Form";
86
	
87
	public static final String DEFAULT_AUTHOR_FORENAME = "Default author forename";
88
	public static final String DEFAULT_AUTHOR_SURNAME = "Default author surname";
89
	public static final String TAXON_GROUPS = "Taxon groups";
90
	public static final String DATES = "Dates";
91
	public static final String ALTERNATIVE_NAMES = "Alternative names";
92
	
93
	public static final String DEFAULT_AUTHOR_NAME = "Default author name";
94
	
95
	public static final String NAME_NOTES = "Name notes";
96
	public static final String NAME_SOURCE = "Name source";
97
	public static final String DATE_TYPE_CODE = "Date type code";
98
	public static final String DATE_TYPE_STRING = "Date type string";
99
	
100
	public static final String ALTERNATIVE_ABBREVIATIONS = "Alternative abbreviations";
101
	public static final String EXAMPLE_OF_NAME_PUBLISHED = "Example of name published";
102
	
103
	
104
	//PUBLICATIONS
105
	
106
	public static final String ABBREVIATION = "Abbreviation";
107
	public static final String TITLE = "Title";
108
	public static final String BPH_NUMBER = "BPH number";
109
	public static final String ISBN = "ISBN";
110
	public static final String ISSN = "ISSN";
111
	public static final String AUTHORS_ROLE = "Authors role";
112
	public static final String EDITION = "Edition";
113
	public static final String DATE = "Date";
114
	public static final String IN_PUBLICATION_FACADE = "In publication facade";
115
	public static final String LC_NUMBER = "LC number";
116
	public static final String PLACE = "Place";
117
	public static final String PUBLICATION_AUTHOR_TEAM = "Publication author team";
118
	public static final String PRECEDED_BY = "Preceded";
119
	public static final String TL2_AUTHOR = "TL2 author";
120
	public static final String TL2_NUMBER = "TL2 number";
121
	public static final String TDWG_ABBREVIATION = "TDWG abbreviation";
122
	
123
	private enum ServiceType{
124
		 AUTHOR,
125
		 NAME,
126
		 PUBLICATION,
127
	}
128
	
129
	public enum IpniRank{
130
		ALL ("All"),
131
		FAMILIAL ("Familial"),
132
		INFRA_FAMILIAL ("Infrafamilial"),
133
		GENERIC("Generic"),
134
		INFRA_GENERIC("Infrageneric"),
135
		SPECIFIC ("Specific"),
136
		INFRA_SPECIFIC("InfraSpecific");
137
		
138
		String strRank;
139
		IpniRank(String strRank){
140
			this.strRank = strRank;
141
		}
142
		
143
		public static IpniRank valueOf(Rank rank){
144
			if (rank == null){
145
				return ALL;
146
			}else if (rank.isInfraSpecific()){
147
				return INFRA_SPECIFIC;
148
			}else if (rank.isSpecies()){
149
				return SPECIFIC;
150
			}else if (rank.isInfraGeneric()){
151
				return INFRA_GENERIC;
152
			}else if (rank.isGenus()){
153
				return GENERIC;
154
			}else if (rank.isLower(Rank.FAMILY())){
155
				return INFRA_FAMILIAL;
156
			}else if (rank.isHigher(Rank.SUBFAMILY())){
157
				return FAMILIAL;
158
			}else{
159
				logger.warn("Rank could not be transformed to ipni rank. Use ALL instead");
160
				return ALL;
161
			}
162
		}
163
	}
164
		
165
	 
166
//	private URL serviceUrl;
167
	 
168
// ******************************** CONSTRUCTOR **************************************
169
	   
170
	   
171
//	/**
172
//	 * Creates new instance of this factory and connects it to the given
173
//	 * CDM Community Stores access point.
174
//	 *
175
//	 * Typically, there is no need to instantiate this class.
176
//	 */
177
//	protected IpniService(URL webserviceUrl){
178
//		this.serviceUrl = webserviceUrl;
179
//	}
180

  
181
// ****************************** METHODS ****************************************************/	
182
	
... This diff was truncated because it exceeds the maximum size that can be displayed.

Also available in: Unified diff