View Javadoc

1   // $Id$
2   /**
3   * Copyright (C) 2007 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  
11  package eu.etaxonomy.cdm.io.common.mapping;
12  
13  import java.sql.ResultSet;
14  import java.sql.SQLException;
15  import java.util.UUID;
16  
17  import org.apache.log4j.Logger;
18  
19  import eu.etaxonomy.cdm.api.service.ITaxonTreeService;
20  import eu.etaxonomy.cdm.io.common.CdmImportBase;
21  import eu.etaxonomy.cdm.io.common.DbImportStateBase;
22  import eu.etaxonomy.cdm.io.common.ImportConfiguratorBase;
23  import eu.etaxonomy.cdm.io.erms.ICheckIgnoreMapper;
24  import eu.etaxonomy.cdm.model.common.CdmBase;
25  import eu.etaxonomy.cdm.model.reference.ReferenceBase;
26  import eu.etaxonomy.cdm.model.taxon.Taxon;
27  import eu.etaxonomy.cdm.model.taxon.TaxonBase;
28  import eu.etaxonomy.cdm.model.taxon.TaxonNode;
29  import eu.etaxonomy.cdm.model.taxon.TaxonRelationshipType;
30  import eu.etaxonomy.cdm.model.taxon.TaxonomicTree;
31  
32  /**
33   * @author a.mueller
34   * @created 12.05.2009
35   * @version 1.0
36   */
37  /**
38   * @author a.mueller
39   * @created 02.03.2010
40   * @version 1.0
41   * @param <CDM_BASE>
42   * @param <STATE>
43   */
44  public class DbImportTaxIncludedInMapper<STATE extends DbImportStateBase<ImportConfiguratorBase,?>> extends DbImportMultiAttributeMapperBase<CdmBase, STATE> {
45  	private static final Logger logger = Logger.getLogger(DbImportTaxIncludedInMapper.class);
46  	
47  //******************************** FACTORY METHOD ***************************************************/
48  	
49  	public static DbImportTaxIncludedInMapper<?> NewInstance(String dbChildAttribute, String dbChildNamespace, String dbParentAttribute, String parentNamespace, String dbAlternativeParentAttribute, String alternativeParentNamespace, String dbTreeAttribute){
50  		String citationNamespace = null;
51  		String citationAttribute = null;
52  		return new DbImportTaxIncludedInMapper(dbChildAttribute, dbChildNamespace, dbParentAttribute, parentNamespace, dbAlternativeParentAttribute, alternativeParentNamespace, dbTreeAttribute, citationAttribute, citationNamespace);
53  	}
54  	
55  //******************************* ATTRIBUTES ***************************************/
56  	private String fromAttribute;
57  	private String toAttribute;
58  
59  	private String fromNamespace;
60  	private String toNamespace;
61  	
62  	private String citationAttribute;
63  	private String citationNamespace;
64  	
65  	private String microCitationAttribute;
66  	private String treeAttribute;
67  	private String alternativeAttribute;
68  	private String alternativeNamespace;
69  	
70  	
71  //********************************* CONSTRUCTOR ****************************************/
72  	/**
73  	 * @param relatedObjectNamespace 
74  	 * @param mappingImport
75  	 */
76  	protected DbImportTaxIncludedInMapper(String fromAttribute, String fromNamespace, String toAttribute, String toNamespace, String alternativeAttribute, String alternativeNamespace, String treeAttribute, String citationAttribute, String citationNamespace) {
77  		super();
78  		//TODO make it a single attribute mapper
79  		this.fromAttribute = fromAttribute;
80  		this.fromNamespace = fromNamespace;
81  		this.toAttribute = toAttribute;
82  		this.toNamespace = toNamespace;
83  		this.treeAttribute = treeAttribute;
84  		this.alternativeAttribute = alternativeAttribute;
85  		this.alternativeNamespace = alternativeNamespace;
86  		this.citationAttribute = citationAttribute;
87  		this.citationNamespace = citationNamespace;
88  	}
89  
90  //************************************ METHODS *******************************************/
91  
92  	
93  	/* (non-Javadoc)
94  	 * @see eu.etaxonomy.cdm.io.common.mapping.IDbImportMapper#invoke(java.sql.ResultSet, eu.etaxonomy.cdm.model.common.CdmBase)
95  	 */
96  	public CdmBase invoke(ResultSet rs, CdmBase cdmBase) throws SQLException {
97  		STATE state = getState();
98  		CdmImportBase currentImport = state.getCurrentIO();
99  		if (currentImport instanceof ICheckIgnoreMapper){
100 			boolean ignoreRecord = ((ICheckIgnoreMapper)currentImport).checkIgnoreMapper(this, rs);
101 			if (ignoreRecord){
102 				return cdmBase;
103 			}
104 		}
105 		
106 		TaxonBase fromObject = (TaxonBase)getRelatedObject(rs, fromAttribute, fromNamespace);
107 		TaxonBase toObject = (TaxonBase)getRelatedObject(rs, toAttribute, toNamespace);
108 		TaxonBase alternativeToObject = (TaxonBase)getRelatedObject(rs, alternativeAttribute, alternativeNamespace);
109 		
110 		String fromId = String.valueOf(rs.getObject(fromAttribute));
111 		String toId = String.valueOf(rs.getObject(toAttribute));
112 		String alternativeToId = String.valueOf(rs.getObject(alternativeAttribute));
113 
114 		ReferenceBase citation = (ReferenceBase)getRelatedObject(rs, citationAttribute, citationNamespace);
115 		String microCitation = null;
116 		if (citationAttribute != null){
117 			microCitation = rs.getString(microCitationAttribute);
118 		}
119 		//TODO check int
120 		Integer treeFk = null;
121 		if (treeAttribute != null){
122 			treeFk = rs.getInt(treeAttribute);
123 		}
124 		
125 		if (fromObject == null){
126 			String warning  = "The child taxon could not be found. Child taxon not added to the tree";
127 			logger.warn(warning);
128 			return cdmBase;
129 		}
130 		Taxon fromTaxon;
131 		try {
132 			fromTaxon = checkTaxonType(fromObject, "Child", fromId);
133 		} catch (IllegalArgumentException e2) {
134 			//fromTaxon is null
135 			return cdmBase;
136 		}
137 		
138 		if (toObject == null){
139 			String warning  = "The parent taxon could not be found. Child taxon not added to the tree";
140 			logger.warn(warning);
141 			return cdmBase;
142 		}
143 		
144 		Taxon toTaxon;
145 		try {
146 			toTaxon = checkTaxonType(toObject, "Parent", toId);
147 		} catch (IllegalArgumentException e) {
148 			if (alternativeToObject != null){
149 				try {
150 					toTaxon = checkTaxonType(alternativeToObject, "Alternative parent", alternativeToId);
151 				} catch (IllegalArgumentException e1) {
152 					return cdmBase;
153 				}
154 			}else{
155 				
156 				return cdmBase;
157 			}
158 		}
159 		
160 		if (fromTaxon.equals(toTaxon)){
161 			String warning  = "A taxon may not be a child of itself. Taxon not added to the tree";
162 			logger.warn(warning);
163 			return cdmBase;
164 		}
165 		//maps the reference
166 		makeTaxonomicallyIncluded(state, treeFk, fromTaxon, toTaxon, citation, microCitation);
167 		return fromTaxon;
168 	}
169 
170 	
171 	
172 
173 
174 	/**
175 	 * TODO copied from BM import. May be more generic
176 	 * @param state
177 	 * @param taxonTreeMap
178 	 * @param treeRefFk
179 	 * @param child
180 	 * @param parent
181 	 * @param citation
182 	 * @param microCitation
183 	 * @return
184 	 */
185 	
186 	public static final String TAXONOMIC_TREE_NAMESPACE = "TaxonomicTree";
187 	
188 	private boolean makeTaxonomicallyIncluded(STATE state, Integer treeRefFk, Taxon child, Taxon parent, ReferenceBase citation, String microCitation){
189 		String treeKey;
190 		UUID treeUuid;
191 		if (treeRefFk == null){
192 			treeKey = "1";  // there is only one tree and it gets the key '1'
193 			treeUuid = state.getConfig().getTaxonomicTreeUuid();
194 		}else{
195 			treeKey =String.valueOf(treeRefFk);
196 			treeUuid = state.getTreeUuidByTreeKey(treeKey);
197 		}
198 		TaxonomicTree tree = (TaxonomicTree)state.getRelatedObject(TAXONOMIC_TREE_NAMESPACE, treeKey);
199 		if (tree == null){
200 			ITaxonTreeService service = state.getCurrentIO().getTaxonTreeService();
201 			tree = service.getTaxonomicTreeByUuid(treeUuid);
202 			if (tree == null){
203 				String treeName = state.getConfig().getTaxonomicTreeName();
204 				tree = TaxonomicTree.NewInstance(treeName);
205 				tree.setUuid(treeUuid);
206 				//FIXME tree reference
207 				//tree.setReference(ref);
208 				service.save(tree);
209 			}
210 			state.addRelatedObject(TAXONOMIC_TREE_NAMESPACE, treeKey, tree);
211 		}
212 		
213 		TaxonNode childNode = tree.addParentChild(parent, child, citation, microCitation);
214 		return (childNode != null);
215 	}
216 	
217 //	
218 //	private boolean makeTaxonomicallyIncluded_OLD(STATE state, Integer treeRefFk, Taxon child, Taxon parent, ReferenceBase citation, String microCitation){
219 //		Map<Integer, TaxonomicTree> taxonTreeMap = state.getPartitionTaxonTreeMap();
220 //		
221 //		
222 //		TaxonomicTree tree = taxonTreeMap.get(treeRefFk);
223 //		if (tree == null){
224 //			UUID treeUuid = state.getTreeUuidByTreeKey(treeRefFk);
225 //			tree = state.getCurrentImport().getTaxonTreeService().getTaxonomicTreeByUuid(treeUuid);
226 //			if (tree == null){
227 //				//FIXME FIXME FIXME
228 //				String treeName = "TaxonTree - No Name";
229 //				tree = TaxonomicTree.NewInstance(treeName);
230 //				//tree.setReference(ref);
231 //				//throw new IllegalStateException("Tree for ToTaxon reference does not exist.");
232 //			}
233 //			taxonTreeMap.put(treeRefFk, tree);
234 //		}
235 //		return tree.addParentChild(parent, child, citation, microCitation);
236 //	}
237 	
238 	
239 	/**
240 	 *	//TODO copied from DbImportObjectMapper. Maybe these can be merged again in future
241 	 * @param rs
242 	 * @param dbAttribute
243 	 * @return
244 	 * @throws SQLException
245 	 */
246 	protected CdmBase getRelatedObject(ResultSet rs, String dbAttribute, String namespace) throws SQLException {
247 		CdmBase result = null;
248 		if (dbAttribute != null){
249 			Object dbValue = rs.getObject(dbAttribute);
250 			String id = String.valueOf(dbValue);
251 			DbImportStateBase state = importMapperHelper.getState();
252 			result = state.getRelatedObject(namespace, id);
253 		}
254 		return result;
255 	}
256 	
257 
258 	/**
259 	 * Checks if cdmBase is of type Taxon 
260 	 * @param taxonBase
261 	 * @param typeString
262 	 * @param id
263 	 * @return
264 	 */
265 	private Taxon checkTaxonType(TaxonBase taxonBase, String typeString, String id) throws IllegalArgumentException{
266 		if (! taxonBase.isInstanceOf(Taxon.class)){
267 			String warning = typeString + " (" + id + ") is not of type Taxon but of type " + taxonBase.getClass().getSimpleName();
268 			logger.warn(warning);
269 			throw new IllegalArgumentException(warning);
270 		}
271 		return (taxonBase.deproxy(taxonBase, Taxon.class));
272 	}
273 
274 
275 }