Project

General

Profile

Download (24.1 KB) Statistics
| Branch: | Revision:
1
/**
2
* Copyright (C) 2007 EDIT
3
* European Distributed Institute of Taxonomy
4
* http://www.e-taxonomy.eu
5
*
6
* The contents of this file are subject to the Mozilla Public License Version 1.1
7
* See LICENSE.TXT at the top of this package for the full license terms.
8
*/
9

    
10
package eu.etaxonomy.cdm.io.algaterra;
11

    
12
import java.net.URI;
13
import java.sql.Date;
14
import java.sql.ResultSet;
15
import java.sql.SQLException;
16
import java.util.HashMap;
17
import java.util.Map;
18
import java.util.Set;
19
import java.util.UUID;
20

    
21
import org.apache.commons.lang.StringUtils;
22
import org.apache.log4j.Logger;
23
import org.springframework.transaction.TransactionStatus;
24

    
25
import eu.etaxonomy.cdm.api.facade.DerivedUnitFacade;
26
import eu.etaxonomy.cdm.io.berlinModel.in.BerlinModelImportBase;
27
import eu.etaxonomy.cdm.io.common.ResultSetPartitioner;
28
import eu.etaxonomy.cdm.io.common.Source;
29
import eu.etaxonomy.cdm.io.common.TdwgAreaProvider;
30
import eu.etaxonomy.cdm.model.agent.Team;
31
import eu.etaxonomy.cdm.model.agent.TeamOrPersonBase;
32
import eu.etaxonomy.cdm.model.common.Annotation;
33
import eu.etaxonomy.cdm.model.common.AnnotationType;
34
import eu.etaxonomy.cdm.model.common.DefinedTerm;
35
import eu.etaxonomy.cdm.model.common.Language;
36
import eu.etaxonomy.cdm.model.common.OrderedTermVocabulary;
37
import eu.etaxonomy.cdm.model.common.TermType;
38
import eu.etaxonomy.cdm.model.common.TermVocabulary;
39
import eu.etaxonomy.cdm.model.common.TimePeriod;
40
import eu.etaxonomy.cdm.model.description.DescriptionBase;
41
import eu.etaxonomy.cdm.model.description.Feature;
42
import eu.etaxonomy.cdm.model.description.SpecimenDescription;
43
import eu.etaxonomy.cdm.model.description.State;
44
import eu.etaxonomy.cdm.model.description.TaxonDescription;
45
import eu.etaxonomy.cdm.model.location.Country;
46
import eu.etaxonomy.cdm.model.location.NamedArea;
47
import eu.etaxonomy.cdm.model.location.Point;
48
import eu.etaxonomy.cdm.model.location.ReferenceSystem;
49
import eu.etaxonomy.cdm.model.occurrence.Collection;
50
import eu.etaxonomy.cdm.model.occurrence.SpecimenOrObservationType;
51
import eu.etaxonomy.cdm.model.reference.Reference;
52
import eu.etaxonomy.cdm.model.taxon.Taxon;
53

    
54
/**
55
 * @author a.mueller
56
 * @created 12.09.2012
57
 */
