diff --git a/src/main/java/li/strolch/agent/api/ComponentContainer.java b/src/main/java/li/strolch/agent/api/ComponentContainer.java index 002a7bf64..96e680546 100644 --- a/src/main/java/li/strolch/agent/api/ComponentContainer.java +++ b/src/main/java/li/strolch/agent/api/ComponentContainer.java @@ -15,6 +15,7 @@ */ package li.strolch.agent.api; +import li.strolch.agent.impl.DataStoreMode; import li.strolch.agent.impl.StrolchRealm; /** @@ -25,6 +26,8 @@ public interface ComponentContainer { public abstract StrolchAgent getAgent(); public abstract ComponentState getState(); + + public abstract DataStoreMode getDataStoreMode(); public abstract boolean hasComponent(Class clazz); diff --git a/src/main/java/li/strolch/agent/api/ElementMap.java b/src/main/java/li/strolch/agent/api/ElementMap.java index 290eb2287..aa2aa4060 100644 --- a/src/main/java/li/strolch/agent/api/ElementMap.java +++ b/src/main/java/li/strolch/agent/api/ElementMap.java @@ -44,7 +44,13 @@ public interface ElementMap { public void add(StrolchTransaction tx, T element); + public void addAll(StrolchTransaction tx, List elements); + public void update(StrolchTransaction tx, T element); + public void updateAll(StrolchTransaction tx, List elements); + public void remove(StrolchTransaction tx, T element); + + public void removeAll(StrolchTransaction tx, List elements); } diff --git a/src/main/java/li/strolch/agent/api/StrolchAgent.java b/src/main/java/li/strolch/agent/api/StrolchAgent.java index b00f22313..05a4ea286 100644 --- a/src/main/java/li/strolch/agent/api/StrolchAgent.java +++ b/src/main/java/li/strolch/agent/api/StrolchAgent.java @@ -100,7 +100,7 @@ public class StrolchAgent { this.strolchConfiguration.addConfiguration(configuration.getName(), configuration); } - ComponentContainerImpl container = new ComponentContainerImpl(this); + ComponentContainerImpl container = new ComponentContainerImpl(this, dataStoreMode); this.container = container; logger.info(MessageFormat.format("Setup Agent {0}", runtimeConfiguration.getApplicationName())); //$NON-NLS-1$ diff --git a/src/main/java/li/strolch/agent/impl/CachedElementMap.java b/src/main/java/li/strolch/agent/impl/CachedElementMap.java new file mode 100644 index 000000000..3a72cf372 --- /dev/null +++ b/src/main/java/li/strolch/agent/impl/CachedElementMap.java @@ -0,0 +1,347 @@ +/* + * Copyright 2013 Robert von Burg + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package li.strolch.agent.impl; + +import java.text.MessageFormat; +import java.util.ArrayList; +import java.util.Collections; +import java.util.HashMap; +import java.util.HashSet; +import java.util.List; +import java.util.Map; +import java.util.Set; + +import li.strolch.agent.api.ElementMap; +import li.strolch.model.StrolchElement; +import li.strolch.persistence.api.StrolchDao; +import li.strolch.persistence.api.StrolchPersistenceException; +import li.strolch.persistence.api.StrolchTransaction; +import ch.eitchnet.utils.dbc.DBC; + +/** + * @author Robert von Burg + */ +public abstract class CachedElementMap implements ElementMap { + + private Set allKeys; + private Map> elementMap; + + public CachedElementMap() { + this.allKeys = Collections.synchronizedSet(new HashSet()); + this.elementMap = Collections.synchronizedMap(new HashMap>()); + } + + protected abstract StrolchDao getDao(StrolchTransaction tx); + + @Override + public boolean hasType(StrolchTransaction tx, String type) { + return this.elementMap.containsKey(type); + } + + @Override + public boolean hasElement(StrolchTransaction tx, String type, String id) { + Map byType = this.elementMap.get(type); + if (byType == null) + return false; + + return byType.containsKey(id); + } + + @Override + public T getBy(StrolchTransaction tx, String type, String id) { + Map byType = this.elementMap.get(type); + if (byType == null) + return null; + + return byType.get(id); + } + + @Override + public List getAllElements(StrolchTransaction tx) { + List allElements = new ArrayList<>(); + for (String type : this.elementMap.keySet()) { + Map byType = this.elementMap.get(type); + allElements.addAll(byType.values()); + } + + return allElements; + } + + @Override + public List getElementsBy(StrolchTransaction tx, String type) { + Map byType = this.elementMap.get(type); + if (byType == null) + return Collections.emptyList(); + return new ArrayList<>(byType.values()); + } + + @Override + public Set getTypes(StrolchTransaction tx) { + return new HashSet<>(this.elementMap.keySet()); + } + + @Override + public Set getAllKeys(StrolchTransaction tx) { + Set keys = new HashSet<>(); + for (String type : this.elementMap.keySet()) { + Map byType = this.elementMap.get(type); + keys.addAll(byType.keySet()); + } + return keys; + } + + @Override + public Set getKeysBy(StrolchTransaction tx, String type) { + Map byType = this.elementMap.get(type); + if (byType == null) + return Collections.emptySet(); + return byType.keySet(); + } + + @Override + public void add(StrolchTransaction tx, T element) { + DBC.PRE.assertNotNull("Transaction may not be null!", tx); + DBC.PRE.assertNotNull("Element may not be null!", element); + + insert(element, tx); + } + + @Override + public void update(StrolchTransaction tx, T element) { + DBC.PRE.assertNotNull("Transaction may not be null!", tx); + DBC.PRE.assertNotNull("Element may not be null!", element); + + String msg = "The element {0} can not be updated as it does not exist!"; + Map byType = this.elementMap.get(element.getType()); + if (byType == null) { + msg = MessageFormat.format(msg, element.getLocator()); + throw new StrolchPersistenceException(msg); + } + + synchronized (byType) { + if (byType.remove(element.getId()) == null) { + msg = MessageFormat.format(msg, element.getLocator()); + throw new StrolchPersistenceException(msg); + } + byType.put(element.getId(), element); + getDao(tx).update(element); + } + } + + @Override + public void remove(StrolchTransaction tx, T element) { + DBC.PRE.assertNotNull("Transaction may not be null!", tx); + DBC.PRE.assertNotNull("Element may not be null!", element); + + String msg = "The element {0} can not be removed as it does not exist!"; + + synchronized (this.elementMap) { + Map byType = this.elementMap.get(element.getType()); + if (byType == null) { + msg = MessageFormat.format(msg, element.getLocator()); + throw new StrolchPersistenceException(msg); + } + + // TODO remove empty byType map after element removal, but be wary of synchronisation... + + synchronized (byType) { + if (byType.remove(element.getId()) == null) { + msg = MessageFormat.format(msg, element.getLocator()); + throw new StrolchPersistenceException(msg); + } + if (byType.isEmpty()) { + this.elementMap.remove(element.getType()); + } + this.allKeys.remove(element.getId()); + getDao(tx).remove(element); + } + } + } + + /** + * Special method used when starting the container to cache the values. Not to be used anywhere else but from the + * {@link CachedElementMapHandler} and of course through the {@link #add(StrolchTransaction, StrolchElement)}-call + * to not duplicate code + * + * @param element + * @param tx + */ + void insert(T element, StrolchTransaction tx) { + if (this.allKeys.contains(element.getId())) { + String msg = "An element already exists with the id " + element.getId() + + ". Elements of the same class must always have a unique id, regardless of their type!"; + throw new StrolchPersistenceException(msg); + } + + Map byType; + synchronized (this.elementMap) { + byType = this.elementMap.get(element.getType()); + if (byType == null) { + byType = Collections.synchronizedMap(new HashMap()); + this.elementMap.put(element.getType(), byType); + } + } + + synchronized (byType) { + if (byType.containsKey(element.getId())) { + String msg = MessageFormat.format("The element {0} already exists!", element.getLocator()); + throw new StrolchPersistenceException(msg); + } + + byType.put(element.getId(), element); + this.allKeys.add(element.getId()); + if (tx != null) + getDao(tx).save(element); + } + } + + private Map> sortElementsToType(List elements) { + Map> map = new HashMap<>(1); + for (T element : elements) { + List byType = map.get(element.getType()); + if (byType == null) { + byType = new ArrayList<>(1); + map.put(element.getType(), byType); + } + byType.add(element); + } + return map; + } + + @Override + public void addAll(StrolchTransaction tx, List elements) { + DBC.PRE.assertNotNull("Transaction may not be null!", tx); + DBC.PRE.assertNotNull("Elements may not be null!", elements); + + if (elements.isEmpty()) + return; + + // sort elements by type + Map> map = sortElementsToType(elements); + + // now add elements by type + for (String type : map.keySet()) { + + Map byType; + synchronized (this.elementMap) { + byType = this.elementMap.get(type); + if (byType == null) { + byType = new HashMap<>(); + this.elementMap.put(type, byType); + } + + List newByType = map.get(type); + for (T element : newByType) { + synchronized (byType) { + if (byType.containsKey(element.getId())) { + String msg = "An element already exists with the id {0}. Elements of the same class must always have a unique id, regardless of their type!"; + msg = MessageFormat.format(msg, element.getId()); + throw new StrolchPersistenceException(msg); + } + + byType.put(element.getId(), element); + this.allKeys.add(element.getId()); + } + } + } + } + + // last is to perform DB changes + getDao(tx).saveAll(elements); + } + + @Override + public void updateAll(StrolchTransaction tx, List elements) { + DBC.PRE.assertNotNull("Transaction may not be null!", tx); + DBC.PRE.assertNotNull("Elements may not be null!", elements); + + if (elements.isEmpty()) + return; + + // sort elements by type + Map> map = sortElementsToType(elements); + + String msg = "The element {0} can not be updated as it does not exist!"; + + // update elements + for (String type : map.keySet()) { + List list = map.get(type); + + synchronized (this.elementMap) { + Map byType = this.elementMap.get(type); + if (byType == null) { + msg = MessageFormat.format(msg, list.get(0).getLocator()); + throw new StrolchPersistenceException(msg); + } + + synchronized (byType) { + for (T element : list) { + if (byType.remove(element.getId()) == null) { + msg = MessageFormat.format(msg, element.getLocator()); + throw new StrolchPersistenceException(msg); + } + byType.put(element.getId(), element); + } + } + } + } + + // last is to perform DB changes + getDao(tx).updateAll(elements); + } + + @Override + public void removeAll(StrolchTransaction tx, List elements) { + DBC.PRE.assertNotNull("Transaction may not be null!", tx); + DBC.PRE.assertNotNull("Elements may not be null!", elements); + + if (elements.isEmpty()) + return; + + // sort elements by type + Map> map = sortElementsToType(elements); + + String msg = "The element {0} can not be removed as it does not exist!"; + + // update elements + for (String type : map.keySet()) { + List list = map.get(type); + + synchronized (this.elementMap) { + Map byType = this.elementMap.get(type); + if (byType == null) { + msg = MessageFormat.format(msg, list.get(0).getLocator()); + throw new StrolchPersistenceException(msg); + } + synchronized (byType) { + for (T element : list) { + if (byType.remove(element.getId()) == null) { + msg = MessageFormat.format(msg, element.getLocator()); + throw new StrolchPersistenceException(msg); + } + + if (byType.isEmpty()) { + this.elementMap.remove(type); + } + } + } + } + } + + // last is to perform DB changes + getDao(tx).removeAll(elements); + } +} diff --git a/src/main/java/li/strolch/agent/impl/CachedElementMapHandler.java b/src/main/java/li/strolch/agent/impl/CachedElementMapHandler.java index 951e7f3a2..e45b1515c 100644 --- a/src/main/java/li/strolch/agent/impl/CachedElementMapHandler.java +++ b/src/main/java/li/strolch/agent/impl/CachedElementMapHandler.java @@ -16,22 +16,26 @@ package li.strolch.agent.impl; import java.text.MessageFormat; +import java.util.HashMap; import java.util.List; import java.util.Set; -import li.strolch.agent.api.OrderMap; -import li.strolch.agent.api.ResourceMap; +import li.strolch.agent.api.StrolchAgent; import li.strolch.model.Order; import li.strolch.model.Resource; import li.strolch.persistence.api.OrderDao; +import li.strolch.persistence.api.PersistenceHandler; import li.strolch.persistence.api.ResourceDao; import li.strolch.persistence.api.StrolchTransaction; +import li.strolch.runtime.StrolchConstants; +import li.strolch.runtime.configuration.ComponentConfiguration; +import li.strolch.runtime.configuration.RuntimeConfiguration; import ch.eitchnet.utils.helper.StringHelper; /** * @author Robert von Burg */ -public class CachedElementMapHandler extends InMemoryElementMapHandler { +public class CachedElementMapHandler extends AbstractElementMapHandler { /** * @param container @@ -41,6 +45,24 @@ public class CachedElementMapHandler extends InMemoryElementMapHandler { super(container, componentName); } + @Override + public void initialize(ComponentConfiguration configuration) { + + RuntimeConfiguration runtimeConfiguration = configuration.getRuntimeConfiguration(); + String[] realms = runtimeConfiguration.getStringArray(StrolchAgent.PROP_REALMS, StrolchConstants.DEFAULT_REALM); + + this.realms = new HashMap<>(); + for (String realm : realms) { + PersistenceHandler persistenceHandler = getContainer().getComponent(PersistenceHandler.class); + CachedResourceMap resourceMap = new CachedResourceMap(); + CachedOrderMap orderMap = new CachedOrderMap(); + StrolchRealm strolchRealm = new StrolchRealm(realm, persistenceHandler, resourceMap, orderMap); + this.realms.put(realm, strolchRealm); + } + + super.initialize(configuration); + } + @Override public void start() { @@ -51,28 +73,28 @@ public class CachedElementMapHandler extends InMemoryElementMapHandler { int nrOfResources = 0; StrolchRealm strolchRealm = this.realms.get(realm); - OrderMap orderMap = strolchRealm.getOrderMap(); - ResourceMap resourceMap = strolchRealm.getResourceMap(); + CachedOrderMap orderMap = (CachedOrderMap) strolchRealm.getOrderMap(); + CachedResourceMap resourceMap = (CachedResourceMap) strolchRealm.getResourceMap(); try (StrolchTransaction tx = strolchRealm.openTx()) { - ResourceDao resourceDao = tx.getResourceDao(); + ResourceDao resourceDao = tx.getPersistenceHandler().getResourceDao(tx); Set resourceTypes = resourceDao.queryTypes(); for (String type : resourceTypes) { List resources = resourceDao.queryAll(type); for (Resource resource : resources) { - resourceMap.add(tx, resource); + resourceMap.insert(resource, null); nrOfResources++; } } } try (StrolchTransaction tx = strolchRealm.openTx()) { - OrderDao orderDao = tx.getOrderDao(); + OrderDao orderDao = tx.getPersistenceHandler().getOrderDao(tx); Set orderTypes = orderDao.queryTypes(); for (String type : orderTypes) { List orders = orderDao.queryAll(type); for (Order order : orders) { - orderMap.add(tx, order); + orderMap.insert(order, null); nrOfOrders++; } } diff --git a/src/main/java/li/strolch/agent/impl/CachedOrderMap.java b/src/main/java/li/strolch/agent/impl/CachedOrderMap.java new file mode 100644 index 000000000..d01dff95b --- /dev/null +++ b/src/main/java/li/strolch/agent/impl/CachedOrderMap.java @@ -0,0 +1,14 @@ +package li.strolch.agent.impl; + +import li.strolch.agent.api.OrderMap; +import li.strolch.model.Order; +import li.strolch.persistence.api.OrderDao; +import li.strolch.persistence.api.StrolchTransaction; + +public class CachedOrderMap extends CachedElementMap implements OrderMap { + + @Override + protected OrderDao getDao(StrolchTransaction tx) { + return tx.getPersistenceHandler().getOrderDao(tx); + } +} diff --git a/src/main/java/li/strolch/agent/impl/CachedResourceMap.java b/src/main/java/li/strolch/agent/impl/CachedResourceMap.java new file mode 100644 index 000000000..98473da98 --- /dev/null +++ b/src/main/java/li/strolch/agent/impl/CachedResourceMap.java @@ -0,0 +1,14 @@ +package li.strolch.agent.impl; + +import li.strolch.agent.api.ResourceMap; +import li.strolch.model.Resource; +import li.strolch.persistence.api.ResourceDao; +import li.strolch.persistence.api.StrolchTransaction; + +public class CachedResourceMap extends CachedElementMap implements ResourceMap { + + @Override + protected ResourceDao getDao(StrolchTransaction tx) { + return tx.getPersistenceHandler().getResourceDao(tx); + } +} diff --git a/src/main/java/li/strolch/agent/impl/ComponentContainerImpl.java b/src/main/java/li/strolch/agent/impl/ComponentContainerImpl.java index 1c83070a1..7b93f92da 100644 --- a/src/main/java/li/strolch/agent/impl/ComponentContainerImpl.java +++ b/src/main/java/li/strolch/agent/impl/ComponentContainerImpl.java @@ -39,16 +39,18 @@ public class ComponentContainerImpl implements ComponentContainer { private static final Logger logger = LoggerFactory.getLogger(ComponentContainerImpl.class); + private StrolchAgent agent; + private DataStoreMode dataStoreMode; + private Map, StrolchComponent> componentMap; private Map controllerMap; private ComponentDependencyAnalyzer dependencyAnalyzer; private StrolchConfiguration strolchConfiguration; private ComponentState state; - private StrolchAgent agent; - - public ComponentContainerImpl(StrolchAgent agent) { + public ComponentContainerImpl(StrolchAgent agent, DataStoreMode dataStoreMode) { this.agent = agent; + this.dataStoreMode = dataStoreMode; this.state = ComponentState.UNDEFINED; } @@ -61,6 +63,11 @@ public class ComponentContainerImpl implements ComponentContainer { return this.state; } + @Override + public DataStoreMode getDataStoreMode() { + return this.dataStoreMode; + } + @Override public boolean hasComponent(Class clazz) { return this.componentMap.containsKey(clazz); diff --git a/src/main/java/li/strolch/agent/impl/InMemoryElementMapHandler.java b/src/main/java/li/strolch/agent/impl/InMemoryElementMapHandler.java index 4c5edf568..eaebb4430 100644 --- a/src/main/java/li/strolch/agent/impl/InMemoryElementMapHandler.java +++ b/src/main/java/li/strolch/agent/impl/InMemoryElementMapHandler.java @@ -45,8 +45,8 @@ public class InMemoryElementMapHandler extends AbstractElementMapHandler { this.realms = new HashMap<>(); for (String realm : realms) { PersistenceHandler persistenceHandler = getContainer().getComponent(PersistenceHandler.class); - TransactionalResourceMap resourceMap = new TransactionalResourceMap(realm, persistenceHandler); - TransactionalOrderMap orderMap = new TransactionalOrderMap(realm, persistenceHandler); + TransactionalResourceMap resourceMap = new TransactionalResourceMap(); + TransactionalOrderMap orderMap = new TransactionalOrderMap(); StrolchRealm strolchRealm = new StrolchRealm(realm, persistenceHandler, resourceMap, orderMap); this.realms.put(realm, strolchRealm); } diff --git a/src/main/java/li/strolch/agent/impl/TransactionalElementMap.java b/src/main/java/li/strolch/agent/impl/TransactionalElementMap.java index 7083c91a9..7fd93ce43 100644 --- a/src/main/java/li/strolch/agent/impl/TransactionalElementMap.java +++ b/src/main/java/li/strolch/agent/impl/TransactionalElementMap.java @@ -5,8 +5,6 @@ import java.util.Set; import li.strolch.agent.api.ElementMap; import li.strolch.model.StrolchElement; -import li.strolch.model.query.StrolchQuery; -import li.strolch.persistence.api.PersistenceHandler; import li.strolch.persistence.api.StrolchDao; import li.strolch.persistence.api.StrolchTransaction; @@ -15,24 +13,7 @@ import li.strolch.persistence.api.StrolchTransaction; * * @param */ -public abstract class TransactionalElementMap> implements - ElementMap { - - private PersistenceHandler persistenceHandler; - private String realm; - - public TransactionalElementMap(String realm, PersistenceHandler persistenceHandler) { - this.realm = realm; - this.persistenceHandler = persistenceHandler; - } - - protected String getRealm() { - return this.realm; - } - - protected PersistenceHandler getPersistenceHandler() { - return this.persistenceHandler; - } +public abstract class TransactionalElementMap implements ElementMap { protected abstract StrolchDao getDao(StrolchTransaction tx); @@ -90,4 +71,19 @@ public abstract class TransactionalElementMap elements) { + getDao(tx).saveAll(elements); + } + + @Override + public void removeAll(StrolchTransaction tx, List elements) { + getDao(tx).removeAll(elements); + } + + @Override + public void updateAll(StrolchTransaction tx, List elements) { + getDao(tx).updateAll(elements); + } } diff --git a/src/main/java/li/strolch/agent/impl/TransactionalOrderMap.java b/src/main/java/li/strolch/agent/impl/TransactionalOrderMap.java index 612adc85f..4f3194145 100644 --- a/src/main/java/li/strolch/agent/impl/TransactionalOrderMap.java +++ b/src/main/java/li/strolch/agent/impl/TransactionalOrderMap.java @@ -2,19 +2,13 @@ package li.strolch.agent.impl; import li.strolch.agent.api.OrderMap; import li.strolch.model.Order; -import li.strolch.model.query.OrderQuery; import li.strolch.persistence.api.OrderDao; -import li.strolch.persistence.api.PersistenceHandler; import li.strolch.persistence.api.StrolchTransaction; -public class TransactionalOrderMap extends TransactionalElementMap implements OrderMap { - - public TransactionalOrderMap(String realm, PersistenceHandler persistenceHandler) { - super(realm, persistenceHandler); - } +public class TransactionalOrderMap extends TransactionalElementMap implements OrderMap { @Override protected OrderDao getDao(StrolchTransaction tx) { - return tx.getOrderDao(); + return tx.getPersistenceHandler().getOrderDao(tx); } } diff --git a/src/main/java/li/strolch/agent/impl/TransactionalResourceMap.java b/src/main/java/li/strolch/agent/impl/TransactionalResourceMap.java index 4d54b4ee3..a39f7dd92 100644 --- a/src/main/java/li/strolch/agent/impl/TransactionalResourceMap.java +++ b/src/main/java/li/strolch/agent/impl/TransactionalResourceMap.java @@ -2,19 +2,13 @@ package li.strolch.agent.impl; import li.strolch.agent.api.ResourceMap; import li.strolch.model.Resource; -import li.strolch.model.query.ResourceQuery; -import li.strolch.persistence.api.PersistenceHandler; import li.strolch.persistence.api.ResourceDao; import li.strolch.persistence.api.StrolchTransaction; -public class TransactionalResourceMap extends TransactionalElementMap implements ResourceMap { - - public TransactionalResourceMap(String realm, PersistenceHandler persistenceHandler) { - super(realm, persistenceHandler); - } +public class TransactionalResourceMap extends TransactionalElementMap implements ResourceMap { @Override protected ResourceDao getDao(StrolchTransaction tx) { - return tx.getResourceDao(); + return tx.getPersistenceHandler().getResourceDao(tx); } } diff --git a/src/main/java/li/strolch/persistence/api/PersistenceHandler.java b/src/main/java/li/strolch/persistence/api/PersistenceHandler.java index 08d988591..862c8df95 100644 --- a/src/main/java/li/strolch/persistence/api/PersistenceHandler.java +++ b/src/main/java/li/strolch/persistence/api/PersistenceHandler.java @@ -23,4 +23,8 @@ import li.strolch.agent.impl.StrolchRealm; public interface PersistenceHandler { public StrolchTransaction openTx(StrolchRealm realm); + + public OrderDao getOrderDao(StrolchTransaction tx); + + public ResourceDao getResourceDao(StrolchTransaction tx); } diff --git a/src/main/java/li/strolch/persistence/api/StrolchTransaction.java b/src/main/java/li/strolch/persistence/api/StrolchTransaction.java index cd9e7cfb5..3caf3dcb6 100644 --- a/src/main/java/li/strolch/persistence/api/StrolchTransaction.java +++ b/src/main/java/li/strolch/persistence/api/StrolchTransaction.java @@ -34,8 +34,6 @@ public interface StrolchTransaction extends AutoCloseable { public ResourceMap getResourceMap(); public OrderMap getOrderMap(); - - public OrderDao getOrderDao(); - - public ResourceDao getResourceDao(); + + public PersistenceHandler getPersistenceHandler(); } diff --git a/src/main/java/li/strolch/persistence/inmemory/InMemoryPersistenceHandler.java b/src/main/java/li/strolch/persistence/inmemory/InMemoryPersistenceHandler.java index f080f3e1a..69a573cb0 100644 --- a/src/main/java/li/strolch/persistence/inmemory/InMemoryPersistenceHandler.java +++ b/src/main/java/li/strolch/persistence/inmemory/InMemoryPersistenceHandler.java @@ -22,13 +22,15 @@ public class InMemoryPersistenceHandler extends StrolchComponent implements Pers return new InMemoryTransaction(realm, this); } - public OrderDao getOrderDao() { + @Override + public OrderDao getOrderDao(StrolchTransaction tx) { if (this.orderDao == null) this.orderDao = new InMemoryOrderDao(); return this.orderDao; } - public ResourceDao getResourceDao() { + @Override + public ResourceDao getResourceDao(StrolchTransaction tx) { if (this.resourceDao == null) this.resourceDao = new InMemoryResourceDao(); return this.resourceDao; diff --git a/src/main/java/li/strolch/persistence/inmemory/InMemoryTransaction.java b/src/main/java/li/strolch/persistence/inmemory/InMemoryTransaction.java index 5f4030091..b0861a870 100644 --- a/src/main/java/li/strolch/persistence/inmemory/InMemoryTransaction.java +++ b/src/main/java/li/strolch/persistence/inmemory/InMemoryTransaction.java @@ -7,8 +7,7 @@ import li.strolch.agent.impl.StrolchRealm; import li.strolch.model.StrolchElement; import li.strolch.persistence.api.AbstractTransaction; import li.strolch.persistence.api.ModificationResult; -import li.strolch.persistence.api.OrderDao; -import li.strolch.persistence.api.ResourceDao; +import li.strolch.persistence.api.PersistenceHandler; import li.strolch.persistence.api.StrolchPersistenceException; import li.strolch.persistence.api.TransactionCloseStrategy; import li.strolch.persistence.api.TransactionResult; @@ -153,12 +152,7 @@ public class InMemoryTransaction extends AbstractTransaction { } @Override - public OrderDao getOrderDao() { - return this.persistenceHandler.getOrderDao(); - } - - @Override - public ResourceDao getResourceDao() { - return this.persistenceHandler.getResourceDao(); + public PersistenceHandler getPersistenceHandler() { + return this.persistenceHandler; } } diff --git a/src/test/java/li/strolch/runtime/test/component/ComponentContainerTest.java b/src/test/java/li/strolch/runtime/test/component/ComponentContainerTest.java index 9c8c488e9..dcf11e864 100644 --- a/src/test/java/li/strolch/runtime/test/component/ComponentContainerTest.java +++ b/src/test/java/li/strolch/runtime/test/component/ComponentContainerTest.java @@ -22,9 +22,13 @@ import java.io.File; import java.text.MessageFormat; import li.strolch.agent.api.ComponentContainer; +import li.strolch.agent.api.OrderMap; +import li.strolch.agent.api.ResourceMap; import li.strolch.agent.api.StrolchAgent; import li.strolch.model.ModelGenerator; +import li.strolch.model.Order; import li.strolch.model.Resource; +import li.strolch.persistence.api.OrderDao; import li.strolch.persistence.api.ResourceDao; import li.strolch.persistence.api.StrolchTransaction; import li.strolch.runtime.configuration.RuntimeConfiguration; @@ -88,6 +92,7 @@ public class ComponentContainerTest { try { StrolchAgent agent = startContainer(PATH_TRANSACTIONAL_RUNTIME, PATH_TRANSACTIONAL_CONTAINER); testPersistenceContainer(agent); + testElementMaps(agent); destroyContainer(agent); } catch (Exception e) { logger.error(e.getMessage(), e); @@ -101,6 +106,7 @@ public class ComponentContainerTest { try { StrolchAgent agent = startContainer(PATH_CACHED_RUNTIME, PATH_CACHED_CONTAINER); testPersistenceContainer(agent); + testElementMaps(agent); destroyContainer(agent); } catch (Exception e) { logger.error(e.getMessage(), e); @@ -129,7 +135,8 @@ public class ComponentContainerTest { ServiceResultTest result = serviceHandler.doService(); assertEquals(1, result.getResult()); - ResourceGeneratorHandlerTest resourceGeneratorHandler = container.getComponent(ResourceGeneratorHandlerTest.class); + ResourceGeneratorHandlerTest resourceGeneratorHandler = container + .getComponent(ResourceGeneratorHandlerTest.class); Resource resource = resourceGeneratorHandler.getTestResource("@testRes", "Test Res", "Test"); assertNotNull(resource); assertEquals("@testRes", resource.getId()); @@ -144,11 +151,40 @@ public class ComponentContainerTest { assertEquals(1, result.getResult()); try (StrolchTransaction tx = container.getDefaultRealm().openTx()) { - ResourceDao resourceDao = tx.getResourceDao(); - resourceDao.save(ModelGenerator.createResource("@testRes", "Test Res", "Test")); - Resource queriesRes = resourceDao.queryBy("Test", "@testRes"); - assertNotNull(queriesRes); - assertEquals("@testRes", queriesRes.getId()); + ResourceDao resourceDao = tx.getPersistenceHandler().getResourceDao(tx); + resourceDao.save(ModelGenerator.createResource("@testRes0", "Test Res", "Test")); + Resource queriedRes = resourceDao.queryBy("Test", "@testRes0"); + assertNotNull(queriedRes); + assertEquals("@testRes0", queriedRes.getId()); + } + + try (StrolchTransaction tx = container.getDefaultRealm().openTx()) { + OrderDao orderDao = tx.getPersistenceHandler().getOrderDao(tx); + orderDao.save(ModelGenerator.createOrder("@testOrder0", "Test Order", "Test")); + Order queriedOrder = orderDao.queryBy("Test", "@testOrder0"); + assertNotNull(queriedOrder); + assertEquals("@testOrder0", queriedOrder.getId()); + } + } + + private static void testElementMaps(StrolchAgent agent) { + + ComponentContainer container = agent.getContainer(); + + try (StrolchTransaction tx = container.getDefaultRealm().openTx()) { + ResourceMap resourceMap = tx.getResourceMap(); + resourceMap.add(tx, ModelGenerator.createResource("@testRes1", "Test Res", "Test")); + Resource queriedRes = resourceMap.getBy(tx, "Test", "@testRes1"); + assertNotNull(queriedRes); + assertEquals("@testRes1", queriedRes.getId()); + } + + try (StrolchTransaction tx = container.getDefaultRealm().openTx()) { + OrderMap orderMap = tx.getOrderMap(); + orderMap.add(tx, ModelGenerator.createOrder("@testOrder1", "Test Order", "Test")); + Order queriedOrder = orderMap.getBy(tx, "Test", "@testOrder1"); + assertNotNull(queriedOrder); + assertEquals("@testOrder1", queriedOrder.getId()); } } diff --git a/src/test/java/li/strolch/runtime/test/component/ControllerDependencyTest.java b/src/test/java/li/strolch/runtime/test/component/ControllerDependencyTest.java index 1f41c3140..3a8366019 100644 --- a/src/test/java/li/strolch/runtime/test/component/ControllerDependencyTest.java +++ b/src/test/java/li/strolch/runtime/test/component/ControllerDependencyTest.java @@ -29,6 +29,7 @@ import li.strolch.agent.api.StrolchComponent; import li.strolch.agent.impl.ComponentContainerImpl; import li.strolch.agent.impl.ComponentController; import li.strolch.agent.impl.ComponentDependencyAnalyzer; +import li.strolch.agent.impl.DataStoreMode; import li.strolch.runtime.configuration.ConfigurationParser; import li.strolch.runtime.configuration.StrolchConfiguration; import li.strolch.runtime.configuration.StrolchConfigurationException; @@ -110,7 +111,7 @@ public class ControllerDependencyTest { @Before public void setupModel() { - this.container = new ComponentContainerImpl(null); + this.container = new ComponentContainerImpl(null, DataStoreMode.EMPTY); this.con2 = new ComponentController(new StrolchComponent(this.container, "2")); this.con5 = new ComponentController(new StrolchComponent(this.container, "5")); @@ -539,7 +540,7 @@ public class ControllerDependencyTest { @Test public void shouldAddDepedencies() { - ComponentContainerImpl container = new ComponentContainerImpl(null); + ComponentContainerImpl container = new ComponentContainerImpl(null, DataStoreMode.EMPTY); StrolchComponent component = new StrolchComponent(container, "1"); //$NON-NLS-1$ ComponentController controller = new ComponentController(component); diff --git a/src/test/java/li/strolch/runtime/test/query/inmemory/QueryTest.java b/src/test/java/li/strolch/runtime/test/query/inmemory/QueryTest.java index a8ba8b980..c3f2a4041 100644 --- a/src/test/java/li/strolch/runtime/test/query/inmemory/QueryTest.java +++ b/src/test/java/li/strolch/runtime/test/query/inmemory/QueryTest.java @@ -77,7 +77,7 @@ public class QueryTest { InMemoryQuery inMemoryQuery = resourceQuery.visit(query); List result; try (StrolchTransaction tx = container.getDefaultRealm().openTx()) { - result = inMemoryQuery.doQuery(tx.getResourceDao()); + result = inMemoryQuery.doQuery(tx.getPersistenceHandler().getResourceDao(tx)); } assertEquals(1, result.size()); assertEquals("@1", result.get(0).getId()); @@ -108,7 +108,7 @@ public class QueryTest { InMemoryQuery inMemoryQuery = orderQuery.visit(query); List result; try (StrolchTransaction tx = container.getDefaultRealm().openTx()) { - result = inMemoryQuery.doQuery(tx.getOrderDao()); + result = inMemoryQuery.doQuery(tx.getPersistenceHandler().getOrderDao(tx)); } assertEquals(1, result.size()); assertEquals("@1", result.get(0).getId());