KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > hibernate > ejb > HibernatePersistence


1 //$Id: HibernatePersistence.java,v 1.34 2005/08/04 14:14:01 epbernard Exp $
2
package org.hibernate.ejb;
3
4 import java.io.DataInputStream JavaDoc;
5 import java.io.IOException JavaDoc;
6 import java.io.InputStream JavaDoc;
7 import java.net.URL JavaDoc;
8 import java.util.ArrayList JavaDoc;
9 import java.util.Collection JavaDoc;
10 import java.util.Enumeration JavaDoc;
11 import java.util.Iterator JavaDoc;
12 import java.util.List JavaDoc;
13 import java.util.Map JavaDoc;
14 import java.util.Properties JavaDoc;
15 import java.util.Set JavaDoc;
16 import java.util.StringTokenizer JavaDoc;
17 import javax.persistence.Embeddable;
18 import javax.persistence.EmbeddableSuperclass;
19 import javax.persistence.Entity;
20 import javax.persistence.EntityManagerFactory;
21 import javax.persistence.PersistenceException;
22 import javax.persistence.spi.PersistenceInfo;
23
24 import javassist.ClassPool;
25 import javassist.CtClass;
26 import javassist.LoaderClassPath;
27 import javassist.NotFoundException;
28 import javassist.bytecode.AnnotationsAttribute;
29 import javassist.bytecode.ClassFile;
30 import org.apache.commons.logging.Log;
31 import org.apache.commons.logging.LogFactory;
32 import org.hibernate.MappingException;
33 import org.hibernate.SessionFactory;
34 import org.hibernate.event.SessionEventListenerConfig;
35 import org.hibernate.cfg.AnnotationConfiguration;
36 import org.hibernate.cfg.Environment;
37 import org.hibernate.ejb.callback.EJB3DeleteEventListener;
38 import org.hibernate.ejb.callback.EJB3MergeEventListener;
39 import org.hibernate.ejb.callback.EJB3PersistEventListener;
40 import org.hibernate.ejb.callback.EJB3PostDeleteEventListener;
41 import org.hibernate.ejb.callback.EJB3PostLoadEventListener;
42 import org.hibernate.ejb.callback.EJB3PostUpdateEventListener;
43 import org.hibernate.ejb.callback.EntityCallbackHandler;
44 import org.hibernate.ejb.callback.EJB3PostInsertEventListener;
45 import org.hibernate.ejb.callback.EJB3SaveEventListener;
46 import org.hibernate.ejb.callback.EJB3SaveOrUpdateEventListener;
47 import org.hibernate.ejb.callback.EJB3FlushEntityEventListener;
48 import org.hibernate.ejb.packaging.JarVisitor;
49 import org.hibernate.ejb.packaging.PersistenceMetadata;
50 import org.hibernate.ejb.packaging.PersistenceXmlLoader;
51 import org.hibernate.mapping.PersistentClass;
52 import org.hibernate.secure.JACCConfiguration;
53 import org.hibernate.util.StringHelper;
54 import org.jboss.util.file.ArchiveBrowser;
55
56 /**
57  * Hibernate EJB3 persistence provider implementation
58  *
59  * @author Gavin King
60  */

