Commit ca57f3e4753e17bba76035f409c34f579bfd71c0

Authored by Dancovich
1 parent 187a6500
Exists in master

Alterada forma como cache de entity manager factory é gerada, evitando

recarregar o cache a cada chamada do producer.
impl/extension/jpa/src/main/java/br/gov/frameworkdemoiselle/internal/producer/EntityManagerFactoryProducer.java
1 1 package br.gov.frameworkdemoiselle.internal.producer;
2 2  
3 3 import java.io.Serializable;
  4 +import java.util.ArrayList;
4 5 import java.util.Collections;
5 6 import java.util.HashMap;
6 7 import java.util.Map;
7 8  
  9 +import javax.annotation.PostConstruct;
8 10 import javax.annotation.PreDestroy;
9 11 import javax.enterprise.context.ApplicationScoped;
10 12 import javax.inject.Inject;
... ... @@ -40,32 +42,42 @@ public class EntityManagerFactoryProducer implements Serializable {
40 42 // private final Map<String, EntityManagerFactory> cache = Collections
41 43 // .synchronizedMap(new HashMap<String, EntityManagerFactory>());
42 44  
43   - private final Map<Key, EntityManagerFactory> cache = Collections
44   - .synchronizedMap(new HashMap<Key, EntityManagerFactory>());
  45 + /*
  46 + * private final Map<Key, EntityManagerFactory> cache = Collections .synchronizedMap(new HashMap<Key,
  47 + * EntityManagerFactory>());
  48 + */
  49 +
  50 + private final Map<ClassLoader, Map<String, EntityManagerFactory>> factoryCache = Collections
  51 + .synchronizedMap(new HashMap<ClassLoader, Map<String, EntityManagerFactory>>());
45 52  
46 53 public EntityManagerFactory create(String persistenceUnit) {
47 54 EntityManagerFactory factory;
48 55  
49   - //String[] key = new String [] { persistenceUnit, Thread.currentThread().getContextClassLoader().toString()};
50   - Key key = new Key(persistenceUnit, Thread.currentThread().getContextClassLoader());
51   -
52   - if (cache.containsKey(key)) {
53   - factory = cache.get(key);
  56 + ClassLoader c = Thread.currentThread().getContextClassLoader();
  57 +
  58 + if (factoryCache.containsKey(c)) {
  59 + Map<String, EntityManagerFactory> localCache = factoryCache.get(c);
  60 + if (localCache.containsKey(persistenceUnit)) {
  61 + factory = localCache.get(persistenceUnit);
  62 + } else {
  63 + factory = Persistence.createEntityManagerFactory(persistenceUnit);
  64 + localCache.put(persistenceUnit, factory);
  65 + }
54 66 } else {
  67 + Map<String, EntityManagerFactory> localCache = new HashMap<String, EntityManagerFactory>();
55 68 factory = Persistence.createEntityManagerFactory(persistenceUnit);
56   - cache.put(key, factory);
  69 + localCache.put(persistenceUnit, factory);
  70 + factoryCache.put(c, localCache);
57 71 }
58 72  
59 73 return factory;
60 74 }
61 75  
62   - // @PostConstruct
63   - public void init() {
64   - ClassLoader contextClassLoader = Thread.currentThread().getContextClassLoader();
65   -
  76 + private String[] loadPersistenceUnitFromClassloader(ClassLoader classLoader) {
66 77 try {
  78 + ArrayList<String> persistenceUnits = new ArrayList<String>();
67 79 DocumentBuilder documentBuilder = DocumentBuilderFactory.newInstance().newDocumentBuilder();
68   - Document document = documentBuilder.parse(contextClassLoader.getResourceAsStream(ENTITY_MANAGER_RESOURCE));
  80 + Document document = documentBuilder.parse(classLoader.getResourceAsStream(ENTITY_MANAGER_RESOURCE));
69 81 NodeList nodes = document.getElementsByTagName("persistence-unit");
70 82  
71 83 String persistenceUnit = "";
... ... @@ -75,88 +87,57 @@ public class EntityManagerFactoryProducer implements Serializable {
75 87  
76 88 if ("".equals(persistenceUnit)) {
77 89 throw new DemoiselleException(bundle.getString("can-not-get-persistence-unit-from-persistence"));
  90 + } else {
  91 + persistenceUnits.add(persistenceUnit);
78 92 }
  93 + // logger.debug(bundle.getString("persistence-unit-name-found",
  94 + // persistenceUnit));
79 95  
80   - create(persistenceUnit);
81   - logger.debug(bundle.getString("persistence-unit-name-found", persistenceUnit));
82 96 }
83 97  
  98 + return persistenceUnits.toArray(new String[0]);
  99 +
84 100 } catch (Exception cause) {
85 101 String message = bundle.getString("can-not-get-persistence-unit-from-persistence");
86 102 logger.error(message, cause);
87 103  
88 104 throw new DemoiselleException(message, cause);
89 105 }
  106 +
  107 + }
  108 +
  109 + @PostConstruct
  110 + public void loadPersistenceUnits() {
  111 + ClassLoader contextClassLoader = Thread.currentThread().getContextClassLoader();
  112 + for (String persistenceUnit : loadPersistenceUnitFromClassloader(contextClassLoader)) {
  113 + create(persistenceUnit);
  114 + logger.debug(bundle.getString("persistence-unit-name-found", persistenceUnit));
  115 + }
90 116 }
91 117  
92 118 @PreDestroy
93 119 public void close() {
94   - for (EntityManagerFactory factory : cache.values()) {
95   - factory.close();
  120 + for (Map<String, EntityManagerFactory> factories : factoryCache.values()) {
  121 + for (EntityManagerFactory factory : factories.values()) {
  122 + factory.close();
  123 + }
96 124 }
97   -
98   - cache.clear();
  125 + factoryCache.clear();
99 126 }
100 127  
101 128 public Map<String, EntityManagerFactory> getCache() {
102   - init();
103   - Map<String, EntityManagerFactory> result = new HashMap<String, EntityManagerFactory>();
104 129 ClassLoader classLoader = Thread.currentThread().getContextClassLoader();
105   -
106   - for (Key key : cache.keySet()) {
107   - if(key.classLoader.equals(classLoader)) {
108   - result.put(key.persistenceUnit, cache.get(key));
109   - }
110   - }
111   -
112   - return result;
113   - }
114   -
115   -
116   - class Key{
117   -
118   - private String persistenceUnit;
119   - private ClassLoader classLoader;
120   -
121   -
122   - public Key(String persistenceUnit, ClassLoader classLoader) {
123   - this.persistenceUnit = persistenceUnit;
124   - this.classLoader = classLoader;
125   - }
126   -
127   - @Override
128   - public int hashCode() {
129   - final int prime = 31;
130   - int result = 1;
131   - result = prime * result + ((classLoader == null) ? 0 : classLoader.hashCode());
132   - result = prime * result + ((persistenceUnit == null) ? 0 : persistenceUnit.hashCode());
133   - return result;
134   - }
  130 + Map<String, EntityManagerFactory> result = factoryCache.get(classLoader);
135 131  
136   - @Override
137   - public boolean equals(Object obj) {
138   - if (this == obj)
139   - return true;
140   - if (obj == null)
141   - return false;
142   - if (getClass() != obj.getClass())
143   - return false;
144   - Key other = (Key) obj;
145   - if (classLoader == null) {
146   - if (other.classLoader != null)
147   - return false;
148   - } else if (!classLoader.equals(other.classLoader))
149   - return false;
150   - if (persistenceUnit == null) {
151   - if (other.persistenceUnit != null)
152   - return false;
153   - } else if (!persistenceUnit.equals(other.persistenceUnit))
154   - return false;
155   - return true;
  132 + if (result == null || result.isEmpty()) {
  133 + logger.debug(bundle.getString("entity-manager-factory-not-found-in-cache"));
  134 + for (String persistenceUnit : loadPersistenceUnitFromClassloader(classLoader)) {
  135 + create(persistenceUnit);
  136 + result = factoryCache.get(classLoader);
  137 + }
156 138 }
157 139  
  140 + return result;
158 141 }
159 142  
160 143 }
161   -
162   -
... ...
impl/extension/jpa/src/main/resources/demoiselle-jpa-bundle.properties
... ... @@ -34,6 +34,7 @@
34 34 # 51 Franklin St, Fifth Floor, Boston, MA 02111-1301, USA.
35 35  
36 36 entity-manager-was-created=Gerenciador de entidades criado a partir da unidade de persist\u00EAncia "{0}".
  37 +entity-manager-factory-not-found-in-cache=Entity Manager Factory n\u00E3o encontrado para contexto atual, criando um agora.
37 38 operation-not-supported=Esta operação não é suportada.
38 39 getting-persistence-unit-from-properties=Obtendo a unidade de persist\u00EAncia a partir do arquivo de configura\u00E7\u00E3o "{0}".
39 40 getting-persistence-unit-from-persistence=Obtendo a unidade de persist\u00EAncia a partir do arquivo "persistence.xml".
... ...
impl/extension/jpa/src/test/java/br/gov/frameworkdemoiselle/internal/producer/EntityManagerFactoryProducerTest.java
... ... @@ -72,14 +72,14 @@ public class EntityManagerFactoryProducerTest {
72 72 expect(Persistence.createEntityManagerFactory("pu1")).andReturn(emFactory);
73 73 replay(Persistence.class);
74 74  
75   - producer.init();
  75 + producer.loadPersistenceUnits();
76 76 Assert.assertEquals(emFactory, cache.get("pu1"));
77 77 }
78 78  
79 79 @Test
80 80 public void testInitWithError() {
81 81 try {
82   - producer.init();
  82 + producer.loadPersistenceUnits();
83 83 Assert.fail();
84 84 }catch(DemoiselleException cause) {
85 85 Assert.assertTrue(true);
... ...
impl/extension/jpa/src/test/resources/demoiselle-jpa-bundle.properties
... ... @@ -34,6 +34,7 @@
34 34 # 51 Franklin St, Fifth Floor, Boston, MA 02111-1301, USA.
35 35  
36 36 entity-manager-was-created=Gerenciador de entidades criado a partir da unidade de persist\u00EAncia "{0}".
  37 +entity-manager-factory-not-found-in-cache=Entity Manager Factory n\u00E3o encontrado para contexto atual, criando um agora.
37 38 operation-not-supported=Esta operação não é suportada.
38 39 getting-persistence-unit-from-properties=Obtendo a unidade de persist\u00EAncia a partir do arquivo de configura\u00E7\u00E3o "{0}".
39 40 getting-persistence-unit-from-persistence=Obtendo a unidade de persist\u00EAncia a partir do arquivo "persistence.xml".
... ...