diff --git a/spring-integration-amqp/src/main/java/org/springframework/integration/amqp/config/AmqpChannelFactoryBean.java b/spring-integration-amqp/src/main/java/org/springframework/integration/amqp/config/AmqpChannelFactoryBean.java index c1f21a5080..d3b4d2e618 100644 --- a/spring-integration-amqp/src/main/java/org/springframework/integration/amqp/config/AmqpChannelFactoryBean.java +++ b/spring-integration-amqp/src/main/java/org/springframework/integration/amqp/config/AmqpChannelFactoryBean.java @@ -1,5 +1,5 @@ /* - * Copyright 2002-2014 the original author or authors. + * Copyright 2002-2015 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,6 +16,7 @@ package org.springframework.integration.amqp.config; +import java.util.Arrays; import java.util.List; import java.util.concurrent.Executor; @@ -239,7 +240,7 @@ public class AmqpChannelFactoryBean extends AbstractFactoryBean> { * doesn't then the numbered message comes first, or finally of neither has a sequence number then they are equal in * rank. */ + @Override public int compare(Message o1, Message o2) { Integer sequenceNumber1 = new IntegrationMessageHeaderAccessor(o1).getSequenceNumber(); Integer sequenceNumber2 = new IntegrationMessageHeaderAccessor(o2).getSequenceNumber(); - if (sequenceNumber1 == sequenceNumber2) { + if (sequenceNumber1 == sequenceNumber2) {//NOSONAR - early exit optimization return 0; } if (sequenceNumber1 == null) { diff --git a/spring-integration-core/src/main/java/org/springframework/integration/aop/MessagePublishingInterceptor.java b/spring-integration-core/src/main/java/org/springframework/integration/aop/MessagePublishingInterceptor.java index daebe27e71..d8aa321ff1 100644 --- a/spring-integration-core/src/main/java/org/springframework/integration/aop/MessagePublishingInterceptor.java +++ b/spring-integration-core/src/main/java/org/springframework/integration/aop/MessagePublishingInterceptor.java @@ -142,7 +142,7 @@ public class MessagePublishingInterceptor implements MethodInterceptor, BeanFact context.setVariable(PublisherMetadataSource.RETURN_VALUE_VARIABLE_NAME, returnValue); return returnValue; } - catch (Throwable t) { + catch (Throwable t) {//NOSONAR - rethrown below context.setVariable(PublisherMetadataSource.EXCEPTION_VARIABLE_NAME, t); throw t; } diff --git a/spring-integration-core/src/main/java/org/springframework/integration/channel/AbstractMessageChannel.java b/spring-integration-core/src/main/java/org/springframework/integration/channel/AbstractMessageChannel.java index 0f8a69fc48..48830e089b 100644 --- a/spring-integration-core/src/main/java/org/springframework/integration/channel/AbstractMessageChannel.java +++ b/spring-integration-core/src/main/java/org/springframework/integration/channel/AbstractMessageChannel.java @@ -1,5 +1,5 @@ /* - * Copyright 2002-2014 the original author or authors. + * Copyright 2002-2015 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. @@ -396,7 +396,7 @@ public abstract class AbstractMessageChannel extends IntegrationObjectSupport try { interceptor.afterSendCompletion(message, channel, sent, ex); } - catch (Throwable ex2) { + catch (Exception ex2) { logger.error("Exception from afterSendCompletion in " + interceptor, ex2); } } @@ -443,7 +443,7 @@ public abstract class AbstractMessageChannel extends IntegrationObjectSupport try { interceptor.afterReceiveCompletion(message, channel, ex); } - catch (Throwable ex2) { + catch (Exception ex2) { logger.error("Exception from afterReceiveCompletion in " + interceptor, ex2); } } diff --git a/spring-integration-core/src/main/java/org/springframework/integration/channel/MessagePublishingErrorHandler.java b/spring-integration-core/src/main/java/org/springframework/integration/channel/MessagePublishingErrorHandler.java index 75531f338d..9ae2b692ae 100644 --- a/spring-integration-core/src/main/java/org/springframework/integration/channel/MessagePublishingErrorHandler.java +++ b/spring-integration-core/src/main/java/org/springframework/integration/channel/MessagePublishingErrorHandler.java @@ -1,5 +1,5 @@ /* - * Copyright 2002-2009 the original author or authors. + * Copyright 2002-2015 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. @@ -67,6 +67,7 @@ public class MessagePublishingErrorHandler implements ErrorHandler, BeanFactoryA this.sendTimeout = sendTimeout; } + @Override public void setBeanFactory(BeanFactory beanFactory) { Assert.notNull(beanFactory, "beanFactory must not be null"); if (this.channelResolver == null) { @@ -74,6 +75,7 @@ public class MessagePublishingErrorHandler implements ErrorHandler, BeanFactoryA } } + @Override public final void handleError(Throwable t) { MessageChannel errorChannel = this.resolveErrorChannel(t); boolean sent = false; @@ -86,10 +88,14 @@ public class MessagePublishingErrorHandler implements ErrorHandler, BeanFactoryA sent = errorChannel.send(new ErrorMessage(t)); } } - catch (Throwable errorDeliveryError) { // message will be logged only + catch (Throwable errorDeliveryError) {//NOSONAR + // message will be logged only if (logger.isWarnEnabled()) { logger.warn("Error message was not delivered.", errorDeliveryError); } + if (errorDeliveryError instanceof Error) { + throw ((Error) errorDeliveryError); + } } } if (!sent && logger.isErrorEnabled()) { diff --git a/spring-integration-core/src/main/java/org/springframework/integration/channel/interceptor/GlobalChannelInterceptorWrapper.java b/spring-integration-core/src/main/java/org/springframework/integration/channel/interceptor/GlobalChannelInterceptorWrapper.java index 5f98a006f9..2e0fe06036 100644 --- a/spring-integration-core/src/main/java/org/springframework/integration/channel/interceptor/GlobalChannelInterceptorWrapper.java +++ b/spring-integration-core/src/main/java/org/springframework/integration/channel/interceptor/GlobalChannelInterceptorWrapper.java @@ -1,5 +1,5 @@ /* - * Copyright 2002-2013 the original author or authors. + * Copyright 2002-2015 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,6 +16,8 @@ package org.springframework.integration.channel.interceptor; +import java.util.Arrays; + import org.springframework.core.Ordered; import org.springframework.messaging.support.ChannelInterceptor; import org.springframework.util.Assert; @@ -23,6 +25,7 @@ import org.springframework.util.Assert; /** * @author Oleg Zhurakousky * @author Mark Fisher + * @author Gary Russell * @since 2.0 */ public class GlobalChannelInterceptorWrapper implements Ordered { @@ -59,7 +62,7 @@ public class GlobalChannelInterceptorWrapper implements Ordered { } public void setPatterns(String[] patterns) { - this.patterns = patterns; + this.patterns = Arrays.copyOf(patterns, patterns.length); } public String[] getPatterns() { diff --git a/spring-integration-core/src/main/java/org/springframework/integration/endpoint/MethodInvokingMessageSource.java b/spring-integration-core/src/main/java/org/springframework/integration/endpoint/MethodInvokingMessageSource.java index 6a1b001a5f..9409d07b43 100644 --- a/spring-integration-core/src/main/java/org/springframework/integration/endpoint/MethodInvokingMessageSource.java +++ b/spring-integration-core/src/main/java/org/springframework/integration/endpoint/MethodInvokingMessageSource.java @@ -1,5 +1,5 @@ /* - * Copyright 2002-2014 the original author or authors. + * Copyright 2002-2015 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. @@ -115,7 +115,7 @@ public class MethodInvokingMessageSource extends AbstractMessageSource } return ReflectionUtils.invokeMethod(this.method, this.object); } - catch (Throwable e) { + catch (Exception e) { throw new MessagingException("Failed to invoke method", e); } } diff --git a/spring-integration-core/src/main/java/org/springframework/integration/gateway/GatewayProxyFactoryBean.java b/spring-integration-core/src/main/java/org/springframework/integration/gateway/GatewayProxyFactoryBean.java index 925d70e832..104af0e7e9 100644 --- a/spring-integration-core/src/main/java/org/springframework/integration/gateway/GatewayProxyFactoryBean.java +++ b/spring-integration-core/src/main/java/org/springframework/integration/gateway/GatewayProxyFactoryBean.java @@ -29,11 +29,6 @@ import java.util.concurrent.Future; import org.aopalliance.intercept.MethodInterceptor; import org.aopalliance.intercept.MethodInvocation; -import reactor.core.Environment; -import reactor.core.composable.Promise; -import reactor.core.composable.spec.Promises; -import reactor.function.Functions; - import org.springframework.aop.framework.ProxyFactory; import org.springframework.aop.support.AopUtils; import org.springframework.beans.SimpleTypeConverter; @@ -68,6 +63,11 @@ import org.springframework.util.ObjectUtils; import org.springframework.util.ReflectionUtils; import org.springframework.util.StringUtils; +import reactor.core.Environment; +import reactor.core.composable.Promise; +import reactor.core.composable.spec.Promises; +import reactor.function.Functions; + /** * Generates a proxy for the provided service interface to enable interaction * with messaging components without application code being aware of them allowing @@ -373,7 +373,7 @@ public class GatewayProxyFactoryBean extends AbstractEndpoint try { return this.invokeGatewayMethod(invocation); } - catch (Throwable e) { + catch (Throwable e) {//NOSONAR - ok to catch, rethrown below this.rethrowExceptionCauseIfPossible(e, invocation.getMethod()); return null; // preceding call should always throw something } @@ -638,7 +638,10 @@ public class GatewayProxyFactoryBean extends AbstractEndpoint try { return doInvoke(this.invocation); } - catch (Throwable t) { + catch (Error e) {//NOSONAR + throw e; + } + catch (Throwable t) {//NOSONAR if (t instanceof RuntimeException) { throw (RuntimeException) t; } diff --git a/spring-integration-core/src/main/java/org/springframework/integration/gateway/MethodArgsHolder.java b/spring-integration-core/src/main/java/org/springframework/integration/gateway/MethodArgsHolder.java index 0a8ce4c792..5410601456 100644 --- a/spring-integration-core/src/main/java/org/springframework/integration/gateway/MethodArgsHolder.java +++ b/spring-integration-core/src/main/java/org/springframework/integration/gateway/MethodArgsHolder.java @@ -1,5 +1,5 @@ /* - * Copyright 2013 the original author or authors. + * Copyright 2013-2015 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. @@ -34,9 +34,9 @@ public final class MethodArgsHolder { private final Object[] args; - public MethodArgsHolder(Method method, Object[] args) { + public MethodArgsHolder(Method method, Object[] args) {//NOSONAR - direct storage this.method = method; - this.args = args; + this.args = args;//NOSONAR - direct storage } public final Method getMethod() { @@ -44,7 +44,7 @@ public final class MethodArgsHolder { } public final Object[] getArgs() { - return args; + return args;//NOSONAR - direct access } } diff --git a/spring-integration-core/src/main/java/org/springframework/integration/handler/AbstractMessageHandler.java b/spring-integration-core/src/main/java/org/springframework/integration/handler/AbstractMessageHandler.java index 6fee8556e8..e6556b4c4d 100644 --- a/spring-integration-core/src/main/java/org/springframework/integration/handler/AbstractMessageHandler.java +++ b/spring-integration-core/src/main/java/org/springframework/integration/handler/AbstractMessageHandler.java @@ -1,5 +1,5 @@ /* - * Copyright 2002-2014 the original author or authors. + * Copyright 2002-2015 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. @@ -67,7 +67,7 @@ public abstract class AbstractMessageHandler extends IntegrationObjectSupport im @Override public final void handleMessage(Message message) { Assert.notNull(message, "Message must not be null"); - Assert.notNull(message.getPayload(), "Message payload must not be null"); + Assert.notNull(message.getPayload(), "Message payload must not be null");//NOSONAR - false positive if (this.logger.isDebugEnabled()) { this.logger.debug(this + " received message: " + message); } diff --git a/spring-integration-core/src/main/java/org/springframework/integration/handler/advice/AbstractRequestHandlerAdvice.java b/spring-integration-core/src/main/java/org/springframework/integration/handler/advice/AbstractRequestHandlerAdvice.java index 45cf53e690..b66e8dccab 100644 --- a/spring-integration-core/src/main/java/org/springframework/integration/handler/advice/AbstractRequestHandlerAdvice.java +++ b/spring-integration-core/src/main/java/org/springframework/integration/handler/advice/AbstractRequestHandlerAdvice.java @@ -1,5 +1,5 @@ /* - * Copyright 2002-2014 the original author or authors. + * Copyright 2002-2015 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. @@ -73,10 +73,10 @@ public abstract class AbstractRequestHandlerAdvice extends IntegrationObjectSupp try { return invocation.proceed(); } - catch (Exception e) { + catch (Exception e) {//NOSONAR - catch necessary so we can wrap Errors throw e; } - catch (Throwable e) { + catch (Throwable e) {//NOSONAR - ok to catch; unwrapped and rethrown below throw new ThrowableHolderException(e); } } @@ -97,10 +97,10 @@ public abstract class AbstractRequestHandlerAdvice extends IntegrationObjectSupp " so please raise an issue if you see this exception"); } } - catch (Exception e) { + catch (Exception e) {//NOSONAR - catch necessary so we can wrap Errors throw e; } - catch (Throwable e) { + catch (Throwable e) {//NOSONAR - ok to catch; unwrapped and rethrown below throw new ThrowableHolderException(e); } } @@ -132,10 +132,9 @@ public abstract class AbstractRequestHandlerAdvice extends IntegrationObjectSupp */ protected Exception unwrapExceptionIfNecessary(Exception e) { Exception actualException = e; - if (e instanceof ThrowableHolderException) { - if (e.getCause() instanceof Exception) { - actualException = (Exception) e.getCause(); - } + if (e instanceof ThrowableHolderException + && e.getCause() instanceof Exception) { + actualException = (Exception) e.getCause(); } return actualException; } diff --git a/spring-integration-core/src/main/java/org/springframework/integration/util/ErrorHandlingTaskExecutor.java b/spring-integration-core/src/main/java/org/springframework/integration/util/ErrorHandlingTaskExecutor.java index 27da96baac..c66a05b0b6 100644 --- a/spring-integration-core/src/main/java/org/springframework/integration/util/ErrorHandlingTaskExecutor.java +++ b/spring-integration-core/src/main/java/org/springframework/integration/util/ErrorHandlingTaskExecutor.java @@ -1,5 +1,5 @@ /* - * Copyright 2002-2010 the original author or authors. + * Copyright 2002-2015 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. @@ -26,9 +26,10 @@ import org.springframework.util.ErrorHandler; * A {@link TaskExecutor} implementation that wraps an existing Executor * instance in order to catch any exceptions. If an exception is thrown, it * will be handled by the provided {@link ErrorHandler}. - * + * * @author Jonas Partner * @author Mark Fisher + * @author Gary Russell */ public class ErrorHandlingTaskExecutor implements TaskExecutor { @@ -45,13 +46,15 @@ public class ErrorHandlingTaskExecutor implements TaskExecutor { } + @Override public void execute(final Runnable task) { this.executor.execute(new Runnable() { + @Override public void run() { try { task.run(); } - catch (Throwable t) { + catch (Throwable t) {//NOSONAR errorHandler.handleError(t); } } diff --git a/spring-integration-core/src/test/java/org/springframework/integration/gateway/AsyncGatewayTests.java b/spring-integration-core/src/test/java/org/springframework/integration/gateway/AsyncGatewayTests.java index e4237f79c0..b88c476312 100644 --- a/spring-integration-core/src/test/java/org/springframework/integration/gateway/AsyncGatewayTests.java +++ b/spring-integration-core/src/test/java/org/springframework/integration/gateway/AsyncGatewayTests.java @@ -1,5 +1,5 @@ /* - * Copyright 2002-2014 the original author or authors. + * Copyright 2002-2015 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. @@ -36,6 +36,7 @@ import org.junit.Test; import org.springframework.beans.factory.BeanFactory; import org.springframework.integration.annotation.Gateway; import org.springframework.integration.annotation.GatewayHeader; +import org.springframework.integration.channel.DirectChannel; import org.springframework.integration.channel.QueueChannel; import org.springframework.messaging.Message; import org.springframework.messaging.MessageChannel; @@ -87,6 +88,34 @@ public class AsyncGatewayTests { assertEquals("foobar", ((Message) result).getPayload()); } + @Test + public void futureWithError() throws Exception { + final Error error = new Error("error"); + DirectChannel channel = new DirectChannel() { + + @Override + protected boolean doSend(Message message, long timeout) { + throw error; + } + + }; + GatewayProxyFactoryBean proxyFactory = new GatewayProxyFactoryBean(); + proxyFactory.setDefaultRequestChannel(channel); + proxyFactory.setServiceInterface(TestEchoService.class); + proxyFactory.setBeanName("testGateway"); + proxyFactory.setBeanFactory(mock(BeanFactory.class)); + proxyFactory.afterPropertiesSet(); + TestEchoService service = (TestEchoService) proxyFactory.getObject(); + Future> f = service.returnMessage("foo"); + try { + f.get(1000, TimeUnit.MILLISECONDS); + fail("Expected Exception"); + } + catch (ExecutionException e) { + assertEquals(error, e.getCause()); + } + } + @Test public void listenableFutureWithMessageReturned() throws Exception { QueueChannel requestChannel = new QueueChannel(); diff --git a/spring-integration-http/src/main/java/org/springframework/integration/http/multipart/UploadedMultipartFile.java b/spring-integration-http/src/main/java/org/springframework/integration/http/multipart/UploadedMultipartFile.java index 15caf3e6d7..86fa539c61 100644 --- a/spring-integration-http/src/main/java/org/springframework/integration/http/multipart/UploadedMultipartFile.java +++ b/spring-integration-http/src/main/java/org/springframework/integration/http/multipart/UploadedMultipartFile.java @@ -1,5 +1,5 @@ /* - * Copyright 2002-2013 the original author or authors. + * Copyright 2002-2015 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. @@ -50,7 +50,8 @@ public class UploadedMultipartFile implements MultipartFile { private final String originalFilename; - public UploadedMultipartFile(File file, long size, String contentType, String formParameterName, String originalFilename) { + public UploadedMultipartFile(File file, long size, String contentType, String formParameterName, + String originalFilename) { Assert.notNull(file, "file must not be null"); Assert.hasText(contentType, "contentType is required"); Assert.hasText(formParameterName, "formParameterName is required"); @@ -63,12 +64,13 @@ public class UploadedMultipartFile implements MultipartFile { this.originalFilename = originalFilename; } - public UploadedMultipartFile(byte[] bytes, String contentType, String formParameterName, String originalFilename) { + public UploadedMultipartFile(byte[] bytes, String contentType, String formParameterName,//NOSONAR - direct storage + String originalFilename) { Assert.notNull(bytes, "bytes must not be null"); Assert.hasText(contentType, "contentType is required"); Assert.hasText(formParameterName, "formParameterName is required"); Assert.hasText(originalFilename, "originalFilename is required"); - this.bytes = bytes; + this.bytes = bytes;//NOSONAR - direct storage this.size = bytes.length; this.file = null; this.contentType = contentType; @@ -77,21 +79,25 @@ public class UploadedMultipartFile implements MultipartFile { } + @Override public String getName() { return this.formParameterName; } + @Override public byte[] getBytes() throws IOException { if (this.bytes != null) { - return this.bytes; + return this.bytes;//NOSONAR - direct access } return FileCopyUtils.copyToByteArray(this.file); } + @Override public String getContentType() { return this.contentType; } + @Override public InputStream getInputStream() throws IOException { if (this.bytes != null) { return new ByteArrayInputStream(this.bytes); @@ -99,18 +105,22 @@ public class UploadedMultipartFile implements MultipartFile { return new BufferedInputStream(new FileInputStream(this.file)); } + @Override public String getOriginalFilename() { return this.originalFilename; } + @Override public long getSize() { return this.size; } + @Override public boolean isEmpty() { return this.size == 0; } + @Override public void transferTo(File dest) throws IOException, IllegalStateException { if (this.bytes != null) { FileCopyUtils.copy(this.bytes, dest); diff --git a/spring-integration-http/src/main/java/org/springframework/integration/http/support/DefaultHttpHeaderMapper.java b/spring-integration-http/src/main/java/org/springframework/integration/http/support/DefaultHttpHeaderMapper.java index ccef34032e..4806c3b8eb 100644 --- a/spring-integration-http/src/main/java/org/springframework/integration/http/support/DefaultHttpHeaderMapper.java +++ b/spring-integration-http/src/main/java/org/springframework/integration/http/support/DefaultHttpHeaderMapper.java @@ -293,6 +293,10 @@ public class DefaultHttpHeaderMapper implements HeaderMapper, BeanF private volatile String userDefinedHeaderPrefix = "X-"; + private volatile boolean isDefaultOutboundMapper; + + private volatile boolean isDefaultInboundMapper; + @Override public void setBeanFactory(BeanFactory beanFactory) throws BeansException { this.beanFactory = beanFactory; @@ -306,8 +310,15 @@ public class DefaultHttpHeaderMapper implements HeaderMapper, BeanF * {@link DefaultHttpHeaderMapper#setUserDefinedHeaderPrefix(String)}. The default is 'X-'. * @param outboundHeaderNames The outbound header names. */ - public void setOutboundHeaderNames(String[] outboundHeaderNames) { - this.outboundHeaderNames = (outboundHeaderNames != null) ? outboundHeaderNames : new String[0]; + public void setOutboundHeaderNames(String[] outboundHeaderNames) {//NOSONAR - false positive + if (HTTP_REQUEST_HEADER_NAMES == outboundHeaderNames) { + this.isDefaultOutboundMapper = true; + } + else if (HTTP_RESPONSE_HEADER_NAMES == outboundHeaderNames) { + this.isDefaultInboundMapper = true; + } + this.outboundHeaderNames = outboundHeaderNames != null ? + Arrays.copyOf(outboundHeaderNames, outboundHeaderNames.length) : new String[0]; this.outboundHeaderNamesLower = new String[this.outboundHeaderNames.length]; for (int i = 0; i < this.outboundHeaderNames.length; i++) { if (HTTP_REQUEST_HEADER_NAME_PATTERN.equals(this.outboundHeaderNames[i]) @@ -333,8 +344,9 @@ public class DefaultHttpHeaderMapper implements HeaderMapper, BeanF * {@link DefaultHttpHeaderMapper#setUserDefinedHeaderPrefix(String)}. The default is 'X-'. * @param inboundHeaderNames The inbound header names. */ - public void setInboundHeaderNames(String[] inboundHeaderNames) { - this.inboundHeaderNames = (inboundHeaderNames != null) ? inboundHeaderNames : new String[0]; + public void setInboundHeaderNames(String[] inboundHeaderNames) {//NOSONAR - false positive + this.inboundHeaderNames = inboundHeaderNames != null ? + Arrays.copyOf(inboundHeaderNames, inboundHeaderNames.length) : new String[0]; this.inboundHeaderNamesLower = new String[this.inboundHeaderNames.length]; for (int i = 0; i < this.inboundHeaderNames.length; i++) { if (HTTP_REQUEST_HEADER_NAME_PATTERN.equals(this.inboundHeaderNames[i]) @@ -355,7 +367,8 @@ public class DefaultHttpHeaderMapper implements HeaderMapper, BeanF public void setExcludedOutboundStandardRequestHeaderNames(String[] excludedOutboundStandardRequestHeaderNames) { Assert.notNull(excludedOutboundStandardRequestHeaderNames, "'excludedOutboundStandardRequestHeaderNames' must not be null"); - this.excludedOutboundStandardRequestHeaderNames = excludedOutboundStandardRequestHeaderNames; + this.excludedOutboundStandardRequestHeaderNames = Arrays.copyOf(excludedOutboundStandardRequestHeaderNames, + excludedOutboundStandardRequestHeaderNames.length); } /** @@ -366,7 +379,8 @@ public class DefaultHttpHeaderMapper implements HeaderMapper, BeanF public void setExcludedInboundStandardResponseHeaderNames(String[] excludedInboundStandardResponseHeaderNames) { Assert.notNull(excludedInboundStandardResponseHeaderNames, "'excludedInboundStandardResponseHeaderNames' must not be null"); - this.excludedInboundStandardResponseHeaderNames = excludedInboundStandardResponseHeaderNames; + this.excludedInboundStandardResponseHeaderNames = Arrays.copyOf(excludedInboundStandardResponseHeaderNames, + excludedInboundStandardResponseHeaderNames.length); } /** @@ -476,34 +490,34 @@ public class DefaultHttpHeaderMapper implements HeaderMapper, BeanF } private boolean shouldMapOutboundHeader(String headerName) { - String[] outboundHeaderNames = this.outboundHeaderNamesLower; + String[] outboundHeaderNamesLower = this.outboundHeaderNamesLower; - if (this.outboundHeaderNames == HTTP_RESPONSE_HEADER_NAMES) { // a default inbound mapper + if (this.isDefaultInboundMapper) { /* * When using the default response header name list, suppress the * mapping of exclusions for specific headers. */ if (this.containsElementIgnoreCase(this.excludedInboundStandardResponseHeaderNames, headerName)) { if (logger.isDebugEnabled()) { - logger.debug(MessageFormat.format("headerName=[{0}] WILL NOT be mapped", headerName)); + logger.debug(MessageFormat.format("headerName=[{0}] WILL NOT be mapped (excluded)", headerName)); } return false; } } - else if (this.outboundHeaderNames == HTTP_REQUEST_HEADER_NAMES) { // a default outbound mapper - outboundHeaderNames = this.outboundHeaderNamesLowerWithContentType; + else if (this.isDefaultOutboundMapper) { + outboundHeaderNamesLower = this.outboundHeaderNamesLowerWithContentType; /* * When using the default request header name list, suppress the * mapping of exclusions for specific headers. */ if (this.containsElementIgnoreCase(this.excludedOutboundStandardRequestHeaderNames, headerName)) { if (logger.isDebugEnabled()) { - logger.debug(MessageFormat.format("headerName=[{0}] WILL NOT be mapped", headerName)); + logger.debug(MessageFormat.format("headerName=[{0}] WILL NOT be mapped (excluded)", headerName)); } return false; } } - return this.shouldMapHeader(headerName, outboundHeaderNames); + return this.shouldMapHeader(headerName, outboundHeaderNamesLower); } private boolean shouldMapInboundHeader(String headerName) { diff --git a/spring-integration-ip/src/main/java/org/springframework/integration/ip/tcp/connection/TcpConnectionInterceptorFactoryChain.java b/spring-integration-ip/src/main/java/org/springframework/integration/ip/tcp/connection/TcpConnectionInterceptorFactoryChain.java index 9615c7e7c9..f9d7aede0a 100644 --- a/spring-integration-ip/src/main/java/org/springframework/integration/ip/tcp/connection/TcpConnectionInterceptorFactoryChain.java +++ b/spring-integration-ip/src/main/java/org/springframework/integration/ip/tcp/connection/TcpConnectionInterceptorFactoryChain.java @@ -1,5 +1,5 @@ /* - * Copyright 2002-2010 the original author or authors. + * Copyright 2002-2015 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. @@ -15,6 +15,8 @@ */ package org.springframework.integration.ip.tcp.connection; +import java.util.Arrays; + /** * @author Gary Russell * @since 2.0 @@ -25,11 +27,11 @@ public class TcpConnectionInterceptorFactoryChain { private TcpConnectionInterceptorFactory[] interceptorFactories; public TcpConnectionInterceptorFactory[] getInterceptorFactories() { - return interceptorFactories; + return interceptorFactories;//NOSONAR } public void setInterceptors(TcpConnectionInterceptorFactory[] interceptorFactories) { - this.interceptorFactories = interceptorFactories; + this.interceptorFactories = Arrays.copyOf(interceptorFactories, interceptorFactories.length); } - + } diff --git a/spring-integration-ip/src/main/java/org/springframework/integration/ip/tcp/connection/TcpNioSSLConnection.java b/spring-integration-ip/src/main/java/org/springframework/integration/ip/tcp/connection/TcpNioSSLConnection.java index 3a4bc5279e..267a0a3841 100644 --- a/spring-integration-ip/src/main/java/org/springframework/integration/ip/tcp/connection/TcpNioSSLConnection.java +++ b/spring-integration-ip/src/main/java/org/springframework/integration/ip/tcp/connection/TcpNioSSLConnection.java @@ -1,5 +1,5 @@ /* - * Copyright 2002-2014 the original author or authors. + * Copyright 2002-2015 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. @@ -159,7 +159,7 @@ public class TcpNioSSLConnection extends TcpNioConnection { } switch (result.getHandshakeStatus()) { case FINISHED: - resumeWriterIfNeeded(); + resumeWriterIfNeeded();//NOSONAR - fall-through inteded // switch fall-through intended case NOT_HANDSHAKING: case NEED_UNWRAP: diff --git a/spring-integration-ip/src/main/java/org/springframework/integration/ip/tcp/serializer/TcpDeserializationExceptionEvent.java b/spring-integration-ip/src/main/java/org/springframework/integration/ip/tcp/serializer/TcpDeserializationExceptionEvent.java index 120404f1ab..4011755d51 100644 --- a/spring-integration-ip/src/main/java/org/springframework/integration/ip/tcp/serializer/TcpDeserializationExceptionEvent.java +++ b/spring-integration-ip/src/main/java/org/springframework/integration/ip/tcp/serializer/TcpDeserializationExceptionEvent.java @@ -1,5 +1,5 @@ /* - * Copyright 2014 the original author or authors. + * Copyright 2014-2015 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. @@ -34,14 +34,15 @@ public class TcpDeserializationExceptionEvent extends IpIntegrationEvent { private final int offset; - public TcpDeserializationExceptionEvent(Object source, Throwable cause, byte[] buffer, int offset) { + public TcpDeserializationExceptionEvent(Object source, Throwable cause, byte[] buffer,//NOSONAR - direct storage + int offset) { super(source, cause); - this.buffer = buffer; + this.buffer = buffer;//NOSONAR - direct storage this.offset = offset; } public byte[] getBuffer() { - return buffer; + return buffer;//NOSONAR - direct access } public int getOffset() { diff --git a/spring-integration-ip/src/main/java/org/springframework/integration/ip/udp/UnicastSendingMessageHandler.java b/spring-integration-ip/src/main/java/org/springframework/integration/ip/udp/UnicastSendingMessageHandler.java index 8965153eca..176b624763 100644 --- a/spring-integration-ip/src/main/java/org/springframework/integration/ip/udp/UnicastSendingMessageHandler.java +++ b/spring-integration-ip/src/main/java/org/springframework/integration/ip/udp/UnicastSendingMessageHandler.java @@ -1,5 +1,5 @@ /* - * Copyright 2001-2013 the original author or authors. + * Copyright 2001-2015 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. @@ -75,8 +75,6 @@ public class UnicastSendingMessageHandler extends private volatile Map ackControl = Collections .synchronizedMap(new HashMap()); - private volatile Exception fatalException; - private volatile int soReceiveBufferSize = -1; private volatile String localAddress; @@ -224,9 +222,6 @@ public class UnicastSendingMessageHandler extends try { DatagramPacket packet; if (this.waitForAck) { - if (this.fatalException != null) { - throw new MessagingException(message, "Acknowledgment failure", fatalException); - } countdownLatch = new CountDownLatch(ackCounter); this.ackControl.put(messageId, countdownLatch); } @@ -402,10 +397,6 @@ public class UnicastSendingMessageHandler extends * (bind) error occurred, without bouncing the JVM. */ public void restartAckThread() { - if (fatalException == null) { - return; - } - this.fatalException = null; this.taskExecutor.execute(this); } diff --git a/spring-integration-jmx/src/main/java/org/springframework/integration/monitor/DirectChannelMetrics.java b/spring-integration-jmx/src/main/java/org/springframework/integration/monitor/DirectChannelMetrics.java index 3173504e26..8814ccf4f2 100644 --- a/spring-integration-jmx/src/main/java/org/springframework/integration/monitor/DirectChannelMetrics.java +++ b/spring-integration-jmx/src/main/java/org/springframework/integration/monitor/DirectChannelMetrics.java @@ -1,5 +1,5 @@ /* - * Copyright 2009-2014 the original author or authors. + * Copyright 2009-2015 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 @@ -31,6 +31,7 @@ import org.springframework.util.StopWatch; * * @author Dave Syer * @author Helena Edelson + * @author Gary Russell * @since 2.0 */ @ManagedResource @@ -45,7 +46,7 @@ public class DirectChannelMetrics implements MethodInterceptor, MessageChannelMe public static final int DEFAULT_MOVING_AVERAGE_WINDOW = 10; - private ExponentialMovingAverage sendDuration = new ExponentialMovingAverage( + private final ExponentialMovingAverage sendDuration = new ExponentialMovingAverage( DEFAULT_MOVING_AVERAGE_WINDOW); private final ExponentialMovingAverageRate sendErrorRate = new ExponentialMovingAverageRate( @@ -86,6 +87,7 @@ public class DirectChannelMetrics implements MethodInterceptor, MessageChannelMe return name; } + @Override public Object invoke(MethodInvocation invocation) throws Throwable { String method = invocation.getMethod().getName(); MessageChannel channel = (MessageChannel) invocation.getThis(); @@ -125,7 +127,7 @@ public class DirectChannelMetrics implements MethodInterceptor, MessageChannelMe } return result; } - catch (Throwable e) { + catch (Throwable e) {//NOSONAR - rethrown below sendSuccessRatio.failure(); sendErrorCount.incrementAndGet(); sendErrorRate.increment(); @@ -138,6 +140,7 @@ public class DirectChannelMetrics implements MethodInterceptor, MessageChannelMe } } + @Override public synchronized void reset() { sendDuration.reset(); sendErrorRate.reset(); @@ -147,62 +150,77 @@ public class DirectChannelMetrics implements MethodInterceptor, MessageChannelMe sendErrorCount.set(0); } + @Override public int getSendCount() { return (int) sendCount.get(); } + @Override public long getSendCountLong() { return sendCount.get(); } + @Override public int getSendErrorCount() { return (int) sendErrorCount.get(); } + @Override public long getSendErrorCountLong() { return sendErrorCount.get(); } + @Override public double getTimeSinceLastSend() { return sendRate.getTimeSinceLastMeasurement(); } + @Override public double getMeanSendRate() { return sendRate.getMean(); } + @Override public double getMeanErrorRate() { return sendErrorRate.getMean(); } + @Override public double getMeanErrorRatio() { return 1 - sendSuccessRatio.getMean(); } + @Override public double getMeanSendDuration() { return sendDuration.getMean(); } + @Override public double getMinSendDuration() { return sendDuration.getMin(); } + @Override public double getMaxSendDuration() { return sendDuration.getMax(); } + @Override public double getStandardDeviationSendDuration() { return sendDuration.getStandardDeviation(); } + @Override public Statistics getSendDuration() { return sendDuration.getStatistics(); } + @Override public Statistics getSendRate() { return sendRate.getStatistics(); } + @Override public Statistics getErrorRate() { return sendErrorRate.getStatistics(); } diff --git a/spring-integration-jmx/src/main/java/org/springframework/integration/monitor/IntegrationMBeanExporter.java b/spring-integration-jmx/src/main/java/org/springframework/integration/monitor/IntegrationMBeanExporter.java index b9770297a1..daa10545af 100644 --- a/spring-integration-jmx/src/main/java/org/springframework/integration/monitor/IntegrationMBeanExporter.java +++ b/spring-integration-jmx/src/main/java/org/springframework/integration/monitor/IntegrationMBeanExporter.java @@ -1,5 +1,5 @@ /* - * Copyright 2002-2014 the original author or authors. + * Copyright 2002-2015 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 @@ -14,6 +14,7 @@ package org.springframework.integration.monitor; import java.lang.reflect.Field; +import java.util.Arrays; import java.util.HashMap; import java.util.HashSet; import java.util.Map; @@ -210,7 +211,7 @@ public class IntegrationMBeanExporter extends MBeanExporter implements BeanPostP public void setComponentNamePatterns(String[] componentNamePatterns) { Assert.notEmpty(componentNamePatterns, "componentNamePatterns must not be empty"); - this.componentNamePatterns = componentNamePatterns; + this.componentNamePatterns = Arrays.copyOf(componentNamePatterns, componentNamePatterns.length); } @Override diff --git a/spring-integration-jmx/src/main/java/org/springframework/integration/monitor/PollableChannelMetrics.java b/spring-integration-jmx/src/main/java/org/springframework/integration/monitor/PollableChannelMetrics.java index 89b6ed8b27..71b20d327a 100644 --- a/spring-integration-jmx/src/main/java/org/springframework/integration/monitor/PollableChannelMetrics.java +++ b/spring-integration-jmx/src/main/java/org/springframework/integration/monitor/PollableChannelMetrics.java @@ -1,5 +1,5 @@ /* - * Copyright 2002-2014 the original author or authors. + * Copyright 2002-2015 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. @@ -27,6 +27,7 @@ import org.springframework.messaging.MessageChannel; /** * @author Dave Syer + * @author Gary Russell * @since 2.0 */ public class PollableChannelMetrics extends DirectChannelMetrics { @@ -59,12 +60,13 @@ public class PollableChannelMetrics extends DirectChannelMetrics { } return object; } - catch (Throwable e) { + catch (Throwable e) {//NOSONAR - rethrown below this.receiveErrorCount.incrementAndGet(); throw e; } } + @Override @ManagedOperation public synchronized void reset() { super.reset(); diff --git a/spring-integration-jmx/src/main/java/org/springframework/integration/monitor/SimpleMessageHandlerMetrics.java b/spring-integration-jmx/src/main/java/org/springframework/integration/monitor/SimpleMessageHandlerMetrics.java index fa2e674981..09be02dd13 100644 --- a/spring-integration-jmx/src/main/java/org/springframework/integration/monitor/SimpleMessageHandlerMetrics.java +++ b/spring-integration-jmx/src/main/java/org/springframework/integration/monitor/SimpleMessageHandlerMetrics.java @@ -1,5 +1,5 @@ /* - * Copyright 2002-2014 the original author or authors. + * Copyright 2002-2015 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. @@ -64,6 +64,7 @@ public class SimpleMessageHandlerMetrics implements MethodInterceptor, MessageHa this.name = name; } + @Override public String getName() { return this.name; } @@ -72,6 +73,7 @@ public class SimpleMessageHandlerMetrics implements MethodInterceptor, MessageHa this.source = source; } + @Override public String getSource() { return this.source; } @@ -80,6 +82,7 @@ public class SimpleMessageHandlerMetrics implements MethodInterceptor, MessageHa return this.handler; } + @Override public Object invoke(MethodInvocation invocation) throws Throwable { String method = invocation.getMethod().getName(); if ("handleMessage".equals(method)) { @@ -109,7 +112,7 @@ public class SimpleMessageHandlerMetrics implements MethodInterceptor, MessageHa timer.stop(); this.duration.append(timer.getTotalTimeMillis()); } - catch (Throwable e) { + catch (Throwable e) {//NOSONAR - rethrown below this.errorCount.incrementAndGet(); throw e; } @@ -118,12 +121,14 @@ public class SimpleMessageHandlerMetrics implements MethodInterceptor, MessageHa } } + @Override public synchronized void reset() { this.duration.reset(); this.errorCount.set(0); this.handleCount.set(0); } + @Override public long getHandleCountLong() { if (logger.isTraceEnabled()) { logger.trace("Getting Handle Count:" + this); @@ -131,42 +136,52 @@ public class SimpleMessageHandlerMetrics implements MethodInterceptor, MessageHa return this.handleCount.get(); } + @Override public int getHandleCount() { return (int) getHandleCountLong(); } + @Override public int getErrorCount() { return (int) this.errorCount.get(); } + @Override public long getErrorCountLong() { return this.errorCount.get(); } + @Override public double getMeanDuration() { return this.duration.getMean(); } + @Override public double getMinDuration() { return this.duration.getMin(); } + @Override public double getMaxDuration() { return this.duration.getMax(); } + @Override public double getStandardDeviationDuration() { return this.duration.getStandardDeviation(); } + @Override public int getActiveCount() { return (int) this.activeCount.get(); } + @Override public long getActiveCountLong() { return this.activeCount.get(); } + @Override public Statistics getDuration() { return this.duration.getStatistics(); } diff --git a/spring-integration-mqtt/src/main/java/org/springframework/integration/mqtt/core/DefaultMqttPahoClientFactory.java b/spring-integration-mqtt/src/main/java/org/springframework/integration/mqtt/core/DefaultMqttPahoClientFactory.java index 0a6d8e1653..40a7bff514 100644 --- a/spring-integration-mqtt/src/main/java/org/springframework/integration/mqtt/core/DefaultMqttPahoClientFactory.java +++ b/spring-integration-mqtt/src/main/java/org/springframework/integration/mqtt/core/DefaultMqttPahoClientFactory.java @@ -1,5 +1,5 @@ /* - * Copyright 2002-2014 the original author or authors. + * Copyright 2002-2015 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. @@ -15,6 +15,7 @@ */ package org.springframework.integration.mqtt.core; +import java.util.Arrays; import java.util.Properties; import javax.net.SocketFactory; @@ -104,7 +105,7 @@ public class DefaultMqttPahoClientFactory implements MqttPahoClientFactory { * @since 4.1 */ public void setServerURIs(String[] serverURIs) { - this.serverURIs = serverURIs; + this.serverURIs = Arrays.copyOf(serverURIs, serverURIs.length); } @Override @@ -162,9 +163,9 @@ public class DefaultMqttPahoClientFactory implements MqttPahoClientFactory { private final boolean retained; - public Will(String topic, byte[] payload, int qos, boolean retained) { + public Will(String topic, byte[] payload, int qos, boolean retained) {//NOSONAR this.topic = topic; - this.payload = payload; + this.payload = payload;//NOSONAR this.qos = qos; this.retained = retained; } @@ -174,7 +175,7 @@ public class DefaultMqttPahoClientFactory implements MqttPahoClientFactory { } protected byte[] getPayload() { - return payload; + return payload;//NOSONAR } protected int getQos() { diff --git a/spring-integration-websocket/src/main/java/org/springframework/integration/websocket/IntegrationWebSocketContainer.java b/spring-integration-websocket/src/main/java/org/springframework/integration/websocket/IntegrationWebSocketContainer.java index 734d7efb36..8e392628cf 100644 --- a/spring-integration-websocket/src/main/java/org/springframework/integration/websocket/IntegrationWebSocketContainer.java +++ b/spring-integration-websocket/src/main/java/org/springframework/integration/websocket/IntegrationWebSocketContainer.java @@ -123,16 +123,20 @@ public abstract class IntegrationWebSocketContainer implements DisposableBean { @Override public void destroy() throws Exception { - // Notify sessions to stop flushing messages - for (WebSocketSession session : this.sessions.values()) { - try { - session.close(CloseStatus.GOING_AWAY); - } - catch (Throwable t) { - logger.error("Failed to close session id '" + session.getId() + "': " + t.getMessage()); + try { + // Notify sessions to stop flushing messages + for (WebSocketSession session : this.sessions.values()) { + try { + session.close(CloseStatus.GOING_AWAY); + } + catch (Exception e) { + logger.error("Failed to close session id '" + session.getId() + "': " + e.getMessage()); + } } } - this.sessions.clear(); + finally { + this.sessions.clear(); + } } /** diff --git a/spring-integration-websocket/src/main/java/org/springframework/integration/websocket/ServerWebSocketContainer.java b/spring-integration-websocket/src/main/java/org/springframework/integration/websocket/ServerWebSocketContainer.java index 23a2d0f357..464e01b80d 100644 --- a/spring-integration-websocket/src/main/java/org/springframework/integration/websocket/ServerWebSocketContainer.java +++ b/spring-integration-websocket/src/main/java/org/springframework/integration/websocket/ServerWebSocketContainer.java @@ -1,5 +1,22 @@ +/* + * Copyright 2014-2015 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.websocket; +import java.util.Arrays; + import org.springframework.scheduling.TaskScheduler; import org.springframework.util.Assert; import org.springframework.util.ObjectUtils; @@ -23,6 +40,7 @@ import org.springframework.web.socket.sockjs.transport.TransportHandler; * implementation of this class. * * @author Artem Bilan + * @author Gary Russell * @since 4.1 */ public class ServerWebSocketContainer extends IntegrationWebSocketContainer implements WebSocketConfigurer { @@ -45,7 +63,7 @@ public class ServerWebSocketContainer extends IntegrationWebSocketContainer impl } public ServerWebSocketContainer setInterceptors(HandshakeInterceptor[] interceptors) { - this.interceptors = interceptors; + this.interceptors = Arrays.copyOf(interceptors, interceptors.length); return this; } diff --git a/spring-integration-xml/src/main/java/org/springframework/integration/xml/transformer/XsltPayloadTransformer.java b/spring-integration-xml/src/main/java/org/springframework/integration/xml/transformer/XsltPayloadTransformer.java index f4d85bf06a..1b0be4c05c 100644 --- a/spring-integration-xml/src/main/java/org/springframework/integration/xml/transformer/XsltPayloadTransformer.java +++ b/spring-integration-xml/src/main/java/org/springframework/integration/xml/transformer/XsltPayloadTransformer.java @@ -17,6 +17,7 @@ package org.springframework.integration.xml.transformer; import java.io.IOException; +import java.util.Arrays; import java.util.Map; import java.util.Map.Entry; @@ -181,7 +182,7 @@ public class XsltPayloadTransformer extends AbstractXmlTransformer implements Be } public void setXsltParamHeaders(String[] xsltParamHeaders) { - this.xsltParamHeaders = xsltParamHeaders; + this.xsltParamHeaders = Arrays.copyOf(xsltParamHeaders, xsltParamHeaders.length); } @Override