View Javadoc

1   /*
2    * HibernateMapping.java
3    *
4    * Created on June 16, 2005, 4:22 PM
5    *
6    * To change this template, choose Tools | Options and locate the template under
7    * the Source Creation and Management node. Right-click the template and choose
8    * Open. You can then make changes to the template in the Source Editor.
9    */
10  
11  package gov.bnl.gums.db;
12  
13  
14  import gov.bnl.gums.persistence.HibernatePersistenceFactory;
15  
16  import java.util.Hashtable;
17  import java.util.Iterator;
18  import java.util.List;
19  import java.util.Map;
20  
21  import net.sf.hibernate.Query;
22  import net.sf.hibernate.Session;
23  import net.sf.hibernate.Transaction;
24  import net.sf.hibernate.type.StringType;
25  import net.sf.hibernate.type.Type;
26  
27  import org.apache.commons.logging.Log;
28  import org.apache.commons.logging.LogFactory;
29  
30  /**
31   *
32   * @author Gabriele Carcassi, Jay Packard
33   */
34  public class HibernateAccountMapperDB implements ManualAccountMapperDB, AccountPoolMapperDB {
35      private Log log = LogFactory.getLog(HibernateAccountMapperDB.class);
36      private HibernatePersistenceFactory persistenceFactory;
37      private String map;
38      private boolean needsCacheRefresh = true;
39      
40      /** Creates a new instance of HibernateMapping */
41      public HibernateAccountMapperDB(HibernatePersistenceFactory persistenceFactory, String map) {
42          this.persistenceFactory = persistenceFactory;
43          this.map = map;
44      }
45  
46      public void addAccount(String account) {
47          Session session = null;
48          Transaction tx = null;
49          try {
50              log.trace("Adding account '" + account + "' to pool '" + map + "'");
51              session = persistenceFactory.retrieveSessionFactory().openSession();
52              tx = session.beginTransaction();
53              HibernateMapping map = retrieveMapping(session, tx, null, account);
54              if (map != null) {
55                  return;
56              }
57              createMapping(session, tx, null, account);
58              tx.commit();
59          // Handles when transaction goes wrong...
60          } catch (Exception e) {
61              log.error("Couldn't add account to pool '" + map + "'", e);
62              if (tx != null) {
63                  try {
64                      tx.rollback();
65                  } catch (Exception e1) {
66                      log.error("Hibernate error: rollback failed", e1);
67                      throw new RuntimeException("Database errors: " + e.getMessage() + " - " + e1.getMessage(), e);
68                  }
69              }
70              throw new RuntimeException("Database error: " + e.getMessage(), e);
71          } finally {
72              if (session != null) {
73                  try {
74                      session.close();
75                  } catch (Exception e1) {
76                      log.error("Hibernate error: couldn't close session", e1);
77                      throw new RuntimeException("Database error: " + e1.getMessage(), e1);
78                  }
79              }
80          }
81      }
82      
83      public String assignAccount(String userDN) {
84          Session session = null;
85          Transaction tx = null;
86          try {
87              log.trace("Assing an account to '" + userDN + "' from pool '" + map + "'");
88              session = persistenceFactory.retrieveSessionFactory().openSession();
89              tx = session.beginTransaction();
90              Query q;
91              q = session.createQuery("FROM HibernateMapping m WHERE m.map = ? AND m.dn is null ORDER BY m.account LIMIT 1");
92              q.setString(0, map);
93              HibernateMapping mapping = (HibernateMapping) q.uniqueResult();
94              if (mapping == null) {
95                  tx.commit();
96                  return null;
97              }
98              mapping.setDn(userDN);
99              tx.commit();
100             return mapping.getAccount();
101         // Handles when transaction goes wrong...
102         } catch (Exception e) {
103             log.error("Couldn't assign account to '" + userDN + "' from pool '" + map + "'", e);
104             if (tx != null) {
105                 try {
106                     tx.rollback();
107                 } catch (Exception e1) {
108                     log.error("Hibernate error: rollback failed", e1);
109                     throw new RuntimeException("Database errors: " + e.getMessage() + " - " + e1.getMessage(), e);
110                 }
111             }
112             throw new RuntimeException("Database error: " + e.getMessage(), e);
113         } finally {
114             if (session != null) {
115                 try {
116                     session.close();
117                 } catch (Exception e1) {
118                     log.error("Hibernate error: couldn't close session", e1);
119                     throw new RuntimeException("Database error: " + e1.getMessage(), e1);
120                 }
121             }
122         }
123     }
124 
125     public void createMapping(String userDN, String account) {
126         Session session = null;
127         Transaction tx = null;
128         try {
129             log.trace("Creating mapping for map '" + map + "' DN '" + userDN + "' -> '" + account + "'");
130             session = persistenceFactory.retrieveSessionFactory().openSession();
131             tx = session.beginTransaction();
132             HibernateMapping map = retrieveMapping(session, tx, userDN, account);
133             if (map != null) {
134                 return;
135             }
136             createMapping(session, tx, userDN, account);
137             tx.commit();
138         // Handles when transaction goes wrong...
139         } catch (Exception e) {
140             log.error("Couldn't create mapping to '" + map + "'", e);
141             if (tx != null) {
142                 try {
143                     tx.rollback();
144                 } catch (Exception e1) {
145                     log.error("Hibernate error: rollback failed", e1);
146                     throw new RuntimeException("Database errors: " + e.getMessage() + " - " + e1.getMessage(), e);
147                 }
148             }
149             throw new RuntimeException("Database error: " + e.getMessage(), e);
150         } finally {
151             if (session != null) {
152                 try {
153                     session.close();
154                 } catch (Exception e1) {
155                     log.error("Hibernate error: couldn't close session", e1);
156                     throw new RuntimeException("Database error: " + e1.getMessage(), e1);
157                 }
158             }
159         }
160     }
161     
162     public boolean needsCacheRefresh() {
163     	return needsCacheRefresh;
164     }
165 
166     public boolean removeAccount(String account) {
167         Session session = null;
168         Transaction tx = null;
169         try {
170             log.trace("Removing mapping from map '" + map + "' for account '" + account + "'");
171             session = persistenceFactory.retrieveSessionFactory().openSession();
172             tx = session.beginTransaction();
173             boolean result = removeAccount(session, tx, account);
174             tx.commit();
175             return result;
176         // Handles when transaction goes wrong...
177         } catch (Exception e) {
178             log.error("Couldn't remove mapping from '" + map + "' for account '" + account + "'", e);
179             if (tx != null) {
180                 try {
181                     tx.rollback();
182                 } catch (Exception e1) {
183                     log.error("Hibernate error: rollback failed", e1);
184                     throw new RuntimeException("Database errors: " + e.getMessage() + " - " + e1.getMessage(), e);
185                 }
186             }
187             throw new RuntimeException("Database error: " + e.getMessage(), e);
188         } finally {
189             if (session != null) {
190                 try {
191                     session.close();
192                 } catch (Exception e1) {
193                     log.error("Hibernate error: couldn't close session", e1);
194                     throw new RuntimeException("Database error: " + e1.getMessage(), e1);
195                 }
196             }
197         }
198     }
199         
200     public boolean removeMapping(String userDN) {
201         Session session = null;
202         Transaction tx = null;
203         try {
204             log.trace("Removing mapping from map '" + map + "' for DN '" + userDN + "'");
205             session = persistenceFactory.retrieveSessionFactory().openSession();
206             tx = session.beginTransaction();
207             boolean result = removeMapping(session, tx, userDN);
208             tx.commit();
209             return result;
210         // Handles when transaction goes wrong...
211         } catch (Exception e) {
212             log.error("Couldn't remove mapping from '" + map + "' for DN '" + userDN + "'", e);
213             if (tx != null) {
214                 try {
215                     tx.rollback();
216                 } catch (Exception e1) {
217                     log.error("Hibernate error: rollback failed", e1);
218                     throw new RuntimeException("Database errors: " + e.getMessage() + " - " + e1.getMessage(), e);
219                 }
220             }
221             throw new RuntimeException("Database error: " + e.getMessage(), e);
222         } finally {
223             if (session != null) {
224                 try {
225                     session.close();
226                 } catch (Exception e1) {
227                     log.error("Hibernate error: couldn't close session", e1);
228                     throw new RuntimeException("Database error: " + e1.getMessage(), e1);
229                 }
230             }
231         }
232     }
233 
234     public String retrieveAccount(String userDN) {
235         Session session = null;
236         Transaction tx = null;
237         try {
238             log.trace("Retrieving account for user '" + userDN + "' from pool '" + map + "'");
239             session = persistenceFactory.retrieveSessionFactory().openSession();
240             tx = session.beginTransaction();
241             Query q;
242             q = session.createQuery("FROM HibernateMapping m WHERE m.map = ? AND m.dn = ? ORDER BY m.account LIMIT 1");
243             q.setString(0, map);
244             q.setString(1, userDN);
245             HibernateMapping mapping = (HibernateMapping) q.uniqueResult();
246             tx.commit();
247             if (mapping == null) return null;
248             return mapping.getAccount();
249         // Handles when transaction goes wrong...
250         } catch (Exception e) {
251             log.error("Couldn't retrieve account for user '" + userDN + "' from pool '" + map + "'", e);
252             if (tx != null) {
253                 try {
254                     tx.rollback();
255                 } catch (Exception e1) {
256                     log.error("Hibernate error: rollback failed", e1);
257                     throw new RuntimeException("Database errors: " + e.getMessage() + " - " + e1.getMessage(), e);
258                 }
259             }
260             throw new RuntimeException("Database error: " + e.getMessage(), e);
261         } finally {
262             if (session != null) {
263                 try {
264                     session.close();
265                 } catch (Exception e1) {
266                     log.error("Hibernate error: couldn't close session", e1);
267                     throw new RuntimeException("Database error: " + e1.getMessage(), e1);
268                 }
269             }
270         }
271     }
272 
273     public java.util.Map retrieveAccountMap() {
274         Session session = null;
275         Transaction tx = null;
276         try {
277             log.trace("Retrieving map for pool '" + map + "'");
278             session = persistenceFactory.retrieveSessionFactory().openSession();
279             tx = session.beginTransaction();
280             Query q;
281             q = session.createQuery("FROM HibernateMapping m WHERE m.map = ? AND m.dn is not null");
282             q.setString(0, map);
283             List mappings = (List) q.list();
284             Iterator iter = mappings.iterator();
285             Map map = new Hashtable();
286             while (iter.hasNext()) {
287                 HibernateMapping mapping = (HibernateMapping) iter.next();
288                 map.put(mapping.getDn(), mapping.getAccount());
289             }
290             tx.commit();
291             return map;
292         // Handles when transaction goes wrong...
293         } catch (Exception e) {
294             log.error("Couldn't retrieve map for pool '" + map + "'", e);
295             if (tx != null) {
296                 try {
297                     tx.rollback();
298                 } catch (Exception e1) {
299                     log.error("Hibernate error: rollback failed", e1);
300                     throw new RuntimeException("Database errors: " + e.getMessage() + " - " + e1.getMessage(), e);
301                 }
302             }
303             throw new RuntimeException("Database error: " + e.getMessage(), e);
304         } finally {
305             if (session != null) {
306                 try {
307                     session.close();
308                 } catch (Exception e1) {
309                     log.error("Hibernate error: couldn't close session", e1);
310                     throw new RuntimeException("Database error: " + e1.getMessage(), e1);
311                 }
312             }
313         }
314     }
315 
316     public String retrieveMapping(String userDN) {
317         Session session = null;
318         Transaction tx = null;
319         try {
320             log.trace("Retrieving mapping from map '" + map + "' for DN '" + userDN + "'");
321             session = persistenceFactory.retrieveSessionFactory().openSession();
322             tx = session.beginTransaction();
323             HibernateMapping map = retrieveMapping(session, tx, userDN);
324             tx.commit();
325             if (map == null) return null;
326             return map.getAccount();
327         // Handles when transaction goes wrong...
328         } catch (Exception e) {
329             log.error("Couldn't retrieve mapping from '" + map + "' for DN '" + userDN + "'", e);
330             if (tx != null) {
331                 try {
332                     tx.rollback();
333                 } catch (Exception e1) {
334                     log.error("Hibernate error: rollback failed", e1);
335                     throw new RuntimeException("Database errors: " + e.getMessage() + " - " + e1.getMessage(), e);
336                 }
337             }
338             throw new RuntimeException("Database error: " + e.getMessage(), e);
339         } finally {
340             if (session != null) {
341                 try {
342                     session.close();
343                 } catch (Exception e1) {
344                     log.error("Hibernate error: couldn't close session", e1);
345                     throw new RuntimeException("Database error: " + e1.getMessage(), e1);
346                 }
347             }
348         }
349     }
350     
351     public java.util.List retrieveMappings() {
352         Session session = null;
353         Transaction tx = null;
354         try {
355             // Retrieving members from the db
356             log.trace("Retrieving mappings from map " + map);
357             session = persistenceFactory.retrieveSessionFactory().openSession();
358             tx = session.beginTransaction();
359             List mappings = retrieveMappings(session, tx);
360             tx.commit();
361             return mappings;
362         // Handles when transaction goes wrong...
363         } catch (Exception e) {
364             log.error("Couldn't retrieve members from map " + map, e);
365             if (tx != null) {
366                 try {
367                     tx.rollback();
368                 } catch (Exception e1) {
369                     log.error("Hibernate error: rollback failed", e1);
370                     throw new RuntimeException("Database errors: " + e.getMessage() + " - " + e1.getMessage(), e);
371                 }
372             }
373             throw new RuntimeException("Database error: " + e.getMessage(), e);
374         } finally {
375             if (session != null) {
376                 try {
377                     session.close();
378                 } catch (Exception e1) {
379                     log.error("Hibernate error: couldn't close session", e1);
380                     throw new RuntimeException("Database error: " + e1.getMessage(), e1);
381                 }
382             }
383         }
384     }
385 
386     public java.util.Map retrieveReverseAccountMap() {
387         Session session = null;
388         Transaction tx = null;
389         try {
390             log.trace("Retrieving reverse map for pool '" + map + "'");
391             session = persistenceFactory.retrieveSessionFactory().openSession();
392             tx = session.beginTransaction();
393             Query q;
394             q = session.createQuery("FROM HibernateMapping m WHERE m.map = ? AND m.account is not null");
395             q.setString(0, map);
396             List mappings = (List) q.list();
397             Iterator iter = mappings.iterator();
398             Map reverseMap = new Hashtable();
399             while (iter.hasNext()) {
400                 HibernateMapping mapping = (HibernateMapping) iter.next();
401                 reverseMap.put(mapping.getAccount(), mapping.getDn()!=null?mapping.getDn():"");
402             }
403             tx.commit();
404             return reverseMap;
405         // Handles when transaction goes wrong...
406         } catch (Exception e) {
407             log.error("Couldn't retrieve reverse map for pool '" + map + "'", e);
408             if (tx != null) {
409                 try {
410                     tx.rollback();
411                 } catch (Exception e1) {
412                     log.error("Hibernate error: rollback failed", e1);
413                     throw new RuntimeException("Database errors: " + e.getMessage() + " - " + e1.getMessage(), e);
414                 }
415             }
416             throw new RuntimeException("Database error: " + e.getMessage(), e);
417         } finally {
418             if (session != null) {
419                 try {
420                     session.close();
421                 } catch (Exception e1) {
422                     log.error("Hibernate error: couldn't close session", e1);
423                     throw new RuntimeException("Database error: " + e1.getMessage(), e1);
424                 }
425             }
426         }
427     }
428     
429     public java.util.List retrieveUsersNotUsedSince(java.util.Date date) {
430         throw new UnsupportedOperationException("retrieveUsersNotUsedSince is not supported anymore");
431     }
432 
433     public synchronized void setNeedsCacheRefresh(boolean value) {
434     	needsCacheRefresh = value;
435     }
436     
437     public void unassignAccount(String account) {
438         Session session = null;
439         Transaction tx = null;
440         try {
441             log.trace("Unassign account '" + account + "' from pool '" + map + "'");
442             session = persistenceFactory.retrieveSessionFactory().openSession();
443             tx = session.beginTransaction();
444             Query q;
445             q = session.createQuery("FROM HibernateMapping m WHERE m.map = ? AND m.account = ?");
446             q.setString(0, map);
447             q.setString(1, account);
448             List mappings = (List) q.list();
449             Iterator iter = mappings.iterator();
450             while (iter.hasNext()) {
451                 HibernateMapping mapping = (HibernateMapping) iter.next();
452                 mapping.setDn(null);
453             }
454             tx.commit();
455         // Handles when transaction goes wrong...
456         } catch (Exception e) {
457             log.error("Couldn't unassign account '" + account + "' from pool '" + map + "'", e);
458             if (tx != null) {
459                 try {
460                     tx.rollback();
461                 } catch (Exception e1) {
462                     log.error("Hibernate error: rollback failed", e1);
463                     throw new RuntimeException("Database errors: " + e.getMessage() + " - " + e1.getMessage(), e);
464                 }
465             }
466             throw new RuntimeException("Database error: " + e.getMessage(), e);
467         } finally {
468             if (session != null) {
469                 try {
470                     session.close();
471                 } catch (Exception e1) {
472                     log.error("Hibernate error: couldn't close session", e1);
473                     throw new RuntimeException("Database error: " + e1.getMessage(), e1);
474                 }
475             }
476         }
477     }
478     
479     public void unassignUser(String userDN) {
480         Session session = null;
481         Transaction tx = null;
482         try {
483             log.trace("Unassign account for user '" + userDN + "' from pool '" + map + "'");
484             session = persistenceFactory.retrieveSessionFactory().openSession();
485             tx = session.beginTransaction();
486             Query q;
487             q = session.createQuery("FROM HibernateMapping m WHERE m.map = ? AND m.dn = ? ORDER BY m.account LIMIT 1");
488             q.setString(0, map);
489             q.setString(1, userDN);
490             HibernateMapping mapping = (HibernateMapping) q.uniqueResult();
491             mapping.setDn(null);
492             tx.commit();
493         // Handles when transaction goes wrong...
494         } catch (Exception e) {
495             log.error("Couldn't unassign account for user '" + userDN + "' from pool '" + map + "'", e);
496             if (tx != null) {
497                 try {
498                     tx.rollback();
499                 } catch (Exception e1) {
500                     log.error("Hibernate error: rollback failed", e1);
501                     throw new RuntimeException("Database errors: " + e.getMessage() + " - " + e1.getMessage(), e);
502                 }
503             }
504             throw new RuntimeException("Database error: " + map + " " + userDN + " " + e.getMessage(), e);
505         } finally {
506             if (session != null) {
507                 try {
508                     session.close();
509                 } catch (Exception e1) {
510                     log.error("Hibernate error: couldn't close session", e1);
511                     throw new RuntimeException("Database error: " + e1.getMessage(), e1);
512                 }
513             }
514         }
515     }
516     
517     private void createMapping(Session session, Transaction tx, String userDN, String account) throws Exception {
518 	    HibernateMapping hMapping = new HibernateMapping();
519 	    hMapping.setMap(map);
520 	    hMapping.setDn(userDN);
521 	    hMapping.setAccount(account);
522 	    session.save(hMapping);
523         setNeedsCacheRefresh(true);
524     }
525 
526     private boolean removeAccount(Session session, Transaction tx, String account) throws Exception {
527         int n = session.delete("FROM HibernateMapping m WHERE m.map = ? AND m.account = ?", new Object[] {map, account}, new Type[] {new StringType(), new StringType()});
528         setNeedsCacheRefresh(true);
529         return n > 0;
530     }
531 
532     private boolean removeMapping(Session session, Transaction tx, String userDN) throws Exception {
533         int n = session.delete("FROM HibernateMapping m WHERE m.map = ? AND m.dn = ?", new Object[] {map, userDN}, new Type[] {new StringType(), new StringType()});
534         setNeedsCacheRefresh(true);
535         return n > 0;
536     }    
537     
538     private HibernateMapping retrieveMapping(Session session, Transaction tx, String userDN) throws Exception{
539         Query q;
540         q = session.createQuery("FROM HibernateMapping m WHERE m.map = ? AND m.dn = ?");
541         q.setString(0, map);
542         q.setString(1, userDN);
543         return (HibernateMapping) q.uniqueResult();
544     }
545     
546     private HibernateMapping retrieveMapping(Session session, Transaction tx, String userDN, String account) throws Exception{
547         Query q;
548         if (userDN!=null) {
549 	        q = session.createQuery("FROM HibernateMapping m WHERE m.map = ? AND m.dn = ? AND m.account = ? ");
550 	        q.setString(0, map);
551 	        q.setString(1, userDN);
552 	        q.setString(2, account);
553         }
554         else {
555 	        q = session.createQuery("FROM HibernateMapping m WHERE m.map = ? AND m.dn is null AND m.account = ? ");
556 	        q.setString(0, map);
557 	        q.setString(1, account);
558         }
559         return (HibernateMapping) q.uniqueResult();
560     }
561     
562     private java.util.List retrieveMappings(Session session, Transaction tx) throws Exception {
563         Query q;
564         q = session.createQuery("FROM HibernateMapping m WHERE m.map = ?");
565         q.setString(0, map);
566         List hibernateMappings = q.list();
567         return hibernateMappings;
568     }
569     
570 }