58
public abstract class AlgaTerraSpecimenImportBase extends BerlinModelImportBase{
59
    private static final long serialVersionUID = -1741703900571072861L;
60

    
61
    private static final Logger logger = Logger.getLogger(AlgaTerraSpecimenImportBase.class);
62

    
63
	public static final String ECO_FACT_FIELD_OBSERVATION_NAMESPACE = "EcoFact_FieldObservation";
64
	public static final String ECO_FACT_DERIVED_UNIT_NAMESPACE = "EcoFact_DerivedUnit";
65
	public static final String TYPE_SPECIMEN_FIELD_OBSERVATION_NAMESPACE = "TypeSpecimen_FieldObservation";
66
	public static final String TYPE_SPECIMEN_DERIVED_UNIT_NAMESPACE = "TypeSpecimen_DerivedUnit";
67
	public static final String FACT_ECOLOGY_NAMESPACE = "Fact (Ecology)";
68

    
69

    
70
	public static final String TERMS_NAMESPACE = "ALGA_TERRA_TERMS";
71

    
72
	//TODO move to transformrer
73
	final static UUID uuidMarkerAlkalinity = UUID.fromString("e52d0ea2-0c1f-4d95-ae6d-e21ab317c594");
74
	final static UUID uuidRefSystemGps = UUID.fromString("c23e4928-c137-4e4a-b6ab-b430da3d0b94");
75
	public final static UUID uuidFeatureSpecimenCommunity = UUID.fromString("3ff5b1ab-3999-4b5a-b8f7-01fd2f6c12c7");
76
	public final static UUID uuidFeatureAdditionalData = UUID.fromString("0ac82ab8-2c2b-4953-98eb-a9f718eb9c57");
77
	public final static UUID uuidFeatureHabitatExplanation = UUID.fromString("6fe32295-61a3-44fc-9fcf-a85790ea888f");
78

    
79
	final static UUID uuidVocAlgaTerraClimate = UUID.fromString("b0a677c6-8bb6-43f4-b1b8-fc377a10feb5");
80
	final static UUID uuidVocAlgaTerraHabitat = UUID.fromString("06f30114-e19c-4e7d-a8e5-5488c41fcbc5");
81
	final static UUID uuidVocAlgaTerraLifeForm = UUID.fromString("3c0b194e-809c-4b42-9498-6ff034066ed7");
82

    
83
	public final static UUID uuidFeatureAlgaTerraClimate = UUID.fromString("8754674c-9ab9-4f28-95f1-91eeee2314ee");
84
	public final static UUID uuidFeatureAlgaTerraHabitat = UUID.fromString("7def3fc2-cdc5-4739-8e13-62edbd053415");
85
	public final static UUID uuidFeatureAlgaTerraLifeForm = UUID.fromString("9b657901-1b0d-4a2a-8d21-dd8c1413e2e6");
86

    
87
	final static UUID uuidVocParameter = UUID.fromString("45888b40-5bbb-4293-aa1e-02479796cd7c");
88
	final static UUID uuidStatMeasureSingleValue = UUID.fromString("eb4c3d98-4d4b-4c37-8eb4-17315ce79920");
89
	final static UUID uuidMeasurementValueModifier = UUID.fromString("0218a7a3-f6c0-4d06-a4f8-6b50b73aef5e");
90

    
91
	final static UUID uuidModifierLowerThan = UUID.fromString("2b500085-6bef-4003-b6ea-e0ad0237d79d");
92
	final static UUID uuidModifierGreaterThan = UUID.fromString("828df49d-c745-48f7-b083-0ada43356c34");
93

    
94
	public AlgaTerraSpecimenImportBase(String tableName, String pluralString) {
95
		super(tableName, pluralString);
96
	}
97

    
98
	/**
99
	 * Creates the vocabularies and the features for Climate, Habitat and Lifeform
100
	 * @param state
101
	 * @throws SQLException
102
	 */
103
	protected void makeVocabulariesAndFeatures(AlgaTerraImportState state) throws SQLException {
104
		String abbrevLabel = null;
105
		URI uri = null;
106

    
107
		if (! state.isSpecimenVocabulariesCreated()){
108

    
109
			TransactionStatus txStatus = this.startTransaction();
110

    
111
			boolean isOrdered = true;
112
			State tmp = State.NewInstance();
113
			OrderedTermVocabulary<State> climateVoc = (OrderedTermVocabulary<State>)getVocabulary(TermType.State, uuidVocAlgaTerraClimate, "Climate", "Climate", abbrevLabel, uri, isOrdered, tmp);
114
			OrderedTermVocabulary<State> habitatVoc = (OrderedTermVocabulary<State>)getVocabulary(TermType.State, uuidVocAlgaTerraHabitat, "Habitat", "Habitat", abbrevLabel, uri, isOrdered, tmp);
115
			OrderedTermVocabulary<State> lifeformVoc = (OrderedTermVocabulary<State>)getVocabulary(TermType.State, uuidVocAlgaTerraLifeForm, "Lifeform", "Lifeform", abbrevLabel, uri, isOrdered, tmp);
116

    
117
			Feature feature = getFeature(state, uuidFeatureAlgaTerraClimate, "Climate","Climate", null, null);
118
			feature.setSupportsCategoricalData(true);
119

    
120
			feature = getFeature(state, uuidFeatureAlgaTerraLifeForm, "LifeForm","LifeForm", null, null);
121
			feature.setSupportsCategoricalData(true);
122

    
123
			feature = Feature.HABITAT();
124
			feature.setSupportsCategoricalData(true);
125
			getTermService().saveOrUpdate(feature);
126

    
127
			Source source = state.getAlgaTerraConfigurator().getSource();
128

    
129
			String climateSql = "SELECT * FROM EcoClimate";
130
			ResultSet rs = source.getResultSet(climateSql);
131
			while (rs.next()){
132
				String climate = rs.getString("Climate");
133
				String description = rs.getString("Description");
134
				Integer id = rs.getInt("ClimateId");
135
				UUID uuid = UUID.fromString(rs.getString("UUID"));
136
				State stateTerm = getStateTerm(state, uuid, climate, description, null, climateVoc);
137
				addOriginalSource(stateTerm, id.toString(), "EcoClimate", state.getTransactionalSourceReference());
138
				getTermService().saveOrUpdate(stateTerm);
139
			}
140

    
141
			String habitatSql = "SELECT * FROM EcoHabitat";
142
			rs = source.getResultSet(habitatSql);
143
			while (rs.next()){
144
				String habitat = rs.getString("Habitat");
145
				String description = rs.getString("Description");
146
				Integer id = rs.getInt("HabitatId");
147
				UUID uuid = UUID.fromString(rs.getString("UUID"));
148
				State stateTerm = getStateTerm(state, uuid, habitat, description, null, habitatVoc);
149
				addOriginalSource(stateTerm, id.toString(), "EcoHabitat", state.getTransactionalSourceReference());
150
				getTermService().saveOrUpdate(stateTerm);
151
			}
152

    
153
			String lifeformSql = "SELECT * FROM EcoLifeForm";
154
			rs = source.getResultSet(lifeformSql);
155
			while (rs.next()){
156
				String lifeform = rs.getString("LifeForm");
157
				String description = rs.getString("Description");
158
				Integer id = rs.getInt("LifeFormId");
159
				UUID uuid = UUID.fromString(rs.getString("UUID"));
160
				State stateTerm = getStateTerm(state, uuid, lifeform, description, null, lifeformVoc);
161
				addOriginalSource(stateTerm, id.toString(), "EcoLifeForm", state.getTransactionalSourceReference());
162
				getTermService().saveOrUpdate(stateTerm);
163
			}
164

    
165
			//material category
166
			TermVocabulary<DefinedTerm> materialCategoryVoc = getVocabulary(TermType.KindOfUnit, AlgaTerraImportTransformer.uuidKindOfUnitVoc, "Alga Terra Material Category", "Alga Terra Material Category", abbrevLabel, uri, false, DefinedTerm.NewKindOfUnitInstance(null, null, null));
167
			getVocabularyService().save(materialCategoryVoc);
168

    
169
			String materialSql = "SELECT * FROM MaterialCategory WHERE MaterialCategoryId <> 16 ";
170
			rs = source.getResultSet(materialSql);
171
			while (rs.next()){
172
				Integer id = rs.getInt("MaterialCategoryId");
173
				String category = rs.getString("MaterialCategory");
174
				String description = rs.getString("Description");
175
				UUID uuid = UUID.randomUUID();
176

    
177
				DefinedTerm kindOfUnit = DefinedTerm.NewKindOfUnitInstance(description, category, null);
178
				kindOfUnit.setUuid(uuid);
179
				addOriginalSource(kindOfUnit, id.toString(), "MaterialCategory", state.getTransactionalSourceReference());
180
				materialCategoryVoc.addTerm(kindOfUnit);
181
				getTermService().saveOrUpdate(kindOfUnit);
182
				materialCategoryMapping.put(id, uuid);
183
			}
184

    
185
			//areas
186
			OrderedTermVocabulary<NamedArea> informalAreasVoc = (OrderedTermVocabulary<NamedArea>)getVocabulary(TermType.NamedArea, AlgaTerraImportTransformer.uuidNamedAreaVocAlgaTerraInformalAreas, "AlgaTerra Specific Areas", "AlgaTerra Specific Areas", abbrevLabel, uri, true, NamedArea.NewInstance());
187
			getVocabularyService().save(informalAreasVoc);
188

    
189
			String areaSql = "SELECT * FROM TDWGGazetteer WHERE subL4 = 1 ";
190
			rs = source.getResultSet(areaSql);
191
			while (rs.next()){
192
				String l1Code = rs.getString("L1Code");
193
				String l2Code = rs.getString("L2Code");
194
				String l3Code = rs.getString("L3Code");
195
				String l4Code = rs.getString("L4Code");
196
				String gazetteer = rs.getString("Gazetteer");
197
				Integer id = rs.getInt("ID");
198
				String notes = rs.getString("Notes");
199
				//TODO stable uuids
200
//				UUID uuid = UUID.fromString(rs.getString("UUID"));
201
				UUID uuid = UUID.randomUUID();
202
				subL4Mapping.put(id, uuid);
203

    
204
				String tdwgCode =  (l4Code != null) ? l4Code : (l3Code != null) ? l3Code : (l2Code != null) ? l2Code : l1Code;
205

    
206
				NamedArea tdwgArea = TdwgAreaProvider.getAreaByTdwgAbbreviation(tdwgCode);
207
				NamedArea newArea  = getNamedArea(state, uuid ,gazetteer, gazetteer, null, null, null, informalAreasVoc, TermMatchMode.UUID_ONLY, null);
208
				if (isNotBlank(notes)){
209
					newArea.addAnnotation(Annotation.NewInstance(notes, AnnotationType.EDITORIAL(), Language.DEFAULT()));
210
				}
211

    
212
				addOriginalSource(newArea, id.toString(), "TDWGGazetteer", state.getTransactionalSourceReference());
213
				getTermService().saveOrUpdate(newArea);
214
				newArea.setPartOf(tdwgArea);
215
				informalAreasVoc.addTerm(newArea);
216
			}
217

    
218
			this.commitTransaction(txStatus);
219

    
220
			state.setSpecimenVocabulariesCreated(true);
221
		}
222
	}
223

    
224
	//tmp
225
	static Map<Integer, UUID> subL4Mapping = new HashMap<>();
226
	static Map<Integer, UUID> materialCategoryMapping = new HashMap<>();
227

    
228
	protected String getLocalityString(){
229
		return "Locality";
230
	}
231

    
232
	protected void handleFieldObservationSpecimen(ResultSet rs, DerivedUnitFacade facade, AlgaTerraImportState state, ResultSetPartitioner partitioner) throws SQLException {
233
		//FIXME missing fields #3084, #3085, #3080
234
		try {
235

    
236
			Integer unitId = nullSafeInt(rs, "unitId");
237
			String locality = rs.getString(getLocalityString());
238
			Double latitude = nullSafeDouble(rs, "Latitude");
239
			Double longitude = nullSafeDouble(rs, "Longitude");
240
			Integer errorRadius = nullSafeInt(rs,"Prec");
241
			String geoCodeMethod = rs.getString("GeoCodeMethod");
242

    
243
			Integer altitude = nullSafeInt(rs, "Altitude");
244
			Integer lowerAltitude = nullSafeInt(rs, "AltitudeLowerValue");
245
			String altitudeUnit = rs.getString("AltitudeUnit");
246
			Double depth = nullSafeDouble(rs, "Depth");
247
			Double depthLow = nullSafeDouble(rs, "DepthLow");
248

    
249
			String collectorsNumber = rs.getString("CollectorsNumber");
250
			Date collectionDateStart = rs.getDate("CollectionDate");
251
			Date collectionDateEnd = rs.getDate("CollectionDateEnd");
252

    
253
			//location
254
			facade.setLocality(locality);
255

    
256
			//exact location
257
			ReferenceSystem referenceSystem = makeRefrenceSystem(geoCodeMethod, state);
258
			if (longitude != null || latitude != null || referenceSystem != null || errorRadius != null){
259
				Point exactLocation = Point.NewInstance(longitude, latitude, referenceSystem, errorRadius);
260
				facade.setExactLocation(exactLocation);
261
			}
262

    
263
			//altitude, depth
264
			if (StringUtils.isNotBlank(altitudeUnit) && ! altitudeUnit.trim().equalsIgnoreCase("m")){
265
				logger.warn("Altitude unit is not [m] but: " +  altitudeUnit);
266
			}
267
			if ( altitude != null){
268
				if (lowerAltitude == null){
269
					facade.setAbsoluteElevation(altitude);
270
				}else{
271
					facade.setAbsoluteElevationRange(lowerAltitude,altitude);
272
			   	}
273
			}
274
			if ( depth != null){
275
				if (depthLow == null){
276
					facade.setDistanceToWaterSurface(depth);
277
				}else{
278
					//TODO which direction is correct?
279
					facade.setDistanceToWaterSurfaceRange(depth, depthLow);
280
			   	}
281
			}
282

    
283
			//field
284
			facade.setFieldNumber(collectorsNumber);
285
			TimePeriod gatheringPeriod = TimePeriod.NewInstance(collectionDateStart, collectionDateEnd);
286
			facade.setGatheringPeriod(gatheringPeriod);
287
			handleCollectorTeam(state, facade, rs);
288

    
289
			//areas
290
			makeAreas(state, rs, facade);
291

    
292
			//notes
293
			//=> not required according to Henning
294

    
295
			//id, created, updated, notes
296
			if (unitId != null){
297
				this.doIdCreatedUpdatedNotes(state, facade.innerFieldUnit(), rs, unitId, getFieldObservationNameSpace());
298
			}else{
299
				logger.warn("FieldObservation has no unitId: " +  facade.innerFieldUnit() + ": " + getFieldObservationNameSpace());
300
			}
301
		} catch (Exception e) {
302
			throw new RuntimeException(e);
303
		}
304

    
305
	}
306

    
307
	protected void handleFirstDerivedSpecimen(ResultSet rs, DerivedUnitFacade facade, AlgaTerraImportState state, ResultSetPartitioner partitioner) throws SQLException {
308
		Integer unitId = nullSafeInt(rs, "unitId");
309
		Integer collectionFk = nullSafeInt(rs,"CollectionFk");
310
		String label = rs.getString("Label");
311

    
312
		//collection
313
		if (collectionFk != null){
314
			Collection subCollection = state.getRelatedObject(AlgaTerraCollectionImport.NAMESPACE_SUBCOLLECTION, String.valueOf(collectionFk), Collection.class);
315
			if (subCollection != null){
316
				facade.setCollection(subCollection);
317
			}else{
318
				Collection collection = state.getRelatedObject(AlgaTerraCollectionImport.NAMESPACE_COLLECTION, String.valueOf(collectionFk), Collection.class);
319
				if (collection == null){
320
					logger.warn("Collection for collectionFK " + collectionFk + " can not be found.");
321
				}
322
				facade.setCollection(collection);
323
			}
324
		}
325

    
326
		//Label
327
		if (isNotBlank(label)){
328
			//TODO implement label #4218, #3090, #3084
329
			logger.warn("Label not yet implemented for specimen, #4218, #3090, #3084");
330
		}
331

    
332
		//TODO id, created for fact +  ecoFact
333
		//    	this.doIdCreatedUpdatedNotes(state, descriptionElement, rs, id, namespace);
334
		if (unitId != null){
335
			this.doIdCreatedUpdatedNotes(state, facade.innerDerivedUnit(), rs, unitId, getDerivedUnitNameSpace());
336
		}else{
337
			logger.warn("Specimen has no unitId: " +  facade.innerDerivedUnit() + ": " + getDerivedUnitNameSpace());
338
		}
339
	}
340

    
341

    
342

    
343
	protected abstract String getDerivedUnitNameSpace();
344

    
345
	protected abstract String getFieldObservationNameSpace();
346

    
347

    
348
	protected DescriptionBase<?> getFieldObservationDescription(DerivedUnitFacade facade) {
349
		Set<DescriptionBase<?>> descriptions = (Set)facade.innerFieldUnit().getDescriptions();
350
		for (DescriptionBase<?> desc : descriptions){
351
			if (desc.isImageGallery() == false){
352
				return desc;
353
			}
354
		}
355
		SpecimenDescription specDesc = SpecimenDescription.NewInstance(facade.innerFieldUnit());
356
		descriptions.add(specDesc);
357
		return specDesc;
358
	}
359

    
360

    
361
	private void makeAreas(AlgaTerraImportState state, ResultSet rs, DerivedUnitFacade facade) throws SQLException {
362
	   	Integer gazetteerId = nullSafeInt(rs, "GazetteerId");
363
	   	if (gazetteerId != null){
364
	   		//TDWG
365
	   		NamedArea tdwgArea;
366
	   		String tdwg4 = rs.getString("L4Code");
367
	   		if (isNotBlank(tdwg4)){
368
	   			tdwgArea = TdwgAreaProvider.getAreaByTdwgAbbreviation(tdwg4);
369
	   		}else{
370
	   			String tdwg3 = rs.getString("L3Code");
371
	   			if (isNotBlank(tdwg3)){
372
	   				tdwgArea = TdwgAreaProvider.getAreaByTdwgAbbreviation(tdwg3);
373
	   			}else{
374
	   				Number tdwg2D = nullSafeDouble(rs, "L2Code");
375
	   				if (tdwg2D != null){
376
	   					Integer tdwg2 = tdwg2D.intValue();
377
		   				tdwgArea = TdwgAreaProvider.getAreaByTdwgAbbreviation(String.valueOf(tdwg2));
378
	   				}else{
379
	   					Number tdwg1D = nullSafeDouble(rs, "L1Code");
380
		   				if (tdwg1D != null){
381
		   					Integer tdwg1 = tdwg1D.intValue();
382
		   					tdwgArea = TdwgAreaProvider.getAreaByTdwgAbbreviation(String.valueOf(tdwg1));
383
		   				}else{
384
		   					tdwgArea = null;
385
		   				}
386
	   				}
387
		   		}
388
	   		}
389
	   		if (tdwgArea == null){
390
	   			logger.warn("TDWG area could not be defined for gazetterId: " + gazetteerId);
391
	   		}else{
392
	   			facade.addCollectingArea(tdwgArea);
393
	   		}
394

    
395
	   		//Countries
396
	   		Country country = null;
397
	   		String isoCountry = rs.getString("ISOCountry");
398
	   		String countryStr = rs.getString("Country");
399
	   		if (isNotBlank(isoCountry)){
400
		   		country = Country.getCountryByIso3166A2(isoCountry);
401
	   		}else if (isNotBlank(countryStr)){
402
	   			logger.warn("Country exists but no ISO code");
403
	   		}else{
404

    
405
	   		}
406

    
407
	   		NamedArea subL4Area = null;
408
	   		Boolean subL4 = nullSafeBoolean(rs, "subL4");
409
	   		if (subL4 != null && subL4.booleanValue() == true){
410
	   			subL4Area = makeSubL4Area(state, gazetteerId);
411
	   			if (subL4Area != null){
412
	   				facade.addCollectingArea(subL4Area);
413
	   			}else{
414
	   				logger.warn("SubL4 area not found for gazetteerId: " + gazetteerId);
415
	   			}
416
	   		}
417

    
418
	   		if (country == null ){
419
	   			if (! gazetteerId.equals(40)){//special handling for Borneo, TDWG area is enough here as it matches exactly
420
		   			if (subL4Area == null ){
421
		   				logger.warn("Country does not exist and SubL4 could not be found for GazetteerID " + gazetteerId);
422
		   			}else {
423
		   				logger.info("Country could not be defined but subL4 area was added");
424
		   			}
425
	   			}
426
	   		}else{
427
	   			facade.setCountry(country);
428
	   		}
429

    
430
	   	}
431

    
432
	   	//Waterbody
433
	   	NamedArea waterbody = null;
434
	   	String waterbodyStr = rs.getString("WaterBody");
435
	   	if (isNotBlank(waterbodyStr)){
436
	   		if (waterbodyStr.equals("Atlantic Ocean")){
437
	   			waterbody = NamedArea.ATLANTICOCEAN();
438
	   		}else if (waterbodyStr.equals("Pacific Ocean")){
439
	   			waterbody = NamedArea.PACIFICOCEAN();
440
	   		}else if (waterbodyStr.equals("Indian Ocean")){
441
	   			waterbody = NamedArea.INDIANOCEAN();
442
	   		}else if (waterbodyStr.equals("Arctic Ocean")){
443
	   			waterbody = NamedArea.ARCTICOCEAN();
444
	   		}else{
445
	   			logger.warn("Waterbody not recognized: " + waterbody);
446
	   		}
447
	   		if (waterbody != null){
448
	   			facade.addCollectingArea(waterbody);
449
	   		}
450
	   	}
451

    
452

    
453
	   	//countries sub
454
	   	//TODO -> SpecimenImport (not existing in TypeSpecimen)
455
	}
456

    
457

    
458
	private NamedArea makeSubL4Area(AlgaTerraImportState state, Integer gazetteerId) {
459
		UUID uuid = subL4Mapping.get(gazetteerId);
460
		NamedArea area = (NamedArea)getTermService().find(uuid);
461
		if (area == null){
462
			logger.warn("SubL4 area could not be found in repository");
463
		}
464
		return area;
465
	}
466

    
467
	private boolean handleMissingCountry(AlgaTerraImportState state, DerivedUnitFacade facade, Integer gazetteerId) {
468
		NamedArea area = null;
469
		if (gazetteerId != null){
470
			if (gazetteerId.equals(42)){
471
				area = getNamedArea(state, AlgaTerraImportTransformer.uuidNamedAreaBorneo, null, null, null, null, null);
472
			}else if (gazetteerId.equals(1684)){
473
				area = getNamedArea(state, AlgaTerraImportTransformer.uuidNamedAreaPatagonia, null, null, null, null, null);
474
			}else if (gazetteerId.equals(2167)){
475
				area = getNamedArea(state, AlgaTerraImportTransformer.uuidNamedAreaTierraDelFuego, null, null, null, null, null);
476
			}
477
		}
478
		if (area != null){
479
			facade.addCollectingArea(area);
480
			return true;
481
		}
482
		return false;
483

    
484
	}
485

    
486
	protected SpecimenOrObservationType makeDerivedUnitType(String recordBasis) {
487
		SpecimenOrObservationType result = null;
488
		if (StringUtils.isBlank(recordBasis)){
489
			result = SpecimenOrObservationType.DerivedUnit;
490
		} else if (recordBasis.equalsIgnoreCase("FossileSpecimen")){
491
			result = SpecimenOrObservationType.Fossil;
492
		}else if (recordBasis.equalsIgnoreCase("HumanObservation")){
493
			result = SpecimenOrObservationType.HumanObservation;
494
		}else if (recordBasis.equalsIgnoreCase("Literature")){
495
			//FIXME
496
			logger.warn("Literature record basis not yet supported");
497
			result = SpecimenOrObservationType.DerivedUnit;
498
		}else if (recordBasis.equalsIgnoreCase("LivingSpecimen")){
499
			result = SpecimenOrObservationType.LivingSpecimen;
500
		}else if (recordBasis.equalsIgnoreCase("MachineObservation")){
501
			result = SpecimenOrObservationType.MachineObservation;
502
		}else if (recordBasis.equalsIgnoreCase("Observation")){
503
			result = SpecimenOrObservationType.Observation;
504
		}else if (recordBasis.equalsIgnoreCase("LivingCulture")){
505
			//FIXME
506
			logger.warn("LivingCulture record basis not yet supported");
507
			result = SpecimenOrObservationType.DerivedUnit;
508
		}else if (recordBasis.equalsIgnoreCase("PreservedSpecimen")){
509
			result = SpecimenOrObservationType.PreservedSpecimen;
510
		}
511
		return result;
512
	}
513

    
514

    
515
	protected Feature makeFeature(SpecimenOrObservationType type, AlgaTerraImportState state) {
516
		if (type.equals(SpecimenOrObservationType.DerivedUnit)){
517
			return Feature.INDIVIDUALS_ASSOCIATION();
518
		}else if (type.isFeatureObservation()){
519
			return Feature.OBSERVATION();
520
		}else if (type.isPreservedSpecimen()){
521
			return Feature.SPECIMEN();
522
		}else if (type.equals(SpecimenOrObservationType.LivingSpecimen)){
523
			UUID uuid = AlgaTerraImportTransformer.uuidFeatureLivingSpecimen;
524
			Feature feature = getFeature(state, uuid, "Living Specimen", "Living Specimen", null, Feature.SPECIMEN().getVocabulary());
525
			if (feature == null){
526
				logger.warn("Living Specimen Feature could not be created");
527
			}
528
			return feature;
529
		}
530
		logger.warn("No feature defined for derived unit type: " + type);
531
		return null;
532
	}
533

    
534
	private ReferenceSystem makeRefrenceSystem(String geoCodeMethod, AlgaTerraImportState state) {
535
		if (StringUtils.isBlank(geoCodeMethod)){
536
			return null;
537
		}else if(geoCodeMethod.startsWith("GPS")){
538
			getReferenceSystem(state, uuidRefSystemGps, "GPS", "GPS", "GPS", ReferenceSystem.GOOGLE_EARTH().getVocabulary());
539
			return ReferenceSystem.WGS84();
540
		}else if(geoCodeMethod.startsWith("Google")){
541
			return ReferenceSystem.GOOGLE_EARTH();
542
		}else if(geoCodeMethod.startsWith("Map")){
543
			return ReferenceSystem.MAP();
544
		}else if(geoCodeMethod.startsWith("WikiProjekt Georeferenzierung") || geoCodeMethod.startsWith("http://toolserver.org/~geohack/geohack.php") ){
545
			return ReferenceSystem.WGS84();
546
		}else {
547
			logger.warn("Reference system " +  geoCodeMethod +  " not yet supported.");
548
			return null;
549
		}
550
	}
551

    
552

    
553

    
554

    
555
	private void handleCollectorTeam(AlgaTerraImportState state, DerivedUnitFacade facade, ResultSet rs) throws SQLException {
556
		String collector = rs.getString("Collector");
557
		TeamOrPersonBase<?> author = getAuthor(collector);
558
		facade.setCollector(author);
559
	}
560

    
561
	/**
562
	 * @param facade
563
	 * @param collector
564
	 */
565
	protected TeamOrPersonBase<?> getAuthor(String author) {
566
		// FIXME TODO parsen und deduplizieren
567
		Team team = Team.NewTitledInstance(author, author);
568
		return team;
569
	}
570

    
571

    
572
	/**
573
	 * Use same TaxonDescription if two records belong to the same taxon
574
	 * @param state
575
	 * @param newTaxonId
576
	 * @param oldTaxonId
577
	 * @param oldDescription
578
	 * @param taxonMap
579
	 * @return
580
	 */
581
	protected TaxonDescription getTaxonDescription(AlgaTerraImportState state, Taxon taxon, Reference sourceSec){
582
		TaxonDescription result = null;
583
		Set<TaxonDescription> descriptionSet= taxon.getDescriptions();
584
		if (descriptionSet.size() > 0) {
585
			result = descriptionSet.iterator().next();
586
		}else{
587
			result = TaxonDescription.NewInstance();
588
			result.setTitleCache(sourceSec.getTitleCache(), true);
589
			taxon.addDescription(result);
590
		}
591
		return result;
592
	}
593

    
594

    
595

    
596

    
597
}
(12-12/15)