Merge pull request #328 from garyrussell/INT-2407

INT-2404 Fix Auto-Created Channel; Event, TCP, UDP
This commit is contained in:
Mark Fisher
2012-01-23 10:13:09 -05:00
47 changed files with 457 additions and 130 deletions

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2002-2010 the original author or authors.
* Copyright 2002-2012 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.
@@ -23,6 +23,7 @@ import org.springframework.beans.factory.support.BeanDefinitionBuilder;
import org.springframework.beans.factory.xml.ParserContext;
import org.springframework.integration.config.xml.AbstractChannelAdapterParser;
import org.springframework.integration.config.xml.IntegrationNamespaceUtils;
import org.springframework.integration.event.inbound.ApplicationEventListeningMessageProducer;
/**
* @author Oleg Zhurakousky
@@ -34,9 +35,9 @@ public class EventInboundChannelAdapterParser extends AbstractChannelAdapterPars
@Override
protected AbstractBeanDefinition doParse(Element element, ParserContext parserContext, String channelName) {
BeanDefinitionBuilder adapterBuilder = BeanDefinitionBuilder.rootBeanDefinition(
"org.springframework.integration.event.inbound.ApplicationEventListeningMessageProducer");
IntegrationNamespaceUtils.setReferenceIfAttributeDefined(adapterBuilder, element, "channel", "outputChannel");
BeanDefinitionBuilder adapterBuilder = BeanDefinitionBuilder
.rootBeanDefinition(ApplicationEventListeningMessageProducer.class);
adapterBuilder.addPropertyReference("outputChannel", channelName);
IntegrationNamespaceUtils.setReferenceIfAttributeDefined(adapterBuilder, element, "error-channel", "errorChannel");
IntegrationNamespaceUtils.setValueIfAttributeDefined(adapterBuilder, element, "event-types");
IntegrationNamespaceUtils.setValueIfAttributeDefined(adapterBuilder, element, "payload-expression");

View File

@@ -25,7 +25,7 @@
</xsd:annotation>
<xsd:complexType>
<xsd:attribute name="id" type="xsd:ID" use="optional" />
<xsd:attribute name="channel" type="xsd:string" use="required">
<xsd:attribute name="channel" type="xsd:string">
<xsd:annotation>
<xsd:appinfo>
<tool:annotation kind="ref">

View File

@@ -25,7 +25,7 @@
</xsd:annotation>
<xsd:complexType>
<xsd:attribute name="id" type="xsd:string" use="optional" />
<xsd:attribute name="channel" type="xsd:string" use="required">
<xsd:attribute name="channel" type="xsd:string">
<xsd:annotation>
<xsd:appinfo>
<tool:annotation kind="ref">

View File

@@ -38,6 +38,10 @@
<int:queue/>
</int:channel>
<int-event:inbound-channel-adapter id="autoChannel" payload-expression="source + '-test'"/>
<int:bridge input-channel="autoChannel" output-channel="nullChannel"/>
<context:property-placeholder location="classpath:org/springframework/integration/event/config/inbound-adapter.properties"/>
</beans>

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2002-2010 the original author or authors.
* Copyright 2002-2012 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.
@@ -19,6 +19,7 @@ package org.springframework.integration.event.config;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertNotNull;
import static org.junit.Assert.assertNull;
import static org.junit.Assert.assertSame;
import static org.junit.Assert.assertTrue;
import java.util.Properties;
@@ -31,6 +32,7 @@ import org.junit.runner.RunWith;
import org.springframework.beans.DirectFieldAccessor;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.context.ApplicationContext;
import org.springframework.context.ApplicationEvent;
import org.springframework.context.event.ContextRefreshedEvent;
@@ -60,6 +62,12 @@ public class EventInboundChannelAdapterParserTests {
@Autowired
MessageChannel errorChannel;
@Autowired
MessageChannel autoChannel;
@Autowired @Qualifier("autoChannel.adapter")
ApplicationEventListeningMessageProducer eventListener;
@Test
public void validateEventParser() {
Object adapter = context.getBean("eventAdapterSimple");
@@ -126,6 +134,10 @@ public class EventInboundChannelAdapterParserTests {
Assert.assertEquals("source + '-test'", expression.getExpressionString());
}
@Test
public void testAutoCreateChannel() {
assertSame(autoChannel, TestUtils.getPropertyValue(eventListener, "outputChannel"));
}
@SuppressWarnings("serial")
public static class SampleEvent extends ApplicationEvent {

View File

@@ -30,7 +30,7 @@
</xsd:documentation>
</xsd:annotation>
</xsd:attribute>
<xsd:attribute name="channel" use="required" type="xsd:string">
<xsd:attribute name="channel" type="xsd:string">
<xsd:annotation>
<xsd:appinfo>
<tool:annotation kind="ref">

View File

@@ -0,0 +1,17 @@
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:int="http://www.springframework.org/schema/integration"
xmlns:feed="http://www.springframework.org/schema/integration/feed"
xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/integration http://www.springframework.org/schema/integration/spring-integration.xsd
http://www.springframework.org/schema/integration/feed http://www.springframework.org/schema/integration/feed/spring-integration-feed.xsd">
<feed:inbound-channel-adapter id="autoChannel"
auto-startup="false"
url="file:dummy.rss">
<int:poller fixed-rate="10000" max-messages-per-poll="100" />
</feed:inbound-channel-adapter>
<int:bridge input-channel="autoChannel" output-channel="nullChannel" />
</beans>

View File

@@ -18,6 +18,7 @@ package org.springframework.integration.feed.config;
import static junit.framework.Assert.assertEquals;
import static junit.framework.Assert.assertTrue;
import static org.junit.Assert.assertSame;
import static org.mockito.Mockito.atLeast;
import static org.mockito.Mockito.spy;
import static org.mockito.Mockito.times;
@@ -36,6 +37,7 @@ import org.mockito.Mockito;
import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;
import org.springframework.integration.Message;
import org.springframework.integration.MessageChannel;
import org.springframework.integration.MessagingException;
import org.springframework.integration.channel.DirectChannel;
import org.springframework.integration.core.MessageHandler;
@@ -52,6 +54,7 @@ import com.sun.syndication.fetcher.impl.HttpURLFeedFetcher;
/**
* @author Oleg Zhurakousky
* @author Mark Fisher
* @author Gary Russell
* @since 2.0
*/
public class FeedInboundChannelAdapterParserTests {
@@ -154,6 +157,15 @@ public class FeedInboundChannelAdapterParserTests {
verify(handler, atLeast(3)).handleMessage(Mockito.any(Message.class));
}
@Test
public void testAutoChannel() {
ClassPathXmlApplicationContext context = new ClassPathXmlApplicationContext(
"FeedInboundChannelAdapterParserTests-autoChannel-context.xml", this.getClass());
MessageChannel autoChannel = context.getBean("autoChannel", MessageChannel.class);
SourcePollingChannelAdapter adapter = context.getBean("autoChannel.adapter", SourcePollingChannelAdapter.class);
assertSame(autoChannel, TestUtils.getPropertyValue(adapter, "outputChannel"));
context.destroy();
}
public static class SampleService {

View File

@@ -388,7 +388,7 @@
</xsd:documentation>
</xsd:annotation>
</xsd:attribute>
<xsd:attribute name="channel" use="required" type="xsd:string">
<xsd:attribute name="channel" type="xsd:string">
<xsd:annotation>
<xsd:appinfo>
<tool:annotation kind="ref">

View File

@@ -60,4 +60,13 @@
<constructor-arg value="org.springframework.integration.file.filters.FileListFilter"/>
</bean>
<int-ftp:inbound-channel-adapter id="autoChannel"
session-factory="ftpSessionFactory"
local-directory="."
remote-directory="foo/bar">
<int:poller fixed-rate="1000"/>
</int-ftp:inbound-channel-adapter>
<int:bridge input-channel="autoChannel" output-channel="nullChannel" />
</beans>

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2002-2011 the original author or authors.
* Copyright 2002-2012 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.
@@ -20,6 +20,7 @@ import static junit.framework.Assert.assertEquals;
import static junit.framework.Assert.assertNotNull;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertSame;
import static org.junit.Assert.assertTrue;
import static org.mockito.Mockito.mock;
import static org.mockito.Mockito.when;
@@ -33,6 +34,7 @@ import org.junit.Test;
import org.springframework.beans.factory.FactoryBean;
import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;
import org.springframework.integration.MessageChannel;
import org.springframework.integration.endpoint.SourcePollingChannelAdapter;
import org.springframework.integration.file.remote.session.CachingSessionFactory;
import org.springframework.integration.file.remote.session.Session;
@@ -45,6 +47,7 @@ import org.springframework.integration.test.util.TestUtils;
/**
* @author Oleg Zhurakousky
* @author Mark Fisher
* @author Gary Russell
*/
public class FtpInboundChannelAdapterParserTests {
@@ -105,6 +108,15 @@ public class FtpInboundChannelAdapterParserTests {
assertNotNull(adapter);
}
@Test
public void testAutoChannel() {
ApplicationContext context =
new ClassPathXmlApplicationContext("FtpInboundChannelAdapterParserTests-context.xml", this.getClass());
// Auto-created channel
MessageChannel autoChannel = context.getBean("autoChannel", MessageChannel.class);
SourcePollingChannelAdapter autoChannelAdapter = context.getBean("autoChannel.adapter", SourcePollingChannelAdapter.class);
assertSame(autoChannel, TestUtils.getPropertyValue(autoChannelAdapter, "outputChannel"));
}
public static class TestSessionFactoryBean implements FactoryBean<DefaultFtpSessionFactory> {

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2002-2011 the original author or authors.
* Copyright 2002-2012 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.
@@ -19,6 +19,7 @@ package org.springframework.integration.http.config;
import java.util.List;
import org.springframework.beans.factory.BeanDefinitionStoreException;
import org.springframework.beans.factory.config.BeanDefinitionHolder;
import org.springframework.beans.factory.support.AbstractBeanDefinition;
import org.springframework.beans.factory.support.BeanDefinitionBuilder;
import org.springframework.beans.factory.support.BeanDefinitionReaderUtils;
@@ -26,6 +27,7 @@ import org.springframework.beans.factory.support.ManagedMap;
import org.springframework.beans.factory.support.RootBeanDefinition;
import org.springframework.beans.factory.xml.AbstractSingleBeanDefinitionParser;
import org.springframework.beans.factory.xml.ParserContext;
import org.springframework.integration.channel.DirectChannel;
import org.springframework.integration.config.ExpressionFactoryBean;
import org.springframework.integration.config.xml.IntegrationNamespaceUtils;
import org.springframework.util.CollectionUtils;
@@ -41,6 +43,7 @@ import org.w3c.dom.Element;
*
* @author Mark Fisher
* @author Oleg Zhurakousky
* @author Gary Russell
*/
public class HttpInboundEndpointParser extends AbstractSingleBeanDefinitionParser {
@@ -65,11 +68,16 @@ public class HttpInboundEndpointParser extends AbstractSingleBeanDefinitionParse
String id = super.resolveId(element, definition, parserContext);
if (!StringUtils.hasText(id)) {
id = element.getAttribute("name");
} else {
if (!element.hasAttribute(getInputChannelAttributeName())) {
// the created channel will get the 'id', so the adapter's bean name includes a suffix
id = id + ".adapter";
}
}
if (!StringUtils.hasText(id)) {
id = BeanDefinitionReaderUtils.generateBeanName(definition, parserContext.getRegistry());
}
return id;
}
@@ -79,8 +87,12 @@ public class HttpInboundEndpointParser extends AbstractSingleBeanDefinitionParse
String inputChannelAttributeName = this.getInputChannelAttributeName();
String inputChannelRef = element.getAttribute(inputChannelAttributeName);
if (!StringUtils.hasText(inputChannelRef)) {
parserContext.getReaderContext().error(
"a '" + inputChannelAttributeName + "' reference is required", element);
if (this.expectReply) {
parserContext.getReaderContext().error(
"a '" + inputChannelAttributeName + "' reference is required", element);
} else {
inputChannelRef = createDirectChannel(element, parserContext);
}
}
builder.addPropertyReference("requestChannel", inputChannelRef);
IntegrationNamespaceUtils.setReferenceIfAttributeDefined(builder, element, "error-channel");
@@ -158,4 +170,15 @@ public class HttpInboundEndpointParser extends AbstractSingleBeanDefinitionParse
return this.expectReply ? "request-channel" : "channel";
}
private String createDirectChannel(Element element, ParserContext parserContext) {
String channelId = element.getAttribute("id");
if (!StringUtils.hasText(channelId)) {
parserContext.getReaderContext().error("The channel-adapter's 'id' attribute is required when no 'channel' "
+ "reference has been provided, because that 'id' would be used for the created channel.", element);
}
BeanDefinitionBuilder channelBuilder = BeanDefinitionBuilder.genericBeanDefinition(DirectChannel.class);
BeanDefinitionHolder holder = new BeanDefinitionHolder(channelBuilder.getBeanDefinition(), channelId);
BeanDefinitionReaderUtils.registerBeanDefinition(holder, parserContext.getRegistry());
return channelId;
}
}

View File

@@ -32,7 +32,7 @@
</xsd:documentation>
</xsd:annotation>
</xsd:attribute>
<xsd:attribute name="channel" type="xsd:string" use="required">
<xsd:attribute name="channel" type="xsd:string">
<xsd:annotation>
<xsd:appinfo>
<tool:annotation kind="ref">
@@ -284,7 +284,7 @@ The String "HTTP_REQUEST_HEADERS" will match against any of the standard HTTP Re
<xsd:union memberTypes="httpMethodEnumeration xsd:string" />
</xsd:simpleType>
</xsd:attribute>
<xsd:attribute name="channel" type="xsd:string" use="required">
<xsd:attribute name="channel" type="xsd:string">
<xsd:annotation>
<xsd:appinfo>
<tool:annotation kind="ref">

View File

@@ -50,4 +50,13 @@
<header name="lname" expression="#pathVariables.l"/>
</inbound-channel-adapter>
<inbound-channel-adapter id="autoChannel"
path="/fname/{f}/lname/{l}"
mapped-request-headers="foo,bar"
payload-expression="#pathVariables.f">
<header name="lname" expression="#pathVariables.l"/>
</inbound-channel-adapter>
<si:bridge input-channel="autoChannel" output-channel="nullChannel" />
</beans:beans>

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2002-2011 the original author or authors.
* Copyright 2002-2012 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.
@@ -19,6 +19,7 @@ package org.springframework.integration.http.config;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertNotNull;
import static org.junit.Assert.assertNull;
import static org.junit.Assert.assertSame;
import static org.junit.Assert.assertTrue;
import java.io.ByteArrayOutputStream;
@@ -40,6 +41,7 @@ import org.springframework.expression.spel.SpelEvaluationException;
import org.springframework.http.HttpHeaders;
import org.springframework.http.HttpMethod;
import org.springframework.integration.Message;
import org.springframework.integration.MessageChannel;
import org.springframework.integration.core.PollableChannel;
import org.springframework.integration.history.MessageHistory;
import org.springframework.integration.http.MockHttpServletRequest;
@@ -56,6 +58,7 @@ import org.springframework.util.MultiValueMap;
/**
* @author Mark Fisher
* @author Oleg Zhurakousky
* @author Gary Russell
*/
@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration
@@ -90,6 +93,11 @@ public class HttpInboundChannelAdapterParserTests {
@Autowired
private HttpRequestHandlingController inboundController;
@Autowired
private MessageChannel autoChannel;
@Autowired @Qualifier("autoChannel.adapter")
private HttpRequestHandlingMessagingGateway autoChannelAdapter;
@Test
@SuppressWarnings("unchecked")
@@ -259,6 +267,10 @@ public class HttpInboundChannelAdapterParserTests {
assertEquals("oops", errorCode);
}
@Test
public void testAutoChannel() {
assertSame(autoChannel, TestUtils.getPropertyValue(autoChannelAdapter, "requestChannel"));
}
@SuppressWarnings("serial")
private static class TestObject implements Serializable {

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2002-2010 the original author or authors.
* Copyright 2002-2012 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.
@@ -21,6 +21,7 @@ import org.springframework.beans.factory.support.BeanDefinitionBuilder;
import org.springframework.beans.factory.xml.ParserContext;
import org.springframework.integration.config.xml.AbstractChannelAdapterParser;
import org.springframework.integration.config.xml.IntegrationNamespaceUtils;
import org.springframework.integration.ip.tcp.TcpReceivingChannelAdapter;
import org.w3c.dom.Element;
/**
@@ -31,15 +32,11 @@ import org.w3c.dom.Element;
*/
public class TcpInboundChannelAdapterParser extends AbstractChannelAdapterParser {
private static final String BASE_PACKAGE = "org.springframework.integration.ip.tcp";
protected AbstractBeanDefinition doParse(Element element, ParserContext parserContext, String channelName) {
BeanDefinitionBuilder builder = BeanDefinitionBuilder.genericBeanDefinition(BASE_PACKAGE +
".TcpReceivingChannelAdapter");
BeanDefinitionBuilder builder = BeanDefinitionBuilder.genericBeanDefinition(TcpReceivingChannelAdapter.class);
IntegrationNamespaceUtils.setReferenceIfAttributeDefined(builder, element,
IpAdapterParserUtils.TCP_CONNECTION_FACTORY);
IntegrationNamespaceUtils.setReferenceIfAttributeDefined(builder,
element, "channel", "outputChannel");
builder.addPropertyReference("outputChannel", channelName);
IntegrationNamespaceUtils.setReferenceIfAttributeDefined(builder,
element, "error-channel", "errorChannel");
IntegrationNamespaceUtils.setValueIfAttributeDefined(builder, element,

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2002-2010 the original author or authors.
* Copyright 2002-2012 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.
@@ -21,6 +21,8 @@ import org.springframework.beans.factory.support.BeanDefinitionBuilder;
import org.springframework.beans.factory.xml.ParserContext;
import org.springframework.integration.config.xml.AbstractChannelAdapterParser;
import org.springframework.integration.config.xml.IntegrationNamespaceUtils;
import org.springframework.integration.ip.udp.MulticastReceivingChannelAdapter;
import org.springframework.integration.ip.udp.UnicastReceivingChannelAdapter;
import org.springframework.util.StringUtils;
import org.w3c.dom.Element;
@@ -32,8 +34,6 @@ import org.w3c.dom.Element;
*/
public class UdpInboundChannelAdapterParser extends AbstractChannelAdapterParser {
private static final String BASE_PACKAGE = "org.springframework.integration.ip.udp";
protected AbstractBeanDefinition doParse(Element element, ParserContext parserContext, String channelName) {
BeanDefinitionBuilder builder = parseUdp(element, parserContext);
IpAdapterParserUtils.addCommonSocketOptions(builder, element);
@@ -41,8 +41,7 @@ public class UdpInboundChannelAdapterParser extends AbstractChannelAdapterParser
IpAdapterParserUtils.RECEIVE_BUFFER_SIZE);
IntegrationNamespaceUtils.setValueIfAttributeDefined(builder, element,
IpAdapterParserUtils.POOL_SIZE);
IntegrationNamespaceUtils.setReferenceIfAttributeDefined(builder,
element, "channel", "outputChannel");
builder.addPropertyReference("outputChannel", channelName);
IntegrationNamespaceUtils.setReferenceIfAttributeDefined(builder,
element, "error-channel", "errorChannel");
IntegrationNamespaceUtils.setReferenceIfAttributeDefined(builder, element,
@@ -72,12 +71,10 @@ public class UdpInboundChannelAdapterParser extends AbstractChannelAdapterParser
BeanDefinitionBuilder builder;
String multicast = IpAdapterParserUtils.getMulticast(element);
if (multicast.equals("false")) {
builder = BeanDefinitionBuilder.genericBeanDefinition(BASE_PACKAGE +
".UnicastReceivingChannelAdapter");
builder = BeanDefinitionBuilder.genericBeanDefinition(UnicastReceivingChannelAdapter.class);
}
else {
builder = BeanDefinitionBuilder.genericBeanDefinition(BASE_PACKAGE +
".MulticastReceivingChannelAdapter");
builder = BeanDefinitionBuilder.genericBeanDefinition(MulticastReceivingChannelAdapter.class);
String mcAddress = element
.getAttribute(IpAdapterParserUtils.MULTICAST_ADDRESS);
if (!StringUtils.hasText(mcAddress)) {

View File

@@ -331,4 +331,12 @@
<task:scheduler id="sched"/>
<ip:tcp-inbound-channel-adapter id="tcpAutoChannel" />
<int:bridge input-channel="tcpAutoChannel" output-channel="nullChannel" />
<ip:udp-inbound-channel-adapter id="udpAutoChannel" port="#{tcpIpUtils.findAvailableUdpSocket(5050)}" />
<int:bridge input-channel="udpAutoChannel" output-channel="nullChannel" />
</beans>

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2002-2011 the original author or authors.
* Copyright 2002-2012 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.
@@ -195,6 +195,18 @@ public class ParserUnitTests {
@Qualifier(value="org.springframework.integration.ip.tcp.TcpSendingMessageHandler#3")
TcpSendingMessageHandler tcpOutClientMode;
@Autowired
MessageChannel tcpAutoChannel;
@Autowired
MessageChannel udpAutoChannel;
@Autowired @Qualifier("tcpAutoChannel.adapter")
TcpReceivingChannelAdapter tcpAutoAdapter;
@Autowired @Qualifier("udpAutoChannel.adapter")
UnicastReceivingChannelAdapter udpAutoAdapter;
@Test
public void testInUdp() {
DirectFieldAccessor dfa = new DirectFieldAccessor(udpIn);
@@ -518,4 +530,13 @@ public class ParserUnitTests {
assertEquals(125000L, dfa.getPropertyValue("retryInterval"));
}
@Test
public void testAutoTcp() {
assertSame(tcpAutoChannel, TestUtils.getPropertyValue(tcpAutoAdapter, "outputChannel"));
}
@Test
public void testAutoUdp() {
assertSame(udpAutoChannel, TestUtils.getPropertyValue(udpAutoAdapter, "outputChannel"));
}
}

View File

@@ -178,7 +178,7 @@
</xsd:documentation>
</xsd:annotation>
</xsd:attribute>
<xsd:attribute name="channel" type="xsd:string" use="required">
<xsd:attribute name="channel" type="xsd:string">
<xsd:annotation>
<xsd:appinfo>
<xsd:documentation>
@@ -267,7 +267,7 @@
</xsd:annotation>
</xsd:attribute>
<xsd:attribute name="id" type="xsd:string" use="optional"/>
<xsd:attribute name="channel" type="xsd:string" use="required">
<xsd:attribute name="channel" type="xsd:string">
<xsd:annotation>
<xsd:appinfo>
<xsd:documentation>
@@ -681,7 +681,7 @@
</xsd:appinfo>
</xsd:annotation>
</xsd:attribute>
<xsd:attribute name="channel" type="xsd:string" use="required">
<xsd:attribute name="channel" type="xsd:string">
<xsd:annotation>
<xsd:appinfo>
<xsd:documentation>
@@ -1096,7 +1096,7 @@
<xsd:union memberTypes="xsd:boolean xsd:string" />
</xsd:simpleType>
</xsd:attribute>
<xsd:attribute name="channel" type="xsd:string" use="required">
<xsd:attribute name="channel" type="xsd:string">
<xsd:annotation>
<xsd:documentation>
Channel to which polled messages will be send. If the stored

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2002-2011 the original author or authors.
* Copyright 2002-2012 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.
@@ -19,6 +19,7 @@ package org.springframework.integration.jdbc.config;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertNotNull;
import static org.junit.Assert.assertNull;
import static org.junit.Assert.assertSame;
import static org.junit.Assert.assertTrue;
import java.util.List;
@@ -32,8 +33,10 @@ import org.junit.Test;
import org.springframework.context.ConfigurableApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;
import org.springframework.integration.Message;
import org.springframework.integration.MessageChannel;
import org.springframework.integration.core.MessagingTemplate;
import org.springframework.integration.core.PollableChannel;
import org.springframework.integration.endpoint.SourcePollingChannelAdapter;
import org.springframework.integration.history.MessageHistory;
import org.springframework.integration.test.util.TestUtils;
import org.springframework.jdbc.core.JdbcTemplate;
@@ -43,6 +46,12 @@ import org.springframework.transaction.TransactionStatus;
import org.springframework.transaction.support.TransactionCallback;
import org.springframework.transaction.support.TransactionTemplate;
/**
* @author David Syer
* @author Gary Russell
* @since 2.0
*
*/
// Not transactional because the poller threads need access to the data
// @Transactional
public class JdbcPollingChannelAdapterParserTests {
@@ -149,6 +158,14 @@ public class JdbcPollingChannelAdapterParserTests {
}
}
@Test
public void testAutoChannel() {
setUp("autoChannelJdbcPollingChannelAdapterParserTests-context.xml", getClass());
MessageChannel autoChannel = appCtx.getBean("autoChannel", MessageChannel.class);
SourcePollingChannelAdapter autoChannelAdapter = appCtx.getBean("autoChannel.adapter", SourcePollingChannelAdapter.class);
assertSame(autoChannel, TestUtils.getPropertyValue(autoChannelAdapter, "outputChannel"));
}
@After
public void tearDown() {
if (appCtx != null) {

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2002-2011 the original author or authors.
* Copyright 2002-2012 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
@@ -13,6 +13,12 @@
package org.springframework.integration.jdbc.config;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertNotNull;
import static org.junit.Assert.assertNull;
import static org.junit.Assert.assertSame;
import static org.junit.Assert.assertTrue;
import java.sql.Types;
import java.util.List;
import java.util.Map;
@@ -20,25 +26,22 @@ import java.util.Map.Entry;
import org.junit.After;
import org.junit.Test;
import org.springframework.beans.DirectFieldAccessor;
import org.springframework.context.ConfigurableApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;
import org.springframework.integration.MessageChannel;
import org.springframework.integration.endpoint.SourcePollingChannelAdapter;
import org.springframework.integration.jdbc.storedproc.PrimeMapper;
import org.springframework.integration.jdbc.storedproc.ProcedureParameter;
import org.springframework.integration.test.util.TestUtils;
import org.springframework.jdbc.core.RowMapper;
import org.springframework.jdbc.core.SqlInOutParameter;
import org.springframework.jdbc.core.SqlOutParameter;
import org.springframework.jdbc.core.SqlParameter;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertNotNull;
import static org.junit.Assert.assertNull;
import static org.junit.Assert.assertTrue;
/**
* @author Gunnar Hillert
* @author Gary Russell
* @since 2.1
*
*/
@@ -185,6 +188,14 @@ public class StoredProcPollingChannelAdapterParserTests {
}
@Test
public void testAutoChannel() throws Exception {
setUp("storedProcPollingChannelAdapterParserTest.xml", getClass());
MessageChannel autoChannel = context.getBean("autoChannel", MessageChannel.class);
SourcePollingChannelAdapter autoChannelAdapter = context.getBean("autoChannel.adapter", SourcePollingChannelAdapter.class);
assertSame(autoChannel, TestUtils.getPropertyValue(autoChannelAdapter, "outputChannel"));
}
@After
public void tearDown(){
if(context != null){

View File

@@ -0,0 +1,18 @@
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:int="http://www.springframework.org/schema/integration"
xmlns:int-jdbc="http://www.springframework.org/schema/integration/jdbc"
xsi:schemaLocation="http://www.springframework.org/schema/integration http://www.springframework.org/schema/integration/spring-integration.xsd
http://www.springframework.org/schema/integration/jdbc http://www.springframework.org/schema/integration/jdbc/spring-integration-jdbc.xsd
http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd">
<int-jdbc:inbound-channel-adapter id="autoChannel"
query="select * from item where status=2"
data-source="dataSource" />
<int:bridge input-channel="autoStartup" output-channel="nullChannel" />
<import resource="jdbcInboundChannelAdapterCommonConfig.xml" />
</beans>

View File

@@ -19,7 +19,7 @@
<int-jdbc:sql-parameter-definition name="username" direction="IN" type="VARCHAR"/>
<int-jdbc:sql-parameter-definition name="password" direction="OUT" />
<int-jdbc:sql-parameter-definition name="age" direction="INOUT" type="INTEGER" scale="5"/>
<int-jdbc:sql-parameter-definition name="description" />
<int-jdbc:sql-parameter-definition name="description" />
<int-jdbc:parameter name="username" value="kenny" type="java.lang.String"/>
<int-jdbc:parameter name="description" value="Who killed Kenny?"/>
<int-jdbc:parameter name="password" expression="payload.username"/>
@@ -29,4 +29,23 @@
</int-jdbc:stored-proc-inbound-channel-adapter>
<int:poller default="true" fixed-rate="10000"/>
<int-jdbc:stored-proc-inbound-channel-adapter id="autoChannel"
data-source="dataSource"
stored-procedure-name="GET_PRIME_NUMBERS"
is-function="false">
<int-jdbc:sql-parameter-definition name="username" direction="IN" type="VARCHAR"/>
<int-jdbc:sql-parameter-definition name="password" direction="OUT" />
<int-jdbc:sql-parameter-definition name="age" direction="INOUT" type="INTEGER" scale="5"/>
<int-jdbc:sql-parameter-definition name="description" />
<int-jdbc:parameter name="username" value="kenny" type="java.lang.String"/>
<int-jdbc:parameter name="description" value="Who killed Kenny?"/>
<int-jdbc:parameter name="password" expression="payload.username"/>
<int-jdbc:parameter name="age" value="30" type="java.lang.Integer"/>
<int-jdbc:returning-resultset name="out" row-mapper="org.springframework.integration.jdbc.storedproc.PrimeMapper"/>
</int-jdbc:stored-proc-inbound-channel-adapter>
<int:bridge input-channel="autoChannel" output-channel="nullChannel" />
</beans>

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2002-2010 the original author or authors.
* Copyright 2002-2012 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.
@@ -16,19 +16,20 @@
package org.springframework.integration.jmx.config;
import org.w3c.dom.Element;
import org.springframework.beans.factory.support.AbstractBeanDefinition;
import org.springframework.beans.factory.support.BeanDefinitionBuilder;
import org.springframework.beans.factory.xml.AbstractSimpleBeanDefinitionParser;
import org.springframework.beans.factory.xml.ParserContext;
import org.springframework.integration.config.xml.AbstractChannelAdapterParser;
import org.springframework.integration.config.xml.IntegrationNamespaceUtils;
import org.springframework.util.StringUtils;
import org.springframework.integration.jmx.NotificationListeningMessageProducer;
import org.w3c.dom.Element;
/**
* @author Mark Fisher
* @author Gary Russell
* @since 2.0
*/
public class NotificationListeningChannelAdapterParser extends AbstractSimpleBeanDefinitionParser {
public class NotificationListeningChannelAdapterParser extends AbstractChannelAdapterParser {
@Override
protected boolean shouldGenerateIdAsFallback() {
@@ -36,23 +37,16 @@ public class NotificationListeningChannelAdapterParser extends AbstractSimpleBea
}
@Override
protected String getBeanClassName(Element element) {
return "org.springframework.integration.jmx.NotificationListeningMessageProducer";
}
@Override
protected void doParse(Element element, ParserContext parserContext, BeanDefinitionBuilder builder) {
Object source = parserContext.extractSource(element);
String channel = element.getAttribute("channel");
if (!StringUtils.hasText(channel)) {
parserContext.getReaderContext().error("The 'channel' attribute is required.", source);
}
builder.addPropertyReference("outputChannel", channel);
protected AbstractBeanDefinition doParse(Element element,
ParserContext parserContext, String channelName) {
BeanDefinitionBuilder builder = BeanDefinitionBuilder.genericBeanDefinition(NotificationListeningMessageProducer.class);
builder.addPropertyReference("outputChannel", channelName);
IntegrationNamespaceUtils.setReferenceIfAttributeDefined(builder, element, "server");
IntegrationNamespaceUtils.setReferenceIfAttributeDefined(builder, element, "notification-filter", "filter");
IntegrationNamespaceUtils.setReferenceIfAttributeDefined(builder, element, "handback");
IntegrationNamespaceUtils.setValueIfAttributeDefined(builder, element, "send-timeout");
IntegrationNamespaceUtils.setValueIfAttributeDefined(builder, element, "object-name");
return builder.getBeanDefinition();
}
}

View File

@@ -149,7 +149,7 @@
</xsd:annotation>
<xsd:complexContent>
<xsd:extension base="mbeanServerIdentifyerType">
<xsd:attribute name="channel" type="xsd:string" use="required" />
<xsd:attribute name="channel" type="xsd:string" />
<xsd:attribute name="object-name" type="xsd:string" use="required" />
</xsd:extension>
</xsd:complexContent>

View File

@@ -30,4 +30,13 @@
<bean id="testBean1" class="org.springframework.integration.jmx.config.TestBean"/>
<jmx:attribute-polling-channel-adapter id="autoChannel"
object-name="org.springframework.integration.jmx.config:type=TestBean,name=testBean1"
attribute-name="FirstMessage"
auto-startup="false">
<si:poller max-messages-per-poll="1" fixed-rate="2000"/>
</jmx:attribute-polling-channel-adapter>
<si:bridge input-channel="autoChannel" output-channel="nullChannel" />
</beans>

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2002-2010 the original author or authors.
* Copyright 2002-2012 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.
@@ -18,19 +18,23 @@ package org.springframework.integration.jmx.config;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertNotNull;
import static org.junit.Assert.assertSame;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.integration.Message;
import org.springframework.integration.MessageChannel;
import org.springframework.integration.core.PollableChannel;
import org.springframework.integration.endpoint.SourcePollingChannelAdapter;
import org.springframework.integration.test.util.TestUtils;
import org.springframework.test.context.ContextConfiguration;
import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
/**
* @author Mark Fisher
* @author Gary Russell
* @since 2.0
*/
@ContextConfiguration
@@ -46,6 +50,11 @@ public class AttributePollingChannelAdapterParserTests {
@Autowired
private TestBean testBean;
@Autowired
private MessageChannel autoChannel;
@Autowired @Qualifier("autoChannel.adapter")
private SourcePollingChannelAdapter autoChannelAdapter;
@Test
public void pollForAttribute() throws Exception {
@@ -56,4 +65,9 @@ public class AttributePollingChannelAdapterParserTests {
assertEquals("foo", result.getPayload());
}
@Test
public void testAutoChannel() {
assertSame(autoChannel, TestUtils.getPropertyValue(autoChannelAdapter, "outputChannel"));
}
}

View File

@@ -26,4 +26,9 @@
<bean id="testPublisher" class="org.springframework.integration.jmx.config.TestPublisher"/>
<jmx:notification-listening-channel-adapter id="autoChannel"
object-name="org.springframework.integration.jmx.config:type=TestPublisher,name=testPublisher"/>
<si:bridge input-channel="autoChannel" output-channel="nullChannel" />
</beans>

View File

@@ -19,14 +19,19 @@ package org.springframework.integration.jmx.config;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertNotNull;
import static org.junit.Assert.assertNull;
import static org.junit.Assert.assertSame;
import javax.management.Notification;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.integration.Message;
import org.springframework.integration.MessageChannel;
import org.springframework.integration.core.PollableChannel;
import org.springframework.integration.jmx.NotificationListeningMessageProducer;
import org.springframework.integration.test.util.TestUtils;
import org.springframework.test.context.ContextConfiguration;
import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
@@ -44,6 +49,11 @@ public class NotificationListeningChannelAdapterParserTests {
@Autowired
private TestPublisher testPublisher;
@Autowired
private MessageChannel autoChannel;
@Autowired @Qualifier("autoChannel.adapter")
private NotificationListeningMessageProducer autoChannelAdapter;
@Test
public void receiveNotification() throws Exception {
@@ -55,4 +65,9 @@ public class NotificationListeningChannelAdapterParserTests {
assertEquals("ABC", ((Notification) message.getPayload()).getMessage());
}
@Test
public void testAutoChannel() {
assertSame(autoChannel, TestUtils.getPropertyValue(autoChannelAdapter, "outputChannel"));
}
}

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2002-2011 the original author or authors.
* Copyright 2002-2012 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.
@@ -16,16 +16,17 @@
package org.springframework.integration.mail.config;
import org.w3c.dom.Element;
import org.springframework.beans.factory.config.BeanDefinition;
import org.springframework.beans.factory.support.AbstractBeanDefinition;
import org.springframework.beans.factory.support.BeanDefinitionBuilder;
import org.springframework.beans.factory.support.RootBeanDefinition;
import org.springframework.beans.factory.xml.AbstractSingleBeanDefinitionParser;
import org.springframework.beans.factory.xml.ParserContext;
import org.springframework.integration.config.xml.AbstractChannelAdapterParser;
import org.springframework.integration.config.xml.IntegrationNamespaceUtils;
import org.springframework.util.Assert;
import org.springframework.integration.mail.ImapIdleChannelAdapter;
import org.springframework.integration.mail.ImapMailReceiver;
import org.springframework.util.StringUtils;
import org.w3c.dom.Element;
/**
* Parser for the &lt;imap-idle-channel-adapter&gt; element in the 'mail' namespace.
@@ -35,34 +36,19 @@ import org.springframework.util.StringUtils;
* @author Oleg Zhurakousky
* @author Gary Russell
*/
public class ImapIdleChannelAdapterParser extends AbstractSingleBeanDefinitionParser {
public class ImapIdleChannelAdapterParser extends AbstractChannelAdapterParser {
private static final String BASE_PACKAGE = "org.springframework.integration.mail";
protected String getBeanClassName(Element element) {
return BASE_PACKAGE + ".ImapIdleChannelAdapter";
}
protected boolean shouldGenerateId() {
return false;
}
protected boolean shouldGenerateIdAsFallback() {
return true;
}
protected void doParse(Element element, ParserContext parserContext, BeanDefinitionBuilder builder) {
String channel = element.getAttribute("channel");
Assert.hasText(channel, "the 'channel' attribute is required");
protected AbstractBeanDefinition doParse(Element element, ParserContext parserContext, String channelName) {
BeanDefinitionBuilder builder = BeanDefinitionBuilder.genericBeanDefinition(ImapIdleChannelAdapter.class);
builder.addConstructorArgValue(this.parseImapMailReceiver(element, parserContext));
builder.addPropertyReference("outputChannel", channel);
builder.addPropertyReference("outputChannel", channelName);
IntegrationNamespaceUtils.setReferenceIfAttributeDefined(builder, element, "error-channel", "errorChannel");
IntegrationNamespaceUtils.setValueIfAttributeDefined(builder, element, "auto-startup");
return builder.getBeanDefinition();
}
private BeanDefinition parseImapMailReceiver(Element element, ParserContext parserContext) {
BeanDefinitionBuilder receiverBuilder = BeanDefinitionBuilder.genericBeanDefinition(BASE_PACKAGE + ".ImapMailReceiver");
BeanDefinitionBuilder receiverBuilder = BeanDefinitionBuilder.genericBeanDefinition(ImapMailReceiver.class);
Object source = parserContext.extractSource(element);
String uri = element.getAttribute("store-uri");
if (StringUtils.hasText(uri)) {

View File

@@ -135,7 +135,7 @@
</xsd:documentation>
</xsd:annotation>
</xsd:attribute>
<xsd:attribute name="channel" type="xsd:string" use="required">
<xsd:attribute name="channel" type="xsd:string">
<xsd:annotation>
<xsd:documentation>
Reference for the MessageChannel to which this adapter will send Messages.

View File

@@ -71,4 +71,12 @@
<task:executor id="executor" pool-size="5"/>
<mail:imap-idle-channel-adapter
id="autoChannel"
store-uri="imap:foo"
auto-startup="false"
should-delete-messages="true"/>
<integration:bridge input-channel="autoChannel" output-channel="nullChannel" />
</beans>

View File

@@ -28,9 +28,12 @@ import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.beans.DirectFieldAccessor;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.context.ApplicationContext;
import org.springframework.integration.MessageChannel;
import org.springframework.integration.mail.ImapIdleChannelAdapter;
import org.springframework.integration.mail.ImapMailReceiver;
import org.springframework.integration.test.util.TestUtils;
import org.springframework.test.context.ContextConfiguration;
import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
@@ -46,6 +49,11 @@ public class ImapIdleChannelAdapterParserTests {
@Autowired
private ApplicationContext context;
@Autowired
private MessageChannel autoChannel;
@Autowired @Qualifier("autoChannel.adapter")
private ImapIdleChannelAdapter autoChannelAdapter;
@Test
public void simpleAdapter() {
@@ -140,4 +148,9 @@ public class ImapIdleChannelAdapterParserTests {
assertEquals("bar", properties.getProperty("foo"));
assertEquals(Boolean.FALSE, receiverAccessor.getPropertyValue("shouldDeleteMessages"));
}
@Test
public void testAutoChannel() {
assertSame(autoChannel, TestUtils.getPropertyValue(autoChannelAdapter, "outputChannel"));
}
}

View File

@@ -98,6 +98,11 @@
<mail:inbound-channel-adapter id="imapShouldMarkAsReadTrue" channel="testChannel" protocol="imap" should-delete-messages="false" auto-startup="false" should-mark-messages-as-read="true"/>
<!-- INT-2407 -->
<mail:inbound-channel-adapter id="autoChannel" protocol="pop3" should-delete-messages="false" auto-startup="false"/>
<si:bridge input-channel="autoChannel" output-channel="nullChannel"/>
<!-- COMMON CONFIGURATION -->

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2002-2010 the original author or authors.
* Copyright 2002-2012 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.
@@ -20,6 +20,7 @@ import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertNotNull;
import static org.junit.Assert.assertNull;
import static org.junit.Assert.assertSame;
import static org.junit.Assert.assertTrue;
import static org.junit.Assert.fail;
@@ -27,19 +28,22 @@ import javax.mail.Authenticator;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.xml.sax.SAXParseException;
import org.springframework.beans.DirectFieldAccessor;
import org.springframework.beans.factory.BeanDefinitionStoreException;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;
import org.springframework.integration.MessageChannel;
import org.springframework.integration.endpoint.SourcePollingChannelAdapter;
import org.springframework.integration.mail.AbstractMailReceiver;
import org.springframework.integration.mail.ImapIdleChannelAdapter;
import org.springframework.integration.mail.ImapMailReceiver;
import org.springframework.integration.mail.Pop3MailReceiver;
import org.springframework.integration.test.util.TestUtils;
import org.springframework.test.context.ContextConfiguration;
import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
import org.xml.sax.SAXParseException;
/**
* @author Mark Fisher
@@ -53,6 +57,11 @@ public class InboundChannelAdapterParserTests {
@Autowired
private ApplicationContext context;
@Autowired
private MessageChannel autoChannel;
@Autowired @Qualifier("autoChannel.adapter")
private SourcePollingChannelAdapter autoChannelAdapter;
//==================== INT-982 =====================
@@ -283,4 +292,9 @@ public class InboundChannelAdapterParserTests {
return (AbstractMailReceiver) new DirectFieldAccessor(target).getPropertyValue("mailReceiver");
}
@Test
public void testAutoChannel() {
assertSame(autoChannel, TestUtils.getPropertyValue(autoChannelAdapter, "outputChannel"));
}
}

View File

@@ -16,7 +16,6 @@
package org.springframework.integration.redis.config;
import org.springframework.beans.factory.config.RuntimeBeanReference;
import org.springframework.beans.factory.support.AbstractBeanDefinition;
import org.springframework.beans.factory.support.BeanDefinitionBuilder;
import org.springframework.beans.factory.xml.ParserContext;
@@ -28,6 +27,7 @@ import org.w3c.dom.Element;
/**
* @author Oleg Zhurakousky
* @author Mark Fisher
* @author Gary Russell
* @since 2.1
*/
public class RedisInboundChannelAdapterParser extends AbstractChannelAdapterParser {
@@ -41,7 +41,7 @@ public class RedisInboundChannelAdapterParser extends AbstractChannelAdapterPars
connectionFactory = "redisConnectionFactory";
}
builder.addConstructorArgReference(connectionFactory);
builder.addPropertyValue("outputChannel", new RuntimeBeanReference(channelName));
builder.addPropertyReference("outputChannel", channelName);
IntegrationNamespaceUtils.setValueIfAttributeDefined(builder, element, "topics");
IntegrationNamespaceUtils.setReferenceIfAttributeDefined(builder, element, "error-channel");
IntegrationNamespaceUtils.setReferenceIfAttributeDefined(builder, element, "message-converter");

View File

@@ -173,7 +173,7 @@
</xsd:documentation>
</xsd:annotation>
</xsd:attribute>
<xsd:attribute name="channel" type="xsd:string" use="required">
<xsd:attribute name="channel" type="xsd:string">
<xsd:annotation>
<xsd:documentation>
Channel to which Messages will be sent.

View File

@@ -23,4 +23,10 @@
<bean id="testConverter"
class="org.springframework.integration.redis.config.RedisInboundChannelAdapterParserTests$TestMessageConverter" />
<int-redis:inbound-channel-adapter
id="autoChannel" topics="foo, bar" error-channel="testErrorChannel"
message-converter="testConverter" />
<int:bridge input-channel="autoChannel" output-channel="nullChannel"/>
</beans>

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2002-2011 the original author or authors.
* Copyright 2002-2012 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.
@@ -16,26 +16,30 @@
package org.springframework.integration.redis.config;
import static junit.framework.Assert.assertEquals;
import static org.junit.Assert.assertSame;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.beans.DirectFieldAccessor;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.context.ApplicationContext;
import org.springframework.data.redis.connection.jedis.JedisConnectionFactory;
import org.springframework.integration.MessageChannel;
import org.springframework.integration.channel.QueueChannel;
import org.springframework.integration.redis.inbound.RedisInboundChannelAdapter;
import org.springframework.integration.redis.rules.RedisAvailable;
import org.springframework.integration.redis.rules.RedisAvailableTests;
import org.springframework.integration.support.converter.SimpleMessageConverter;
import org.springframework.integration.test.util.TestUtils;
import org.springframework.test.context.ContextConfiguration;
import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
import static junit.framework.Assert.assertEquals;
/**
* @author Oleg Zhurakousky
* @author Mark Fisher
* @author Gary Russell
*/
@ContextConfiguration
@RunWith(SpringJUnit4ClassRunner.class)
@@ -43,7 +47,12 @@ public class RedisInboundChannelAdapterParserTests extends RedisAvailableTests{
@Autowired
private ApplicationContext context;
@Autowired
private MessageChannel autoChannel;
@Autowired @Qualifier("autoChannel.adapter")
private RedisInboundChannelAdapter autoChannelAdapter;
@Test
@RedisAvailable
@@ -72,6 +81,11 @@ public class RedisInboundChannelAdapterParserTests extends RedisAvailableTests{
assertEquals("Hello Redis from bar", receiveChannel.receive(1000).getPayload());
}
@Test
@RedisAvailable
public void testAutoChannel() {
assertSame(autoChannel, TestUtils.getPropertyValue(autoChannelAdapter, "outputChannel"));
}
@SuppressWarnings("unused")
private static class TestMessageConverter extends SimpleMessageConverter {

View File

@@ -389,7 +389,7 @@
</xsd:documentation>
</xsd:annotation>
</xsd:attribute>
<xsd:attribute name="channel" use="required" type="xsd:string">
<xsd:attribute name="channel" type="xsd:string">
<xsd:annotation>
<xsd:appinfo>
<tool:annotation kind="ref">

View File

@@ -93,5 +93,16 @@
<beans:constructor-arg value="."/>
</beans:bean>
<sftp:inbound-channel-adapter id="autoChannel"
session-factory="sftpSessionFactory"
filter="filter"
remote-directory="/foo"
local-directory="file:foo"
auto-create-local-directory="false"
delete-remote-files="false">
<poller fixed-rate="1000"/>
</sftp:inbound-channel-adapter>
<bridge input-channel="autoChannel" output-channel="nullChannel" />
</beans:beans>

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2002-2010 the original author or authors.
* Copyright 2002-2012 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.
@@ -20,6 +20,7 @@ import static junit.framework.Assert.assertEquals;
import static junit.framework.Assert.assertFalse;
import static junit.framework.Assert.assertNotNull;
import static junit.framework.Assert.assertTrue;
import static org.junit.Assert.assertSame;
import java.io.File;
import java.util.Comparator;
@@ -33,6 +34,7 @@ import org.springframework.beans.factory.BeanCreationException;
import org.springframework.beans.factory.BeanDefinitionStoreException;
import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;
import org.springframework.integration.MessageChannel;
import org.springframework.integration.core.PollableChannel;
import org.springframework.integration.endpoint.SourcePollingChannelAdapter;
import org.springframework.integration.sftp.inbound.SftpInboundFileSynchronizer;
@@ -41,6 +43,7 @@ import org.springframework.integration.test.util.TestUtils;
/**
* @author Oleg Zhurakousky
* @author Gary Russell
*/
public class InboundChannelAdapterParserTests {
@@ -82,6 +85,16 @@ public class InboundChannelAdapterParserTests {
assertNotNull(requestChannel.receive(2000));
}
@Test
public void testAutoChannel() {
ApplicationContext context =
new ClassPathXmlApplicationContext("InboundChannelAdapterParserTests-context.xml", this.getClass());
// Auto-created channel
MessageChannel autoChannel = context.getBean("autoChannel", MessageChannel.class);
SourcePollingChannelAdapter autoChannelAdapter = context.getBean("autoChannel.adapter", SourcePollingChannelAdapter.class);
assertSame(autoChannel, TestUtils.getPropertyValue(autoChannelAdapter, "outputChannel"));
}
@Test(expected=BeanDefinitionStoreException.class)
//exactly one of 'filename-pattern' or 'filter' is allowed on SFTP inbound adapter
public void testFailWithFilePatternAndFilter() throws Exception{

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2002-2011 the original author or authors.
* Copyright 2002-2012 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.
@@ -16,23 +16,24 @@
package org.springframework.integration.xmpp.config;
import org.w3c.dom.Element;
import org.springframework.beans.factory.BeanCreationException;
import org.springframework.beans.factory.support.AbstractBeanDefinition;
import org.springframework.beans.factory.support.BeanDefinitionBuilder;
import org.springframework.beans.factory.xml.AbstractSingleBeanDefinitionParser;
import org.springframework.beans.factory.xml.ParserContext;
import org.springframework.integration.config.xml.AbstractChannelAdapterParser;
import org.springframework.integration.config.xml.IntegrationNamespaceUtils;
import org.springframework.integration.xmpp.support.DefaultXmppHeaderMapper;
import org.springframework.util.StringUtils;
import org.w3c.dom.Element;
/**
* Base class for XMPP inbound parsers
*
* @author Oleg Zhurakousky
* @author Gary Russell
* @since 2.0.1
*/
public abstract class AbstractXmppInboundChannelAdapterParser extends AbstractSingleBeanDefinitionParser {
public abstract class AbstractXmppInboundChannelAdapterParser extends AbstractChannelAdapterParser {
@Override
protected boolean shouldGenerateId() {
@@ -44,13 +45,15 @@ public abstract class AbstractXmppInboundChannelAdapterParser extends AbstractSi
return true;
}
@Override
protected void doParse(Element element, ParserContext parserContext, BeanDefinitionBuilder builder) {
protected abstract String getBeanClassName(Element element);
protected AbstractBeanDefinition doParse(Element element, ParserContext parserContext, String channelName) {
BeanDefinitionBuilder builder = BeanDefinitionBuilder.genericBeanDefinition(getBeanClassName(element));
IntegrationNamespaceUtils.configureHeaderMapper(element, builder, parserContext, DefaultXmppHeaderMapper.class, null);
String connectionName = element.getAttribute("xmpp-connection");
if (StringUtils.hasText(connectionName)){
builder.addConstructorArgReference(connectionName);
}
@@ -62,10 +65,11 @@ public abstract class AbstractXmppInboundChannelAdapterParser extends AbstractSi
"'xmpp-connection' attribute or have default XMPP connection bean registered under the name 'xmppConnection'" +
"(e.g., <int-xmpp:xmpp-connection .../>). If 'id' is not provided the default will be 'xmppConnection'.");
}
IntegrationNamespaceUtils.setReferenceIfAttributeDefined(builder, element, "channel", "outputChannel");
builder.addPropertyReference("outputChannel", channelName);
IntegrationNamespaceUtils.setValueIfAttributeDefined(builder, element, "auto-startup");
IntegrationNamespaceUtils.setReferenceIfAttributeDefined(builder, element, "error-channel");
this.postProcess(element, parserContext, builder);
return builder.getBeanDefinition();
}
protected void postProcess(Element element, ParserContext parserContext, BeanDefinitionBuilder builder){

View File

@@ -161,7 +161,7 @@
</xsd:documentation>
</xsd:annotation>
</xsd:attribute>
<xsd:attribute name="channel" use="required" type="xsd:string">
<xsd:attribute name="channel" type="xsd:string">
<xsd:annotation>
<xsd:appinfo>
<tool:annotation kind="ref">

View File

@@ -21,14 +21,21 @@
<beans:bean id="testConnection" class="org.mockito.Mockito" factory-method="mock">
<beans:constructor-arg value="org.jivesoftware.smack.XMPPConnection"/>
</beans:bean>
<channel id="xmppInbound">
<queue/>
</channel>
<xmpp:inbound-channel-adapter id="xmppInboundAdapter" channel="xmppInbound"
xmpp-connection="testConnection" extract-payload="false"
<xmpp:inbound-channel-adapter id="xmppInboundAdapter" channel="xmppInbound"
xmpp-connection="testConnection" extract-payload="false"
auto-startup="false" error-channel="errorChannel"
mapped-request-headers="foo*, xmpp*"/>
<xmpp:inbound-channel-adapter id="autoChannel"
xmpp-connection="testConnection" extract-payload="false"
auto-startup="false" error-channel="errorChannel"
mapped-request-headers="foo*, xmpp*"/>
<bridge input-channel="autoChannel" output-channel="nullChannel" />
</beans:beans>

View File

@@ -16,6 +16,10 @@
package org.springframework.integration.xmpp.config;
import static junit.framework.Assert.assertEquals;
import static junit.framework.Assert.assertFalse;
import static org.junit.Assert.assertSame;
import java.lang.reflect.Field;
import org.jivesoftware.smack.Chat;
@@ -23,12 +27,11 @@ import org.jivesoftware.smack.ChatManager;
import org.jivesoftware.smack.PacketListener;
import org.jivesoftware.smack.XMPPConnection;
import org.jivesoftware.smack.packet.Message;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.mockito.Mockito;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.context.ApplicationContext;
import org.springframework.integration.MessageChannel;
import org.springframework.integration.channel.QueueChannel;
@@ -38,9 +41,6 @@ import org.springframework.test.context.ContextConfiguration;
import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
import org.springframework.util.ReflectionUtils;
import static junit.framework.Assert.assertEquals;
import static junit.framework.Assert.assertFalse;
/**
* @author Oleg Zhurakousky
* @author Mark Fisher
@@ -51,10 +51,16 @@ public class ChatMessageInboundChannelAdapterParserTests {
@Autowired
private ApplicationContext context;
@Autowired
private QueueChannel xmppInbound;
@Autowired
private MessageChannel autoChannel;
@Autowired @Qualifier("autoChannel.adapter")
private ChatMessageListeningEndpoint autoChannelAdapter;
@Test
public void testInboundAdapter(){
ChatMessageListeningEndpoint adapter = context.getBean("xmppInboundAdapter", ChatMessageListeningEndpoint.class);
@@ -94,4 +100,8 @@ public class ChatMessageInboundChannelAdapterParserTests {
assertEquals("oleg", siMessage.getHeaders().get("xmpp_to"));
}
@Test
public void testAutoChannel() {
assertSame(autoChannel, TestUtils.getPropertyValue(autoChannelAdapter, "outputChannel"));
}
}