From c35a79a0e94fba0e404f09b25cef3f84a5ca60dc Mon Sep 17 00:00:00 2001 From: Mark Fisher Date: Thu, 4 Aug 2011 16:16:13 -0400 Subject: [PATCH] INT-2032 migrated 'spring-integration-gemfire' to main branch from sandbox in preparation for 2.1 development --- build.gradle | 17 +- pom.xml | 1 + settings.gradle | 1 + spring-integration-amqp/pom.xml | 42 +-- spring-integration-core/pom.xml | 42 +-- spring-integration-event/pom.xml | 42 +-- spring-integration-feed/pom.xml | 42 +-- spring-integration-file/pom.xml | 42 +-- spring-integration-ftp/pom.xml | 36 +- spring-integration-gemfire/pom.xml | 183 ++++++++++ .../CacheListeningMessageProducer.java | 147 ++++++++ .../ContinuousQueryMessageProducer.java | 205 +++++++++++ .../gemfire/inbound/EventType.java | 35 ++ .../outbound/CacheWritingMessageHandler.java | 65 ++++ .../store/GemfireMessageGroupStore.java | 41 +++ .../gemfire/store/GemfireMessageStore.java | 57 +++ .../gemfire/store/KeyValueMessageGroup.java | 339 ++++++++++++++++++ .../store/KeyValueMessageGroupStore.java | 155 ++++++++ .../gemfire/TestCacheListenerLogger.java | 57 +++ .../CacheListeningMessageProducerTests.java | 141 ++++++++ .../inbound/cq/CqServiceActivator.java | 32 ++ .../cq/client/CqClientConfiguration.java | 126 +++++++ .../cq/server/CqServerConfiguration.java | 78 ++++ .../CacheWritingMessageHandlerTests.java | 60 ++++ .../store/GemfireMessageStoreTests.java | 57 +++ .../GemfireMessageStoreConfiguration.java | 70 ++++ .../gemfire/store/messagegroupstore/Main.java | 41 +++ .../MessageGroupStoreActivator.java | 44 +++ .../store/messagegroupstore/Producer.java | 74 ++++ .../gemfire/inbound/cq/CqClient-context.xml | 26 ++ .../gemfire/inbound/cq/CqServer-context.xml | 28 ++ .../gemfire/inbound/cq/common.properties | 5 + .../gemfire/inbound/cq/gfe-cache.properties | 3 + .../GemfireMessageStore-context.xml | 35 ++ spring-integration-gemfire/template.mf | 16 + spring-integration-groovy/pom.xml | 26 +- spring-integration-http/pom.xml | 48 +-- spring-integration-ip/pom.xml | 50 +-- spring-integration-jdbc/pom.xml | 56 +-- spring-integration-jms/pom.xml | 58 +-- spring-integration-jmx/pom.xml | 42 +-- spring-integration-mail/pom.xml | 48 +-- spring-integration-mongodb/pom.xml | 38 +- spring-integration-redis/pom.xml | 38 +- spring-integration-rmi/pom.xml | 48 +-- spring-integration-scripting/pom.xml | 36 +- spring-integration-security/pom.xml | 38 +- spring-integration-sftp/pom.xml | 60 ++-- spring-integration-stream/pom.xml | 30 +- spring-integration-test/pom.xml | 36 +- spring-integration-twitter/pom.xml | 48 +-- spring-integration-ws/pom.xml | 50 +-- spring-integration-xml/pom.xml | 50 +-- spring-integration-xmpp/pom.xml | 60 ++-- 54 files changed, 2690 insertions(+), 555 deletions(-) create mode 100644 spring-integration-gemfire/pom.xml create mode 100644 spring-integration-gemfire/src/main/java/org/springframework/integration/gemfire/inbound/CacheListeningMessageProducer.java create mode 100644 spring-integration-gemfire/src/main/java/org/springframework/integration/gemfire/inbound/ContinuousQueryMessageProducer.java create mode 100644 spring-integration-gemfire/src/main/java/org/springframework/integration/gemfire/inbound/EventType.java create mode 100644 spring-integration-gemfire/src/main/java/org/springframework/integration/gemfire/outbound/CacheWritingMessageHandler.java create mode 100644 spring-integration-gemfire/src/main/java/org/springframework/integration/gemfire/store/GemfireMessageGroupStore.java create mode 100644 spring-integration-gemfire/src/main/java/org/springframework/integration/gemfire/store/GemfireMessageStore.java create mode 100644 spring-integration-gemfire/src/main/java/org/springframework/integration/gemfire/store/KeyValueMessageGroup.java create mode 100644 spring-integration-gemfire/src/main/java/org/springframework/integration/gemfire/store/KeyValueMessageGroupStore.java create mode 100644 spring-integration-gemfire/src/test/java/org/springframework/integration/gemfire/TestCacheListenerLogger.java create mode 100644 spring-integration-gemfire/src/test/java/org/springframework/integration/gemfire/inbound/CacheListeningMessageProducerTests.java create mode 100644 spring-integration-gemfire/src/test/java/org/springframework/integration/gemfire/inbound/cq/CqServiceActivator.java create mode 100644 spring-integration-gemfire/src/test/java/org/springframework/integration/gemfire/inbound/cq/client/CqClientConfiguration.java create mode 100644 spring-integration-gemfire/src/test/java/org/springframework/integration/gemfire/inbound/cq/server/CqServerConfiguration.java create mode 100644 spring-integration-gemfire/src/test/java/org/springframework/integration/gemfire/outbound/CacheWritingMessageHandlerTests.java create mode 100644 spring-integration-gemfire/src/test/java/org/springframework/integration/gemfire/store/GemfireMessageStoreTests.java create mode 100644 spring-integration-gemfire/src/test/java/org/springframework/integration/gemfire/store/messagegroupstore/GemfireMessageStoreConfiguration.java create mode 100644 spring-integration-gemfire/src/test/java/org/springframework/integration/gemfire/store/messagegroupstore/Main.java create mode 100644 spring-integration-gemfire/src/test/java/org/springframework/integration/gemfire/store/messagegroupstore/MessageGroupStoreActivator.java create mode 100644 spring-integration-gemfire/src/test/java/org/springframework/integration/gemfire/store/messagegroupstore/Producer.java create mode 100644 spring-integration-gemfire/src/test/resources/org/springframework/integration/gemfire/inbound/cq/CqClient-context.xml create mode 100644 spring-integration-gemfire/src/test/resources/org/springframework/integration/gemfire/inbound/cq/CqServer-context.xml create mode 100644 spring-integration-gemfire/src/test/resources/org/springframework/integration/gemfire/inbound/cq/common.properties create mode 100644 spring-integration-gemfire/src/test/resources/org/springframework/integration/gemfire/inbound/cq/gfe-cache.properties create mode 100644 spring-integration-gemfire/src/test/resources/org/springframework/integration/gemfire/store/messagegroupstore/GemfireMessageStore-context.xml create mode 100644 spring-integration-gemfire/template.mf diff --git a/build.gradle b/build.gradle index 3e24f48d2c..7ce68314ff 100644 --- a/build.gradle +++ b/build.gradle @@ -121,12 +121,12 @@ configure(javaprojects) { junitVersion = '4.8.2' log4jVersion = '1.2.12' mockitoVersion = '1.8.4' - //springVersion = '3.1.0.M2' - springVersion = '3.0.6.BUILD-SNAPSHOT' + springVersion = '3.1.0.M2' springAmqpVersion = '1.0.0.BUILD-SNAPSHOT' springDataMongoVersion = '1.0.0.BUILD-SNAPSHOT' springDataCommonsVersion = '1.2.0.BUILD-SNAPSHOT' springDataRedisVersion = '1.0.0.BUILD-SNAPSHOT' + springGemfireVersion = '1.0.1.RELEASE' springSecurityVersion = '3.0.5.RELEASE' springWsVersion = '2.0.2.RELEASE' @@ -233,6 +233,19 @@ project('spring-integration-ftp') { } } +project('spring-integration-gemfire') { + description = 'Spring Integration GemFire Support' + dependencies { + compile project(":spring-integration-core") + compile "org.springframework:spring-context:$springVersion" + compile "org.springframework.data.gemfire:spring-gemfire:$springGemfireVersion" + testCompile project(":spring-integration-stream") + } + repositories { + mavenRepo urls: 'http://dist.gemstone.com/maven/release' // for gemfire + } +} + project('spring-integration-groovy') { description = 'Spring Integration Groovy Support' dependencies { diff --git a/pom.xml b/pom.xml index d2596e7b24..76076b0006 100644 --- a/pom.xml +++ b/pom.xml @@ -14,6 +14,7 @@ spring-integration-feed spring-integration-file spring-integration-ftp + spring-integration-gemfire spring-integration-groovy spring-integration-http spring-integration-ip diff --git a/settings.gradle b/settings.gradle index b21f690c05..dcf01a2a5b 100644 --- a/settings.gradle +++ b/settings.gradle @@ -23,6 +23,7 @@ include 'spring-integration-event' include 'spring-integration-feed' include 'spring-integration-file' include 'spring-integration-ftp' +include 'spring-integration-gemfire' include 'spring-integration-groovy' include 'spring-integration-http' include 'spring-integration-ip' diff --git a/spring-integration-amqp/pom.xml b/spring-integration-amqp/pom.xml index 62ac603b39..f99112709f 100644 --- a/spring-integration-amqp/pom.xml +++ b/spring-integration-amqp/pom.xml @@ -100,41 +100,23 @@ - - org.springframework.integration - spring-integration-stream - 2.1.0.BUILD-SNAPSHOT - test - org.easymock easymock 2.3 test - - org.springframework - spring-test - 3.0.6.BUILD-SNAPSHOT - test - org.easymock easymockclassextension 2.3 test - - org.hamcrest - hamcrest-all - 1.1 - test - org.springframework - spring-context - 3.0.6.BUILD-SNAPSHOT - compile + spring-test + 3.1.0.M2 + test org.springframework.integration @@ -142,6 +124,24 @@ 2.1.0.BUILD-SNAPSHOT compile + + org.springframework.integration + spring-integration-stream + 2.1.0.BUILD-SNAPSHOT + test + + + org.springframework + spring-context + 3.1.0.M2 + compile + + + org.hamcrest + hamcrest-all + 1.1 + test + org.mockito mockito-all diff --git a/spring-integration-core/pom.xml b/spring-integration-core/pom.xml index 5d99850fa7..f610bb7282 100644 --- a/spring-integration-core/pom.xml +++ b/spring-integration-core/pom.xml @@ -102,28 +102,16 @@ org.springframework - spring-aop - 3.0.6.BUILD-SNAPSHOT + spring-context + 3.1.0.M2 compile - - org.springframework - spring-test - 3.0.6.BUILD-SNAPSHOT - test - org.aspectj aspectjweaver 1.6.8 test - - org.springframework - spring-context - 3.0.6.BUILD-SNAPSHOT - compile - cglib cglib-nodep @@ -142,6 +130,12 @@ 2.3 test + + org.springframework + spring-aop + 3.1.0.M2 + compile + org.easymock easymockclassextension @@ -155,6 +149,12 @@ compile true + + org.springframework + spring-test + 3.1.0.M2 + test + org.hamcrest hamcrest-all @@ -167,19 +167,19 @@ 1.8.4 test + + org.springframework + spring-tx + 3.1.0.M2 + compile + true + org.aspectj aspectjrt 1.6.8 test - - org.springframework - spring-tx - 3.0.6.BUILD-SNAPSHOT - compile - true - junit junit-dep diff --git a/spring-integration-event/pom.xml b/spring-integration-event/pom.xml index 41230dcf0f..de503bf3db 100644 --- a/spring-integration-event/pom.xml +++ b/spring-integration-event/pom.xml @@ -100,41 +100,23 @@ - - org.springframework.integration - spring-integration-test - 2.1.0.BUILD-SNAPSHOT - test - org.easymock easymock 2.3 test - - org.springframework - spring-test - 3.0.6.BUILD-SNAPSHOT - test - org.easymock easymockclassextension 2.3 test - - org.hamcrest - hamcrest-all - 1.1 - test - org.springframework - spring-context - 3.0.6.BUILD-SNAPSHOT - compile + spring-test + 3.1.0.M2 + test org.springframework.integration @@ -142,6 +124,24 @@ 2.1.0.BUILD-SNAPSHOT compile + + org.springframework.integration + spring-integration-test + 2.1.0.BUILD-SNAPSHOT + test + + + org.springframework + spring-context + 3.1.0.M2 + compile + + + org.hamcrest + hamcrest-all + 1.1 + test + org.mockito mockito-all diff --git a/spring-integration-feed/pom.xml b/spring-integration-feed/pom.xml index 3d69f94733..ba456593cc 100644 --- a/spring-integration-feed/pom.xml +++ b/spring-integration-feed/pom.xml @@ -102,9 +102,9 @@ org.springframework - spring-test - 3.0.6.BUILD-SNAPSHOT - test + spring-context + 3.1.0.M2 + compile net.java.dev.rome @@ -118,12 +118,6 @@ - - org.springframework - spring-context - 3.0.6.BUILD-SNAPSHOT - compile - cglib cglib-nodep @@ -136,12 +130,6 @@ 1.2.12 test - - org.springframework.integration - spring-integration-test - 2.1.0.BUILD-SNAPSHOT - test - org.easymock easymock @@ -154,6 +142,24 @@ 2.3 test + + org.springframework + spring-test + 3.1.0.M2 + test + + + org.springframework.integration + spring-integration-core + 2.1.0.BUILD-SNAPSHOT + compile + + + org.springframework.integration + spring-integration-test + 2.1.0.BUILD-SNAPSHOT + test + org.hamcrest hamcrest-all @@ -166,12 +172,6 @@ 1.8.4 test - - org.springframework.integration - spring-integration-core - 2.1.0.BUILD-SNAPSHOT - compile - net.java.dev.rome rome diff --git a/spring-integration-file/pom.xml b/spring-integration-file/pom.xml index 36e6b5471f..7e1578f79b 100644 --- a/spring-integration-file/pom.xml +++ b/spring-integration-file/pom.xml @@ -100,41 +100,23 @@ - - org.springframework.integration - spring-integration-test - 2.1.0.BUILD-SNAPSHOT - test - org.easymock easymock 2.3 test - - org.springframework - spring-test - 3.0.6.BUILD-SNAPSHOT - test - org.easymock easymockclassextension 2.3 test - - org.hamcrest - hamcrest-all - 1.1 - test - org.springframework - spring-context - 3.0.6.BUILD-SNAPSHOT - compile + spring-test + 3.1.0.M2 + test org.springframework.integration @@ -142,6 +124,24 @@ 2.1.0.BUILD-SNAPSHOT compile + + org.springframework.integration + spring-integration-test + 2.1.0.BUILD-SNAPSHOT + test + + + org.springframework + spring-context + 3.1.0.M2 + compile + + + org.hamcrest + hamcrest-all + 1.1 + test + org.mockito mockito-all diff --git a/spring-integration-ftp/pom.xml b/spring-integration-ftp/pom.xml index 826c2d6679..934b19299b 100644 --- a/spring-integration-ftp/pom.xml +++ b/spring-integration-ftp/pom.xml @@ -100,12 +100,6 @@ - - org.springframework - spring-test - 3.0.6.BUILD-SNAPSHOT - test - org.springframework.integration spring-integration-file @@ -124,12 +118,6 @@ 1.2.12 test - - org.springframework.integration - spring-integration-test - 2.1.0.BUILD-SNAPSHOT - test - commons-net commons-net @@ -148,6 +136,18 @@ 2.3 test + + org.springframework + spring-test + 3.1.0.M2 + test + + + org.springframework + spring-context-support + 3.1.0.M2 + compile + javax.activation activation @@ -155,18 +155,18 @@ compile true + + org.springframework.integration + spring-integration-test + 2.1.0.BUILD-SNAPSHOT + test + org.hamcrest hamcrest-all 1.1 test - - org.springframework - spring-context-support - 3.0.6.BUILD-SNAPSHOT - compile - org.mockito mockito-all diff --git a/spring-integration-gemfire/pom.xml b/spring-integration-gemfire/pom.xml new file mode 100644 index 0000000000..565db60ce4 --- /dev/null +++ b/spring-integration-gemfire/pom.xml @@ -0,0 +1,183 @@ + + + 4.0.0 + org.springframework.integration + spring-integration-gemfire + 2.1.0.BUILD-SNAPSHOT + Spring Integration GemFire Support + + + The Apache Software License, Version 2.0 + http://www.apache.org/licenses/LICENSE-2.0.txt + repo + + + + + + src/main/java + + **/* + + + **/*.java + + + + src/main/resources + + **/* + + + + + + src/test/java + + **/* + + + **/*.java + + + + src/test/resources + + **/* + + + + + + maven-compiler-plugin + + 1.5 + 1.5 + + + + maven-surefire-plugin + + + **/*Tests.java + + + **/*Abstract*.java + + + + + + + + http://dist.gemstone.com/maven/release + http://dist.gemstone.com/maven/release + + + http://download.java.net/maven/2 + http://download.java.net/maven/2 + + + http://maven.springframework.org/milestone + http://maven.springframework.org/milestone + + + http://maven.springframework.org/release + http://maven.springframework.org/release + + + http://maven.springframework.org/snapshot + http://maven.springframework.org/snapshot + + + http://repository.springsource.com/maven/bundles/external + http://repository.springsource.com/maven/bundles/external + + + http://repository.springsource.com/maven/bundles/milestone + http://repository.springsource.com/maven/bundles/milestone + + + http://repository.springsource.com/maven/bundles/release + http://repository.springsource.com/maven/bundles/release + + + + + org.easymock + easymock + 2.3 + test + + + org.easymock + easymockclassextension + 2.3 + test + + + org.springframework + spring-test + 3.1.0.M2 + test + + + org.springframework.data.gemfire + spring-gemfire + 1.0.1.RELEASE + compile + + + org.springframework.integration + spring-integration-core + 2.1.0.BUILD-SNAPSHOT + compile + + + org.springframework.integration + spring-integration-stream + 2.1.0.BUILD-SNAPSHOT + test + + + org.springframework + spring-context + 3.1.0.M2 + compile + + + org.hamcrest + hamcrest-all + 1.1 + test + + + org.mockito + mockito-all + 1.8.4 + test + + + log4j + log4j + 1.2.12 + test + + + cglib + cglib-nodep + 2.2 + test + + + junit + junit-dep + 4.8.2 + test + + + + UTF8 + + diff --git a/spring-integration-gemfire/src/main/java/org/springframework/integration/gemfire/inbound/CacheListeningMessageProducer.java b/spring-integration-gemfire/src/main/java/org/springframework/integration/gemfire/inbound/CacheListeningMessageProducer.java new file mode 100644 index 0000000000..8890082244 --- /dev/null +++ b/spring-integration-gemfire/src/main/java/org/springframework/integration/gemfire/inbound/CacheListeningMessageProducer.java @@ -0,0 +1,147 @@ +/* + * Copyright 2002-2011 the original author or authors. + * + * 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 org.springframework.integration.gemfire.inbound; + +import java.util.Arrays; +import java.util.HashSet; +import java.util.Set; + +import org.apache.commons.logging.Log; +import org.apache.commons.logging.LogFactory; + +import org.springframework.expression.Expression; +import org.springframework.expression.spel.standard.SpelExpressionParser; +import org.springframework.integration.endpoint.MessageProducerSupport; +import org.springframework.integration.support.MessageBuilder; +import org.springframework.util.Assert; + +import com.gemstone.gemfire.cache.CacheListener; +import com.gemstone.gemfire.cache.EntryEvent; +import com.gemstone.gemfire.cache.Region; +import com.gemstone.gemfire.cache.util.CacheListenerAdapter; + +/** + * An inbound endpoint that listens to a GemFire region for events and then publishes Messages to + * a channel. The default supported event types are CREATED and UPDATED. See the {@link EventType} + * enum for all options. A SpEL expression may be provided to generate a Message payload by + * evaluating that expression against the {@link EntryEvent} instance as the root object. If no + * payloadExpression is provided, the {@link EntryEvent} itself will be the payload. + * + * @author Mark Fisher + * @since 2.1 + */ +@SuppressWarnings({"rawtypes", "unchecked"}) +public class CacheListeningMessageProducer extends MessageProducerSupport { + + private final Log logger = LogFactory.getLog(this.getClass()); + + private final Region region; + + private final CacheListener listener; + + private volatile Set supportedEventTypes = + new HashSet(Arrays.asList(EventType.CREATED, EventType.UPDATED)); + + private volatile Expression payloadExpression; + + private final SpelExpressionParser parser = new SpelExpressionParser(); + + + public CacheListeningMessageProducer(Region region) { + Assert.notNull(region, "region must not be null"); + this.region = region; + this.listener = new MessageProducingCacheListener(); + } + + + public void setSupportedEventTypes(EventType... eventTypes) { + Assert.notEmpty(eventTypes, "eventTypes must not be empty"); + this.supportedEventTypes = new HashSet(Arrays.asList(eventTypes)); + } + + public void setPayloadExpression(String payloadExpression) { + if (payloadExpression == null) { + this.payloadExpression = null; + } + else { + this.payloadExpression = this.parser.parseExpression(payloadExpression); + } + } + + @Override + protected void doStart() { + if (logger.isInfoEnabled()) { + logger.info("adding MessageProducingCacheListener to GemFire Region '" + this.region.getName() + "'"); + } + this.region.getAttributesMutator().addCacheListener(this.listener); + } + + @Override + protected void doStop() { + if (logger.isInfoEnabled()) { + logger.info("removing MessageProducingCacheListener from GemFire Region '" + this.region.getName() + "'"); + } + this.region.getAttributesMutator().removeCacheListener(this.listener); + } + + + private class MessageProducingCacheListener extends CacheListenerAdapter { + + @Override + public void afterCreate(EntryEvent event) { + if (supportedEventTypes.contains(EventType.CREATED)) { + this.processEvent(event); + } + } + + @Override + public void afterUpdate(EntryEvent event) { + if (supportedEventTypes.contains(EventType.UPDATED)) { + this.processEvent(event); + } + } + + @Override + public void afterInvalidate(EntryEvent event) { + if (supportedEventTypes.contains(EventType.INVALIDATED)) { + this.processEvent(event); + } + } + + @Override + public void afterDestroy(EntryEvent event) { + if (supportedEventTypes.contains(EventType.DESTROYED)) { + this.processEvent(event); + } + } + + private void processEvent(EntryEvent event) { + if (payloadExpression != null) { + Object evaluationResult = payloadExpression.getValue(event); + this.publish(evaluationResult); + } + else { + this.publish(event); + } + } + + private void publish(Object payload) { + sendMessage(MessageBuilder.withPayload(payload).build()); + } + } + +} diff --git a/spring-integration-gemfire/src/main/java/org/springframework/integration/gemfire/inbound/ContinuousQueryMessageProducer.java b/spring-integration-gemfire/src/main/java/org/springframework/integration/gemfire/inbound/ContinuousQueryMessageProducer.java new file mode 100644 index 0000000000..2fcfd13871 --- /dev/null +++ b/spring-integration-gemfire/src/main/java/org/springframework/integration/gemfire/inbound/ContinuousQueryMessageProducer.java @@ -0,0 +1,205 @@ +/* + * Copyright 2002-2011 the original author or authors. + * + * 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 org.springframework.integration.gemfire.inbound; + +import org.apache.commons.logging.Log; +import org.apache.commons.logging.LogFactory; + +import org.springframework.integration.Message; +import org.springframework.integration.endpoint.MessageProducerSupport; +import org.springframework.integration.support.MessageBuilder; +import org.springframework.util.Assert; +import org.springframework.util.StringUtils; + +import com.gemstone.gemfire.cache.Region; +import com.gemstone.gemfire.cache.client.Pool; +import com.gemstone.gemfire.cache.query.CqAttributes; +import com.gemstone.gemfire.cache.query.CqAttributesFactory; +import com.gemstone.gemfire.cache.query.CqEvent; +import com.gemstone.gemfire.cache.query.CqException; +import com.gemstone.gemfire.cache.query.CqListener; +import com.gemstone.gemfire.cache.query.CqQuery; +import com.gemstone.gemfire.cache.query.QueryService; + +/** + * Responds to a continuous query (set using the #queryString field) that is + * constantly evaluated against a cache {@link com.gemstone.gemfire.cache.Region}. + * This is much faster than re-querying the cache manually. + * + * @author Josh Long + * @since 2.1 + */ +public class ContinuousQueryMessageProducer extends MessageProducerSupport { + + private final Log logger = LogFactory.getLog(this.getClass()); + + /** + * Not sure yet if there's a way to avoid depending on this. + */ + private volatile Pool pool; + + /** + * Must be provided by the client of this class + */ + private final Region region; + + /** + * Is the queryString durable (optional) + */ + private volatile boolean durable = false; + + /** + * the {@link com.gemstone.gemfire.cache.query.CqQuery} instance created and + * registered with the server + */ + private volatile CqQuery cqQuery; + + /** + * the query to be registered against the cache + */ + private final String queryString; + + /** + * a reference to a {@link com.gemstone.gemfire.cache.query.QueryService} + * that is obtained through the #regionService instance. + */ + private volatile QueryService queryService; + + /** + * used when building the queryString itself - optional + */ + private volatile String queryName; + + /** + * a {@link com.gemstone.gemfire.cache.query.CqAttributesFactory} to generate + * the {@link com.gemstone.gemfire.cache.query.CqAttributes} that in turn + * hold the reference to the listener that we register to in turn funnel + * messages to the clients of this adapter. + */ + private final CqAttributesFactory cqAttributesFactory = new CqAttributesFactory(); + + /** + * the adapter requires a query string to continuously evaluate as well as a + * {@link com.gemstone.gemfire.cache.Region} against which to evaluate the + * query. + * + * @param region + * the region against which the query should be evaluated + * @param queryString + * the query string + */ + public ContinuousQueryMessageProducer(Region region, Pool pool, String queryString) { + this.region = region; + Assert.notNull(this.region, "You must provide a reference to a 'Region'"); + this.pool = pool; + Assert.notNull(this.pool, "You must provide a 'pool'"); + this.queryString = queryString; + Assert.hasText(this.queryString, "You must provide a queryString to evaluate against the region"); + } + + /** + * whether or not the query is durable (that is, whether or not this query + * should live beyond the registered query) + * + * @param durable + * whether or not the query is registered and saved and + * subsequently retrievable by a query name. + */ + public void setDurable(boolean durable) { + this.durable = durable; + } + + /** + * Specify the name of the queryString (optional). + */ + public void setQueryName(String queryName) { + this.queryName = queryName; + } + + @Override + protected void doStart() { + try { + cqQuery.execute(); + } + catch (Throwable e) { + throw new RuntimeException("Failed to start the continuous query", e); + } + } + + @Override + protected void doStop() { + try { + this.cqQuery.stop(); + } + catch (CqException e) { + throw new RuntimeException("Failed to stop the continuous query", e); + } + } + + /** + * hook to handle registration of the query + */ + private CqQuery registerContinuousQuery(QueryService queryService, + String name, String query, boolean durable, CqListener cqListener) throws Throwable { + cqAttributesFactory.addCqListener(cqListener); + CqAttributes attrs = cqAttributesFactory.create(); + CqQuery cqQuery = queryService.newCq(name, query, attrs, durable); + return cqQuery; + } + + @Override + protected void onInit() { + try { + super.onInit(); + + // regionService = this.region.getRegionService(); + queryService = this.pool.getQueryService(); + String defaultName = String.format("%s-%s-query", + getComponentName() + "", getComponentType() + ""); + queryName = StringUtils.hasText(queryName) ? queryName : defaultName; + this.cqQuery = registerContinuousQuery(queryService, queryName, + this.queryString, this.durable, + new MessageProducingCqListener()); + } + catch (Throwable e) { + throw new RuntimeException("Couldn't properly setup the " + getClass().getName(), e); + } + } + + + /** + * Listener that listens for any events being broadcast as a result of the + * evaluation of a continuous query {@link CqQuery}. + */ + class MessageProducingCqListener implements CqListener { + + public void onEvent(CqEvent cqEvent) { + Message cqEventMessage = MessageBuilder.withPayload(cqEvent).build(); + sendMessage(cqEventMessage); + } + + public void onError(CqEvent cqEvent) { + logger.debug("error on " + getClass() + " (a CqListener) "); + throw new RuntimeException("error when interacting with region.", cqEvent.getThrowable()); + } + + public void close() { + logger.debug(getClass() + " close() called"); + } + } + +} diff --git a/spring-integration-gemfire/src/main/java/org/springframework/integration/gemfire/inbound/EventType.java b/spring-integration-gemfire/src/main/java/org/springframework/integration/gemfire/inbound/EventType.java new file mode 100644 index 0000000000..62790e3948 --- /dev/null +++ b/spring-integration-gemfire/src/main/java/org/springframework/integration/gemfire/inbound/EventType.java @@ -0,0 +1,35 @@ +/* + * Copyright 2002-2011 the original author or authors. + * + * 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 org.springframework.integration.gemfire.inbound; + +/** + * Enumeration of GemFire event types. + * + * @author Mark Fisher + * @since 2.1 + */ +public enum EventType { + + CREATED, + + UPDATED, + + DESTROYED, + + INVALIDATED + +} diff --git a/spring-integration-gemfire/src/main/java/org/springframework/integration/gemfire/outbound/CacheWritingMessageHandler.java b/spring-integration-gemfire/src/main/java/org/springframework/integration/gemfire/outbound/CacheWritingMessageHandler.java new file mode 100644 index 0000000000..cde54c777c --- /dev/null +++ b/spring-integration-gemfire/src/main/java/org/springframework/integration/gemfire/outbound/CacheWritingMessageHandler.java @@ -0,0 +1,65 @@ +/* + * Copyright 2002-2011 the original author or authors. + * + * 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 org.springframework.integration.gemfire.outbound; + +import java.util.Map; + +import org.springframework.data.gemfire.GemfireCallback; +import org.springframework.data.gemfire.GemfireTemplate; +import org.springframework.integration.Message; +import org.springframework.integration.core.MessageHandler; +import org.springframework.util.Assert; + +import com.gemstone.gemfire.GemFireCheckedException; +import com.gemstone.gemfire.GemFireException; +import com.gemstone.gemfire.cache.Region; + +/** + * A {@link MessageHandler} implementation that writes to a GemFire Region. + * The Message's payload must be an instance of java.util.Map. + * + * @author Mark Fisher + * @since 2.1 + */ +public class CacheWritingMessageHandler implements MessageHandler { + + private final GemfireTemplate gemfireTemplate = new GemfireTemplate(); + + + @SuppressWarnings("rawtypes") + public CacheWritingMessageHandler(Region region) { + Assert.notNull(region, "region must not be null"); + this.gemfireTemplate.setRegion(region); + this.gemfireTemplate.afterPropertiesSet(); + } + + + public void handleMessage(Message message) { + // TODO: add support for more options to get key/value (SpEL?) + Object payload = message.getPayload(); + Assert.isTrue(payload instanceof Map, "only Map payloads are supported"); + final Map map = (Map) payload; + this.gemfireTemplate.execute(new GemfireCallback() { + @SuppressWarnings({ "rawtypes", "unchecked" }) + public Object doInGemfire(Region region) throws GemFireCheckedException, GemFireException { + region.putAll(map); + return null; + } + }); + } + +} diff --git a/spring-integration-gemfire/src/main/java/org/springframework/integration/gemfire/store/GemfireMessageGroupStore.java b/spring-integration-gemfire/src/main/java/org/springframework/integration/gemfire/store/GemfireMessageGroupStore.java new file mode 100644 index 0000000000..856ff1e5da --- /dev/null +++ b/spring-integration-gemfire/src/main/java/org/springframework/integration/gemfire/store/GemfireMessageGroupStore.java @@ -0,0 +1,41 @@ +/* + * Copyright 2002-2011 the original author or authors. + * + * 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 org.springframework.integration.gemfire.store; + +import org.springframework.integration.Message; + +import com.gemstone.gemfire.cache.Region; + +/** + * Provides GemFire specific support as a backing key-value based {@link org.springframework.integration.store.MessageGroupStore}. + * Currently, this support is limited to explicitly depending on GemFire {@link com.gemstone.gemfire.cache.Region}s, but + * might conceptually also support optimized key traversal (using a {@link com.gemstone.gemfire.cache.query.Query}, for example). + * + * @author Josh Long + * @since 2.1 + * @see {@link org.springframework.integration.gemfire.store.KeyValueMessageGroupStore} + */ +public class GemfireMessageGroupStore extends KeyValueMessageGroupStore { + + public GemfireMessageGroupStore( + Region groupIdToMessageGroup, + Region> marked, + Region> unmarked ) { + super(groupIdToMessageGroup, marked, unmarked); + } + +} diff --git a/spring-integration-gemfire/src/main/java/org/springframework/integration/gemfire/store/GemfireMessageStore.java b/spring-integration-gemfire/src/main/java/org/springframework/integration/gemfire/store/GemfireMessageStore.java new file mode 100644 index 0000000000..222f5efa1f --- /dev/null +++ b/spring-integration-gemfire/src/main/java/org/springframework/integration/gemfire/store/GemfireMessageStore.java @@ -0,0 +1,57 @@ +/* + * Copyright 2002-2011 the original author or authors. + * + * 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 org.springframework.integration.gemfire.store; + +import java.util.UUID; + +import org.springframework.integration.Message; +import org.springframework.integration.store.MessageStore; +import org.springframework.util.Assert; + +import com.gemstone.gemfire.cache.Region; + +/** + * @author Mark Fisher + * @since 2.1 + */ +public class GemfireMessageStore implements MessageStore { + + private final Region> region; + + public GemfireMessageStore(Region> region) { + Assert.notNull(region, "region must not be null"); + this.region = region; + } + + public Message getMessage(UUID id) { + return this.region.get(id); + } + + public Message addMessage(Message message) { + this.region.put(message.getHeaders().getId(), message); + return message; + } + + public Message removeMessage(UUID id) { + return this.region.remove(id); + } + + public int getMessageCount() { + return this.region.size(); + } + +} diff --git a/spring-integration-gemfire/src/main/java/org/springframework/integration/gemfire/store/KeyValueMessageGroup.java b/spring-integration-gemfire/src/main/java/org/springframework/integration/gemfire/store/KeyValueMessageGroup.java new file mode 100644 index 0000000000..525c2c87cd --- /dev/null +++ b/spring-integration-gemfire/src/main/java/org/springframework/integration/gemfire/store/KeyValueMessageGroup.java @@ -0,0 +1,339 @@ +/* + * Copyright 2002-2011 the original author or authors. + * + * 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 org.springframework.integration.gemfire.store; + +import java.io.Serializable; +import java.util.ArrayList; +import java.util.Collection; +import java.util.Map; +import java.util.UUID; +import java.util.concurrent.ConcurrentMap; + +import org.springframework.integration.Message; +import org.springframework.integration.store.MessageGroup; + +/** + * A {@link org.springframework.integration.store.MessageGroup} that manipulates keys and values to provide persistence. + * Responsible for managing one group's messages as a {@link org.springframework.integration.store.MessageGroup}. + * + * @author Josh Long + * @since 2.1 + */ +public class KeyValueMessageGroup implements MessageGroup, Serializable { + + /** + * this should not be persisted. it's passed in through {@link KeyValueMessageGroupStore}, which has the reference to the {@link java.util.concurrent.ConcurrentMap} instance that should be set here + */ + private transient Map> marked; + + /** + * this should not be persisted. it's passed in through {@link KeyValueMessageGroupStore}, which has the reference to the {@link java.util.concurrent.ConcurrentMap} instance that should be set here + */ + private transient Map> unmarked; + + /** + * the #groupId is the unique ID to associate this aggregation of {@link org.springframework.integration.Message}s + */ + private Object groupId; + + /** + * passed in through the {@link org.springframework.integration.store.MessageGroupStore} + */ + private long timestamp; + + + /** + * default javabean ctor (so that this object plays well as a {@link java.io.Serializable} object) + */ + public KeyValueMessageGroup() { + } + + public KeyValueMessageGroup(Object groupId) { + this(groupId, System.currentTimeMillis(), null, null); + } + + public KeyValueMessageGroup(Object groupId, long timestamp, + ConcurrentMap> marked, + ConcurrentMap> unmarked) { + this.groupId = groupId; + this.timestamp = timestamp; + this.marked = marked; + this.unmarked = unmarked; + } + + public KeyValueMessageGroup(Object groupId, + ConcurrentMap> marked, + ConcurrentMap> unmarked) { + this(groupId, System.currentTimeMillis(), marked, unmarked); + } + + + @Override + public int hashCode() { + return groupId.hashCode(); + } + + @Override + public boolean equals(Object obj) { + if (obj instanceof KeyValueMessageGroup) { + Object otherGroupId = ((KeyValueMessageGroup) obj).getGroupId(); + return getGroupId().equals(otherGroupId); + } + return false; + } + + public void setUnmarked(Map> unmarked) { + this.unmarked = unmarked; + } + + public void setMarked( Map> marked) { + this.marked = marked; + } + + /** + * @return the timestamp (milliseconds since epoch) associated with the creation of this group + */ + public long getTimestamp() { + return timestamp; + } + + /** + * Query if the message can be added. + */ + public boolean canAdd(Message message) { + return !isMember(message); + } + + /** + * Add this {@link org.springframework.integration.Message} to the + * {@link org.springframework.integration.store.MessageGroup}, delegating in this case to the {@link #unmarked} field + * + * @param message the {@link org.springframework.integration.Message} you are adding to the {@link java.util.Map} + */ + public void add(Message message) { + if (isMember(message)) { + return; + } + + String unmarkedKey = this.unmarkedKey(message); + this.unmarked.put(unmarkedKey, (Message) message); + } + + /** + * the only reason we differentiate the keys is so that conceptually you could use the same {@link java.util.Map} instance for both marked and unmarked messages. + * + * This method simply differentiates the key, building on {@link #baseKey(org.springframework.integration.Message)}'s return value + * + * @param msg the {@link org.springframework.integration.Message} from which the key should be generated. + * @return a String to be used as a key + */ + protected String markedKey(Message msg) { + return baseKey(msg) + "-m"; + } + + /** + * the only reason we differentiate the keys is so that conceptually you could use the same {@link java.util.Map} instance for both marked and unmarked messages. + * + * This method simply differentiates the key, building on {@link #baseKey(org.springframework.integration.Message)}'s return value + * + * @param msg the {@link org.springframework.integration.Message} from which the key should be generated. + * @return a String to be used as a key + */ + protected String unmarkedKey(Message msg) { + return baseKey(msg) + "-u"; + } + + /** + * Removes this {@link org.springframework.integration.Message} from this {@link org.springframework.integration.store.MessageGroup}'s memory + * + * @param message the message to remove + */ + public void remove(Message message) { + if (unmarked.containsValue(message)) { + unmarked.remove(unmarkedKey(message)); + } + + if (marked.containsValue(message)) { + marked.remove(markedKey(message)); + } + } + + /** + * the groupKey is based on the groupID and it sits at the beginning of all the keys for this {@link org.springframework.integration.store.MessageGroup}s keys + * + * @return a string based on {@link #getGroupId()} + */ + protected String groupKey() { + return (getGroupId()).toString(); + } + + protected String baseKey(Message msg) { + String groupKey = groupKey(); + UUID id = msg.getHeaders().getId(); + Integer sn = msg.getHeaders().getSequenceNumber(); + Integer ss = msg.getHeaders().getSequenceSize(); + + return String.format("%s-%s-%s-%s", groupKey, id.toString(), + sn.toString(), ss.toString()); + } + + public Collection> getUnmarked() { + return getMessagesForMessageGroup(this.unmarked); + } + + /** + * this method will be used to discover all the messages for a given group in a {@link com.gemstone.gemfire.cache.Region} + * + * @param region the region from which we're hoping to discover these {@link org.springframework.integration.Message}s + * @return a collection of messages + */ + protected Collection> getMessagesForMessageGroup( + Map> region) { + try { + String groupMsgKey = groupKey(); + Collection> msgs = new ArrayList>(); + + for (String k : region.keySet()) { + if (k.startsWith(groupMsgKey)) { + msgs.add(region.get(k)); + } + } + + return msgs; + } catch (Throwable th) { + throw new RuntimeException(th); + } + } + + public Collection> getMarked() { + return getMessagesForMessageGroup(this.marked); + } + + /** + * @return the key that links these messages together + */ + public Object getGroupId() { + return groupId; + } + + /** + * @return true if the group is complete (i.e. no more messages are expected to be added) + */ + public boolean isComplete() { + if (size() == 0) { + return true; + } + + int sequenceSize = getSequenceSize(); + + return (sequenceSize > 0) && (sequenceSize == size()); + } + + public int getSequenceSize() { + if (size() == 0) { + return 0; + } + + return getOne().getHeaders().getSequenceSize(); + } + + /** + * Mark the given message in this group. If the message is not part of this group then this call has no effect. + * + * @param messageToMark the message that should be marked + */ + public void mark(Message messageToMark) { + if (this.unmarked.containsValue(messageToMark)) { + this.unmarked.remove(baseKey(messageToMark)); + } + + this.marked.put(baseKey(messageToMark), messageToMark); + } + + public void markAll() { + for (Message msg : getUnmarked()) + mark(msg); + } + + /** + * @return the total number of messages (marked and unmarked) in this group + */ + public int size() { + return getMarked().size() + getUnmarked().size(); + } + + /** + * @return a single message from the group + */ + public Message getOne() { + if (!this.unmarked.isEmpty()) { + String aKey = this.unmarked.keySet().iterator().next(); + + return this.unmarked.get(aKey); + } + + return null; + } + + /** + * This method determines whether messages have been added to this group that supersede the given message based on + * its sequence id. This can be helpful to avoid ending up with sequences larger than their required sequence size + * or sequences that are missing certain sequence numbers. + * + * @param message the message to test for candidacy + * + * @return whether or not the message is a member of the group + * + */ + protected boolean isMember(Message message) { + if (size() == 0) { + return false; + } + + Integer messageSequenceNumber = message.getHeaders().getSequenceNumber(); + + if ((messageSequenceNumber != null) && (messageSequenceNumber > 0)) { + Integer messageSequenceSize = message.getHeaders().getSequenceSize(); + + if (!messageSequenceSize.equals(getSequenceSize())) { + return true; + } else { + if (containsSequenceNumber(getUnmarked(), messageSequenceNumber) || + containsSequenceNumber(getUnmarked(), + messageSequenceNumber)) { + return true; + } + } + } + + return false; + } + + protected boolean containsSequenceNumber(Collection> messages, + Integer messageSequenceNumber) { + for (Message member : messages) { + Integer memberSequenceNumber = member.getHeaders() + .getSequenceNumber(); + + if (messageSequenceNumber.equals(memberSequenceNumber)) { + return true; + } + } + + return false; + } +} diff --git a/spring-integration-gemfire/src/main/java/org/springframework/integration/gemfire/store/KeyValueMessageGroupStore.java b/spring-integration-gemfire/src/main/java/org/springframework/integration/gemfire/store/KeyValueMessageGroupStore.java new file mode 100644 index 0000000000..324094df2b --- /dev/null +++ b/spring-integration-gemfire/src/main/java/org/springframework/integration/gemfire/store/KeyValueMessageGroupStore.java @@ -0,0 +1,155 @@ +/* + * Copyright 2002-2011 the original author or authors. + * + * 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 org.springframework.integration.gemfire.store; + +import org.springframework.integration.Message; +import org.springframework.integration.store.AbstractMessageGroupStore; +import org.springframework.integration.store.MessageGroup; +import org.springframework.util.Assert; + +import java.util.HashSet; +import java.util.Iterator; +import java.util.Map; +import java.util.concurrent.ConcurrentMap; + +/** + * Provides an implementation of {@link org.springframework.integration.store.MessageGroupStore} that delegates to a backend Gemfire instance. + * Gemfire holds keys and values. This class provides a strategy to hold objects. + * + * @author Josh Long + * @since 2.1 + */ +public class KeyValueMessageGroupStore extends AbstractMessageGroupStore { + + /** + * Some operations can be done atomically and we should support them if possible + */ + // TODO: this is unused + //private boolean unmarkedIsConcurrentMap; + + /** + * Some operations can be done atomically and we should support them if possible + */ + // TODO: this is unused + //private boolean markedIsConcurrentMap; + + /** + * Some operations can be done atomically and we should support them if possible + */ + private boolean groupIdToMessageGroupIsConcurrentMap; + + /** + * Required {@link com.gemstone.gemfire.cache.Region} to managed the association of groups => {@link KeyValueMessageGroup} + */ + protected Map groupIdToMessageGroup; + + /** + * Required {@link com.gemstone.gemfire.cache.Region} to manage the #unmarked data + */ + protected Map> unmarked; + + /** + * Required {@link com.gemstone.gemfire.cache.Region} to manage the #marked data + */ + protected Map> marked; + + + /** + * Create a KeyValueMessageGroupStore with two backing regions to handle the state management. + * + * @param groupIdToMessageGroup the region to associate + * @param marked the collection that will hold which messages are marked (delivered) + * @param unmarked the collection that holds which messages are unmarked (not yet delivered) + */ + public KeyValueMessageGroupStore(Map groupIdToMessageGroup, + Map> marked, Map> unmarked) { + this.marked = marked; + // TODO: these claim that a ConcurrentMap is required, but don't enforce it + Assert.notNull(this.marked, + "you must provide a ConcurrentMap to hold String => Message for marked"); + this.unmarked = unmarked; + Assert.notNull(this.unmarked, + "you must provide a ConcurrentMap to hold String => Message for unmarked"); + this.groupIdToMessageGroup = groupIdToMessageGroup; + Assert.notNull(this.groupIdToMessageGroup, + "you must provide a ConcurrentMap to hold associations of group ids to message groups ('groupIdToMessageGroup')"); + //this.markedIsConcurrentMap = marked instanceof ConcurrentMap; + //this.unmarkedIsConcurrentMap = unmarked instanceof ConcurrentMap; + this.groupIdToMessageGroupIsConcurrentMap = this.groupIdToMessageGroup instanceof ConcurrentMap; + } + + + public MessageGroup getMessageGroup(Object groupId) { + Assert.notNull(groupId, "'groupId' must not be null"); + return this.getMessageGroupInternal(groupId); + } + + public MessageGroup addMessageToGroup(Object groupId, Message message) { + KeyValueMessageGroup group = getMessageGroupInternal(groupId); + group.add(message); + return group; + } + + public MessageGroup markMessageGroup(MessageGroup group) { + Object groupId = group.getGroupId(); + KeyValueMessageGroup internal = getMessageGroupInternal(groupId); + internal.markAll(); + return internal; + } + + public void removeMessageGroup(Object groupId) { + groupIdToMessageGroup.remove(groupId); + } + + public MessageGroup removeMessageFromGroup(Object key, Message messageToRemove) { + KeyValueMessageGroup group = getMessageGroupInternal(key); + group.remove(messageToRemove); + return group; + } + + public MessageGroup markMessageFromGroup(Object key, Message messageToMark) { + KeyValueMessageGroup group = getMessageGroupInternal(key); + group.mark(messageToMark); + return group; + } + + @Override + public Iterator iterator() { + return new HashSet(groupIdToMessageGroup.values()).iterator(); + } + + protected KeyValueMessageGroup ensureMessageGroupHasReferencesToRegions(KeyValueMessageGroup keyValueMessageGroup) { + if (keyValueMessageGroup == null) { + return null; + } + keyValueMessageGroup.setMarked(this.marked); + keyValueMessageGroup.setUnmarked(this.unmarked); + return keyValueMessageGroup; + } + + protected KeyValueMessageGroup getMessageGroupInternal(Object groupId) { + if (this.groupIdToMessageGroupIsConcurrentMap) { + ConcurrentMap cm = (ConcurrentMap) this.groupIdToMessageGroup; + cm.putIfAbsent(groupId, new KeyValueMessageGroup(groupId)); + } + else if (!groupIdToMessageGroup.containsKey(groupId)) { + groupIdToMessageGroup.put(groupId, new KeyValueMessageGroup(groupId)); + } + return ensureMessageGroupHasReferencesToRegions(groupIdToMessageGroup.get( groupId)); + } + +} diff --git a/spring-integration-gemfire/src/test/java/org/springframework/integration/gemfire/TestCacheListenerLogger.java b/spring-integration-gemfire/src/test/java/org/springframework/integration/gemfire/TestCacheListenerLogger.java new file mode 100644 index 0000000000..09c8566063 --- /dev/null +++ b/spring-integration-gemfire/src/test/java/org/springframework/integration/gemfire/TestCacheListenerLogger.java @@ -0,0 +1,57 @@ +/* + * Copyright 2002-2011 the original author or authors. + * + * 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 org.springframework.integration.gemfire; + +import com.gemstone.gemfire.cache.EntryEvent; +import com.gemstone.gemfire.cache.util.CacheListenerAdapter; +import org.apache.commons.logging.Log; +import org.apache.commons.logging.LogFactory; + +/** + * (this is the CacheLogger class that ships in the Spring-Gemfire samples) + * + * @author Costin Leau + */ +public class TestCacheListenerLogger extends CacheListenerAdapter { + + private static final Log log = LogFactory.getLog(TestCacheListenerLogger.class); + + @Override + public void afterCreate(EntryEvent event) { + log.info("Added " + messageLog(event) + " to the cache"); + } + + @Override + public void afterDestroy(EntryEvent event) { + log.info("Removed " + messageLog(event) + " from the cache"); + } + + @Override + public void afterUpdate(EntryEvent event) { + log.info("Updated " + messageLog(event) + " in the cache"); + } + + private String messageLog(EntryEvent event) { + Object key = event.getKey(); + Object value = event.getNewValue(); + + if (event.getOperation().isUpdate()) { + return "[" + key + "] from [" + event.getOldValue() + "] to [" + event.getNewValue() + "]"; + } + return "[" + key + "=" + value + "]"; + } +} diff --git a/spring-integration-gemfire/src/test/java/org/springframework/integration/gemfire/inbound/CacheListeningMessageProducerTests.java b/spring-integration-gemfire/src/test/java/org/springframework/integration/gemfire/inbound/CacheListeningMessageProducerTests.java new file mode 100644 index 0000000000..a6f5039e5f --- /dev/null +++ b/spring-integration-gemfire/src/test/java/org/springframework/integration/gemfire/inbound/CacheListeningMessageProducerTests.java @@ -0,0 +1,141 @@ +/* + * Copyright 2002-2011 the original author or authors. + * + * 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 org.springframework.integration.gemfire.inbound; + +import static org.junit.Assert.assertEquals; +import static org.junit.Assert.assertNotNull; +import static org.junit.Assert.assertNull; + +import org.junit.Test; + +import org.springframework.data.gemfire.CacheFactoryBean; +import org.springframework.data.gemfire.RegionFactoryBean; +import org.springframework.integration.Message; +import org.springframework.integration.channel.QueueChannel; + +import com.gemstone.gemfire.cache.Cache; +import com.gemstone.gemfire.cache.Region; + +/** + * @author Mark Fisher + * @since 2.1 + */ +public class CacheListeningMessageProducerTests { + + @Test + public void receiveNewValuePayloadForCreateEvent() throws Exception { + CacheFactoryBean cacheFactoryBean = new CacheFactoryBean(); + cacheFactoryBean.afterPropertiesSet(); + Cache cache = cacheFactoryBean.getObject(); + RegionFactoryBean regionFactoryBean = new RegionFactoryBean(); + regionFactoryBean.setName("test.receiveNewValuePayloadForCreateEvent"); + regionFactoryBean.setCache(cache); + regionFactoryBean.afterPropertiesSet(); + Region region = regionFactoryBean.getObject(); + QueueChannel channel = new QueueChannel(); + CacheListeningMessageProducer producer = new CacheListeningMessageProducer(region); + producer.setPayloadExpression("key + '=' + newValue"); + producer.setOutputChannel(channel); + producer.afterPropertiesSet(); + producer.start(); + assertNull(channel.receive(0)); + region.put("x", "abc"); + Message message = channel.receive(0); + assertNotNull(message); + assertEquals("x=abc", message.getPayload()); + } + + @Test + public void receiveNewValuePayloadForUpdateEvent() throws Exception { + CacheFactoryBean cacheFactoryBean = new CacheFactoryBean(); + cacheFactoryBean.afterPropertiesSet(); + Cache cache = cacheFactoryBean.getObject(); + RegionFactoryBean regionFactoryBean = new RegionFactoryBean(); + regionFactoryBean.setName("test.receiveNewValuePayloadForUpdateEvent"); + regionFactoryBean.setCache(cache); + regionFactoryBean.afterPropertiesSet(); + Region region = regionFactoryBean.getObject(); + QueueChannel channel = new QueueChannel(); + CacheListeningMessageProducer producer = new CacheListeningMessageProducer(region); + producer.setPayloadExpression("newValue"); + producer.setOutputChannel(channel); + producer.afterPropertiesSet(); + producer.start(); + assertNull(channel.receive(0)); + region.put("x", "abc"); + Message message1 = channel.receive(0); + assertNotNull(message1); + assertEquals("abc", message1.getPayload()); + region.put("x", "xyz"); + Message message2 = channel.receive(0); + assertNotNull(message2); + assertEquals("xyz", message2.getPayload()); + } + + @Test + public void receiveOldValuePayloadForDestroyEvent() throws Exception { + CacheFactoryBean cacheFactoryBean = new CacheFactoryBean(); + cacheFactoryBean.afterPropertiesSet(); + Cache cache = cacheFactoryBean.getObject(); + RegionFactoryBean regionFactoryBean = new RegionFactoryBean(); + regionFactoryBean.setName("test.receiveOldValuePayloadForDestroyEvent"); + regionFactoryBean.setCache(cache); + regionFactoryBean.afterPropertiesSet(); + Region region = regionFactoryBean.getObject(); + QueueChannel channel = new QueueChannel(); + CacheListeningMessageProducer producer = new CacheListeningMessageProducer(region); + producer.setSupportedEventTypes(EventType.DESTROYED); + producer.setPayloadExpression("oldValue"); + producer.setOutputChannel(channel); + producer.afterPropertiesSet(); + producer.start(); + assertNull(channel.receive(0)); + region.put("foo", "abc"); + assertNull(channel.receive(0)); + region.destroy("foo"); + Message message2 = channel.receive(0); + assertNotNull(message2); + assertEquals("abc", message2.getPayload()); + } + + @Test + public void receiveOldValuePayloadForInvalidateEvent() throws Exception { + CacheFactoryBean cacheFactoryBean = new CacheFactoryBean(); + cacheFactoryBean.afterPropertiesSet(); + Cache cache = cacheFactoryBean.getObject(); + RegionFactoryBean regionFactoryBean = new RegionFactoryBean(); + regionFactoryBean.setName("test.receiveOldValuePayloadForDestroyEvent"); + regionFactoryBean.setCache(cache); + regionFactoryBean.afterPropertiesSet(); + Region region = regionFactoryBean.getObject(); + QueueChannel channel = new QueueChannel(); + CacheListeningMessageProducer producer = new CacheListeningMessageProducer(region); + producer.setSupportedEventTypes(EventType.INVALIDATED); + producer.setPayloadExpression("key + ' was ' + oldValue"); + producer.setOutputChannel(channel); + producer.afterPropertiesSet(); + producer.start(); + assertNull(channel.receive(0)); + region.put("foo", "abc"); + assertNull(channel.receive(0)); + region.invalidate("foo"); + Message message2 = channel.receive(0); + assertNotNull(message2); + assertEquals("foo was abc", message2.getPayload()); + } + +} diff --git a/spring-integration-gemfire/src/test/java/org/springframework/integration/gemfire/inbound/cq/CqServiceActivator.java b/spring-integration-gemfire/src/test/java/org/springframework/integration/gemfire/inbound/cq/CqServiceActivator.java new file mode 100644 index 0000000000..386d335ee8 --- /dev/null +++ b/spring-integration-gemfire/src/test/java/org/springframework/integration/gemfire/inbound/cq/CqServiceActivator.java @@ -0,0 +1,32 @@ +/* + * Copyright 2002-2011 the original author or authors. + * + * 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 org.springframework.integration.gemfire.inbound.cq; + +import org.springframework.integration.Message; +import org.springframework.integration.annotation.ServiceActivator; + +import com.gemstone.gemfire.cache.query.CqEvent; + +public class CqServiceActivator { + + @ServiceActivator + public void handleMessage(Message msg) throws Exception { + CqEvent cqEvent = msg.getPayload(); + System.out.println( "Received an event from the continuous query adapter: " +cqEvent ); + } + +} diff --git a/spring-integration-gemfire/src/test/java/org/springframework/integration/gemfire/inbound/cq/client/CqClientConfiguration.java b/spring-integration-gemfire/src/test/java/org/springframework/integration/gemfire/inbound/cq/client/CqClientConfiguration.java new file mode 100644 index 0000000000..096eb6d9ed --- /dev/null +++ b/spring-integration-gemfire/src/test/java/org/springframework/integration/gemfire/inbound/cq/client/CqClientConfiguration.java @@ -0,0 +1,126 @@ +/* + * Copyright 2002-2011 the original author or authors. + * + * 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 org.springframework.integration.gemfire.inbound.cq.client; + +import org.springframework.beans.factory.annotation.Value; +import org.springframework.context.annotation.Bean; +import org.springframework.context.annotation.Configuration; +import org.springframework.context.support.ClassPathXmlApplicationContext; +import org.springframework.integration.MessageChannel; +import org.springframework.integration.gemfire.inbound.cq.CqServiceActivator; + +import com.gemstone.gemfire.cache.client.Pool; +import com.gemstone.gemfire.cache.client.PoolManager; + +@Configuration +@SuppressWarnings("unused") +public class CqClientConfiguration { + + @Value("${region-name}") + private String regionName; + + @Value("${host}") + private String host; + + @Value("${region-query}") + private String query; + + @Value("${port}") + private int port; + + @Value("#{cqIn}") + private MessageChannel messageChannel; + + + @Bean + public CqServiceActivator cqServiceActivator() { + return new CqServiceActivator(); + } + + /* todo + protected ClientCache buildCache() throws Throwable { + return new ClientCacheFactory().create(); + } + @Bean + public ClientCache clientCache() throws Throwable { + return buildCache(); + } + + @Bean + public Region clientRegion() throws Throwable { + ClientRegionFactory clientRegionFactory = clientCache().createClientRegionFactory(ClientRegionShortcut.PROXY); + return clientRegionFactory.create(this.regionName); + } +*/ + + @Bean + public Pool pool() throws Throwable { + return this.buildPool(this.host, this.port); + } + + /*@Bean + public ContinuousQueryMessageProducer continuousQueryMessageProducer() throws Throwable { + ContinuousQueryMessageProducer continuousQueryMessageProducer + = new ContinuousQueryMessageProducer( this.clientRegion() , this.pool(), this.query); + continuousQueryMessageProducer.setDurable(true); + continuousQueryMessageProducer.setOutputChannel(this.messageChannel); + continuousQueryMessageProducer.setQueryName("pplQuery"); + return continuousQueryMessageProducer; + } +*/ +/* protected CqQuery registerContinuousQuery(QueryService queryService, String name, String query, boolean durable, CqListener cqListener) throws Throwable { + CqAttributesFactory cqAttributesFactory = new CqAttributesFactory(); + cqAttributesFactory.addCqListener(cqListener); + CqAttributes attrs = cqAttributesFactory.create(); + CqQuery cqQuery = queryService.newCq(name, query, attrs, durable); + cqQuery.execute(); + return cqQuery; + }*/ + + protected Pool buildPool(String host, int port) throws Throwable { + Pool pool = PoolManager.createFactory() + .addServer(host, port) + .setSubscriptionEnabled(true) + .create(host + "Pool"); + return pool; + } + + /** + * the continuous query listener attached to the + */ + /*class MyContinuousQueryListener implements CqListener { + public void onEvent(CqEvent cqEvent) { + System.out.println("Received event: " + + new ToStringCreator(cqEvent)); + } + + public void onError(CqEvent cqEvent) { + } + + public void close() { + } + }*/ + + + public static void main(String[] args) throws Exception { + new ClassPathXmlApplicationContext("org/springframework/integration/gemfire/inbound/cq/CqClient-context.xml"); + while (true) { + Thread.sleep(1000 * 10); + } + } + +} diff --git a/spring-integration-gemfire/src/test/java/org/springframework/integration/gemfire/inbound/cq/server/CqServerConfiguration.java b/spring-integration-gemfire/src/test/java/org/springframework/integration/gemfire/inbound/cq/server/CqServerConfiguration.java new file mode 100644 index 0000000000..30dc43f430 --- /dev/null +++ b/spring-integration-gemfire/src/test/java/org/springframework/integration/gemfire/inbound/cq/server/CqServerConfiguration.java @@ -0,0 +1,78 @@ +/* + * Copyright 2002-2011 the original author or authors. + * + * 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 org.springframework.integration.gemfire.inbound.cq.server; + +import org.springframework.beans.factory.annotation.Value; +import org.springframework.context.annotation.Bean; +import org.springframework.context.annotation.Configuration; +import org.springframework.context.support.ClassPathXmlApplicationContext; +import org.springframework.data.gemfire.GemfireTemplate; + +import com.gemstone.gemfire.cache.Cache; +import com.gemstone.gemfire.cache.Region; +import com.gemstone.gemfire.cache.server.CacheServer; + +@Configuration +@SuppressWarnings("unused") +public class CqServerConfiguration { + + @Value("#{c}") + private Cache cache; + + @Value("#{r}") + private Region region; + + @Value("${region-name}") + private String regionName; + + @Value("${host}") + private String host; + + @Value("${port}") + private int port; + + + @Bean + public GemfireTemplate gemfireTemplate() { + return new GemfireTemplate(this.region); + } + + @Bean + public CacheServer cacheServer() throws Throwable { + CacheServer cacheServer = this.cache.addCacheServer(); + cacheServer.setBindAddress(this.host); + cacheServer.setPort(this.port); + cacheServer.start(); + return cacheServer; + } + + public static void main(String[] args) throws Exception { + ClassPathXmlApplicationContext applicationContext = new ClassPathXmlApplicationContext( + "org/springframework/integration/gemfire/inbound/cq/CqServer-context.xml"); + applicationContext.registerShutdownHook(); + applicationContext.start(); + GemfireTemplate gemfireTemplate = applicationContext.getBean(GemfireTemplate.class); + String letters = "abcdefghijk"; + while (true) { + Thread.sleep(1000 * 10); + for (char c : letters.toCharArray()) { + gemfireTemplate.put("" + c, "value-" + c); + } + } + } + +} diff --git a/spring-integration-gemfire/src/test/java/org/springframework/integration/gemfire/outbound/CacheWritingMessageHandlerTests.java b/spring-integration-gemfire/src/test/java/org/springframework/integration/gemfire/outbound/CacheWritingMessageHandlerTests.java new file mode 100644 index 0000000000..074f0b5fdf --- /dev/null +++ b/spring-integration-gemfire/src/test/java/org/springframework/integration/gemfire/outbound/CacheWritingMessageHandlerTests.java @@ -0,0 +1,60 @@ +/* + * Copyright 2002-2011 the original author or authors. + * + * 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 org.springframework.integration.gemfire.outbound; + +import static org.junit.Assert.assertEquals; + +import java.util.HashMap; +import java.util.Map; + +import org.junit.Test; + +import org.springframework.data.gemfire.CacheFactoryBean; +import org.springframework.data.gemfire.RegionFactoryBean; +import org.springframework.integration.Message; +import org.springframework.integration.support.MessageBuilder; + +import com.gemstone.gemfire.cache.Cache; +import com.gemstone.gemfire.cache.Region; + +/** + * @author Mark Fisher + * @since 2.1 + */ +public class CacheWritingMessageHandlerTests { + + @Test + public void mapPayloadWritesToCache() throws Exception { + CacheFactoryBean cacheFactoryBean = new CacheFactoryBean(); + cacheFactoryBean.afterPropertiesSet(); + Cache cache = cacheFactoryBean.getObject(); + RegionFactoryBean regionFactoryBean = new RegionFactoryBean(); + regionFactoryBean.setName("test.mapPayloadWritesToCache"); + regionFactoryBean.setCache(cache); + regionFactoryBean.afterPropertiesSet(); + Region region = regionFactoryBean.getObject(); + assertEquals(0, region.size()); + CacheWritingMessageHandler handler = new CacheWritingMessageHandler(region); + Map map = new HashMap(); + map.put("foo", "bar"); + Message message = MessageBuilder.withPayload(map).build(); + handler.handleMessage(message); + assertEquals(1, region.size()); + assertEquals("bar", region.get("foo")); + } + +} diff --git a/spring-integration-gemfire/src/test/java/org/springframework/integration/gemfire/store/GemfireMessageStoreTests.java b/spring-integration-gemfire/src/test/java/org/springframework/integration/gemfire/store/GemfireMessageStoreTests.java new file mode 100644 index 0000000000..27b969f0f6 --- /dev/null +++ b/spring-integration-gemfire/src/test/java/org/springframework/integration/gemfire/store/GemfireMessageStoreTests.java @@ -0,0 +1,57 @@ +/* + * Copyright 2002-2010 the original author or authors. + * + * 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 org.springframework.integration.gemfire.store; + +import static org.junit.Assert.assertEquals; + +import java.util.UUID; + +import org.junit.Test; + +import org.springframework.data.gemfire.CacheFactoryBean; +import org.springframework.data.gemfire.RegionFactoryBean; +import org.springframework.integration.Message; +import org.springframework.integration.store.MessageStore; +import org.springframework.integration.support.MessageBuilder; + +import com.gemstone.gemfire.cache.Cache; +import com.gemstone.gemfire.cache.Region; + +/** + * @author Mark Fisher + * @since 2.1 + */ +public class GemfireMessageStoreTests { + + @Test + public void addAndGetMessage() throws Exception { + CacheFactoryBean cacheFactoryBean = new CacheFactoryBean(); + cacheFactoryBean.afterPropertiesSet(); + Cache cache = cacheFactoryBean.getObject(); + RegionFactoryBean> regionFactoryBean = new RegionFactoryBean>(); + regionFactoryBean.setName("test.addAndGetMessage"); + regionFactoryBean.setCache(cache); + regionFactoryBean.afterPropertiesSet(); + Region> region = regionFactoryBean.getObject(); + MessageStore store = new GemfireMessageStore(region); + Message message = MessageBuilder.withPayload("test").build(); + store.addMessage(message); + Message retrieved = store.getMessage(message.getHeaders().getId()); + assertEquals(message, retrieved); + } + +} diff --git a/spring-integration-gemfire/src/test/java/org/springframework/integration/gemfire/store/messagegroupstore/GemfireMessageStoreConfiguration.java b/spring-integration-gemfire/src/test/java/org/springframework/integration/gemfire/store/messagegroupstore/GemfireMessageStoreConfiguration.java new file mode 100644 index 0000000000..74f7b86df7 --- /dev/null +++ b/spring-integration-gemfire/src/test/java/org/springframework/integration/gemfire/store/messagegroupstore/GemfireMessageStoreConfiguration.java @@ -0,0 +1,70 @@ +/* + * Copyright 2002-2011 the original author or authors. + * + * 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 org.springframework.integration.gemfire.store.messagegroupstore; + +import java.util.Map; + +import org.springframework.beans.factory.annotation.Value; +import org.springframework.context.annotation.Bean; +import org.springframework.context.annotation.Configuration; +import org.springframework.integration.Message; +import org.springframework.integration.aggregator.CorrelationStrategy; +import org.springframework.integration.aggregator.HeaderAttributeCorrelationStrategy; +import org.springframework.integration.aggregator.ReleaseStrategy; +import org.springframework.integration.aggregator.SequenceSizeReleaseStrategy; +import org.springframework.integration.gemfire.store.KeyValueMessageGroup; +import org.springframework.integration.gemfire.store.KeyValueMessageGroupStore; + +/** + * Our aggregator needs a {@link org.springframework.integration.gemfire.store.KeyValueMessageGroupStore}. + * This handles configuration of the ancillary objects. + * + * @author Josh Long + * @since 2.1 + */ +@Configuration +public class GemfireMessageStoreConfiguration { + + @Value("${correlation-header}") + private String correlationHeader; + + @Value("#{unmarkedRegion}") + private Map> unmarked; + + @Value("#{markedRegion}") + private Map> marked; + + @Value("#{messageGroupRegion}") + private Map messageGroupRegion; + + + @Bean + public ReleaseStrategy releaseStrategy() { + return new SequenceSizeReleaseStrategy(false); + } + + @Bean + public CorrelationStrategy correlationStrategy() { + return new HeaderAttributeCorrelationStrategy(this.correlationHeader); + } + + @Bean + public KeyValueMessageGroupStore gemfireMessageGroupStore() { + return new KeyValueMessageGroupStore(this.messageGroupRegion, this.marked , this.unmarked ); + } + +} diff --git a/spring-integration-gemfire/src/test/java/org/springframework/integration/gemfire/store/messagegroupstore/Main.java b/spring-integration-gemfire/src/test/java/org/springframework/integration/gemfire/store/messagegroupstore/Main.java new file mode 100644 index 0000000000..1c6450e90a --- /dev/null +++ b/spring-integration-gemfire/src/test/java/org/springframework/integration/gemfire/store/messagegroupstore/Main.java @@ -0,0 +1,41 @@ +/* + * Copyright 2002-2011 the original author or authors. + * + * 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 org.springframework.integration.gemfire.store.messagegroupstore; + +import java.util.Arrays; + +import org.springframework.context.support.ClassPathXmlApplicationContext; + +/** + * Simple example demonstrating the use of a {@link org.springframework.integration.gemfire.store.KeyValueMessageGroupStore}. + * + * @author Josh Long + * @since 2.1 + */ +public class Main { + + public static void main(String[] args) throws Throwable { + ClassPathXmlApplicationContext classPathXmlApplicationContext = new ClassPathXmlApplicationContext( + "/org/springframework/integration/gemfire/store/messagegroupstore/GemfireMessageStore-context.xml"); + Producer producer = classPathXmlApplicationContext.getBean(Producer.class); + for(int i =0 ; i < 10 ; i++ ) { + producer.sendManyMessages(i, Arrays.asList("1,2,3,4,5".split(","))); + } + Thread.sleep( 1000 * 10 ); + } + +} diff --git a/spring-integration-gemfire/src/test/java/org/springframework/integration/gemfire/store/messagegroupstore/MessageGroupStoreActivator.java b/spring-integration-gemfire/src/test/java/org/springframework/integration/gemfire/store/messagegroupstore/MessageGroupStoreActivator.java new file mode 100644 index 0000000000..988f11fc8a --- /dev/null +++ b/spring-integration-gemfire/src/test/java/org/springframework/integration/gemfire/store/messagegroupstore/MessageGroupStoreActivator.java @@ -0,0 +1,44 @@ +/* + * Copyright 2002-2011 the original author or authors. + * + * 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 org.springframework.integration.gemfire.store.messagegroupstore; + +import java.util.Collection; + +import org.springframework.integration.Message; +import org.springframework.integration.annotation.ServiceActivator; +import org.springframework.stereotype.Component; +import org.springframework.util.StringUtils; + +/** + * @author Josh Long + * @since 2.1 + */ +@Component +public class MessageGroupStoreActivator { + + @ServiceActivator + public void activate(Message> msg) throws Throwable { + Collection payloads = msg.getPayload(); + StringBuffer buffer = new StringBuffer(); + for (int i = 0; i < 100; i++) { + buffer.append("-"); + } + System.out.println(buffer.toString()); + System.out.println(StringUtils.collectionToCommaDelimitedString(payloads)); + } + +} diff --git a/spring-integration-gemfire/src/test/java/org/springframework/integration/gemfire/store/messagegroupstore/Producer.java b/spring-integration-gemfire/src/test/java/org/springframework/integration/gemfire/store/messagegroupstore/Producer.java new file mode 100644 index 0000000000..31a8c53f32 --- /dev/null +++ b/spring-integration-gemfire/src/test/java/org/springframework/integration/gemfire/store/messagegroupstore/Producer.java @@ -0,0 +1,74 @@ +/* + * Copyright 2002-2011 the original author or authors. + * + * 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 org.springframework.integration.gemfire.store.messagegroupstore; + +import java.util.Collection; + +import javax.annotation.PostConstruct; + +import org.springframework.beans.factory.annotation.Value; +import org.springframework.integration.Message; +import org.springframework.integration.MessageChannel; +import org.springframework.integration.core.MessagingTemplate; +import org.springframework.integration.support.MessageBuilder; +import org.springframework.stereotype.Component; +import org.springframework.util.Assert; + +/** + * Simple endpoint that we can use to send in a lot of test messages. + * + * @author Josh Long + * @since 2.1 + */ +@Component +public class Producer { + + private MessagingTemplate messagingTemplate = new MessagingTemplate(); + + @Value("#{i}") + private MessageChannel messageChannel; + + @Value("${correlation-header}") + private String correlationHeader ; + + + @PostConstruct + public void start() throws Throwable { + this.messagingTemplate.setDefaultChannel(this.messageChannel); + } + + /** + * @param lines + * @throws Throwable + */ + public void sendManyMessages(int correlationValue, Collection lines) throws Throwable { + Assert.notNull( lines, "the collection must be non-null"); + Assert.notEmpty( lines, "the collection must not be empty"); + int ctr = 0; + int size = lines.size() ; + for (String l : lines) { + Message msg = MessageBuilder.withPayload(l) + .setCorrelationId( this.correlationHeader) + .setHeader(this.correlationHeader , correlationValue) + .setSequenceNumber(++ctr) + .setSequenceSize(size) + .build(); + this.messagingTemplate.send(msg); + } + } + +} diff --git a/spring-integration-gemfire/src/test/resources/org/springframework/integration/gemfire/inbound/cq/CqClient-context.xml b/spring-integration-gemfire/src/test/resources/org/springframework/integration/gemfire/inbound/cq/CqClient-context.xml new file mode 100644 index 0000000000..c1ba6b7d5e --- /dev/null +++ b/spring-integration-gemfire/src/test/resources/org/springframework/integration/gemfire/inbound/cq/CqClient-context.xml @@ -0,0 +1,26 @@ + + + + + + + + + + + + + + + + + diff --git a/spring-integration-gemfire/src/test/resources/org/springframework/integration/gemfire/inbound/cq/CqServer-context.xml b/spring-integration-gemfire/src/test/resources/org/springframework/integration/gemfire/inbound/cq/CqServer-context.xml new file mode 100644 index 0000000000..6f37aa49ae --- /dev/null +++ b/spring-integration-gemfire/src/test/resources/org/springframework/integration/gemfire/inbound/cq/CqServer-context.xml @@ -0,0 +1,28 @@ + + + + + + + + + + + + + + + + + + + diff --git a/spring-integration-gemfire/src/test/resources/org/springframework/integration/gemfire/inbound/cq/common.properties b/spring-integration-gemfire/src/test/resources/org/springframework/integration/gemfire/inbound/cq/common.properties new file mode 100644 index 0000000000..5d438b7143 --- /dev/null +++ b/spring-integration-gemfire/src/test/resources/org/springframework/integration/gemfire/inbound/cq/common.properties @@ -0,0 +1,5 @@ +host=127.0.0.1 +port=55221 +region-name=people +region-query=select * from /people +correlation-header=time \ No newline at end of file diff --git a/spring-integration-gemfire/src/test/resources/org/springframework/integration/gemfire/inbound/cq/gfe-cache.properties b/spring-integration-gemfire/src/test/resources/org/springframework/integration/gemfire/inbound/cq/gfe-cache.properties new file mode 100644 index 0000000000..04392af0d1 --- /dev/null +++ b/spring-integration-gemfire/src/test/resources/org/springframework/integration/gemfire/inbound/cq/gfe-cache.properties @@ -0,0 +1,3 @@ +log-level=warning +name=Spring Integration GemFire World +bind-address=127.0.0.1 diff --git a/spring-integration-gemfire/src/test/resources/org/springframework/integration/gemfire/store/messagegroupstore/GemfireMessageStore-context.xml b/spring-integration-gemfire/src/test/resources/org/springframework/integration/gemfire/store/messagegroupstore/GemfireMessageStore-context.xml new file mode 100644 index 0000000000..cb861d2a0f --- /dev/null +++ b/spring-integration-gemfire/src/test/resources/org/springframework/integration/gemfire/store/messagegroupstore/GemfireMessageStore-context.xml @@ -0,0 +1,35 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/spring-integration-gemfire/template.mf b/spring-integration-gemfire/template.mf new file mode 100644 index 0000000000..a4eb9baffd --- /dev/null +++ b/spring-integration-gemfire/template.mf @@ -0,0 +1,16 @@ +Bundle-SymbolicName: org.springframework.integration.gemfire +Bundle-Name: Spring Integration GemFire Support +Bundle-Vendor: SpringSource +Bundle-ManifestVersion: 2 +Import-Template: + org.apache.commons.logging;version="[1.1.1, 2.0.0)", + org.springframework.integration.*;version="[2.1.0, 2.1.1)", + org.springframework.beans.*;version="[3.1.0, 4.0.0)", + org.springframework.context;version="[3.1.0, 4.0.0)", + org.springframework.core.*;version="[3.1.0, 4.0.0)", + org.springframework.expression.*;version="[3.1.0, 4.0.0)", + org.springframework.util;version="[3.1.0, 4.0.0)", + org.springframework.data.gemfire.*;version="[1.0.1, 2.0.0)", + com.gemstone.gemfire.*;version="[6.5.1, 7.0.0)", + javax.*;version="0", + org.w3c.dom.*;version="0" diff --git a/spring-integration-groovy/pom.xml b/spring-integration-groovy/pom.xml index 675c6b3c73..a89b2aed2e 100644 --- a/spring-integration-groovy/pom.xml +++ b/spring-integration-groovy/pom.xml @@ -106,22 +106,28 @@ 2.3 test - - org.springframework - spring-test - 3.0.6.BUILD-SNAPSHOT - test - org.easymock easymockclassextension 2.3 test + + org.springframework + spring-test + 3.1.0.M2 + test + org.springframework spring-context-support - 3.0.6.BUILD-SNAPSHOT + 3.1.0.M2 + compile + + + org.springframework.integration + spring-integration-core + 2.1.0.BUILD-SNAPSHOT compile @@ -136,12 +142,6 @@ 1.7.5 compile - - org.springframework.integration - spring-integration-core - 2.1.0.BUILD-SNAPSHOT - compile - org.mockito mockito-all diff --git a/spring-integration-http/pom.xml b/spring-integration-http/pom.xml index 9fa1eb7814..37071ff108 100644 --- a/spring-integration-http/pom.xml +++ b/spring-integration-http/pom.xml @@ -100,12 +100,6 @@ - - org.springframework - spring-test - 3.0.6.BUILD-SNAPSHOT - test - javax.servlet servlet-api @@ -125,10 +119,10 @@ test - org.springframework.integration - spring-integration-test - 2.1.0.BUILD-SNAPSHOT - test + org.springframework + spring-webmvc + 3.1.0.M2 + compile org.easymock @@ -155,22 +149,10 @@ 2.3 test - - org.hamcrest - hamcrest-all - 1.1 - test - org.springframework - spring-webmvc - 3.0.6.BUILD-SNAPSHOT - compile - - - org.mockito - mockito-all - 1.8.4 + spring-test + 3.1.0.M2 test @@ -179,6 +161,24 @@ 2.1.0.BUILD-SNAPSHOT compile + + org.springframework.integration + spring-integration-test + 2.1.0.BUILD-SNAPSHOT + test + + + org.hamcrest + hamcrest-all + 1.1 + test + + + org.mockito + mockito-all + 1.8.4 + test + junit junit-dep diff --git a/spring-integration-ip/pom.xml b/spring-integration-ip/pom.xml index f6f8e1097a..8d86506d15 100644 --- a/spring-integration-ip/pom.xml +++ b/spring-integration-ip/pom.xml @@ -100,30 +100,12 @@ - - org.springframework.integration - spring-integration-stream - 2.1.0.BUILD-SNAPSHOT - runtime - - - org.springframework.integration - spring-integration-test - 2.1.0.BUILD-SNAPSHOT - test - org.easymock easymock 2.3 test - - org.springframework - spring-test - 3.0.6.BUILD-SNAPSHOT - test - org.easymock easymockclassextension @@ -131,16 +113,16 @@ test - org.hamcrest - hamcrest-all - 1.1 + org.springframework + spring-test + 3.1.0.M2 test - org.springframework - spring-context - 3.0.6.BUILD-SNAPSHOT - compile + org.springframework.integration + spring-integration-stream + 2.1.0.BUILD-SNAPSHOT + runtime org.springframework.integration @@ -148,6 +130,24 @@ 2.1.0.BUILD-SNAPSHOT compile + + org.springframework.integration + spring-integration-test + 2.1.0.BUILD-SNAPSHOT + test + + + org.springframework + spring-context + 3.1.0.M2 + compile + + + org.hamcrest + hamcrest-all + 1.1 + test + org.mockito mockito-all diff --git a/spring-integration-jdbc/pom.xml b/spring-integration-jdbc/pom.xml index 4b2e4fe84f..cba9491675 100644 --- a/spring-integration-jdbc/pom.xml +++ b/spring-integration-jdbc/pom.xml @@ -107,21 +107,15 @@ org.springframework spring-jdbc - 3.0.6.BUILD-SNAPSHOT + 3.1.0.M2 compile org.springframework - spring-aop - 3.0.6.BUILD-SNAPSHOT + spring-context + 3.1.0.M2 compile - - org.springframework - spring-test - 3.0.6.BUILD-SNAPSHOT - test - org.apache.derby derby @@ -134,12 +128,6 @@ 1.6.8 test - - org.springframework - spring-context - 3.0.6.BUILD-SNAPSHOT - compile - log4j log4j @@ -152,12 +140,6 @@ 2.2 test - - org.springframework.integration - spring-integration-test - 2.1.0.BUILD-SNAPSHOT - test - com.h2database h2 @@ -170,12 +152,36 @@ 2.3 test + + org.springframework + spring-aop + 3.1.0.M2 + compile + org.easymock easymockclassextension 2.3 test + + org.springframework + spring-test + 3.1.0.M2 + test + + + org.springframework.integration + spring-integration-core + 2.1.0.BUILD-SNAPSHOT + compile + + + org.springframework.integration + spring-integration-test + 2.1.0.BUILD-SNAPSHOT + test + org.hamcrest hamcrest-all @@ -194,16 +200,10 @@ 1.8.4 test - - org.springframework.integration - spring-integration-core - 2.1.0.BUILD-SNAPSHOT - compile - org.springframework spring-tx - 3.0.6.BUILD-SNAPSHOT + 3.1.0.M2 compile diff --git a/spring-integration-jms/pom.xml b/spring-integration-jms/pom.xml index 82b44e620d..21789b75be 100644 --- a/spring-integration-jms/pom.xml +++ b/spring-integration-jms/pom.xml @@ -106,16 +106,10 @@ 5.3.0 test - - org.springframework - spring-test - 3.0.6.BUILD-SNAPSHOT - test - org.springframework spring-context - 3.0.6.BUILD-SNAPSHOT + 3.1.0.M2 compile @@ -138,15 +132,9 @@ org.springframework - spring-oxm - 3.0.6.BUILD-SNAPSHOT - test - - - org.springframework.integration - spring-integration-test - 2.1.0.BUILD-SNAPSHOT - test + spring-jms + 3.1.0.M2 + compile org.easymock @@ -154,12 +142,36 @@ 2.3 test + + org.springframework + spring-oxm + 3.1.0.M2 + test + org.easymock easymockclassextension 2.3 test + + org.springframework + spring-test + 3.1.0.M2 + test + + + org.springframework.integration + spring-integration-core + 2.1.0.BUILD-SNAPSHOT + compile + + + org.springframework.integration + spring-integration-test + 2.1.0.BUILD-SNAPSHOT + test + org.hamcrest hamcrest-all @@ -172,22 +184,10 @@ 1.8.4 test - - org.springframework.integration - spring-integration-core - 2.1.0.BUILD-SNAPSHOT - compile - - - org.springframework - spring-jms - 3.0.6.BUILD-SNAPSHOT - compile - org.springframework spring-tx - 3.0.6.BUILD-SNAPSHOT + 3.1.0.M2 compile diff --git a/spring-integration-jmx/pom.xml b/spring-integration-jmx/pom.xml index 5807f8adbb..abc81246e6 100644 --- a/spring-integration-jmx/pom.xml +++ b/spring-integration-jmx/pom.xml @@ -102,9 +102,9 @@ org.springframework - spring-test - 3.0.6.BUILD-SNAPSHOT - test + spring-context + 3.1.0.M2 + compile org.aspectj @@ -112,12 +112,6 @@ 1.6.8 compile - - org.springframework - spring-context - 3.0.6.BUILD-SNAPSHOT - compile - cglib cglib-nodep @@ -130,12 +124,6 @@ 1.2.12 test - - org.springframework.integration - spring-integration-test - 2.1.0.BUILD-SNAPSHOT - test - org.easymock easymock @@ -148,6 +136,24 @@ 2.3 test + + org.springframework + spring-test + 3.1.0.M2 + test + + + org.springframework.integration + spring-integration-core + 2.1.0.BUILD-SNAPSHOT + compile + + + org.springframework.integration + spring-integration-test + 2.1.0.BUILD-SNAPSHOT + test + org.hamcrest hamcrest-all @@ -160,12 +166,6 @@ 1.8.4 test - - org.springframework.integration - spring-integration-core - 2.1.0.BUILD-SNAPSHOT - compile - org.aspectj aspectjrt diff --git a/spring-integration-mail/pom.xml b/spring-integration-mail/pom.xml index 20a43f10de..9da386745b 100644 --- a/spring-integration-mail/pom.xml +++ b/spring-integration-mail/pom.xml @@ -100,12 +100,6 @@ - - org.springframework - spring-test - 3.0.6.BUILD-SNAPSHOT - test - cglib cglib-nodep @@ -118,12 +112,6 @@ 1.2.12 test - - org.springframework.integration - spring-integration-test - 2.1.0.BUILD-SNAPSHOT - test - org.easymock easymock @@ -136,6 +124,24 @@ 2.3 test + + org.springframework + spring-test + 3.1.0.M2 + test + + + org.springframework.integration + spring-integration-core + 2.1.0.BUILD-SNAPSHOT + compile + + + org.springframework + spring-context-support + 3.1.0.M2 + compile + javax.activation activation @@ -143,30 +149,24 @@ compile true + + org.springframework.integration + spring-integration-test + 2.1.0.BUILD-SNAPSHOT + test + org.hamcrest hamcrest-all 1.1 test - - org.springframework - spring-context-support - 3.0.6.BUILD-SNAPSHOT - compile - org.mockito mockito-all 1.8.4 test - - org.springframework.integration - spring-integration-core - 2.1.0.BUILD-SNAPSHOT - compile - javax.mail mail diff --git a/spring-integration-mongodb/pom.xml b/spring-integration-mongodb/pom.xml index f566e7dd81..8055e40d01 100644 --- a/spring-integration-mongodb/pom.xml +++ b/spring-integration-mongodb/pom.xml @@ -100,12 +100,6 @@ - - org.springframework - spring-test - 3.0.6.BUILD-SNAPSHOT - test - org.springframework.data spring-data-commons-core @@ -121,7 +115,7 @@ org.springframework spring-context - 3.0.6.BUILD-SNAPSHOT + 3.1.0.M2 compile @@ -136,12 +130,6 @@ 1.2.12 test - - org.springframework.integration - spring-integration-test - 2.1.0.BUILD-SNAPSHOT - test - org.easymock easymock @@ -154,6 +142,24 @@ 2.3 test + + org.springframework + spring-test + 3.1.0.M2 + test + + + org.springframework.integration + spring-integration-core + 2.1.0.BUILD-SNAPSHOT + compile + + + org.springframework.integration + spring-integration-test + 2.1.0.BUILD-SNAPSHOT + test + org.hamcrest hamcrest-all @@ -166,12 +172,6 @@ 1.8.4 test - - org.springframework.integration - spring-integration-core - 2.1.0.BUILD-SNAPSHOT - compile - junit junit-dep diff --git a/spring-integration-redis/pom.xml b/spring-integration-redis/pom.xml index a81e427f75..ea4a7a13fa 100644 --- a/spring-integration-redis/pom.xml +++ b/spring-integration-redis/pom.xml @@ -100,12 +100,6 @@ - - org.springframework - spring-test - 3.0.6.BUILD-SNAPSHOT - test - org.springframework.data spring-data-commons-core @@ -121,7 +115,7 @@ org.springframework spring-context - 3.0.6.BUILD-SNAPSHOT + 3.1.0.M2 compile @@ -136,12 +130,6 @@ 1.2.12 test - - org.springframework.integration - spring-integration-test - 2.1.0.BUILD-SNAPSHOT - test - org.easymock easymock @@ -154,6 +142,24 @@ 2.3 test + + org.springframework + spring-test + 3.1.0.M2 + test + + + org.springframework.integration + spring-integration-core + 2.1.0.BUILD-SNAPSHOT + compile + + + org.springframework.integration + spring-integration-test + 2.1.0.BUILD-SNAPSHOT + test + org.hamcrest hamcrest-all @@ -166,12 +172,6 @@ 1.8.4 test - - org.springframework.integration - spring-integration-core - 2.1.0.BUILD-SNAPSHOT - compile - junit junit-dep diff --git a/spring-integration-rmi/pom.xml b/spring-integration-rmi/pom.xml index c6fd208573..0bda4d9778 100644 --- a/spring-integration-rmi/pom.xml +++ b/spring-integration-rmi/pom.xml @@ -100,18 +100,6 @@ - - org.springframework.integration - spring-integration-test - 2.1.0.BUILD-SNAPSHOT - test - - - org.springframework - spring-aop - 3.0.6.BUILD-SNAPSHOT - compile - org.easymock easymock @@ -120,9 +108,9 @@ org.springframework - spring-test - 3.0.6.BUILD-SNAPSHOT - test + spring-aop + 3.1.0.M2 + compile org.easymock @@ -130,17 +118,11 @@ 2.3 test - - org.hamcrest - hamcrest-all - 1.1 - test - org.springframework - spring-context - 3.0.6.BUILD-SNAPSHOT - compile + spring-test + 3.1.0.M2 + test org.springframework.integration @@ -148,6 +130,24 @@ 2.1.0.BUILD-SNAPSHOT compile + + org.springframework.integration + spring-integration-test + 2.1.0.BUILD-SNAPSHOT + test + + + org.springframework + spring-context + 3.1.0.M2 + compile + + + org.hamcrest + hamcrest-all + 1.1 + test + org.mockito mockito-all diff --git a/spring-integration-scripting/pom.xml b/spring-integration-scripting/pom.xml index 744a4752da..7f33eaefe5 100644 --- a/spring-integration-scripting/pom.xml +++ b/spring-integration-scripting/pom.xml @@ -100,30 +100,36 @@ - - org.springframework.integration - spring-integration-test - 2.1.0.BUILD-SNAPSHOT - test - org.easymock easymock 2.3 test - - org.springframework - spring-test - 3.0.6.BUILD-SNAPSHOT - test - org.easymock easymockclassextension 2.3 test + + org.springframework + spring-test + 3.1.0.M2 + test + + + org.springframework.integration + spring-integration-core + 2.1.0.BUILD-SNAPSHOT + compile + + + org.springframework.integration + spring-integration-test + 2.1.0.BUILD-SNAPSHOT + test + org.hamcrest hamcrest-all @@ -136,12 +142,6 @@ 1.8.4 test - - org.springframework.integration - spring-integration-core - 2.1.0.BUILD-SNAPSHOT - compile - org.codehaus.groovy groovy-all diff --git a/spring-integration-security/pom.xml b/spring-integration-security/pom.xml index 05352f13b5..0341f059e4 100644 --- a/spring-integration-security/pom.xml +++ b/spring-integration-security/pom.xml @@ -100,18 +100,6 @@ - - org.springframework - spring-aop - 3.0.6.BUILD-SNAPSHOT - compile - - - org.springframework - spring-test - 3.0.6.BUILD-SNAPSHOT - test - org.springframework.security spring-security-core @@ -142,12 +130,30 @@ 2.3 test + + org.springframework + spring-aop + 3.1.0.M2 + compile + org.easymock easymockclassextension 2.3 test + + org.springframework + spring-test + 3.1.0.M2 + test + + + org.springframework.integration + spring-integration-core + 2.1.0.BUILD-SNAPSHOT + compile + org.hamcrest hamcrest-all @@ -160,12 +166,6 @@ 1.8.4 test - - org.springframework.integration - spring-integration-core - 2.1.0.BUILD-SNAPSHOT - compile - org.springframework.security spring-security-config @@ -181,7 +181,7 @@ org.springframework spring-tx - 3.0.6.BUILD-SNAPSHOT + 3.1.0.M2 compile diff --git a/spring-integration-sftp/pom.xml b/spring-integration-sftp/pom.xml index 47e19663c8..bc80a36e02 100644 --- a/spring-integration-sftp/pom.xml +++ b/spring-integration-sftp/pom.xml @@ -100,24 +100,12 @@ - - org.springframework.integration - spring-integration-stream - 2.1.0.BUILD-SNAPSHOT - compile - com.jcraft jsch 0.1.42 compile - - org.springframework - spring-test - 3.0.6.BUILD-SNAPSHOT - test - org.springframework.integration spring-integration-file @@ -136,12 +124,6 @@ 2.2 test - - org.springframework.integration - spring-integration-test - 2.1.0.BUILD-SNAPSHOT - test - org.easymock easymock @@ -154,6 +136,30 @@ 2.3 test + + org.springframework + spring-test + 3.1.0.M2 + test + + + org.springframework.integration + spring-integration-core + 2.1.0.BUILD-SNAPSHOT + compile + + + org.springframework.integration + spring-integration-stream + 2.1.0.BUILD-SNAPSHOT + compile + + + org.springframework + spring-context-support + 3.1.0.M2 + compile + javax.activation activation @@ -161,24 +167,18 @@ compile true + + org.springframework.integration + spring-integration-test + 2.1.0.BUILD-SNAPSHOT + test + org.hamcrest hamcrest-all 1.1 test - - org.springframework - spring-context-support - 3.0.6.BUILD-SNAPSHOT - compile - - - org.springframework.integration - spring-integration-core - 2.1.0.BUILD-SNAPSHOT - compile - org.mockito mockito-all diff --git a/spring-integration-stream/pom.xml b/spring-integration-stream/pom.xml index a8d03a1f68..ef12ba4b0f 100644 --- a/spring-integration-stream/pom.xml +++ b/spring-integration-stream/pom.xml @@ -106,29 +106,17 @@ 2.3 test - - org.springframework - spring-test - 3.0.6.BUILD-SNAPSHOT - test - org.easymock easymockclassextension 2.3 test - - org.hamcrest - hamcrest-all - 1.1 - test - org.springframework - spring-context - 3.0.6.BUILD-SNAPSHOT - compile + spring-test + 3.1.0.M2 + test org.springframework.integration @@ -136,6 +124,18 @@ 2.1.0.BUILD-SNAPSHOT compile + + org.springframework + spring-context + 3.1.0.M2 + compile + + + org.hamcrest + hamcrest-all + 1.1 + test + org.mockito mockito-all diff --git a/spring-integration-test/pom.xml b/spring-integration-test/pom.xml index a87768976d..c6a5ba0886 100644 --- a/spring-integration-test/pom.xml +++ b/spring-integration-test/pom.xml @@ -106,42 +106,42 @@ 2.3 test - - org.springframework - spring-test - 3.0.6.BUILD-SNAPSHOT - test - org.easymock easymockclassextension 2.3 test + + org.springframework + spring-test + 3.1.0.M2 + test + + + org.springframework.integration + spring-integration-core + 2.1.0.BUILD-SNAPSHOT + compile + + + org.springframework + spring-context + 3.1.0.M2 + compile + org.hamcrest hamcrest-all 1.1 test - - org.springframework - spring-context - 3.0.6.BUILD-SNAPSHOT - compile - org.mockito mockito-all 1.8.4 compile - - org.springframework.integration - spring-integration-core - 2.1.0.BUILD-SNAPSHOT - compile - log4j log4j diff --git a/spring-integration-twitter/pom.xml b/spring-integration-twitter/pom.xml index 0a897bc661..7afb3bd5fa 100644 --- a/spring-integration-twitter/pom.xml +++ b/spring-integration-twitter/pom.xml @@ -100,12 +100,6 @@ - - org.springframework - spring-test - 3.0.6.BUILD-SNAPSHOT - test - org.twitter4j twitter4j-core @@ -124,12 +118,6 @@ 1.2.12 test - - org.springframework.integration - spring-integration-test - 2.1.0.BUILD-SNAPSHOT - test - org.easymock easymock @@ -142,6 +130,24 @@ 2.3 test + + org.springframework + spring-test + 3.1.0.M2 + test + + + org.springframework.integration + spring-integration-core + 2.1.0.BUILD-SNAPSHOT + compile + + + org.springframework + spring-context-support + 3.1.0.M2 + compile + javax.activation activation @@ -149,30 +155,24 @@ compile true + + org.springframework.integration + spring-integration-test + 2.1.0.BUILD-SNAPSHOT + test + org.hamcrest hamcrest-all 1.1 test - - org.springframework - spring-context-support - 3.0.6.BUILD-SNAPSHOT - compile - org.mockito mockito-all 1.8.4 test - - org.springframework.integration - spring-integration-core - 2.1.0.BUILD-SNAPSHOT - compile - junit junit-dep diff --git a/spring-integration-ws/pom.xml b/spring-integration-ws/pom.xml index 69fc487b92..65ccadca7e 100644 --- a/spring-integration-ws/pom.xml +++ b/spring-integration-ws/pom.xml @@ -100,12 +100,6 @@ - - org.springframework - spring-test - 3.0.6.BUILD-SNAPSHOT - test - com.sun.xml.messaging.saaj saaj-impl @@ -122,7 +116,7 @@ org.springframework spring-expression - 3.0.6.BUILD-SNAPSHOT + 3.1.0.M2 compile @@ -137,12 +131,6 @@ 2.2 test - - org.springframework - spring-oxm - 3.0.6.BUILD-SNAPSHOT - compile - javax.xml.soap saaj-api @@ -156,12 +144,6 @@ true - - org.springframework.integration - spring-integration-test - 2.1.0.BUILD-SNAPSHOT - test - org.easymock easymock @@ -174,12 +156,30 @@ 2.3 test + + org.springframework + spring-oxm + 3.1.0.M2 + compile + stax stax-api 1.0.1 test + + org.springframework + spring-test + 3.1.0.M2 + test + + + org.springframework.integration + spring-integration-core + 2.1.0.BUILD-SNAPSHOT + compile + javax.activation activation @@ -187,18 +187,18 @@ compile true + + org.springframework.integration + spring-integration-test + 2.1.0.BUILD-SNAPSHOT + test + org.hamcrest hamcrest-all 1.1 test - - org.springframework.integration - spring-integration-core - 2.1.0.BUILD-SNAPSHOT - compile - org.mockito mockito-all diff --git a/spring-integration-xml/pom.xml b/spring-integration-xml/pom.xml index ce269276a8..3d165cdfbd 100644 --- a/spring-integration-xml/pom.xml +++ b/spring-integration-xml/pom.xml @@ -100,12 +100,6 @@ - - org.springframework - spring-test - 3.0.6.BUILD-SNAPSHOT - test - org.springframework.ws spring-xml @@ -121,7 +115,7 @@ org.springframework spring-context - 3.0.6.BUILD-SNAPSHOT + 3.1.0.M2 compile @@ -148,18 +142,6 @@ 2.0EA3 test - - org.springframework - spring-oxm - 3.0.6.BUILD-SNAPSHOT - compile - - - org.springframework.integration - spring-integration-test - 2.1.0.BUILD-SNAPSHOT - test - org.easymock easymock @@ -172,12 +154,24 @@ 2.3 test + + org.springframework + spring-oxm + 3.1.0.M2 + compile + stax stax-api 1.0.1 test + + org.springframework + spring-test + 3.1.0.M2 + test + javax.activation activation @@ -185,18 +179,24 @@ compile true - - org.hamcrest - hamcrest-all - 1.1 - test - org.springframework.integration spring-integration-core 2.1.0.BUILD-SNAPSHOT compile + + org.springframework.integration + spring-integration-test + 2.1.0.BUILD-SNAPSHOT + test + + + org.hamcrest + hamcrest-all + 1.1 + test + org.mockito mockito-all diff --git a/spring-integration-xmpp/pom.xml b/spring-integration-xmpp/pom.xml index 6ac9f88a8e..36a7bbeb94 100644 --- a/spring-integration-xmpp/pom.xml +++ b/spring-integration-xmpp/pom.xml @@ -100,18 +100,6 @@ - - org.springframework.integration - spring-integration-stream - 2.1.0.BUILD-SNAPSHOT - test - - - org.springframework - spring-test - 3.0.6.BUILD-SNAPSHOT - test - cglib cglib-nodep @@ -124,12 +112,6 @@ 1.2.12 test - - org.springframework.integration - spring-integration-test - 2.1.0.BUILD-SNAPSHOT - test - org.easymock easymock @@ -142,6 +124,24 @@ 2.3 test + + org.springframework + spring-test + 3.1.0.M2 + test + + + org.springframework.integration + spring-integration-stream + 2.1.0.BUILD-SNAPSHOT + test + + + org.springframework.integration + spring-integration-core + 2.1.0.BUILD-SNAPSHOT + compile + javax.activation activation @@ -155,6 +155,18 @@ 3.1.0 compile + + org.springframework + spring-context-support + 3.1.0.M2 + compile + + + org.springframework.integration + spring-integration-test + 2.1.0.BUILD-SNAPSHOT + test + jivesoftware smackx @@ -167,18 +179,6 @@ 1.1 test - - org.springframework - spring-context-support - 3.0.6.BUILD-SNAPSHOT - compile - - - org.springframework.integration - spring-integration-core - 2.1.0.BUILD-SNAPSHOT - compile - org.mockito mockito-all