rename cdmlib-eflora -> cdm-eflora
[cdmlib-apps.git] / cdm-eflora / src / main / java / eu / etaxonomy / cdm / io / eflora / centralAfrica / checklist / CentralAfricaChecklistTaxonImport.java
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.eflora.centralAfrica.checklist;
11
12 import java.sql.ResultSet;
13 import java.sql.SQLException;
14 import java.util.HashMap;
15 import java.util.HashSet;
16 import java.util.Map;
17 import java.util.Set;
18 import java.util.UUID;
19
20 import org.apache.commons.lang.StringUtils;
21 import org.apache.log4j.Logger;
22 import org.springframework.stereotype.Component;
23
24 import eu.etaxonomy.cdm.api.service.IClassificationService;
25 import eu.etaxonomy.cdm.common.CdmUtils;
26 import eu.etaxonomy.cdm.io.common.IOValidator;
27 import eu.etaxonomy.cdm.io.common.ResultSetPartitioner;
28 import eu.etaxonomy.cdm.io.common.mapping.DbImportMapping;
29 import eu.etaxonomy.cdm.io.common.mapping.DbImportMarkerMapper;
30 import eu.etaxonomy.cdm.io.common.mapping.DbImportObjectCreationMapper;
31 import eu.etaxonomy.cdm.io.common.mapping.DbImportTaxIncludedInMapper;
32 import eu.etaxonomy.cdm.io.common.mapping.IMappingImport;
33 import eu.etaxonomy.cdm.io.eflora.centralAfrica.checklist.validation.CentralAfricaChecklistTaxonImportValidator;
34 import eu.etaxonomy.cdm.model.common.CdmBase;
35 import eu.etaxonomy.cdm.model.description.Distribution;
36 import eu.etaxonomy.cdm.model.description.PresenceTerm;
37 import eu.etaxonomy.cdm.model.description.TaxonDescription;
38 import eu.etaxonomy.cdm.model.location.NamedArea;
39 import eu.etaxonomy.cdm.model.location.TdwgArea;
40 import eu.etaxonomy.cdm.model.name.BotanicalName;
41 import eu.etaxonomy.cdm.model.name.Rank;
42 import eu.etaxonomy.cdm.model.reference.Reference;
43 import eu.etaxonomy.cdm.model.reference.ReferenceFactory;
44 import eu.etaxonomy.cdm.model.taxon.Classification;
45 import eu.etaxonomy.cdm.model.taxon.Taxon;
46 import eu.etaxonomy.cdm.model.taxon.TaxonBase;
47 import eu.etaxonomy.cdm.model.taxon.TaxonNode;
48 import eu.etaxonomy.cdm.strategy.parser.NonViralNameParserImpl;
49
50
51 /**
52 * @author a.mueller
53 * @created 20.02.2010
54 * @version 1.0
55 */
56 @Component
57 public class CentralAfricaChecklistTaxonImport extends CentralAfricaChecklistImportBase<TaxonBase> implements IMappingImport<TaxonBase, CentralAfricaChecklistImportState>{
58 private static final Logger logger = Logger.getLogger(CentralAfricaChecklistTaxonImport.class);
59
60 private NonViralNameParserImpl parser = NonViralNameParserImpl.NewInstance();
61
62 private Map<UUID, Taxon> higherTaxonMap;
63
64 private Integer TREE_ID = null;
65
66 private DbImportMapping mapping;
67
68 private int modCount = 10000;
69 private static final String pluralString = "taxa";
70 private static final String dbTableName = "checklist";
71 private static final Class cdmTargetClass = TaxonBase.class;
72 private static final String strOrderBy = " ORDER BY family, genus, species ";
73
74 public CentralAfricaChecklistTaxonImport(){
75 super(pluralString, dbTableName, cdmTargetClass);
76 }
77
78
79
80 /* (non-Javadoc)
81 * @see eu.etaxonomy.cdm.io.erms.ErmsImportBase#getIdQuery()
82 */
83 @Override
84 protected String getIdQuery() {
85 String strQuery = " SELECT pk FROM " + dbTableName +
86 strOrderBy;
87 return strQuery;
88 }
89
90
91 /* (non-Javadoc)
92 * @see eu.etaxonomy.cdm.io.erms.ErmsImportBase#getMapping()
93 */
94 protected DbImportMapping getMapping() {
95 if (mapping == null){
96 mapping = new DbImportMapping();
97
98 mapping.addMapper(DbImportObjectCreationMapper.NewInstance(this, "pk", TAXON_NAMESPACE)); //id + tu_status
99
100 UUID uuidKew = CentralAfricaChecklistTransformer.uuidAcceptedKew;
101 mapping.addMapper(DbImportMarkerMapper.NewInstance("accepted kew", uuidKew, "Accepted Kew", "Accepted Kew", "Kew", null));
102
103 UUID uuidGeneva = CentralAfricaChecklistTransformer.uuidAcceptedGeneva;
104 mapping.addMapper(DbImportMarkerMapper.NewInstance("accepted geneva", uuidGeneva, "Accepted Geneva", "Accepted Geneva", "Geneva", null));
105
106 UUID uuidItis = CentralAfricaChecklistTransformer.uuidAcceptedItis;
107 mapping.addMapper(DbImportMarkerMapper.NewInstance("accepted itis", uuidItis, "Accepted ITIS", "Accepted ITIS", "ITIS", null));
108 }
109
110 return mapping;
111 }
112
113 /* (non-Javadoc)
114 * @see eu.etaxonomy.cdm.io.berlinModel.in.BerlinModelImportBase#getRecordQuery(eu.etaxonomy.cdm.io.berlinModel.in.BerlinModelImportConfigurator)
115 */
116 @Override
117 protected String getRecordQuery(CentralAfricaChecklistImportConfigurator config) {
118 String strSelect = " SELECT * ";
119 String strFrom = " FROM checklist";
120 String strWhere = " WHERE ( pk IN (" + ID_LIST_TOKEN + ") )";
121 String strRecordQuery = strSelect + strFrom + strWhere + strOrderBy;
122 return strRecordQuery;
123 }
124
125
126 @Override
127 public boolean doPartition(ResultSetPartitioner partitioner, CentralAfricaChecklistImportState state) {
128 higherTaxonMap = new HashMap<UUID, Taxon>();
129 Reference genevaReference = getReferenceService().find(state.getConfig().getUuidGenevaReference());
130 if (genevaReference == null){
131 genevaReference = makeGenevaReference(state);
132 getReferenceService().save(genevaReference);
133 }
134 state.setGenevaReference(genevaReference);
135 boolean success = super.doPartition(partitioner, state);
136 higherTaxonMap = new HashMap<UUID, Taxon>();
137 state.setGenevaReference(null);
138 return success;
139 }
140
141
142 /* (non-Javadoc)
143 * @see eu.etaxonomy.cdm.io.berlinModel.in.IPartitionedIO#getRelatedObjectsForPartition(java.sql.ResultSet)
144 */
145 public Map<Object, Map<String, ? extends CdmBase>> getRelatedObjectsForPartition(ResultSet rs) {
146 String nameSpace;
147 Class cdmClass;
148 Set<String> idSet;
149 Set<String> referenceIdSet = new HashSet<String>();
150
151 Map<Object, Map<String, ? extends CdmBase>> result = new HashMap<Object, Map<String, ? extends CdmBase>>();
152
153 try{
154 while (rs.next()){
155 handleForeignKey(rs, referenceIdSet, "source");
156 }
157
158 //reference map
159 nameSpace = REFERENCE_NAMESPACE;
160 cdmClass = Reference.class;
161 idSet = referenceIdSet;
162 Map<String, Reference> referenceMap = (Map<String, Reference>)getCommonService().getSourcedObjectsByIdInSource(cdmClass, referenceIdSet, nameSpace);
163 result.put(REFERENCE_NAMESPACE, referenceMap);
164
165 } catch (SQLException e) {
166 throw new RuntimeException(e);
167 }
168 return result;
169 }
170
171
172 /* (non-Javadoc)
173 * @see eu.etaxonomy.cdm.io.common.mapping.IMappingImport#createObject(java.sql.ResultSet)
174 */
175 public TaxonBase createObject(ResultSet rs, CentralAfricaChecklistImportState state) throws SQLException {
176 BotanicalName speciesName = BotanicalName.NewInstance(Rank.SPECIES());
177
178 Reference sec = state.getConfig().getSourceReference();
179 getReferenceService().saveOrUpdate(sec);
180
181 String familyString = rs.getString("family");
182 String genusString = rs.getString("genus");
183 String speciesString = rs.getString("species");
184 String authorityString = rs.getString("authority");
185
186 if (logger.isDebugEnabled()){
187 System.out.println(familyString + " " + genusString + " " + speciesString);
188 }
189
190 Taxon speciesTaxon = Taxon.NewInstance(speciesName, sec);;
191 speciesName.setGenusOrUninomial(genusString);
192 speciesName.setSpecificEpithet(speciesString);
193 parser.handleAuthors(speciesName, CdmUtils.concat(" ", new String[] {"", genusString, speciesString, authorityString}), authorityString);
194
195 //family
196 Taxon familyTaxon = null;
197 if (StringUtils.isNotBlank(familyString)){
198 familyTaxon = getHigherTaxon(state, familyString, null);
199 if (familyTaxon == null){
200 BotanicalName familyName = BotanicalName.NewInstance(Rank.FAMILY());
201 familyName.setGenusOrUninomial(familyString);
202 familyTaxon = Taxon.NewInstance(familyName, sec);
203 saveHigherTaxon(state, familyTaxon, familyString, null);
204 }
205 getTaxonService().saveOrUpdate(familyTaxon);
206 }
207
208
209 //genus
210 Taxon genusTaxon = getHigherTaxon(state, familyString, genusString);
211 if (genusTaxon == null){
212 BotanicalName genusName = BotanicalName.NewInstance(Rank.GENUS());
213 genusName.setGenusOrUninomial(genusString);
214 genusTaxon = Taxon.NewInstance(genusName, sec);
215 saveHigherTaxon(state, genusTaxon, familyString, genusString);
216 if (familyTaxon != null){
217 makeTaxonomicallyIncluded(state, TREE_ID, genusTaxon, familyTaxon, null, null);
218 }
219 }
220 makeTaxonomicallyIncluded(state, TREE_ID, speciesTaxon, genusTaxon, null, null);
221 getTaxonService().saveOrUpdate(genusTaxon);
222
223 String sourceString = rs.getString("source");
224 String sourceId = rs.getString("source_id");
225
226 Reference sourceRef = state.getRelatedObject(REFERENCE_NAMESPACE, sourceString, Reference.class);
227 speciesTaxon.addSource(sourceId, REFERENCE_NAMESPACE, sourceRef, null);
228
229
230 //geneva id
231 Reference genevaReference = state.getGenevaReference();
232 Object genevaId = rs.getObject("geneva_ID");
233 speciesTaxon.addSource(String.valueOf(genevaId), null, genevaReference, null);
234
235 //distribution
236 handleDistribution(rs, speciesTaxon);
237
238 return speciesTaxon;
239 }
240
241 private void handleDistribution(ResultSet rs, Taxon speciesTaxon) throws SQLException {
242 TaxonDescription description = TaxonDescription.NewInstance(speciesTaxon);
243
244 Boolean isCongo = rs.getBoolean("drc");
245 Boolean isBurundi = rs.getBoolean("burundi");
246 Boolean isRwanda = rs.getBoolean("rwanda");
247
248 addDistribution(description, isCongo, "ZAI");
249 addDistribution(description, isBurundi, "BUR");
250 addDistribution(description, isRwanda, "RWA");
251
252 }
253
254
255
256 /**
257 * @param description
258 * @param isCongo
259 */
260 private void addDistribution(TaxonDescription description, Boolean exists, String label) {
261 if (exists == true){
262 NamedArea namedArea = TdwgArea.getAreaByTdwgAbbreviation(label);
263 Distribution distribution = Distribution.NewInstance(namedArea, PresenceTerm.PRESENT());
264 description.addElement(distribution);
265 }
266 }
267
268
269
270 private void saveHigherTaxon(CentralAfricaChecklistImportState state, Taxon higherTaxon, String family, String genus) {
271 String higherName = normalizeHigherTaxonName(family, genus);
272 UUID uuid = higherTaxon.getUuid();
273 state.putHigherTaxon(higherName, uuid);
274 higherTaxonMap.put(uuid, higherTaxon);
275 }
276
277
278
279 private Taxon getHigherTaxon(CentralAfricaChecklistImportState state, String family, String genus) {
280 String higherName = normalizeHigherTaxonName(family, genus);
281 UUID uuid = state.getHigherTaxon(higherName);
282
283 Taxon taxon = null;
284 if (uuid != null){
285 taxon = higherTaxonMap.get(uuid);
286 if (taxon == null){
287 taxon = CdmBase.deproxy(getTaxonService().find(uuid), Taxon.class);
288 }
289 }
290 return taxon;
291 }
292
293
294
295 /**
296 * @param family
297 * @param genus
298 */
299 private String normalizeHigherTaxonName(String family, String genus) {
300 return (CdmUtils.Nz(family) + "-" + CdmUtils.Nz(genus)).trim();
301 }
302
303
304
305
306 // private boolean makeTaxonomicallyIncluded(CentralAfricaChecklistImportState state, Taxon parent, Taxon child, Reference citation, String microCitation){
307 // Reference sec = child.getSec();
308 // UUID uuid = state.getTreeUuid(sec);
309 // Classification tree;
310 // tree = state.getTree(sec);
311 //
312 // if (tree == null){
313 // tree = makeTreeMemSave(state, sec);
314 // }
315 // TaxonNode childNode;
316 // if (parent != null){
317 // childNode = tree.addParentChild(parent, child, citation, microCitation);
318 // }else{
319 // childNode = tree.addChildTaxon(child, citation, microCitation, null);
320 // }
321 // return (childNode != null);
322 // }
323
324 //TODO use Mapper
325 private boolean makeTaxonomicallyIncluded(CentralAfricaChecklistImportState state, Integer treeRefFk, Taxon child, Taxon parent, Reference citation, String microCitation){
326 String treeKey;
327 UUID treeUuid;
328 if (treeRefFk == null){
329 treeKey = "1"; // there is only one tree and it gets the map key '1'
330 treeUuid = state.getConfig().getClassificationUuid();
331 }else{
332 treeKey =String.valueOf(treeRefFk);
333 treeUuid = state.getTreeUuidByTreeKey(treeKey);
334 }
335 Classification tree = (Classification)state.getRelatedObject(DbImportTaxIncludedInMapper.TAXONOMIC_TREE_NAMESPACE, treeKey);
336 if (tree == null){
337 IClassificationService service = state.getCurrentIO().getClassificationService();
338 tree = service.find(treeUuid);
339 if (tree == null){
340 String treeName = state.getConfig().getClassificationName();
341 tree = Classification.NewInstance(treeName);
342 tree.setUuid(treeUuid);
343 //FIXME tree reference
344 //tree.setReference(ref);
345 service.save(tree);
346 }
347 state.addRelatedObject(DbImportTaxIncludedInMapper.TAXONOMIC_TREE_NAMESPACE, treeKey, tree);
348 }
349
350 TaxonNode childNode = tree.addParentChild(parent, child, citation, microCitation);
351 return (childNode != null);
352 }
353
354
355 private Reference makeGenevaReference(CentralAfricaChecklistImportState state) {
356 Reference result = ReferenceFactory.newDatabase();
357 result.setTitleCache(state.getConfig().getGenevaReferenceTitle(), true);
358 result.setUuid(state.getConfig().getUuidGenevaReference());
359 return result;
360 }
361
362 /* (non-Javadoc)
363 * @see eu.etaxonomy.cdm.io.common.CdmIoBase#doCheck(eu.etaxonomy.cdm.io.common.IImportConfigurator)
364 */
365 @Override
366 protected boolean doCheck(CentralAfricaChecklistImportState state){
367 IOValidator<CentralAfricaChecklistImportState> validator = new CentralAfricaChecklistTaxonImportValidator();
368 return validator.validate(state);
369 }
370
371
372 /* (non-Javadoc)
373 * @see eu.etaxonomy.cdm.io.common.CdmIoBase#isIgnore(eu.etaxonomy.cdm.io.common.IImportConfigurator)
374 */
375 protected boolean isIgnore(CentralAfricaChecklistImportState state){
376 return ! state.getConfig().isDoTaxa();
377 }
378
379
380
381 }