1 /*
2 * Copyright (c) 2003
3 * Information Desire GmbH
4 * All rights reserved.
5 */
6 package com.infodesire.infobit.dao;
7
8 import com.infodesire.infobit.security.SecurityProvider;
9 import com.infodesire.infobit.hibernate.SessionProvider;
10
11 import com.infodesire.infobit.data.Infobit;
12 import com.infodesire.infobit.data.Version;
13 import com.infodesire.infobit.data.Acl;
14 import com.infodesire.infobit.data.Content;
15 import com.infodesire.infobit.data.PrimitiveContent;
16 import com.infodesire.infobit.data.Keyworded;
17
18 import com.infodesire.infobit.InfobitException;
19 import com.infodesire.infobit.InfobitSecurityException;
20 import com.infodesire.infobit.InfobitManager;
21
22 import java.io.Serializable;
23 import java.io.InputStream;
24 import java.io.ByteArrayInputStream;
25 import java.io.IOException;
26
27 import net.sf.hibernate.Session;
28 import net.sf.hibernate.Hibernate;
29 import net.sf.hibernate.Transaction;
30 import net.sf.hibernate.HibernateException;
31
32 import org.apache.commons.logging.Log;
33 import org.apache.commons.logging.LogFactory;
34
35 import java.util.List;
36 import java.util.HashMap;
37 import java.util.Set;
38 import java.util.Date;
39 import java.util.Map;
40 import java.util.Collection;
41
42 import java.sql.Blob;
43 import java.sql.SQLException;
44 /***
45 * DAO for infobits - encapsulates infobit creation and manipulation as well as
46 * accsess control
47 *
48 * @author konstantin
49 * @created August 7, 2003
50 * @version $Revision: 1.18 $
51 * @todo security testing is disabled due to uncertainities in
52 * inplementation
53 * @todo improve exception handling for lazy loaded collections
54 */
55 public final class InfobitDAO extends BaseDAO implements InfobitManager {
56 private static Log _log = LogFactory.getLog(InfobitDAO.class);
57
58 private final static String ATTRIBUTE_PREFIX = "attribute['";
59 private final static String ATTRIBUTE_SUFFIX = "']";
60 private final static String AND = " and ";
61 private final static String OR = " or ";
62 private final static String ORDER_BY = " order by ";
63 private final static String COMMA = ", ";
64 private final static String QUERY_INFOBITS = "from infobit in class com.infodesire.infobit.dao.InfobitImpl where ";
65
66
67 /***
68 * Constructor for the InfobitDAO object
69 *
70 * @param sec security provider
71 * @param sess session provider
72 */
73 public InfobitDAO(SecurityProvider sec, SessionProvider sess) {
74 super(sec, sess);
75 }
76
77
78 /***
79 * Gets the String attribute of the InfobitDAO object
80 *
81 * @param content Description of Parameter
82 * @return The String value
83 * @exception InfobitException Description of Exception
84 * @exception InfobitSecurityException Description of Exception
85 */
86 public String getString(PrimitiveContent content) throws InfobitException, InfobitSecurityException {
87 return new String(getBytes(content));
88 }
89
90
91 /***
92 * load infobit by name
93 *
94 * @param name name of infobit
95 * @return infobit instance
96 * @exception InfobitException will be thrown is something wrong happens.
97 */
98 public Infobit getInfobit(String name) throws InfobitException {
99 Infobit ib = null;
100 Session sess = null;
101 HashMap params = new HashMap();
102 params.put("name", name);
103 try {
104 List ilist = performQuery("infobitById", params);
105 if (ilist.size() > 0) {
106 ib = (Infobit) ilist.get(0);
107 }
108 } catch (Exception ex) {
109 _log.error("error loading infobit with name: " + name, ex);
110 throw new InfobitException("error loading infobit with name: " + name, ex);
111 }
112
113 return ib;
114 }
115
116
117 /***
118 * return contents of primitive element as binary stream. resulting stream
119 * is coming out of blob, and shall be used ASAP and in any case inside the
120 * same transaction. Intendet use is to stream this content out to web
121 * client.
122 *
123 * @param content Description of Parameter
124 * @return The Content value
125 * @exception InfobitException Description of Exception
126 * @exception InfobitSecurityException Description of Exception
127 */
128 public InputStream getContent(PrimitiveContent content) throws InfobitException, InfobitSecurityException {
129 if (!(content instanceof LongContentImpl)) {
130 throw new InfobitException("supplied content is of wrong type");
131 }
132
133 LongContentImpl lci = null;
134
135 try {
136 lci = (LongContentImpl) doLoad(content.getClass(), ((BaseEntityImpl) content).getId());
137 return lci.getData().getBinaryStream();
138 } catch (Exception ex) {
139 _log.error("error loading content for infobit", ex);
140 throw new InfobitException("error loading content for infobit", ex);
141 }
142 }
143
144
145 /***
146 * Gets the size of the content.
147 *
148 * @param content The content the size of which to
149 * query
150 * @return The size of <content>
151 * @exception InfobitException Description of Exception
152 * @exception InfobitSecurityException Description of Exception
153 */
154 public int getContentLength(PrimitiveContent content)
155 throws InfobitException, InfobitSecurityException {
156
157 if (!(content instanceof LongContentImpl)) {
158 throw new InfobitException("supplied content is of wrong type");
159 }
160
161 LongContentImpl lci = null;
162
163 try {
164 lci = (LongContentImpl) doLoad(content.getClass(),
165 ((BaseEntityImpl) content).getId());
166 // NOTE: createContent asserts content fits to int range
167 return (int) lci.getData().length();
168 } catch (Exception ex) {
169 _log.error("error loading content for infobit", ex);
170 throw new InfobitException("error loading content for infobit", ex);
171 }
172 }
173
174
175 /***
176 * Gets the Bytes attribute of the InfobitDAO object
177 *
178 * @param content Description of Parameter
179 * @return The Bytes value
180 * @exception InfobitException Description of Exception
181 * @exception InfobitSecurityException Description of Exception
182 */
183 public byte[] getBytes(PrimitiveContent content) throws InfobitException, InfobitSecurityException {
184 if (!(content instanceof LongContentImpl)) {
185 throw new InfobitException("supplied content is of wrong type");
186 }
187
188 LongContentImpl lci = null;
189
190 try {
191 lci = (LongContentImpl) doLoad(content.getClass(), ((BaseEntityImpl) content).getId());
192 Blob blob = lci.getData();
193 if (_log.isDebugEnabled()) {
194 _log.debug("blob length is: " + blob.length());
195 }
196 return blob.getBytes(1, (int) blob.length());
197 } catch (Exception ex) {
198 _log.error("error loading content for infobit", ex);
199 throw new InfobitException("error loading content for infobit", ex);
200 }
201 }
202
203
204 /***
205 * set infobit attrobute. to remove infobit attribute set it to null
206 *
207 * @param name attribute name
208 * @param value attribute value
209 * @param infobit The new Attribute value
210 * @exception InfobitException will be thrown if something wrong
211 * happens
212 * @exception InfobitSecurityException will be thrown on insufficient
213 * security permissions
214 */
215 public void setAttribute(Infobit infobit, String name, String value) throws InfobitException, InfobitSecurityException {
216 if (!(infobit instanceof AttributeSettable)) {
217 throw new InfobitException("supplied infobit object is of wrong type");
218 }
219 setAttribute((AttributeSettable) infobit, name, value);
220 }
221
222
223 /***
224 * Sets the Attribute attribute of the Content object
225 *
226 * @param content content object
227 * @param name attribute name
228 * @param value attribute value
229 * @exception InfobitException will be thrown if something wrong
230 * happens
231 * @exception InfobitSecurityException will be thrown on insufficient
232 * security permissions
233 */
234 public void setAttribute(Content content, String name, String value) throws InfobitException, InfobitSecurityException {
235 if (!(content instanceof AttributeSettable)) {
236 throw new InfobitException("supplied infobit object is of wrong type");
237 }
238 setAttribute((AttributeSettable) content, name, value);
239 }
240
241
242 /***
243 * Sets the ActualVersion attribute of the InfobitDAO object
244 *
245 * @param ib The new ActualVersion value
246 * @param version The new ActualVersion value
247 * @exception InfobitException Description of Exception
248 * @exception InfobitSecurityException Description of Exception
249 */
250 public void setActualVersion(Infobit ib, Version version) throws InfobitException, InfobitSecurityException {
251 if (!ib.equals(version.getInfobit())) {
252 throw new InfobitException("can not set actual version because not on this infobit");
253 }
254 InfobitImpl ibit = (InfobitImpl) ib;
255 ibit.setActualVersion(version);
256 try {
257 doUpdate(ibit);
258 } catch (Exception ex) {
259 _log.error("error happened while setting of actual version", ex);
260 throw new InfobitException("error happened while setting of actual version", ex);
261 }
262 }
263
264
265
266 /***
267 * perform query on infobits. supply only where clause
268 *
269 * @param where Description of Parameter
270 * @return Description of the Returned Value
271 * @exception InfobitException Description of Exception
272 * @exception InfobitSecurityException Description of Exception
273 */
274 public Collection queryInfobits(String where) throws InfobitException, InfobitSecurityException {
275 String resQuery = QUERY_INFOBITS + where;
276 try {
277 return performQuery(resQuery);
278 } catch (Exception ex) {
279 _log.error("error performing query: " + resQuery, ex);
280 throw new InfobitException("error performing query: " + resQuery, ex);
281 }
282 }
283
284
285
286 /***
287 * whether given infobit exists
288 *
289 * @param name Description of Parameter
290 * @return infobit existence status
291 * @exception InfobitException canb be thrown if something wents wrong
292 */
293 public boolean hasInfobit(String name) throws InfobitException {
294 return getInfobit(name) != null;
295 }
296
297
298 /***
299 * remove infobit instance.
300 *
301 * @param name Description of Parameter
302 * @exception InfobitException Description of Exception
303 * @exception InfobitSecurityException Description of Exception
304 */
305 public void removeInfobit(String name) throws InfobitException, InfobitSecurityException {
306 Infobit ib = getInfobit(name);
307 if (ib != null) {
308 removeInfobit(ib);
309 }
310 }
311
312
313 /***
314 * remove infobit from existence. if possible
315 *
316 * @param ib Description of Parameter
317 * @exception InfobitException Description of Exception
318 * @exception InfobitSecurityException Description of Exception
319 */
320 public void removeInfobit(Infobit ib) throws InfobitException, InfobitSecurityException {
321 /*
322 * if (!getSecurityProvider().hasRole(ib.getAcl().getRoles(Infobit.REMOVE_PERMISSION))) {
323 * throw new InfobitSecurityException("not allowed to assign this acl to infobits");
324 * }
325 */
326 try {
327 doRemove(ib);
328 } catch (Exception ex) {
329 _log.error("exception while removing infobit. roll back transaction", ex);
330 throw new InfobitException("exception while removing infobit.", ex);
331 }
332
333 }
334
335
336 /***
337 * create new infobit
338 *
339 * @param id string id of infobit
340 * @param acl Description of Parameter
341 * @return Description of the Returned Value
342 * @exception InfobitException will be thrown if something went
343 * wrong
344 * @exception InfobitSecurityException Description of Exception
345 */
346 public Infobit createInfobit(String id, Acl acl) throws InfobitException, InfobitSecurityException {
347 /*
348 * if (!getSecurityProvider().hasRole(acl.getRoles(Infobit.CREATE_PERMISSION))) {
349 * throw new InfobitSecurityException("not allowed to assign this acl to infobits");
350 * }
351 */
352 if (_log.isDebugEnabled()) {
353 _log.debug("create infobit with name: " + id);
354 }
355 InfobitImpl ib = new InfobitImpl();
356 ib.setAcl((AclImpl) acl);
357 ib.setName(id);
358 try {
359 doCreate(ib);
360 } catch (Exception ex) {
361 _log.error("error creating infobit", ex);
362 throw new InfobitException("error creating infobit", ex);
363 }
364 return ib;
365 }
366
367
368 /***
369 * create new version with textual content.
370 *
371 * @param ib infobit
372 * @param name unique version name ( within given
373 * infobit )
374 * @param keywords keywords for searching. shall
375 * contain strings
376 * @param text textual content of infobit
377 * @return Description of the Returned Value
378 * @exception InfobitException when some problem occurs
379 * @exception InfobitSecurityException when insufficient permissions.
380 */
381 public Version createText(Infobit ib, String name, String text, Set keywords) throws InfobitException, InfobitSecurityException {
382 TextContentImpl timpl = new TextContentImpl();
383 timpl.setData(Hibernate.createBlob(text.getBytes()));
384 timpl.setKeywords(keywords);
385 return createVersion(ib, name, timpl);
386 }
387
388
389
390 /***
391 * create binary infobit content
392 *
393 * @param ib infobit
394 * @param name unique version name ( within given
395 * infobit )
396 * @param stream stream containing binary data
397 * @param mime mime type
398 * @param keywords keywords for searching . shall
399 * contain strings
400 * @return Description of the Returned Value
401 * @exception InfobitException when some problem occurs
402 * @exception InfobitSecurityException when insufficient permissions.
403 */
404 public Version createBinary(Infobit ib, String name, InputStream stream, String mime, Set keywords) throws InfobitException, InfobitSecurityException {
405
406 try {
407 BinaryContentImpl bimpl = new BinaryContentImpl();
408 Blob data = Hibernate.createBlob(stream);
409
410 if (_log.isDebugEnabled()) {
411 _log.debug("blob size is: " + data.length());
412 }
413 if (data.length() > Integer.MAX_VALUE) {
414 String m = "Infobit " + ib.getName() + " version " + name +
415 ": binary content too long (exceeds int range)";
416 _log.error(m);
417 throw new InfobitException(m);
418 }
419
420 bimpl.setData(data);
421 bimpl.setKeywords(keywords);
422
423 bimpl.setMimeType(mime);
424 bimpl.setSize((int) data.length());
425
426 return createVersion(ib, name, bimpl);
427 } catch (IOException e) {
428 String m = "error loading binary content for infobit: " +
429 ib.getName() + ", version: " + name;
430 _log.error(m, e);
431 throw new InfobitException(m, e);
432 } catch (SQLException e) {
433 // raised from data.length()
434 String m = "database error creating version " + ib.getName() +
435 " version " + name;
436 _log.error(m, e);
437 throw new InfobitException(m, e);
438 }
439 }
440
441
442 /***
443 * create binary infobit content
444 *
445 * @param ib infobit
446 * @param name unique version name ( within given
447 * infobit )
448 * @param data array coontaining binary data
449 * @param mime mime type
450 * @param keywords keywords for searching. shall
451 * contain strings
452 * @return Description of the Returned Value
453 * @exception InfobitException when some problem occurs
454 * @exception InfobitSecurityException when insufficient permissions.
455 */
456 public Version createBinary(Infobit ib, String name, byte[] data, String mime, Set keywords) throws InfobitException, InfobitSecurityException {
457 return createBinary(ib, name, new ByteArrayInputStream(data), mime, keywords);
458 }
459
460
461 /***
462 * create template for scripts. template does not have any keywords. it does
463 * not need them
464 *
465 * @param ib infobit
466 * @param name unique version name ( within given
467 * infobit )
468 * @param text template text
469 * @return Description of the Returned Value
470 * @exception InfobitException when some problem occurs
471 * @exception InfobitSecurityException when insufficient permissions.
472 */
473 public Version createTemplate(Infobit ib, String name, String text) throws InfobitException, InfobitSecurityException {
474 TemplateImpl timpl = new TemplateImpl();
475 timpl.setData(Hibernate.createBlob(text.getBytes()));
476 return createVersion(ib, name, timpl);
477 }
478
479
480 /***
481 * create script.
482 *
483 * @param ib infobit
484 * @param name unique version name ( within given
485 * infobit )
486 * @param template template infobit
487 * @param links map of links to be merged with
488 * template. shall be keyed by strings and contain infobits
489 * @param keywords keywords for searching. shall
490 * contain strings
491 * @return Description of the Returned Value
492 * @exception InfobitException Description of Exception
493 * @exception InfobitSecurityException Description of Exception
494 */
495 public Version createScript(Infobit ib, String name, Infobit template, Map links, Set keywords) throws InfobitException, InfobitSecurityException {
496 ScriptImpl impl = new ScriptImpl();
497 impl.setTemplate(template);
498 impl.setLinksImpl(links);
499 impl.setKeywords(keywords);
500 return createVersion(ib, name, impl);
501 }
502
503
504 /***
505 * Sets the Attribute attribute of the attribute settable object
506 *
507 * @param name The new Attribute value
508 * @param value The new Attribute value
509 * @param settable The new Attribute value
510 * @exception InfobitException Description of Exception
511 * @exception InfobitSecurityException Description of Exception
512 */
513 void setAttribute(AttributeSettable settable, String name, String value) throws InfobitException, InfobitSecurityException {
514
515 settable.getAttributes().put(name, value);
516 try {
517 doUpdate(settable);
518 } catch (Exception ex) {
519 _log.error("error happened while setting attribute", ex);
520 throw new InfobitException("error happened while setting attribute", ex);
521 }
522
523 }
524
525
526 /***
527 * create new version for this infobit.
528 *
529 * @param ib Description of Parameter
530 * @param name Description of Parameter
531 * @param content Description of Parameter
532 * @return Description of the Returned Value
533 * @exception InfobitException Description of Exception
534 * @exception InfobitSecurityException Description of Exception
535 */
536 Version createVersion(Infobit ib, String name, ContentImpl content) throws InfobitException, InfobitSecurityException {
537 VersionImpl version = new VersionImpl();
538 InfobitImpl ibit = (InfobitImpl) ib;
539 version.setName(name);
540 version.setAuthor(getSecurityProvider().getName());
541 version.setContent(content);
542 version.setDate(new Date());
543
544 content.setVersion(version);
545
546 ibit.addVersion(version);
547
548 try {
549 if (_log.isDebugEnabled()) {
550 _log.debug("creating version : " + version.getId());
551 }
552 doCreate(version);
553 if (_log.isDebugEnabled()) {
554 _log.debug("version created: " + version.getId());
555 }
556 // we must create it separately, because we can not cascade to
557 // one-to-one, we must be sure that id for version was already generated
558 doCreate(content);
559 if (_log.isDebugEnabled()) {
560 _log.debug("created content");
561 }
562
563 } catch (Exception ex) {
564 _log.error("error happened while creation of infobit version", ex);
565 throw new InfobitException("error happened while creation of infobit version", ex);
566 }
567 // try to force load of lazy colection
568
569
570 return version;
571 }
572 }
This page was automatically generated by Maven