Performed project cleanup.
[cdmlib.git] / cdmlib-model / src / main / java / eu / etaxonomy / cdm / model / common / IdentifiableEntity.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.model.common;
11
12
13 import java.util.HashSet;
14 import java.util.Set;
15
16 import javax.persistence.Column;
17 import javax.persistence.ManyToMany;
18 import javax.persistence.MappedSuperclass;
19 import javax.persistence.OneToMany;
20 import javax.persistence.Transient;
21 import javax.xml.bind.annotation.XmlAccessType;
22 import javax.xml.bind.annotation.XmlAccessorType;
23 import javax.xml.bind.annotation.XmlElement;
24 import javax.xml.bind.annotation.XmlElementWrapper;
25 import javax.xml.bind.annotation.XmlTransient;
26 import javax.xml.bind.annotation.XmlType;
27
28 import org.apache.log4j.Logger;
29 import org.hibernate.annotations.Cascade;
30 import org.hibernate.annotations.CascadeType;
31
32 import eu.etaxonomy.cdm.model.media.Rights;
33
34 /**
35 * Superclass for the primary CDM classes that can be referenced from outside via LSIDs and contain a simple generated title string as a label for human reading.
36 * All subclasses inherit the ability to store additional properties that are stored as {@link Extension Extensions}, basically a string value with a type term.
37 * Any number of right statements can be attached as well as multiple {@link OriginalSource} objects.
38 * Original sources carry a reference to the source, an ID within that source and the original title/label of this object as it was used in that source (originalNameString).
39 * A Taxon for example that was taken from 2 sources like FaunaEuropaea and IPNI would have two originalSource objects.
40 * The originalSource representing that taxon as it was found in IPNI would contain IPNI as the reference, the IPNI id of the taxon and the name of the taxon exactly as it was used in IPNI.
41 *
42 * @author m.doering
43 * @version 1.0
44 * @created 08-Nov-2007 13:06:27
45 */
46 @XmlAccessorType(XmlAccessType.FIELD)
47 @XmlType(name = "IdentifiableEntity", propOrder = {
48 "lsid",
49 "titleCache",
50 "protectedTitleCache",
51 "rights",
52 "extensions",
53 "sources"
54 })
55 @MappedSuperclass
56 public abstract class IdentifiableEntity<T extends IdentifiableEntity> extends AnnotatableEntity<T> implements ISourceable, IIdentifiableEntitiy<T> {
57 static Logger logger = Logger.getLogger(IdentifiableEntity.class);
58
59 @XmlTransient
60 public final boolean PROTECTED = true;
61 @XmlTransient
62 public final boolean NOT_PROTECTED = false;
63
64 @XmlElement(name = "LSID")
65 private String lsid;
66
67 @XmlElement(name = "TitleCache", required = true)
68 private String titleCache;
69
70 //if true titleCache will not be automatically generated/updated
71 @XmlElement(name = "ProtectedTitleCache")
72 private boolean protectedTitleCache;
73
74 @XmlElementWrapper(name = "Rights")
75 @XmlElement(name = "Rights")
76 private Set<Rights> rights = getNewRightsSet();
77
78 @XmlElementWrapper(name = "Extensions")
79 @XmlElement(name = "Extension")
80 private Set<Extension> extensions = getNewExtensionSet();
81
82 @XmlElementWrapper(name = "Sources")
83 @XmlElement(name = "OriginalSource")
84 private Set<OriginalSource> sources = getNewOriginalSourcesSet();
85
86
87 /* (non-Javadoc)
88 * @see eu.etaxonomy.cdm.model.common.IIdentifiableEntitiy#getLsid()
89 */
90 public String getLsid(){
91 return this.lsid;
92 }
93 /* (non-Javadoc)
94 * @see eu.etaxonomy.cdm.model.common.IIdentifiableEntitiy#setLsid(java.lang.String)
95 */
96 public void setLsid(String lsid){
97 this.lsid = lsid;
98 }
99
100 /* (non-Javadoc)
101 * @see eu.etaxonomy.cdm.model.common.IIdentifiableEntitiy#generateTitle()
102 */
103 public abstract String generateTitle();
104
105 /* (non-Javadoc)
106 * @see eu.etaxonomy.cdm.model.common.IIdentifiableEntitiy#getTitleCache()
107 */
108 @Transient
109 public String getTitleCache(){
110 if (protectedTitleCache){
111 return this.titleCache;
112 }
113 // is title dirty, i.e. equal NULL?
114 if (titleCache == null){
115 this.setTitleCache(generateTitle(),protectedTitleCache) ; //for truncating
116 }
117 return titleCache;
118 }
119 /* (non-Javadoc)
120 * @see eu.etaxonomy.cdm.model.common.IIdentifiableEntitiy#setTitleCache(java.lang.String)
121 */
122 public void setTitleCache(String titleCache){
123 setTitleCache(titleCache, PROTECTED);
124 }
125
126 //@Index(name="titleCacheIndex")
127 /* (non-Javadoc)
128 * @see eu.etaxonomy.cdm.model.common.IIdentifiableEntitiy#getTitleCache()
129 */
130 @Column(length=254)
131 @Deprecated //for hibernate use only
132 protected String getPersistentTitleCache(){
133 return getTitleCache();
134 }
135 @Deprecated //for hibernate use only
136 protected void setPersistentTitleCache(String titleCache){
137 this.titleCache = titleCache;
138 }
139
140
141
142 /* (non-Javadoc)
143 * @see eu.etaxonomy.cdm.model.common.IIdentifiableEntitiy#setTitleCache(java.lang.String, boolean)
144 */
145 public void setTitleCache(String titleCache, boolean protectCache){
146 //TODO truncation of title cache
147 if (titleCache != null && titleCache.length() > 250){
148 logger.warn("Truncation of title cache: " + this.toString());
149 titleCache = titleCache.substring(0, 249) + "...";
150 }
151 this.titleCache = titleCache;
152 this.setProtectedTitleCache(protectCache);
153 }
154
155 /* (non-Javadoc)
156 * @see eu.etaxonomy.cdm.model.common.IIdentifiableEntitiy#getRights()
157 */
158 @ManyToMany
159 @Cascade({CascadeType.SAVE_UPDATE})
160 public Set<Rights> getRights(){
161 return this.rights;
162 }
163
164 protected void setRights(Set<Rights> rights) {
165 this.rights = rights;
166 }
167 /* (non-Javadoc)
168 * @see eu.etaxonomy.cdm.model.common.IIdentifiableEntitiy#addRights(eu.etaxonomy.cdm.model.media.Rights)
169 */
170 public void addRights(Rights right){
171 this.rights.add(right);
172 }
173 /* (non-Javadoc)
174 * @see eu.etaxonomy.cdm.model.common.IIdentifiableEntitiy#removeRights(eu.etaxonomy.cdm.model.media.Rights)
175 */
176 public void removeRights(Rights right){
177 this.rights.remove(right);
178 }
179
180 /* (non-Javadoc)
181 * @see eu.etaxonomy.cdm.model.common.IIdentifiableEntitiy#getExtensions()
182 */
183 @OneToMany//(mappedBy="extendedObj")
184 @Cascade({CascadeType.SAVE_UPDATE})
185 public Set<Extension> getExtensions(){
186 return this.extensions;
187 }
188 protected void setExtensions(Set<Extension> extensions) {
189 this.extensions = extensions;
190 }
191 /* (non-Javadoc)
192 * @see eu.etaxonomy.cdm.model.common.IIdentifiableEntitiy#addExtension(eu.etaxonomy.cdm.model.common.Extension)
193 */
194 public void addExtension(Extension extension){
195 this.extensions.add(extension);
196 }
197 /* (non-Javadoc)
198 * @see eu.etaxonomy.cdm.model.common.IIdentifiableEntitiy#removeExtension(eu.etaxonomy.cdm.model.common.Extension)
199 */
200 public void removeExtension(Extension extension){
201 this.extensions.remove(extension);
202 }
203
204
205 /* (non-Javadoc)
206 * @see eu.etaxonomy.cdm.model.common.IIdentifiableEntitiy#isProtectedTitleCache()
207 */
208 public boolean isProtectedTitleCache() {
209 return protectedTitleCache;
210 }
211
212 /* (non-Javadoc)
213 * @see eu.etaxonomy.cdm.model.common.IIdentifiableEntitiy#setProtectedTitleCache(boolean)
214 */
215 public void setProtectedTitleCache(boolean protectedTitleCache) {
216 this.protectedTitleCache = protectedTitleCache;
217 }
218
219 /* (non-Javadoc)
220 * @see eu.etaxonomy.cdm.model.common.IIdentifiableEntitiy#getSources()
221 */
222 @OneToMany //(mappedBy="sourcedObj")
223 @Cascade({CascadeType.SAVE_UPDATE})
224 public Set<OriginalSource> getSources() {
225 return this.sources;
226 }
227 protected void setSources(Set<OriginalSource> sources) {
228 this.sources = sources;
229 }
230 /* (non-Javadoc)
231 * @see eu.etaxonomy.cdm.model.common.IIdentifiableEntitiy#addSource(eu.etaxonomy.cdm.model.common.OriginalSource)
232 */
233 public void addSource(OriginalSource source) {
234 if (source != null){
235 IdentifiableEntity oldSourcedObj = source.getSourcedObj();
236 if (oldSourcedObj != null && oldSourcedObj != this){
237 oldSourcedObj.getSources().remove(source);
238 }
239 this.sources.add(source);
240 source.setSourcedObj(this);
241 }
242 }
243 /* (non-Javadoc)
244 * @see eu.etaxonomy.cdm.model.common.IIdentifiableEntitiy#removeSource(eu.etaxonomy.cdm.model.common.OriginalSource)
245 */
246 public void removeSource(OriginalSource source) {
247 this.sources.remove(source);
248 }
249
250 /* (non-Javadoc)
251 * @see eu.etaxonomy.cdm.model.common.IIdentifiableEntitiy#toString()
252 */
253 @Override
254 public String toString() {
255 String result;
256 if (titleCache == null){
257 result = super.toString();
258 }else{
259 result = this.titleCache;
260 }
261 return result;
262 }
263
264 //****************** CLONE ************************************************/
265
266 /* (non-Javadoc)
267 * @see eu.etaxonomy.cdm.model.common.AnnotatableEntity#clone()
268 */
269 @Override
270 public Object clone() throws CloneNotSupportedException{
271 IdentifiableEntity result = (IdentifiableEntity)super.clone();
272
273 //Extensions
274 Set<Extension> newExtensions = getNewExtensionSet();
275 for (Extension extension : this.extensions ){
276 Extension newExtension = extension.clone(this);
277 newExtensions.add(newExtension);
278 }
279 result.setExtensions(newExtensions);
280
281 //OriginalSources
282 Set<OriginalSource> newOriginalSources = getNewOriginalSourcesSet();
283 for (OriginalSource originalSource : this.sources){
284 OriginalSource newSource = originalSource.clone(this);
285 newOriginalSources.add(newSource);
286 }
287 result.setSources(newOriginalSources);
288
289 //Rights
290 Set<Rights> rights = getNewRightsSet();
291 rights.addAll(this.rights);
292 result.setRights(rights);
293
294 //result.setLsid(lsid);
295 //result.setTitleCache(titleCache);
296 //result.setProtectedTitleCache(protectedTitleCache); //must be after setTitleCache
297
298 //no changes to: lsid, titleCache, protectedTitleCache
299 return result;
300 }
301
302 @Transient
303 private Set<Extension> getNewExtensionSet(){
304 return new HashSet<Extension>();
305 }
306
307 @Transient
308 private Set<OriginalSource> getNewOriginalSourcesSet(){
309 return new HashSet<OriginalSource>();
310 }
311
312 @Transient
313 private Set<Rights> getNewRightsSet(){
314 return new HashSet<Rights>();
315 }
316
317 }