61 public class HibernatePersistence implements javax.persistence.spi.PersistenceProvider {
62     private static Log log = LogFactory.getLog( HibernatePersistence.class );
63
64     /**
65      * PAR autodetection artiufacts class, hbm
66      */

67     public static final String JavaDoc AUTODETECTION = "hibernate.ejb.autodetection";
68     /**
69      * List of classes names
70      * Don't use it
71      */

72     public static final String JavaDoc CLASS_NAMES = "hibernate.ejb.classes";
73     /**
74      * List of annotated packages
75      * TODO Check if it's still working
76      */

77     public static final String JavaDoc PACKAGE_NAMES = "hibernate.ejb.packages";
78     /**
79      * cfg.xml configuration file used
80      */

81     public static final String JavaDoc CFG_FILE = "hibernate.ejb.cfgfile";
82     /**
83      * Caching configuratioh should follow the following pattern
84      * hibernate.ejb.classcache.<fully.qualified.Classname> usage[, region]
85      * where usage is the cache strategy used and region the cache region name
86      */

87     public static final String JavaDoc CLASS_CACHE_PREFIX = "hibernate.ejb.classcache";
88     /**
89      * Caching configuratioh should follow the following pattern
90      * hibernate.ejb.collectioncache.<fully.qualified.Classname>.<role> usage[, region]
91      * where usage is the cache strategy used and region the cache region name
92      */

93     public static final String JavaDoc COLLECTION_CACHE_PREFIX = "hibernate.ejb.collectioncache";
94     /**
95      * link to the alternative Hibernate configuration file
96      */

97     public static final String JavaDoc HBXML_FILES = "hibernate.hbmxml.files";
98     public static final String JavaDoc LOADED_CLASSES = "hibernate.ejb.loaded.classes";
99     public static final String JavaDoc JACC_CONTEXT_ID = "hibernate.jacc.ctx.id";
100     public static final String JavaDoc JACC_PREFIX = "hibernate.jacc";
101     //Properties to set special listeners for JACC
102
public static final String JavaDoc JACC_PRE_INSERT_LISTENER = "hibernate.listener.pre.insert";
103     public static final String JavaDoc JACC_PRE_LOAD_LISTENER = "hibernate.listener.pre.load";
104     public static final String JavaDoc JACC_PRE_UPDATE_LISTENER = "hibernate.listener.pre.update";
105     public static final String JavaDoc JACC_PRE_DELETE_LISTENER = "hibernate.listener.pre.delete";
106
107
108     /**
109      * create a factory from a persistence.xml
110      */

111     private EntityManagerFactory createFactory(PersistenceMetadata metadata, Map JavaDoc overrides) {
112         log.debug( "Creating Factory: " + metadata.getName() );
113         if ( metadata.getMappingFiles().size() > 0 ) throw new RuntimeException JavaDoc( "<mapping-file not supported yet" );
114
115         Properties JavaDoc copy = new Properties JavaDoc();
116         if ( StringHelper.isNotEmpty( metadata.getJtaDatasource() ) ) {
117             copy.put( Environment.DATASOURCE, metadata.getJtaDatasource() );
118         }
119         copy.putAll( metadata.getProps() );
120         if ( metadata.getClasses().size() <= 0 &&
121                 !copy.containsKey( LOADED_CLASSES ) &&
122                 !copy.containsKey( CLASS_NAMES ) &&
123                 !copy.containsKey( HBXML_FILES ) &&
124                 !copy.containsKey( CFG_FILE ) ) {
125             //either cfg file or explicit class file declaration is expected
126
throw new MappingException( "Neither classes found/declared nor hibernate.cfg.xml file available" );
127         }
128
129         //if nobody has injected in lieu of us
130
if ( !copy.containsKey( LOADED_CLASSES ) && !copy.containsKey( CLASS_NAMES ) ) {
131             if ( metadata.getClasses().size() > 0 ) {
132                 copy.put( CLASS_NAMES, metadata.getClasses() );
133             }
134             if ( metadata.getPackages().size() > 0 ) {
135                 if ( copy.containsKey( PACKAGE_NAMES ) ) {
136                     ( (Set JavaDoc<String JavaDoc>) copy.get( PACKAGE_NAMES ) ).addAll( metadata.getPackages() );
137                 }
138                 else {
139                     copy.put( PACKAGE_NAMES, metadata.getPackages() );
140                 }
141             }
142             if ( metadata.getHbmfiles().size() > 0 ) {
143                 if ( copy.containsKey( HBXML_FILES ) ) {
144                     ( (Set JavaDoc<InputStream JavaDoc>) copy.get( HBXML_FILES ) ).addAll( metadata.getHbmfiles() );
145                 }
146                 else {
147                     copy.put( HBXML_FILES, metadata.getHbmfiles() );
148                 }
149             }
150         }
151         if ( overrides != null ) copy.putAll( overrides );
152         return createEntityManagerFactory( copy );
153     }
154
155     /**
156      * Get an entity manager factory by its entity manager name and given the
157      * appropriate extra properties. Those proeprties override the one get through
158      * the peristence.xml file.
159      *
160      * @param emName entity manager name
161      * @param map properties passed to the persistence provider
162      * @return
163      */

164     public EntityManagerFactory createEntityManagerFactory(String JavaDoc emName, Map JavaDoc map) {
165         try {
166             Enumeration JavaDoc<URL JavaDoc> xmls = Thread.currentThread().getContextClassLoader().getResources( "META-INF/persistence.xml" );
167             while ( xmls.hasMoreElements() ) {
168                 URL JavaDoc url = xmls.nextElement();
169                 log.debug( "Analyse of persistence.xml: " + url );
170                 PersistenceMetadata metadata = PersistenceXmlLoader.deploy( url );
171                 boolean[] detectArtifacts = detectArtifacts( metadata.getProps(), map);
172
173                 if ( metadata.getProvider() == null || metadata.getProvider().equals( this.getClass().getName() ) ) {
174                     //correct provider
175
//TODO wait for the ArchiveBrowser to work properly for explided jars and string represented URLs
176
//scanForClasses( url, metadata.getPackages(), metadata.getClasses() );
177
//scanForHbmXmlFiles( url, metadata.getHbmfiles() );
178
JarVisitor visitor = JarVisitor.getVisitor( url, detectArtifacts[0], detectArtifacts[1] );
179                     if ( metadata.getName() == null ) {
180                         if ( log.isDebugEnabled() ) {
181                             log.debug( "Defaulting entity factory name to " + visitor.getName() );
182                         }
183                         metadata.setName( visitor.getName() );
184                     }
185                     addMetadataFromVisitor( visitor, metadata );
186                     for ( String JavaDoc jarFile : metadata.getJarFiles() ) {
187                         visitor = JarVisitor.getVisitor( jarFile, detectArtifacts[0], detectArtifacts[1] );
188                         //TODO wait for the ArchiveBrowser to work properly for explided jars and string represented URLs
189
//scanForClasses( new URL(jarFile), metadata.getPackages(), metadata.getClasses() );
190
addMetadataFromVisitor( visitor, metadata );
191                     }
192                     if ( emName == null ) {
193                         if ( xmls.hasMoreElements() ) {
194                             throw new PersistenceException( "No name provided and several persistence units found");
195                         }
196                         return createFactory( metadata, map );
197                     }
198                     else if ( emName.equals( metadata.getName() ) ) {
199                         return createFactory( metadata, map );
200                     }
201                 }
202             }
203             return null;
204         }
205         catch (Exception JavaDoc e) {
206             throw new PersistenceException( e );
207         }
208     }
209
210     private void addMetadataFromVisitor(JarVisitor visitor, PersistenceMetadata metadata) throws IOException JavaDoc,
211             NotFoundException {
212         //TODO reuse this class pool accross all jar searches?
213
ClassPool cp = new ClassPool(); //my own instance not to change the "common" class path def of ClassPoo.getDefault()
214
ClassLoader JavaDoc contextClassLoader = Thread.currentThread().getContextClassLoader();
215         cp.insertClassPath( new LoaderClassPath( contextClassLoader ) );
216         Set JavaDoc<String JavaDoc> elements = visitor.getClassNames();
217         for ( String JavaDoc className : elements ) {
218             CtClass jsClass = cp.get( className );
219             List JavaDoc attributes = jsClass.getClassFile().getAttributes();
220             Iterator JavaDoc attributeIterators = attributes.listIterator();
221             while ( attributeIterators.hasNext() ) {
222                 Object JavaDoc info = attributeIterators.next();
223                 if ( info instanceof AnnotationsAttribute ) {
224                     AnnotationsAttribute ann = (AnnotationsAttribute) info;
225                     if ( ann.getAnnotation( Entity.class.getName() ) != null
226                             || ann.getAnnotation( Embeddable.class.getName() ) != null
227                             || ann.getAnnotation( EmbeddableSuperclass.class.getName() ) != null ) {
228                         if ( log.isDebugEnabled() ) {
229                             log.debug( "Add Javassist mapped class to " + metadata.getName() + ": " + className );
230                         }
231                         metadata.getClasses().add( className );
232                     }
233                 }
234             }
235             jsClass.detach(); //avoid hardlink and enable GC
236
}
237         elements = visitor.getPackageNames();
238         for (String JavaDoc packageName : elements) {
239             metadata.getPackages().add( packageName );
240         }
241
242         elements = visitor.getHbmFiles();
243         for (String JavaDoc hbmFilesName : elements) {
244             log.debug("Trying to get resuource: " + "/" + hbmFilesName);
245             InputStream JavaDoc is = contextClassLoader.getResourceAsStream( hbmFilesName );
246             if (is == null) throw new PersistenceException("Unable to load resource " + hbmFilesName);
247             metadata.getHbmfiles().add( is );
248         }
249     }
250
251     /**
252      * Create a factory from a persistenceinfo object
253      */

254     public EntityManagerFactory createContainerEntityManagerFactory(PersistenceInfo info) {
255         List JavaDoc<String JavaDoc> entities = info.getEntityclassNames();
256         if ( entities == null ) entities = new ArrayList JavaDoc<String JavaDoc>();
257         List JavaDoc<InputStream JavaDoc> hbmFiles = new ArrayList JavaDoc<InputStream JavaDoc>();
258         List JavaDoc<String JavaDoc> packages = new ArrayList JavaDoc<String JavaDoc>();
259         boolean[] detectArtifact = detectArtifacts( info.getProperties(), null );
260         for ( URL JavaDoc jar : info.getJarFiles() ) {
261             if (detectArtifact[0]) scanForClasses( jar, packages, entities );
262             if (detectArtifact[1]) scanForHbmXmlFiles( jar, hbmFiles );
263         }
264         Properties JavaDoc props = info.getProperties();
265         if ( props == null ) props = new Properties JavaDoc();
266         props.put( CLASS_NAMES, entities );
267         props.put( PACKAGE_NAMES, packages );
268         if ( hbmFiles.size() > 0 ) props.put( HBXML_FILES, hbmFiles );
269         Ejb3Configuration cfg = new Ejb3Configuration();
270         if ( info.getJtaDataSource() != null || info.getNonJtaDataSource() != null ) {
271             cfg.setProperties(props);
272             cfg.setDataSource( info.getJtaDataSource() != null ? info.getJtaDataSource() : info.getNonJtaDataSource() );
273             props.setProperty( Environment.CONNECTION_PROVIDER, InjectedDataSourceConnectionProvider.class.getName() );
274         }
275         else {
276             //TODO is it necessary
277
throw new PersistenceException("No datasource provided");
278         }
279         return createEntityManagerFactory( props, cfg );
280
281     }
282
283     private boolean[] detectArtifacts(Properties JavaDoc properties, Map JavaDoc overridenProperties) {
284         boolean[] result = new boolean[2];
285         result[0] = false; //detect classes
286
result[1] = false; //detect hbm
287
if ( (overridenProperties != null
288                 && overridenProperties.get(CFG_FILE) != null )
289             || properties.get( CFG_FILE ) != null ) {
290             log.info( "Avoid .par auto detection: cfg file defined" );
291             return result;
292         }
293         String JavaDoc detect = overridenProperties != null ?
294                 (String JavaDoc) overridenProperties.get(AUTODETECTION) :
295                 null;
296         detect = detect == null ?
297                 properties.getProperty(AUTODETECTION, "class,hbm") :
298                 detect;
299         StringTokenizer JavaDoc st = new StringTokenizer JavaDoc( detect, ",", false);
300         while ( st.hasMoreElements() ) {
301             String JavaDoc element = (String JavaDoc) st.nextElement();
302             if ( "class".equalsIgnoreCase( element ) ) result[0] = true;
303             if ( "hbm".equalsIgnoreCase( element ) ) result[1] = true;
304         }
305         log.debug( "Detect class: " + result[0] + "; detect hbm: " + result[1]);
306         return result;
307     }
308
309     private void scanForHbmXmlFiles(URL JavaDoc jar, List JavaDoc<InputStream JavaDoc> hbmxmls) {
310         Iterator JavaDoc it = ArchiveBrowser.getBrowser(
311                 jar, new ArchiveBrowser.Filter() {
312                     public boolean accept(String JavaDoc filename) {
313                         return filename.endsWith( ".hbm.xml" );
314                     }
315                 }
316         );
317
318         while ( it.hasNext() ) {
319             InputStream JavaDoc stream = (InputStream JavaDoc) it.next();
320             hbmxmls.add( stream );
321         }
322     }
323
324     private void scanForClasses(URL JavaDoc jar, List JavaDoc<String JavaDoc> packages, List JavaDoc<String JavaDoc> entities) {
325         Iterator JavaDoc it = ArchiveBrowser.getBrowser(
326                 jar, new ArchiveBrowser.Filter() {
327                     public boolean accept(String JavaDoc filename) {
328                         return filename.endsWith( ".class" );
329                     }
330                 }
331         );
332
333         // need to look into every entry in the archive to see if anybody has tags
334
// defined.
335
while ( it.hasNext() ) {
336             InputStream JavaDoc stream = (InputStream JavaDoc) it.next();
337             DataInputStream JavaDoc dstream = new DataInputStream JavaDoc( stream );
338             ClassFile cf = null;
339             try {
340                 try {
341                     cf = new ClassFile( dstream );
342                 }
343                 finally {
344                     dstream.close();
345                     stream.close();
346                 }
347             }
348             catch (IOException JavaDoc e) {
349                 throw new RuntimeException JavaDoc( e );
350             }
351             if ( cf.getName().endsWith( ".package-info" ) ) {
352                 int idx = cf.getName().indexOf( ".package-info" );
353                 String JavaDoc pkgName = cf.getName().substring( 0, idx );
354                 log.info( "found package: " + pkgName );
355                 packages.add( pkgName );
356                 continue;
357             }
358
359             AnnotationsAttribute visible = (AnnotationsAttribute) cf.getAttribute( AnnotationsAttribute.visibleTag );
360             if ( visible != null ) {
361                 boolean isEntity = visible.getAnnotation( Entity.class.getName() ) != null;
362                 if ( isEntity ) {
363                     log.info( "found EJB3 Entity bean: " + cf.getName() );
364                     entities.add( cf.getName() );
365                 }
366                 boolean isEmbeddable = visible.getAnnotation( Embeddable.class.getName() ) != null;
367                 if ( isEmbeddable ) {
368                     log.info( "found EJB3 @Embeddable: " + cf.getName() );
369                     entities.add( cf.getName() );
370                 }
371                 boolean isEmbeddableSuperclass = visible.getAnnotation( EmbeddableSuperclass.class.getName() ) != null;
372                 if ( isEmbeddableSuperclass ) {
373                     log.info( "found EJB3 @EmbeddableSuperclass: " + cf.getName() );
374                     entities.add( cf.getName() );
375                 }
376             }
377         }
378     }
379
380     /**
381      * create a factory from a canonical version
382      */

383     // This is used directly by JBoss so don't remove until further notice. bill@jboss.org
384
public EntityManagerFactory createEntityManagerFactory(Map JavaDoc properties) {
385         return createEntityManagerFactory( properties, new AnnotationConfiguration() );
386     }
387
388     /**
389      * create a factory from a canonical Map properties version
390      */

391     private EntityManagerFactory createEntityManagerFactory(Map JavaDoc properties, AnnotationConfiguration cfg) {
392         //EJB3-specific listeners
393
cfg.getSessionEventListenerConfig().setFlushEventListener( EJB3FlushEventListener.INSTANCE );
394         cfg.getSessionEventListenerConfig().setAutoFlushEventListener( EJB3AutoFlushEventListener.INSTANCE );
395
396         Properties JavaDoc props = new Properties JavaDoc();
397
398         //defaults different to Hibernate
399
props.setProperty( Environment.RELEASE_CONNECTIONS, "auto" );
400
401         //settings coming from persistence.properties
402
//and the passed Map
403
props.putAll( properties );
404
405         cfg.setProperties( props );
406
407         if ( properties == null ||
408                 !( properties.containsKey( CLASS_NAMES ) ||
409                 properties.containsKey( LOADED_CLASSES ) ||
410                 properties.containsKey( HBXML_FILES ) ) ) {
411             //use hibernate.cfg.xml
412
if ( properties != null && properties.containsKey( CFG_FILE ) ) {
413                 cfg.configure( (String JavaDoc) properties.get( CFG_FILE ) );
414             }
415             else {
416                 throw new MappingException( "Neither classes found/declared nor hibernate.cfg.xml file available" );
417             }
418         }
419         else {
420             if ( properties.containsKey( CLASS_NAMES ) ) {
421                 Collection JavaDoc<String JavaDoc> classNames = (Collection JavaDoc<String JavaDoc>) properties.get( CLASS_NAMES );
422                 addNamedAnnotatedClasses( cfg, classNames );
423             }
424             if ( properties.containsKey( LOADED_CLASSES ) ) {
425                 List JavaDoc<Class JavaDoc> classes = (List JavaDoc<Class JavaDoc>) properties.get( LOADED_CLASSES );
426                 for ( Class JavaDoc clazz : classes ) {
427                     cfg.addAnnotatedClass( clazz );
428                 }
429             }
430             if ( properties.containsKey( PACKAGE_NAMES ) ) {
431                 List JavaDoc<String JavaDoc> packages = (List JavaDoc<String JavaDoc>) properties.get( PACKAGE_NAMES );
432                 for ( String JavaDoc pkg : packages ) {
433                     cfg.addPackage( pkg );
434                 }
435             }
436             if ( properties.containsKey( HBXML_FILES ) ) {
437                 List JavaDoc<InputStream JavaDoc> hbmXmlFiles = (List JavaDoc<InputStream JavaDoc>) properties.get( HBXML_FILES );
438                 for ( InputStream JavaDoc is : hbmXmlFiles ) {
439                     cfg.addInputStream( is );
440                 }
441             }
442         }
443
444
445         List JavaDoc<String JavaDoc> jaccKeys = new ArrayList JavaDoc<String JavaDoc>();
446         String JavaDoc jaccContextId = (String JavaDoc) properties.get( JACC_CONTEXT_ID );
447
448         Iterator JavaDoc<String JavaDoc> propertyIt = properties.keySet().iterator();
449         while ( propertyIt.hasNext() ) {
450             String JavaDoc propertyKey = propertyIt.next();
451             if ( propertyKey.startsWith( CLASS_CACHE_PREFIX ) ) {
452                 setCacheStrategy( propertyKey, properties, cfg, true );
453             }
454             else if ( propertyKey.startsWith( COLLECTION_CACHE_PREFIX ) ) {
455                 setCacheStrategy( propertyKey, properties, cfg, false );
456             }
457             else if ( propertyKey.startsWith( JACC_PREFIX ) && !propertyKey.equals( JACC_CONTEXT_ID ) ) {
458                 jaccKeys.add( propertyKey );
459             }
460         }
461
462         if ( jaccKeys.size() > 0 ) {
463             addSecurity( jaccKeys, properties, cfg );
464         }
465
466         //settings that always apply to EJB3
467
cfg.setProperty( Environment.AUTOCOMMIT, "true" );
468         cfg.setProperty( Environment.USE_IDENTIFIER_ROLLBACK, "true" );
469
470
471         handleListenerCallbacks( cfg );
472         SessionFactory sf = cfg.buildSessionFactory();
473
474         return new EntityManagerFactoryImpl( sf );
475     }
476
477     private void handleListenerCallbacks(AnnotationConfiguration cfg) {
478         //handle callbacks for all classes
479
//TODO exclude pure hbm file classes?
480
EntityCallbackHandler callbackHandler = new EntityCallbackHandler();
481         cfg.buildMappings(); //needed to get all the classes
482
Iterator JavaDoc classes = cfg.getClassMappings();
483         while ( classes.hasNext() ) {
484             PersistentClass clazz = (PersistentClass) classes.next();
485             callbackHandler.add( clazz.getMappedClass() );
486         }
487         // EntityListeners
488
SessionEventListenerConfig listenerConfig = cfg.getSessionEventListenerConfig();
489
490         //remember that some event are already set previously in the HibernatePersistence process
491
listenerConfig.setDeleteEventListener( new EJB3DeleteEventListener( callbackHandler ) );
492         listenerConfig.setFlushEntityEventListener( new EJB3FlushEntityEventListener( callbackHandler ) );
493         listenerConfig.setMergeEventListener( new EJB3MergeEventListener( callbackHandler ) );
494         listenerConfig.setCreateEventListener( new EJB3PersistEventListener( callbackHandler ) );
495         listenerConfig.setPostDeleteEventListener( new EJB3PostDeleteEventListener( callbackHandler ) );
496         listenerConfig.setPostInsertEventListener( new EJB3PostInsertEventListener( callbackHandler ) );
497         listenerConfig.setPostLoadEventListener( new EJB3PostLoadEventListener( callbackHandler ) );
498         listenerConfig.setPostUpdateEventListener( new EJB3PostUpdateEventListener( callbackHandler ) );
499         listenerConfig.setSaveEventListener( new EJB3SaveEventListener( callbackHandler ) );
500         listenerConfig.setSaveOrUpdateEventListener( new EJB3SaveOrUpdateEventListener( callbackHandler ) );
501     }
502
503     private void setCacheStrategy(String JavaDoc propertyKey, Map JavaDoc properties, AnnotationConfiguration cfg, boolean isClass) {
504         String JavaDoc role = propertyKey.substring(
505                 ( isClass ? CLASS_CACHE_PREFIX.length() : COLLECTION_CACHE_PREFIX.length() )
506                 + 1
507         );
508         //dot size added
509
String JavaDoc value = (String JavaDoc) properties.get( propertyKey );
510         StringTokenizer JavaDoc params = new StringTokenizer JavaDoc( value, ";, " );
511         if ( !params.hasMoreTokens() ) {
512             StringBuffer JavaDoc error = new StringBuffer JavaDoc( "Illegal usage of " );
513             error.append( isClass ? CLASS_CACHE_PREFIX : COLLECTION_CACHE_PREFIX );
514             error.append( ": " ).append( propertyKey ).append( " " ).append( value );
515             throw new MappingException( error.toString() );
516         }
517         String JavaDoc usage = params.nextToken();
518         String JavaDoc region = null;
519         if ( params.hasMoreTokens() ) {
520             region = params.nextToken();
521         }
522         if ( isClass ) {
523             cfg.setCacheConcurrencyStrategy( role, usage, region );
524         }
525         else {
526             cfg.setCollectionCacheConcurrencyStrategy( role, usage, region );
527         }
528     }
529
530     private static void addSecurity(List JavaDoc<String JavaDoc> keys, Map JavaDoc properties, AnnotationConfiguration cfg) {
531         log.debug( "Adding security" );
532         if ( !properties.containsKey( JACC_CONTEXT_ID ) ) {
533             throw new MappingException(
534                     "Entities have been configured for JACC, but " + JACC_CONTEXT_ID + " has not been set"
535             );
536         }
537         String JavaDoc contextId = (String JavaDoc) properties.get( JACC_CONTEXT_ID );
538
539         //If JACC is configured, enable the jacc listeners
540

541         if ( properties.containsKey( JACC_PRE_INSERT_LISTENER ) ) {
542             String JavaDoc listener = (String JavaDoc) properties.get( JACC_PRE_INSERT_LISTENER );
543             cfg.setListener( "pre-insert", listener );
544         }
545
546         if ( properties.containsKey( JACC_PRE_UPDATE_LISTENER ) ) {
547             String JavaDoc listener = (String JavaDoc) properties.get( JACC_PRE_UPDATE_LISTENER );
548             cfg.setListener( "pre-update", listener );
549         }
550
551         if ( properties.containsKey( JACC_PRE_DELETE_LISTENER ) ) {
552             String JavaDoc listener = (String JavaDoc) properties.get( JACC_PRE_DELETE_LISTENER );
553             cfg.setListener( "pre-delete", listener );
554         }
555
556         if ( properties.containsKey( JACC_PRE_LOAD_LISTENER ) ) {
557             String JavaDoc listener = (String JavaDoc) properties.get( JACC_PRE_LOAD_LISTENER );
558             cfg.setListener( "pre-load", listener );
559         }
560
561         int roleStart = JACC_PREFIX.length() + 1;
562
563         for ( String JavaDoc key : keys ) {
564             JACCConfiguration jaccCfg = new JACCConfiguration( contextId );
565
566             try {
567                 String JavaDoc role = key.substring( roleStart, key.indexOf( '.', roleStart ) );
568                 int classStart = roleStart + role.length() + 1;
569                 String JavaDoc clazz = key.substring( classStart, key.length() );
570                 String JavaDoc actions = (String JavaDoc) properties.get( key );
571                 jaccCfg.addPermission( role, clazz, actions );
572             }
573             catch (IndexOutOfBoundsException JavaDoc e) {
574                 throw new MappingException( "Illegal usage of " + JACC_PREFIX + ": " + key );
575             }
576         }
577     }
578
579     private void addNamedAnnotatedClasses(AnnotationConfiguration cfg, Collection JavaDoc<String JavaDoc> classNames) {
580         for ( String JavaDoc name : classNames ) {
581             try {
582                 Class JavaDoc clazz = Thread.currentThread().getContextClassLoader().loadClass( name );
583                 cfg.addAnnotatedClass( clazz );
584                 //handler.add(clazz);
585
}
586             catch (ClassNotFoundException JavaDoc cnfe) {
587                 Package JavaDoc pkg = Package.getPackage( name );
588                 if ( pkg == null ) {
589                     throw new IllegalArgumentException JavaDoc( "class not found", cnfe );
590                 }
591                 else {
592                     cfg.addPackage( name );
593                 }
594             }
595         }
596     }
597
598 }
Popular Tags