in qpid-jms-client/src/main/java/org/apache/qpid/jms/JmsSession.java [330:409]
protected boolean shutdown(Throwable cause) throws JMSException {
boolean listenerPresent = false;
if (closed.compareAndSet(false, true)) {
JMSException shutdownError = null;
try {
sessionInfo.setState(ResourceState.CLOSED);
setFailureCause(cause);
try {
stop();
for (JmsMessageConsumer consumer : new ArrayList<JmsMessageConsumer>(this.consumers.values())) {
if (consumer.hasMessageListener()) {
listenerPresent = true;
}
consumer.shutdown(cause);
}
for (JmsMessageProducer producer : new ArrayList<JmsMessageProducer>(this.producers.values())) {
producer.shutdown(cause);
}
} catch (JMSException jmsEx) {
shutdownError = jmsEx;
}
boolean inDoubt = transactionContext.isInDoubt();
try {
transactionContext.shutdown();
} catch (JMSException jmsEx) {
if (!inDoubt) {
LOG.warn("Rollback of active transaction failed due to error: ", jmsEx);
shutdownError = shutdownError == null ? jmsEx : shutdownError;
} else {
LOG.trace("Rollback of indoubt transaction failed due to error: ", jmsEx);
}
}
// Ensure that no asynchronous completion sends remain blocked after close.
synchronized (sessionInfo) {
if (cause == null) {
cause = new JMSException("Session closed remotely before message transfer result was notified");
}
getCompletionExecutor().execute(new FailOrCompleteAsyncCompletionsTask(JmsExceptionSupport.create(cause)));
getCompletionExecutor().shutdown();
}
try {
getCompletionExecutor().awaitTermination(connection.getCloseTimeout(), TimeUnit.MILLISECONDS);
} catch (InterruptedException e) {
LOG.trace("Session close awaiting send completions was interrupted");
}
try {
if (getSessionMode() == Session.CLIENT_ACKNOWLEDGE) {
acknowledge(ACK_TYPE.SESSION_SHUTDOWN);
}
} catch (Exception e) {
LOG.trace("Exception during session shutdown cleanup acknowledgement", e);
}
if (shutdownError != null) {
throw shutdownError;
}
} catch (Throwable e) {
if (shutdownError != null) {
throw shutdownError;
} else {
throw JmsExceptionSupport.create(e);
}
} finally {
connection.removeSession(sessionInfo);
}
}
return listenerPresent;
}