This closes #1832
This commit is contained in:
commit
4883b0360e
|
@ -0,0 +1,98 @@
|
|||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership.
|
||||
* The ASF licenses this file to You 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
|
||||
* <p>
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
* <p>
|
||||
* 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.apache.activemq.artemis.api.core;
|
||||
|
||||
import static org.apache.activemq.artemis.utils.uri.URISupport.appendParameters;
|
||||
import static org.apache.activemq.artemis.utils.uri.URISupport.parseQuery;
|
||||
|
||||
import java.net.URISyntaxException;
|
||||
import java.util.Map;
|
||||
|
||||
import org.apache.activemq.artemis.utils.uri.URISupport;
|
||||
|
||||
public class ParameterisedAddress {
|
||||
|
||||
public static SimpleString toParameterisedAddress(SimpleString address, Map<String, String> parameters) throws URISyntaxException {
|
||||
if (parameters != null && !parameters.isEmpty()) {
|
||||
return SimpleString.toSimpleString(toParameterisedAddress(address.toString(), parameters));
|
||||
} else {
|
||||
return address;
|
||||
}
|
||||
}
|
||||
|
||||
public static String toParameterisedAddress(String address, Map<String, String> parameters) throws URISyntaxException {
|
||||
if (parameters != null && !parameters.isEmpty()) {
|
||||
return appendParameters(new StringBuilder(address), parameters).toString();
|
||||
} else {
|
||||
return address;
|
||||
}
|
||||
}
|
||||
|
||||
private final SimpleString address;
|
||||
private final QueueAttributes queueAttributes;
|
||||
|
||||
public SimpleString getAddress() {
|
||||
return address;
|
||||
}
|
||||
|
||||
public QueueAttributes getQueueAttributes() {
|
||||
return queueAttributes;
|
||||
}
|
||||
|
||||
public ParameterisedAddress(SimpleString address, QueueAttributes queueAttributes) {
|
||||
this.address = address;
|
||||
this.queueAttributes = queueAttributes;
|
||||
}
|
||||
|
||||
public ParameterisedAddress(String address, QueueAttributes queueAttributes) {
|
||||
this(SimpleString.toSimpleString(address), queueAttributes);
|
||||
}
|
||||
|
||||
public ParameterisedAddress(SimpleString address) {
|
||||
this(address.toString());
|
||||
}
|
||||
|
||||
public ParameterisedAddress(String address) {
|
||||
int index = address.indexOf('?');
|
||||
if (index == -1) {
|
||||
this.address = SimpleString.toSimpleString(address);
|
||||
this.queueAttributes = null;
|
||||
} else {
|
||||
this.address = SimpleString.toSimpleString(address.substring(0, index));
|
||||
QueueAttributes queueAttributes = new QueueAttributes();
|
||||
try {
|
||||
parseQuery(address).forEach(queueAttributes::set);
|
||||
} catch (URISyntaxException use) {
|
||||
throw new IllegalArgumentException("Malformed parameters in address " + address);
|
||||
}
|
||||
this.queueAttributes = queueAttributes;
|
||||
}
|
||||
}
|
||||
|
||||
public boolean isParameterised() {
|
||||
return this.queueAttributes != null;
|
||||
}
|
||||
|
||||
public static boolean isParameterised(String address) {
|
||||
return URISupport.containsQuery(address);
|
||||
}
|
||||
|
||||
public static boolean isParameterised(SimpleString address) {
|
||||
return URISupport.containsQuery(address);
|
||||
}
|
||||
|
||||
}
|
|
@ -0,0 +1,79 @@
|
|||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership.
|
||||
* The ASF licenses this file to You 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
|
||||
* <p>
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
* <p>
|
||||
* 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.apache.activemq.artemis.api.core;
|
||||
|
||||
import java.io.Serializable;
|
||||
|
||||
public class QueueAttributes implements Serializable {
|
||||
|
||||
public static final String MAX_CONSUMERS = "max-consumers";
|
||||
public static final String EXCLUSIVE = "exclusive";
|
||||
public static final String LAST_VALUE = "last-value";
|
||||
public static final String PURGE_ON_NO_CONSUMERS = "purge-on-no-consumers";
|
||||
|
||||
private Integer maxConsumers;
|
||||
private Boolean exclusive;
|
||||
private Boolean lastValue;
|
||||
private Boolean purgeOnNoConsumers;
|
||||
|
||||
public void set(String key, String value) {
|
||||
if (key != null && value != null) {
|
||||
if (key.equals(MAX_CONSUMERS)) {
|
||||
setMaxConsumers(Integer.valueOf(value));
|
||||
} else if (key.equals(EXCLUSIVE)) {
|
||||
setExclusive(Boolean.valueOf(value));
|
||||
} else if (key.equals(LAST_VALUE)) {
|
||||
setLastValue(Boolean.valueOf(value));
|
||||
} else if (key.equals(PURGE_ON_NO_CONSUMERS)) {
|
||||
setPurgeOnNoConsumers(Boolean.valueOf(value));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public Integer getMaxConsumers() {
|
||||
return maxConsumers;
|
||||
}
|
||||
|
||||
public void setMaxConsumers(Integer maxConsumers) {
|
||||
this.maxConsumers = maxConsumers;
|
||||
}
|
||||
|
||||
public Boolean getExclusive() {
|
||||
return exclusive;
|
||||
}
|
||||
|
||||
public void setExclusive(Boolean exclusive) {
|
||||
this.exclusive = exclusive;
|
||||
}
|
||||
|
||||
public Boolean getLastValue() {
|
||||
return lastValue;
|
||||
}
|
||||
|
||||
public void setLastValue(Boolean lastValue) {
|
||||
this.lastValue = lastValue;
|
||||
}
|
||||
|
||||
public Boolean getPurgeOnNoConsumers() {
|
||||
return purgeOnNoConsumers;
|
||||
}
|
||||
|
||||
public void setPurgeOnNoConsumers(Boolean purgeOnNoConsumers) {
|
||||
this.purgeOnNoConsumers = purgeOnNoConsumers;
|
||||
}
|
||||
}
|
|
@ -27,6 +27,8 @@ import java.util.HashMap;
|
|||
import java.util.List;
|
||||
import java.util.Map;
|
||||
|
||||
import org.apache.activemq.artemis.api.core.SimpleString;
|
||||
|
||||
/**
|
||||
* Utility class that provides methods for parsing URI's
|
||||
*
|
||||
|
@ -75,7 +77,7 @@ public class URISupport {
|
|||
}
|
||||
|
||||
public URI toURI() throws URISyntaxException {
|
||||
StringBuffer sb = new StringBuffer();
|
||||
StringBuilder sb = new StringBuilder();
|
||||
if (scheme != null) {
|
||||
sb.append(scheme);
|
||||
sb.append(':');
|
||||
|
@ -98,18 +100,23 @@ public class URISupport {
|
|||
sb.append('/');
|
||||
sb.append(path);
|
||||
}
|
||||
if (!parameters.isEmpty()) {
|
||||
sb.append("?");
|
||||
sb.append(createQueryString(parameters));
|
||||
}
|
||||
appendParameters(sb, parameters);
|
||||
if (fragment != null) {
|
||||
sb.append("#");
|
||||
sb.append('#');
|
||||
sb.append(fragment);
|
||||
}
|
||||
return new URI(sb.toString());
|
||||
}
|
||||
}
|
||||
|
||||
public static StringBuilder appendParameters(StringBuilder sb, Map<String, String> parameters) throws URISyntaxException {
|
||||
if (!parameters.isEmpty()) {
|
||||
sb.append('?');
|
||||
sb.append(createQueryString(parameters));
|
||||
}
|
||||
return sb;
|
||||
}
|
||||
|
||||
/**
|
||||
* Give a URI break off any URI options and store them in a Key / Value Mapping.
|
||||
*
|
||||
|
@ -122,8 +129,7 @@ public class URISupport {
|
|||
uri = uri.substring(uri.lastIndexOf("?") + 1); // get only the relevant part of the query
|
||||
Map<String, String> rc = new HashMap<>();
|
||||
if (uri != null && !uri.isEmpty()) {
|
||||
parseParameters(rc, uri.split("&"));
|
||||
parseParameters(rc, uri.split(";"));
|
||||
parseParameters(rc, uri.split("[&;]"));
|
||||
}
|
||||
return rc;
|
||||
} catch (UnsupportedEncodingException e) {
|
||||
|
@ -131,6 +137,14 @@ public class URISupport {
|
|||
}
|
||||
}
|
||||
|
||||
public static boolean containsQuery(String uri) {
|
||||
return uri.contains("?");
|
||||
}
|
||||
|
||||
public static boolean containsQuery(SimpleString uri) {
|
||||
return uri.contains('?');
|
||||
}
|
||||
|
||||
private static void parseParameters(Map<String, String> rc,
|
||||
String[] parameters) throws UnsupportedEncodingException {
|
||||
for (String parameter : parameters) {
|
||||
|
@ -198,7 +212,7 @@ public class URISupport {
|
|||
Map<String, String> queryParameters,
|
||||
String optionPrefix) throws URISyntaxException {
|
||||
if (queryParameters != null && !queryParameters.isEmpty()) {
|
||||
StringBuffer newQuery = uri.getRawQuery() != null ? new StringBuffer(uri.getRawQuery()) : new StringBuffer();
|
||||
StringBuilder newQuery = uri.getRawQuery() != null ? new StringBuilder(uri.getRawQuery()) : new StringBuilder();
|
||||
for (Map.Entry<String, String> param : queryParameters.entrySet()) {
|
||||
if (param.getKey().startsWith(optionPrefix)) {
|
||||
if (newQuery.length() != 0) {
|
||||
|
|
|
@ -465,6 +465,10 @@ public final class ActiveMQDefaultConfiguration {
|
|||
|
||||
public static final int DEFAULT_MAX_QUEUE_CONSUMERS = -1;
|
||||
|
||||
public static final boolean DEFAULT_EXCLUSIVE = false;
|
||||
|
||||
public static final boolean DEFAULT_LAST_VALUE = false;
|
||||
|
||||
public static final boolean DEFAULT_PURGE_ON_NO_CONSUMERS = false;
|
||||
|
||||
public static final RoutingType DEFAULT_ROUTING_TYPE = RoutingType.MULTICAST;
|
||||
|
@ -1277,6 +1281,14 @@ public final class ActiveMQDefaultConfiguration {
|
|||
return DEFAULT_MAX_QUEUE_CONSUMERS;
|
||||
}
|
||||
|
||||
public static boolean getDefaultExclusive() {
|
||||
return DEFAULT_EXCLUSIVE;
|
||||
}
|
||||
|
||||
public static boolean getDefaultLastValue() {
|
||||
return DEFAULT_EXCLUSIVE;
|
||||
}
|
||||
|
||||
public static boolean getDefaultPurgeOnNoConsumers() {
|
||||
return DEFAULT_PURGE_ON_NO_CONSUMERS;
|
||||
}
|
||||
|
|
|
@ -75,6 +75,10 @@ public interface ClientSession extends XAResource, AutoCloseable {
|
|||
boolean isDefaultPurgeOnNoConsumers();
|
||||
|
||||
int getDefaultMaxConsumers();
|
||||
|
||||
Boolean isDefaultLastValueQueue();
|
||||
|
||||
Boolean isDefaultExclusive();
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -139,6 +143,10 @@ public interface ClientSession extends XAResource, AutoCloseable {
|
|||
boolean isPurgeOnNoConsumers();
|
||||
|
||||
boolean isAutoCreated();
|
||||
|
||||
Boolean isExclusive();
|
||||
|
||||
Boolean isLastValue();
|
||||
}
|
||||
|
||||
// Lifecycle operations ------------------------------------------
|
||||
|
@ -454,6 +462,23 @@ public interface ClientSession extends XAResource, AutoCloseable {
|
|||
void createSharedQueue(SimpleString address, RoutingType routingType, SimpleString queueName, SimpleString filter,
|
||||
boolean durable) throws ActiveMQException;
|
||||
|
||||
/**
|
||||
* Creates Shared queue. A queue that will exist as long as there are consumers or is durable.
|
||||
*
|
||||
* @param address the queue will be bound to this address
|
||||
* @param routingType the delivery mode for this queue, MULTICAST or ANYCAST
|
||||
* @param queueName the name of the queue
|
||||
* @param filter whether the queue is durable or not
|
||||
* @param durable if the queue is durable
|
||||
* @param maxConsumers how many concurrent consumers will be allowed on this queue
|
||||
* @param purgeOnNoConsumers whether to delete the contents of the queue when the last consumer disconnects
|
||||
* @param exclusive if the queue is exclusive queue
|
||||
* @param lastValue if the queue is last value queue
|
||||
* @throws ActiveMQException in an exception occurs while creating the queue
|
||||
*/
|
||||
void createSharedQueue(SimpleString address, RoutingType routingType, SimpleString queueName, SimpleString filter,
|
||||
boolean durable, Integer maxConsumers, Boolean purgeOnNoConsumers, Boolean exclusive, Boolean lastValue) throws ActiveMQException;
|
||||
|
||||
/**
|
||||
* Creates a <em>non-temporary</em> queue.
|
||||
*
|
||||
|
@ -540,6 +565,24 @@ public interface ClientSession extends XAResource, AutoCloseable {
|
|||
void createQueue(SimpleString address, RoutingType routingType, SimpleString queueName, SimpleString filter,
|
||||
boolean durable, boolean autoCreated, int maxConsumers, boolean purgeOnNoConsumers) throws ActiveMQException;
|
||||
|
||||
/**
|
||||
* Creates a <em>non-temporary</em> queue.
|
||||
*
|
||||
* @param address the queue will be bound to this address
|
||||
* @param routingType the delivery mode for this queue, MULTICAST or ANYCAST
|
||||
* @param queueName the name of the queue
|
||||
* @param filter only messages which match this filter will be put in the queue
|
||||
* @param durable whether the queue is durable or not
|
||||
* @param autoCreated whether to mark this queue as autoCreated or not
|
||||
* @param maxConsumers how many concurrent consumers will be allowed on this queue
|
||||
* @param purgeOnNoConsumers whether to delete the contents of the queue when the last consumer disconnects
|
||||
* @param exclusive whether the queue should be exclusive
|
||||
* @param lastValue whether the queue should be lastValue
|
||||
* @throws ActiveMQException
|
||||
*/
|
||||
void createQueue(SimpleString address, RoutingType routingType, SimpleString queueName, SimpleString filter,
|
||||
boolean durable, boolean autoCreated, int maxConsumers, boolean purgeOnNoConsumers, Boolean exclusive, Boolean lastValue) throws ActiveMQException;
|
||||
|
||||
/**
|
||||
* Creates a <em>non-temporary</em>queue.
|
||||
*
|
||||
|
@ -569,6 +612,24 @@ public interface ClientSession extends XAResource, AutoCloseable {
|
|||
void createQueue(String address, RoutingType routingType, String queueName, String filter, boolean durable, boolean autoCreated,
|
||||
int maxConsumers, boolean purgeOnNoConsumers) throws ActiveMQException;
|
||||
|
||||
/**
|
||||
* Creates a <em>non-temporary</em>queue.
|
||||
*
|
||||
* @param address the queue will be bound to this address
|
||||
* @param routingType the delivery mode for this queue, MULTICAST or ANYCAST
|
||||
* @param queueName the name of the queue
|
||||
* @param filter only messages which match this filter will be put in the queue
|
||||
* @param durable whether the queue is durable or not
|
||||
* @param autoCreated whether to mark this queue as autoCreated or not
|
||||
* @param maxConsumers how many concurrent consumers will be allowed on this queue
|
||||
* @param purgeOnNoConsumers whether to delete the contents of the queue when the last consumer disconnects
|
||||
* @param exclusive whether the queue should be exclusive
|
||||
* @param lastValue whether the queue should be lastValue
|
||||
* @throws ActiveMQException
|
||||
*/
|
||||
void createQueue(String address, RoutingType routingType, String queueName, String filter, boolean durable, boolean autoCreated,
|
||||
int maxConsumers, boolean purgeOnNoConsumers, Boolean exclusive, Boolean lastValue) throws ActiveMQException;
|
||||
|
||||
/**
|
||||
* Creates a <em>temporary</em> queue.
|
||||
*
|
||||
|
@ -589,6 +650,22 @@ public interface ClientSession extends XAResource, AutoCloseable {
|
|||
*/
|
||||
void createTemporaryQueue(String address, RoutingType routingType, String queueName) throws ActiveMQException;
|
||||
|
||||
/**
|
||||
* Creates a <em>temporary</em> queue with a filter.
|
||||
*
|
||||
* @param address the queue will be bound to this address
|
||||
* @param routingType the delivery mode for this queue, MULTICAST or ANYCAST
|
||||
* @param queueName the name of the queue
|
||||
* @param filter only messages which match this filter will be put in the queue
|
||||
* @param maxConsumers how many concurrent consumers will be allowed on this queue
|
||||
* @param purgeOnNoConsumers whether to delete the contents of the queue when the last consumer disconnects
|
||||
* @param exclusive if the queue is exclusive queue
|
||||
* @param lastValue if the queue is last value queue
|
||||
* @throws ActiveMQException in an exception occurs while creating the queue
|
||||
*/
|
||||
void createTemporaryQueue(SimpleString address, RoutingType routingType, SimpleString queueName, SimpleString filter, int maxConsumers,
|
||||
boolean purgeOnNoConsumers, Boolean exclusive, Boolean lastValue) throws ActiveMQException;
|
||||
|
||||
/**
|
||||
* Creates a <em>temporary</em> queue with a filter.
|
||||
*
|
||||
|
|
|
@ -617,6 +617,22 @@ public interface ActiveMQServerControl {
|
|||
@Parameter(name = "purgeOnNoConsumers", desc = "Delete this queue when the last consumer disconnects") Boolean purgeOnNoConsumers) throws Exception;
|
||||
|
||||
|
||||
/**
|
||||
* Update a queue.
|
||||
*
|
||||
* @param name name of the queue
|
||||
* @param routingType the routing type used for this address, {@code MULTICAST} or {@code ANYCAST}
|
||||
* @param maxConsumers the maximum number of consumers allowed on this queue at any one time
|
||||
* @param purgeOnNoConsumers delete this queue when the last consumer disconnects
|
||||
* @return a textual summary of the queue
|
||||
* @throws Exception
|
||||
*/
|
||||
String updateQueue(@Parameter(name = "name", desc = "Name of the queue") String name,
|
||||
@Parameter(name = "routingType", desc = "The routing type used for this address, MULTICAST or ANYCAST") String routingType,
|
||||
@Parameter(name = "maxConsumers", desc = "The maximum number of consumers allowed on this queue at any one time") Integer maxConsumers,
|
||||
@Parameter(name = "purgeOnNoConsumers", desc = "Delete this queue when the last consumer disconnects") Boolean purgeOnNoConsumers,
|
||||
@Parameter(name = "exclusive", desc = "If the queue should route exclusively to one consumer") Boolean exclusive) throws Exception;
|
||||
|
||||
|
||||
/**
|
||||
* Deploy a durable queue.
|
||||
|
|
|
@ -164,6 +164,18 @@ public interface QueueControl {
|
|||
@Attribute(desc = "delete this queue when the last consumer disconnects")
|
||||
boolean isPurgeOnNoConsumers();
|
||||
|
||||
/**
|
||||
*
|
||||
*/
|
||||
@Attribute(desc = "If the queue should route exclusively to one consumer")
|
||||
boolean isExclusive();
|
||||
|
||||
/**
|
||||
*
|
||||
*/
|
||||
@Attribute(desc = "is this queue a last value queue")
|
||||
boolean isLastValue();
|
||||
|
||||
// Operations ----------------------------------------------------
|
||||
|
||||
/**
|
||||
|
|
|
@ -36,18 +36,26 @@ public class AddressQueryImpl implements ClientSession.AddressQuery {
|
|||
|
||||
private final int defaultMaxConsumers;
|
||||
|
||||
private final Boolean defaultExclusive;
|
||||
|
||||
private final Boolean defaultLastValue;
|
||||
|
||||
public AddressQueryImpl(final boolean exists,
|
||||
final List<SimpleString> queueNames,
|
||||
final boolean autoCreateQueues,
|
||||
final boolean autoCreateAddresses,
|
||||
final boolean defaultPurgeOnNoConsumers,
|
||||
final int defaultMaxConsumers) {
|
||||
final int defaultMaxConsumers,
|
||||
final Boolean defaultExclusive,
|
||||
final Boolean defaultLastValue) {
|
||||
this.exists = exists;
|
||||
this.queueNames = new ArrayList<>(queueNames);
|
||||
this.autoCreateQueues = autoCreateQueues;
|
||||
this.autoCreateAddresses = autoCreateAddresses;
|
||||
this.defaultPurgeOnNoConsumers = defaultPurgeOnNoConsumers;
|
||||
this.defaultMaxConsumers = defaultMaxConsumers;
|
||||
this.defaultExclusive = defaultExclusive;
|
||||
this.defaultLastValue = defaultLastValue;
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -79,4 +87,14 @@ public class AddressQueryImpl implements ClientSession.AddressQuery {
|
|||
public int getDefaultMaxConsumers() {
|
||||
return defaultMaxConsumers;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Boolean isDefaultLastValueQueue() {
|
||||
return defaultLastValue;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Boolean isDefaultExclusive() {
|
||||
return defaultExclusive;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -376,7 +376,7 @@ public final class ClientSessionImpl implements ClientSessionInternal, FailureLi
|
|||
false,
|
||||
ActiveMQDefaultConfiguration.getDefaultMaxQueueConsumers(),
|
||||
ActiveMQDefaultConfiguration.getDefaultPurgeOnNoConsumers(),
|
||||
autoCreated);
|
||||
autoCreated, null, null);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -400,12 +400,42 @@ public final class ClientSessionImpl implements ClientSessionInternal, FailureLi
|
|||
false,
|
||||
maxConsumers,
|
||||
purgeOnNoConsumers,
|
||||
autoCreated);
|
||||
autoCreated, null, null);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void createQueue(final SimpleString address, final RoutingType routingType, final SimpleString queueName, final SimpleString filterString,
|
||||
final boolean durable, final boolean autoCreated, final int maxConsumers, final boolean purgeOnNoConsumers, final Boolean exclusive, final Boolean lastValue) throws ActiveMQException {
|
||||
internalCreateQueue(address,
|
||||
queueName, routingType,
|
||||
filterString,
|
||||
durable,
|
||||
false,
|
||||
maxConsumers,
|
||||
purgeOnNoConsumers,
|
||||
autoCreated,
|
||||
exclusive,
|
||||
lastValue);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void createQueue(final String address, final RoutingType routingType, final String queueName, final String filterString,
|
||||
final boolean durable, final boolean autoCreated, final int maxConsumers, final boolean purgeOnNoConsumers) throws ActiveMQException {
|
||||
createQueue(address,
|
||||
routingType,
|
||||
queueName,
|
||||
filterString,
|
||||
durable,
|
||||
autoCreated,
|
||||
maxConsumers,
|
||||
purgeOnNoConsumers,
|
||||
null,
|
||||
null);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void createQueue(final String address, final RoutingType routingType, final String queueName, final String filterString,
|
||||
final boolean durable, final boolean autoCreated, final int maxConsumers, final boolean purgeOnNoConsumers, Boolean exclusive, Boolean lastValue) throws ActiveMQException {
|
||||
createQueue(SimpleString.toSimpleString(address),
|
||||
routingType,
|
||||
SimpleString.toSimpleString(queueName),
|
||||
|
@ -413,7 +443,9 @@ public final class ClientSessionImpl implements ClientSessionInternal, FailureLi
|
|||
durable,
|
||||
autoCreated,
|
||||
maxConsumers,
|
||||
purgeOnNoConsumers);
|
||||
purgeOnNoConsumers,
|
||||
exclusive,
|
||||
lastValue);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -432,15 +464,27 @@ public final class ClientSessionImpl implements ClientSessionInternal, FailureLi
|
|||
public void createTemporaryQueue(final SimpleString address,
|
||||
final RoutingType routingType,
|
||||
final SimpleString queueName,
|
||||
final SimpleString filter) throws ActiveMQException {
|
||||
final SimpleString filter,
|
||||
final int maxConsumers,
|
||||
final boolean purgeOnNoConsumers,
|
||||
final Boolean exclusive,
|
||||
final Boolean lastValue) throws ActiveMQException {
|
||||
internalCreateQueue(address,
|
||||
queueName, routingType,
|
||||
filter,
|
||||
false,
|
||||
true,
|
||||
ActiveMQDefaultConfiguration.getDefaultMaxQueueConsumers(),
|
||||
ActiveMQDefaultConfiguration.getDefaultPurgeOnNoConsumers(),
|
||||
false);
|
||||
maxConsumers,
|
||||
purgeOnNoConsumers,
|
||||
false, exclusive, lastValue);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void createTemporaryQueue(final SimpleString address,
|
||||
final RoutingType routingType,
|
||||
final SimpleString queueName,
|
||||
final SimpleString filter) throws ActiveMQException {
|
||||
createTemporaryQueue(address, routingType, queueName, filter, ActiveMQDefaultConfiguration.getDefaultMaxQueueConsumers(), ActiveMQDefaultConfiguration.getDefaultPurgeOnNoConsumers(), null, null);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -466,7 +510,7 @@ public final class ClientSessionImpl implements ClientSessionInternal, FailureLi
|
|||
false,
|
||||
ActiveMQDefaultConfiguration.getDefaultMaxQueueConsumers(),
|
||||
ActiveMQDefaultConfiguration.getDefaultPurgeOnNoConsumers(),
|
||||
false);
|
||||
false, null, null);
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -500,11 +544,31 @@ public final class ClientSessionImpl implements ClientSessionInternal, FailureLi
|
|||
@Override
|
||||
public void createSharedQueue(SimpleString address, RoutingType routingType, SimpleString queueName, SimpleString filter,
|
||||
boolean durable) throws ActiveMQException {
|
||||
createSharedQueue(address, routingType, queueName, filter, durable, null, null, null, null);
|
||||
}
|
||||
|
||||
/**
|
||||
* Creates Shared queue. A queue that will exist as long as there are consumers or is durable.
|
||||
*
|
||||
* @param address the queue will be bound to this address
|
||||
* @param routingType the delivery mode for this queue, MULTICAST or ANYCAST
|
||||
* @param queueName the name of the queue
|
||||
* @param filter whether the queue is durable or not
|
||||
* @param durable if the queue is durable
|
||||
* @param maxConsumers how many concurrent consumers will be allowed on this queue
|
||||
* @param purgeOnNoConsumers whether to delete the contents of the queue when the last consumer disconnects
|
||||
* @param exclusive if the queue is exclusive queue
|
||||
* @param lastValue if the queue is last value queue
|
||||
* @throws ActiveMQException in an exception occurs while creating the queue
|
||||
*/
|
||||
@Override
|
||||
public void createSharedQueue(SimpleString address, RoutingType routingType, SimpleString queueName, SimpleString filter,
|
||||
boolean durable, Integer maxConsumers, Boolean purgeOnNoConsumers, Boolean exclusive, Boolean lastValue) throws ActiveMQException {
|
||||
checkClosed();
|
||||
|
||||
startCall();
|
||||
try {
|
||||
sessionContext.createSharedQueue(address, queueName, routingType, filter, durable);
|
||||
sessionContext.createSharedQueue(address, queueName, routingType, filter, durable, maxConsumers, purgeOnNoConsumers, exclusive, lastValue);
|
||||
} finally {
|
||||
endCall();
|
||||
}
|
||||
|
@ -541,7 +605,7 @@ public final class ClientSessionImpl implements ClientSessionInternal, FailureLi
|
|||
false,
|
||||
ActiveMQDefaultConfiguration.getDefaultMaxQueueConsumers(),
|
||||
ActiveMQDefaultConfiguration.getDefaultPurgeOnNoConsumers(),
|
||||
false);
|
||||
false, null, null);
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -562,7 +626,7 @@ public final class ClientSessionImpl implements ClientSessionInternal, FailureLi
|
|||
false,
|
||||
ActiveMQDefaultConfiguration.getDefaultMaxQueueConsumers(),
|
||||
ActiveMQDefaultConfiguration.getDefaultPurgeOnNoConsumers(),
|
||||
false);
|
||||
false, null, null);
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -586,7 +650,7 @@ public final class ClientSessionImpl implements ClientSessionInternal, FailureLi
|
|||
false,
|
||||
ActiveMQDefaultConfiguration.getDefaultMaxQueueConsumers(),
|
||||
ActiveMQDefaultConfiguration.getDefaultPurgeOnNoConsumers(),
|
||||
false);
|
||||
false, null, null);
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -1847,7 +1911,9 @@ public final class ClientSessionImpl implements ClientSessionInternal, FailureLi
|
|||
final boolean temp,
|
||||
final int maxConsumers,
|
||||
final boolean purgeOnNoConsumers,
|
||||
final boolean autoCreated) throws ActiveMQException {
|
||||
final boolean autoCreated,
|
||||
final Boolean exclusive,
|
||||
final Boolean lastValue) throws ActiveMQException {
|
||||
checkClosed();
|
||||
|
||||
if (durable && temp) {
|
||||
|
@ -1864,7 +1930,9 @@ public final class ClientSessionImpl implements ClientSessionInternal, FailureLi
|
|||
temp,
|
||||
maxConsumers,
|
||||
purgeOnNoConsumers,
|
||||
autoCreated);
|
||||
autoCreated,
|
||||
exclusive,
|
||||
lastValue);
|
||||
} finally {
|
||||
endCall();
|
||||
}
|
||||
|
|
|
@ -48,6 +48,10 @@ public class QueueQueryImpl implements ClientSession.QueueQuery {
|
|||
|
||||
private final int maxConsumers;
|
||||
|
||||
private final Boolean exclusive;
|
||||
|
||||
private final Boolean lastValue;
|
||||
|
||||
public QueueQueryImpl(final boolean durable,
|
||||
final boolean temporary,
|
||||
final int consumerCount,
|
||||
|
@ -84,6 +88,23 @@ public class QueueQueryImpl implements ClientSession.QueueQuery {
|
|||
final boolean autoCreated,
|
||||
final boolean purgeOnNoConsumers,
|
||||
final RoutingType routingType) {
|
||||
this(durable, temporary, consumerCount, messageCount, filterString, address, name, exists, autoCreateQueues, maxConsumers, autoCreated, purgeOnNoConsumers, routingType, null, null);
|
||||
}
|
||||
public QueueQueryImpl(final boolean durable,
|
||||
final boolean temporary,
|
||||
final int consumerCount,
|
||||
final long messageCount,
|
||||
final SimpleString filterString,
|
||||
final SimpleString address,
|
||||
final SimpleString name,
|
||||
final boolean exists,
|
||||
final boolean autoCreateQueues,
|
||||
final int maxConsumers,
|
||||
final boolean autoCreated,
|
||||
final boolean purgeOnNoConsumers,
|
||||
final RoutingType routingType,
|
||||
final Boolean exclusive,
|
||||
final Boolean lastValue) {
|
||||
this.durable = durable;
|
||||
this.temporary = temporary;
|
||||
this.consumerCount = consumerCount;
|
||||
|
@ -97,6 +118,8 @@ public class QueueQueryImpl implements ClientSession.QueueQuery {
|
|||
this.autoCreated = autoCreated;
|
||||
this.purgeOnNoConsumers = purgeOnNoConsumers;
|
||||
this.routingType = routingType;
|
||||
this.exclusive = exclusive;
|
||||
this.lastValue = lastValue;
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -164,5 +187,15 @@ public class QueueQueryImpl implements ClientSession.QueueQuery {
|
|||
return autoCreated;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Boolean isExclusive() {
|
||||
return exclusive;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Boolean isLastValue() {
|
||||
return lastValue;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
|
|
@ -244,13 +244,26 @@ public class ActiveMQSessionContext extends SessionContext {
|
|||
this.sendAckHandler = handler;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void createSharedQueue(SimpleString address,
|
||||
SimpleString queueName,
|
||||
RoutingType routingType,
|
||||
SimpleString filterString,
|
||||
boolean durable,
|
||||
Integer maxConsumers,
|
||||
Boolean purgeOnNoConsumers,
|
||||
Boolean exclusive,
|
||||
Boolean lastValue) throws ActiveMQException {
|
||||
sessionChannel.sendBlocking(new CreateSharedQueueMessage_V2(address, queueName, routingType, filterString, durable, maxConsumers, purgeOnNoConsumers, exclusive, lastValue, true), PacketImpl.NULL_RESPONSE);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void createSharedQueue(SimpleString address,
|
||||
SimpleString queueName,
|
||||
RoutingType routingType,
|
||||
SimpleString filterString,
|
||||
boolean durable) throws ActiveMQException {
|
||||
sessionChannel.sendBlocking(new CreateSharedQueueMessage_V2(address, queueName, routingType, filterString, durable, true), PacketImpl.NULL_RESPONSE);
|
||||
createSharedQueue(address, queueName, routingType, filterString, durable, null, null, null, null);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -325,19 +338,19 @@ public class ActiveMQSessionContext extends SessionContext {
|
|||
if (sessionChannel.supports(PacketImpl.SESS_BINDINGQUERY_RESP_V4, getServerVersion())) {
|
||||
Packet packet = sessionChannel.sendBlocking(new SessionBindingQueryMessage(address), PacketImpl.SESS_BINDINGQUERY_RESP_V4);
|
||||
SessionBindingQueryResponseMessage_V4 response = (SessionBindingQueryResponseMessage_V4) packet;
|
||||
return new AddressQueryImpl(response.isExists(), response.getQueueNames(), response.isAutoCreateQueues(), response.isAutoCreateAddresses(), response.isDefaultPurgeOnNoConsumers(), response.getDefaultMaxConsumers());
|
||||
return new AddressQueryImpl(response.isExists(), response.getQueueNames(), response.isAutoCreateQueues(), response.isAutoCreateAddresses(), response.isDefaultPurgeOnNoConsumers(), response.getDefaultMaxConsumers(), response.isDefaultExclusive(), response.isDefaultLastValue());
|
||||
} else if (sessionChannel.supports(PacketImpl.SESS_BINDINGQUERY_RESP_V3, getServerVersion())) {
|
||||
Packet packet = sessionChannel.sendBlocking(new SessionBindingQueryMessage(address), PacketImpl.SESS_BINDINGQUERY_RESP_V3);
|
||||
SessionBindingQueryResponseMessage_V3 response = (SessionBindingQueryResponseMessage_V3) packet;
|
||||
return new AddressQueryImpl(response.isExists(), response.getQueueNames(), response.isAutoCreateQueues(), response.isAutoCreateAddresses(), ActiveMQDefaultConfiguration.getDefaultPurgeOnNoConsumers(), ActiveMQDefaultConfiguration.getDefaultMaxQueueConsumers());
|
||||
return new AddressQueryImpl(response.isExists(), response.getQueueNames(), response.isAutoCreateQueues(), response.isAutoCreateAddresses(), ActiveMQDefaultConfiguration.getDefaultPurgeOnNoConsumers(), ActiveMQDefaultConfiguration.getDefaultMaxQueueConsumers(), null, null);
|
||||
} else if (sessionChannel.supports(PacketImpl.SESS_BINDINGQUERY_RESP_V2, getServerVersion())) {
|
||||
Packet packet = sessionChannel.sendBlocking(new SessionBindingQueryMessage(address), PacketImpl.SESS_BINDINGQUERY_RESP_V2);
|
||||
SessionBindingQueryResponseMessage_V2 response = (SessionBindingQueryResponseMessage_V2) packet;
|
||||
return new AddressQueryImpl(response.isExists(), response.getQueueNames(), response.isAutoCreateQueues(), false, ActiveMQDefaultConfiguration.getDefaultPurgeOnNoConsumers(), ActiveMQDefaultConfiguration.getDefaultMaxQueueConsumers());
|
||||
return new AddressQueryImpl(response.isExists(), response.getQueueNames(), response.isAutoCreateQueues(), false, ActiveMQDefaultConfiguration.getDefaultPurgeOnNoConsumers(), ActiveMQDefaultConfiguration.getDefaultMaxQueueConsumers(), null, null);
|
||||
} else {
|
||||
Packet packet = sessionChannel.sendBlocking(new SessionBindingQueryMessage(address), PacketImpl.SESS_BINDINGQUERY_RESP);
|
||||
SessionBindingQueryResponseMessage response = (SessionBindingQueryResponseMessage) packet;
|
||||
return new AddressQueryImpl(response.isExists(), response.getQueueNames(), false, false, ActiveMQDefaultConfiguration.getDefaultPurgeOnNoConsumers(), ActiveMQDefaultConfiguration.getDefaultMaxQueueConsumers());
|
||||
return new AddressQueryImpl(response.isExists(), response.getQueueNames(), false, false, ActiveMQDefaultConfiguration.getDefaultPurgeOnNoConsumers(), ActiveMQDefaultConfiguration.getDefaultMaxQueueConsumers(), null, null);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -647,16 +660,32 @@ public class ActiveMQSessionContext extends SessionContext {
|
|||
boolean temp,
|
||||
int maxConsumers,
|
||||
boolean purgeOnNoConsumers,
|
||||
boolean autoCreated) throws ActiveMQException {
|
||||
boolean autoCreated,
|
||||
Boolean exclusive,
|
||||
Boolean lastValue) throws ActiveMQException {
|
||||
if (sessionChannel.getConnection().isVersionBeforeAddressChange()) {
|
||||
CreateQueueMessage request = new CreateQueueMessage(address, queueName, filterString, durable, temp, true);
|
||||
sessionChannel.sendBlocking(request, PacketImpl.NULL_RESPONSE);
|
||||
} else {
|
||||
CreateQueueMessage request = new CreateQueueMessage_V2(address, queueName, routingType, filterString, durable, temp, maxConsumers, purgeOnNoConsumers, autoCreated, true);
|
||||
CreateQueueMessage request = new CreateQueueMessage_V2(address, queueName, routingType, filterString, durable, temp, maxConsumers, purgeOnNoConsumers, autoCreated, true, exclusive, lastValue);
|
||||
sessionChannel.sendBlocking(request, PacketImpl.NULL_RESPONSE);
|
||||
}
|
||||
}
|
||||
|
||||
@Deprecated
|
||||
@Override
|
||||
public void createQueue(SimpleString address,
|
||||
RoutingType routingType,
|
||||
SimpleString queueName,
|
||||
SimpleString filterString,
|
||||
boolean durable,
|
||||
boolean temp,
|
||||
int maxConsumers,
|
||||
boolean purgeOnNoConsumers,
|
||||
boolean autoCreated) throws ActiveMQException {
|
||||
createQueue(address, routingType, queueName, filterString, durable, temp, maxConsumers, purgeOnNoConsumers, autoCreated, null, null);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean reattachOnNewConnection(RemotingConnection newConnection) throws ActiveMQException {
|
||||
|
||||
|
@ -741,7 +770,7 @@ public class ActiveMQSessionContext extends SessionContext {
|
|||
// they are defined in broker.xml
|
||||
// This allows e.g. JMS non durable subs and temporary queues to continue to be used after failover
|
||||
if (!queueInfo.isDurable()) {
|
||||
CreateQueueMessage_V2 createQueueRequest = new CreateQueueMessage_V2(queueInfo.getAddress(), queueInfo.getName(), queueInfo.getRoutingType(), queueInfo.getFilterString(), false, queueInfo.isTemporary(), queueInfo.getMaxConsumers(), queueInfo.isPurgeOnNoConsumers(), queueInfo.isAutoCreated(), false);
|
||||
CreateQueueMessage_V2 createQueueRequest = new CreateQueueMessage_V2(queueInfo.getAddress(), queueInfo.getName(), queueInfo.getRoutingType(), queueInfo.getFilterString(), false, queueInfo.isTemporary(), queueInfo.getMaxConsumers(), queueInfo.isPurgeOnNoConsumers(), queueInfo.isAutoCreated(), false, queueInfo.isExclusive(), queueInfo.isLastValue());
|
||||
|
||||
sendPacketWithoutLock(sessionChannel, createQueueRequest);
|
||||
}
|
||||
|
|
|
@ -19,6 +19,7 @@ package org.apache.activemq.artemis.core.protocol.core.impl.wireformat;
|
|||
import org.apache.activemq.artemis.api.core.ActiveMQBuffer;
|
||||
import org.apache.activemq.artemis.api.core.SimpleString;
|
||||
import org.apache.activemq.artemis.api.core.RoutingType;
|
||||
import org.apache.activemq.artemis.utils.BufferHelper;
|
||||
|
||||
public class CreateQueueMessage_V2 extends CreateQueueMessage {
|
||||
|
||||
|
@ -30,6 +31,10 @@ public class CreateQueueMessage_V2 extends CreateQueueMessage {
|
|||
|
||||
private boolean purgeOnNoConsumers;
|
||||
|
||||
private Boolean exclusive;
|
||||
|
||||
private Boolean lastValue;
|
||||
|
||||
public CreateQueueMessage_V2(final SimpleString address,
|
||||
final SimpleString queueName,
|
||||
final RoutingType routingType,
|
||||
|
@ -39,7 +44,9 @@ public class CreateQueueMessage_V2 extends CreateQueueMessage {
|
|||
final int maxConsumers,
|
||||
final boolean purgeOnNoConsumers,
|
||||
final boolean autoCreated,
|
||||
final boolean requiresResponse) {
|
||||
final boolean requiresResponse,
|
||||
final Boolean exclusive,
|
||||
final Boolean lastValue) {
|
||||
this();
|
||||
|
||||
this.address = address;
|
||||
|
@ -52,6 +59,8 @@ public class CreateQueueMessage_V2 extends CreateQueueMessage {
|
|||
this.routingType = routingType;
|
||||
this.maxConsumers = maxConsumers;
|
||||
this.purgeOnNoConsumers = purgeOnNoConsumers;
|
||||
this.exclusive = exclusive;
|
||||
this.lastValue = lastValue;
|
||||
}
|
||||
|
||||
public CreateQueueMessage_V2() {
|
||||
|
@ -67,6 +76,8 @@ public class CreateQueueMessage_V2 extends CreateQueueMessage {
|
|||
buff.append(", routingType=" + routingType);
|
||||
buff.append(", maxConsumers=" + maxConsumers);
|
||||
buff.append(", purgeOnNoConsumers=" + purgeOnNoConsumers);
|
||||
buff.append(", exclusive=" + exclusive);
|
||||
buff.append(", lastValue=" + lastValue);
|
||||
buff.append("]");
|
||||
return buff.toString();
|
||||
}
|
||||
|
@ -103,6 +114,22 @@ public class CreateQueueMessage_V2 extends CreateQueueMessage {
|
|||
this.autoCreated = autoCreated;
|
||||
}
|
||||
|
||||
public Boolean isExclusive() {
|
||||
return exclusive;
|
||||
}
|
||||
|
||||
public void setExclusive(Boolean exclusive) {
|
||||
this.exclusive = exclusive;
|
||||
}
|
||||
|
||||
public Boolean isLastValue() {
|
||||
return lastValue;
|
||||
}
|
||||
|
||||
public void setLastValue(Boolean lastValue) {
|
||||
this.lastValue = lastValue;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void encodeRest(final ActiveMQBuffer buffer) {
|
||||
super.encodeRest(buffer);
|
||||
|
@ -110,6 +137,8 @@ public class CreateQueueMessage_V2 extends CreateQueueMessage {
|
|||
buffer.writeByte(routingType == null ? -1 : routingType.getType());
|
||||
buffer.writeInt(maxConsumers);
|
||||
buffer.writeBoolean(purgeOnNoConsumers);
|
||||
BufferHelper.writeNullableBoolean(buffer, exclusive);
|
||||
BufferHelper.writeNullableBoolean(buffer, lastValue);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -119,6 +148,10 @@ public class CreateQueueMessage_V2 extends CreateQueueMessage {
|
|||
routingType = RoutingType.getType(buffer.readByte());
|
||||
maxConsumers = buffer.readInt();
|
||||
purgeOnNoConsumers = buffer.readBoolean();
|
||||
if (buffer.readableBytes() > 0) {
|
||||
exclusive = BufferHelper.readNullableBoolean(buffer);
|
||||
lastValue = BufferHelper.readNullableBoolean(buffer);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -129,6 +162,8 @@ public class CreateQueueMessage_V2 extends CreateQueueMessage {
|
|||
result = prime * result + (routingType.getType());
|
||||
result = prime * result + (maxConsumers);
|
||||
result = prime * result + (purgeOnNoConsumers ? 1231 : 1237);
|
||||
result = prime * result + (exclusive == null ? 0 : exclusive ? 1231 : 1237);
|
||||
result = prime * result + (lastValue == null ? 0 : lastValue ? 1231 : 1237);
|
||||
return result;
|
||||
}
|
||||
|
||||
|
@ -147,7 +182,9 @@ public class CreateQueueMessage_V2 extends CreateQueueMessage {
|
|||
return false;
|
||||
if (purgeOnNoConsumers != other.purgeOnNoConsumers)
|
||||
return false;
|
||||
if (purgeOnNoConsumers != other.purgeOnNoConsumers)
|
||||
if (exclusive != other.exclusive)
|
||||
return false;
|
||||
if (lastValue != other.lastValue)
|
||||
return false;
|
||||
if (routingType == null) {
|
||||
if (other.routingType != null)
|
||||
|
|
|
@ -19,16 +19,25 @@ package org.apache.activemq.artemis.core.protocol.core.impl.wireformat;
|
|||
import org.apache.activemq.artemis.api.core.ActiveMQBuffer;
|
||||
import org.apache.activemq.artemis.api.core.SimpleString;
|
||||
import org.apache.activemq.artemis.api.core.RoutingType;
|
||||
import org.apache.activemq.artemis.utils.BufferHelper;
|
||||
|
||||
public class CreateSharedQueueMessage_V2 extends CreateSharedQueueMessage {
|
||||
|
||||
private RoutingType routingType;
|
||||
Integer maxConsumers;
|
||||
Boolean purgeOnNoConsumers;
|
||||
private Boolean exclusive;
|
||||
private Boolean lastValue;
|
||||
|
||||
public CreateSharedQueueMessage_V2(final SimpleString address,
|
||||
final SimpleString queueName,
|
||||
final RoutingType routingType,
|
||||
final SimpleString filterString,
|
||||
final boolean durable,
|
||||
final Integer maxConsumers,
|
||||
final Boolean purgeOnNoConsumers,
|
||||
final Boolean exclusive,
|
||||
final Boolean lastValue,
|
||||
final boolean requiresResponse) {
|
||||
this();
|
||||
|
||||
|
@ -36,8 +45,13 @@ public class CreateSharedQueueMessage_V2 extends CreateSharedQueueMessage {
|
|||
this.queueName = queueName;
|
||||
this.filterString = filterString;
|
||||
this.durable = durable;
|
||||
this.requiresResponse = requiresResponse;
|
||||
this.routingType = routingType;
|
||||
this.maxConsumers = maxConsumers;
|
||||
this.purgeOnNoConsumers = purgeOnNoConsumers;
|
||||
this.exclusive = exclusive;
|
||||
this.lastValue = lastValue;
|
||||
this.requiresResponse = requiresResponse;
|
||||
|
||||
}
|
||||
|
||||
public CreateSharedQueueMessage_V2() {
|
||||
|
@ -52,6 +66,38 @@ public class CreateSharedQueueMessage_V2 extends CreateSharedQueueMessage {
|
|||
this.routingType = routingType;
|
||||
}
|
||||
|
||||
public Integer getMaxConsumers() {
|
||||
return maxConsumers;
|
||||
}
|
||||
|
||||
public void setMaxConsumers(Integer maxConsumers) {
|
||||
this.maxConsumers = maxConsumers;
|
||||
}
|
||||
|
||||
public Boolean isPurgeOnNoConsumers() {
|
||||
return purgeOnNoConsumers;
|
||||
}
|
||||
|
||||
public void setPurgeOnNoConsumers(Boolean purgeOnNoConsumers) {
|
||||
this.purgeOnNoConsumers = purgeOnNoConsumers;
|
||||
}
|
||||
|
||||
public Boolean isExclusive() {
|
||||
return exclusive;
|
||||
}
|
||||
|
||||
public void setExclusive(Boolean exclusive) {
|
||||
this.exclusive = exclusive;
|
||||
}
|
||||
|
||||
public Boolean isLastValue() {
|
||||
return lastValue;
|
||||
}
|
||||
|
||||
public void setLastValue(Boolean lastValue) {
|
||||
this.lastValue = lastValue;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
StringBuffer buff = new StringBuffer(getParentString());
|
||||
|
@ -59,6 +105,11 @@ public class CreateSharedQueueMessage_V2 extends CreateSharedQueueMessage {
|
|||
buff.append(", queueName=" + queueName);
|
||||
buff.append(", filterString=" + filterString);
|
||||
buff.append(", durable=" + durable);
|
||||
buff.append(", routingType=" + routingType);
|
||||
buff.append(", maxConsumers=" + maxConsumers);
|
||||
buff.append(", purgeOnNoConsumers=" + purgeOnNoConsumers);
|
||||
buff.append(", exclusive=" + exclusive);
|
||||
buff.append(", lastValue=" + lastValue);
|
||||
buff.append(", requiresResponse=" + requiresResponse);
|
||||
buff.append("]");
|
||||
return buff.toString();
|
||||
|
@ -72,6 +123,10 @@ public class CreateSharedQueueMessage_V2 extends CreateSharedQueueMessage {
|
|||
buffer.writeBoolean(durable);
|
||||
buffer.writeByte(routingType.getType());
|
||||
buffer.writeBoolean(requiresResponse);
|
||||
BufferHelper.writeNullableInteger(buffer, maxConsumers);
|
||||
BufferHelper.writeNullableBoolean(buffer, purgeOnNoConsumers);
|
||||
BufferHelper.writeNullableBoolean(buffer, exclusive);
|
||||
BufferHelper.writeNullableBoolean(buffer, lastValue);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -82,6 +137,12 @@ public class CreateSharedQueueMessage_V2 extends CreateSharedQueueMessage {
|
|||
durable = buffer.readBoolean();
|
||||
routingType = RoutingType.getType(buffer.readByte());
|
||||
requiresResponse = buffer.readBoolean();
|
||||
if (buffer.readableBytes() > 0) {
|
||||
maxConsumers = BufferHelper.readNullableInteger(buffer);
|
||||
purgeOnNoConsumers = BufferHelper.readNullableBoolean(buffer);
|
||||
exclusive = BufferHelper.readNullableBoolean(buffer);
|
||||
lastValue = BufferHelper.readNullableBoolean(buffer);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -94,6 +155,10 @@ public class CreateSharedQueueMessage_V2 extends CreateSharedQueueMessage {
|
|||
result = prime * result + (durable ? 1231 : 1237);
|
||||
result = prime * result + routingType.getType();
|
||||
result = prime * result + (requiresResponse ? 1231 : 1237);
|
||||
result = prime * result + (maxConsumers == null ? 0 : maxConsumers.hashCode());
|
||||
result = prime * result + (purgeOnNoConsumers == null ? 0 : purgeOnNoConsumers ? 1231 : 1237);
|
||||
result = prime * result + (exclusive == null ? 0 : exclusive ? 1231 : 1237);
|
||||
result = prime * result + (lastValue == null ? 0 : lastValue ? 1231 : 1237);
|
||||
return result;
|
||||
}
|
||||
|
||||
|
@ -127,6 +192,14 @@ public class CreateSharedQueueMessage_V2 extends CreateSharedQueueMessage {
|
|||
return false;
|
||||
if (requiresResponse != other.requiresResponse)
|
||||
return false;
|
||||
if (maxConsumers != other.maxConsumers)
|
||||
return false;
|
||||
if (purgeOnNoConsumers != other.purgeOnNoConsumers)
|
||||
return false;
|
||||
if (exclusive != other.exclusive)
|
||||
return false;
|
||||
if (lastValue != other.lastValue)
|
||||
return false;
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -20,6 +20,7 @@ import java.util.List;
|
|||
|
||||
import org.apache.activemq.artemis.api.core.ActiveMQBuffer;
|
||||
import org.apache.activemq.artemis.api.core.SimpleString;
|
||||
import org.apache.activemq.artemis.utils.BufferHelper;
|
||||
|
||||
public class SessionBindingQueryResponseMessage_V4 extends SessionBindingQueryResponseMessage_V3 {
|
||||
|
||||
|
@ -27,12 +28,18 @@ public class SessionBindingQueryResponseMessage_V4 extends SessionBindingQueryRe
|
|||
|
||||
private int defaultMaxConsumers;
|
||||
|
||||
private Boolean defaultExclusive;
|
||||
|
||||
private Boolean defaultLastValue;
|
||||
|
||||
public SessionBindingQueryResponseMessage_V4(final boolean exists,
|
||||
final List<SimpleString> queueNames,
|
||||
final boolean autoCreateQueues,
|
||||
final boolean autoCreateAddresses,
|
||||
final boolean defaultPurgeOnNoConsumers,
|
||||
final int defaultMaxConsumers) {
|
||||
final int defaultMaxConsumers,
|
||||
final Boolean defaultExclusive,
|
||||
final Boolean defaultLastValue) {
|
||||
super(SESS_BINDINGQUERY_RESP_V4);
|
||||
|
||||
this.exists = exists;
|
||||
|
@ -46,6 +53,10 @@ public class SessionBindingQueryResponseMessage_V4 extends SessionBindingQueryRe
|
|||
this.defaultPurgeOnNoConsumers = defaultPurgeOnNoConsumers;
|
||||
|
||||
this.defaultMaxConsumers = defaultMaxConsumers;
|
||||
|
||||
this.defaultExclusive = defaultExclusive;
|
||||
|
||||
this.defaultLastValue = defaultLastValue;
|
||||
}
|
||||
|
||||
public SessionBindingQueryResponseMessage_V4() {
|
||||
|
@ -60,11 +71,21 @@ public class SessionBindingQueryResponseMessage_V4 extends SessionBindingQueryRe
|
|||
return defaultMaxConsumers;
|
||||
}
|
||||
|
||||
public Boolean isDefaultExclusive() {
|
||||
return defaultExclusive;
|
||||
}
|
||||
|
||||
public Boolean isDefaultLastValue() {
|
||||
return defaultLastValue;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void encodeRest(final ActiveMQBuffer buffer) {
|
||||
super.encodeRest(buffer);
|
||||
buffer.writeBoolean(defaultPurgeOnNoConsumers);
|
||||
buffer.writeInt(defaultMaxConsumers);
|
||||
BufferHelper.writeNullableBoolean(buffer, defaultExclusive);
|
||||
BufferHelper.writeNullableBoolean(buffer, defaultLastValue);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -72,6 +93,10 @@ public class SessionBindingQueryResponseMessage_V4 extends SessionBindingQueryRe
|
|||
super.decodeRest(buffer);
|
||||
defaultPurgeOnNoConsumers = buffer.readBoolean();
|
||||
defaultMaxConsumers = buffer.readInt();
|
||||
if (buffer.readableBytes() > 0) {
|
||||
defaultExclusive = BufferHelper.readNullableBoolean(buffer);
|
||||
defaultLastValue = BufferHelper.readNullableBoolean(buffer);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -80,6 +105,8 @@ public class SessionBindingQueryResponseMessage_V4 extends SessionBindingQueryRe
|
|||
int result = super.hashCode();
|
||||
result = prime * result + (defaultPurgeOnNoConsumers ? 1231 : 1237);
|
||||
result = prime * result + defaultMaxConsumers;
|
||||
result = prime * result + (defaultExclusive == null ? 0 : defaultExclusive ? 1231 : 1237);
|
||||
result = prime * result + (defaultLastValue == null ? 0 : defaultLastValue ? 1231 : 1237);
|
||||
return result;
|
||||
}
|
||||
|
||||
|
@ -95,6 +122,8 @@ public class SessionBindingQueryResponseMessage_V4 extends SessionBindingQueryRe
|
|||
StringBuffer buff = new StringBuffer(super.getParentString());
|
||||
buff.append(", defaultPurgeOnNoConsumers=" + defaultPurgeOnNoConsumers);
|
||||
buff.append(", defaultMaxConsumers=" + defaultMaxConsumers);
|
||||
buff.append(", defaultExclusive=" + defaultExclusive);
|
||||
buff.append(", defaultLastValue=" + defaultLastValue);
|
||||
return buff.toString();
|
||||
}
|
||||
|
||||
|
@ -111,6 +140,10 @@ public class SessionBindingQueryResponseMessage_V4 extends SessionBindingQueryRe
|
|||
return false;
|
||||
if (defaultMaxConsumers != other.defaultMaxConsumers)
|
||||
return false;
|
||||
if (defaultExclusive != other.defaultExclusive)
|
||||
return false;
|
||||
if (defaultLastValue != other.defaultLastValue)
|
||||
return false;
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -22,6 +22,7 @@ import org.apache.activemq.artemis.api.core.client.ClientSession;
|
|||
import org.apache.activemq.artemis.core.client.impl.QueueQueryImpl;
|
||||
import org.apache.activemq.artemis.core.server.QueueQueryResult;
|
||||
import org.apache.activemq.artemis.api.core.RoutingType;
|
||||
import org.apache.activemq.artemis.utils.BufferHelper;
|
||||
|
||||
public class SessionQueueQueryResponseMessage_V3 extends SessionQueueQueryResponseMessage_V2 {
|
||||
|
||||
|
@ -33,12 +34,16 @@ public class SessionQueueQueryResponseMessage_V3 extends SessionQueueQueryRespon
|
|||
|
||||
protected int maxConsumers;
|
||||
|
||||
protected Boolean exclusive;
|
||||
|
||||
protected Boolean lastValue;
|
||||
|
||||
public SessionQueueQueryResponseMessage_V3(final QueueQueryResult result) {
|
||||
this(result.getName(), result.getAddress(), result.isDurable(), result.isTemporary(), result.getFilterString(), result.getConsumerCount(), result.getMessageCount(), result.isExists(), result.isAutoCreateQueues(), result.isAutoCreated(), result.isPurgeOnNoConsumers(), result.getRoutingType(), result.getMaxConsumers());
|
||||
this(result.getName(), result.getAddress(), result.isDurable(), result.isTemporary(), result.getFilterString(), result.getConsumerCount(), result.getMessageCount(), result.isExists(), result.isAutoCreateQueues(), result.isAutoCreated(), result.isPurgeOnNoConsumers(), result.getRoutingType(), result.getMaxConsumers(), result.isExclusive(), result.isLastValue());
|
||||
}
|
||||
|
||||
public SessionQueueQueryResponseMessage_V3() {
|
||||
this(null, null, false, false, null, 0, 0, false, false, false, false, RoutingType.MULTICAST, -1);
|
||||
this(null, null, false, false, null, 0, 0, false, false, false, false, RoutingType.MULTICAST, -1, null, null);
|
||||
}
|
||||
|
||||
private SessionQueueQueryResponseMessage_V3(final SimpleString name,
|
||||
|
@ -53,7 +58,9 @@ public class SessionQueueQueryResponseMessage_V3 extends SessionQueueQueryRespon
|
|||
final boolean autoCreated,
|
||||
final boolean purgeOnNoConsumers,
|
||||
final RoutingType routingType,
|
||||
final int maxConsumers) {
|
||||
final int maxConsumers,
|
||||
final Boolean exclusive,
|
||||
final Boolean lastValue) {
|
||||
super(SESS_QUEUEQUERY_RESP_V3);
|
||||
|
||||
this.durable = durable;
|
||||
|
@ -81,6 +88,10 @@ public class SessionQueueQueryResponseMessage_V3 extends SessionQueueQueryRespon
|
|||
this.routingType = routingType;
|
||||
|
||||
this.maxConsumers = maxConsumers;
|
||||
|
||||
this.exclusive = exclusive;
|
||||
|
||||
this.lastValue = lastValue;
|
||||
}
|
||||
|
||||
public boolean isAutoCreated() {
|
||||
|
@ -115,6 +126,22 @@ public class SessionQueueQueryResponseMessage_V3 extends SessionQueueQueryRespon
|
|||
this.maxConsumers = maxConsumers;
|
||||
}
|
||||
|
||||
public Boolean isExclusive() {
|
||||
return exclusive;
|
||||
}
|
||||
|
||||
public void setExclusive(Boolean exclusive) {
|
||||
this.exclusive = exclusive;
|
||||
}
|
||||
|
||||
public Boolean isLastValue() {
|
||||
return lastValue;
|
||||
}
|
||||
|
||||
public void setLastValue(Boolean lastValue) {
|
||||
this.lastValue = lastValue;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void encodeRest(final ActiveMQBuffer buffer) {
|
||||
super.encodeRest(buffer);
|
||||
|
@ -122,6 +149,8 @@ public class SessionQueueQueryResponseMessage_V3 extends SessionQueueQueryRespon
|
|||
buffer.writeBoolean(purgeOnNoConsumers);
|
||||
buffer.writeByte(routingType.getType());
|
||||
buffer.writeInt(maxConsumers);
|
||||
BufferHelper.writeNullableBoolean(buffer, exclusive);
|
||||
BufferHelper.writeNullableBoolean(buffer, lastValue);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -131,6 +160,10 @@ public class SessionQueueQueryResponseMessage_V3 extends SessionQueueQueryRespon
|
|||
purgeOnNoConsumers = buffer.readBoolean();
|
||||
routingType = RoutingType.getType(buffer.readByte());
|
||||
maxConsumers = buffer.readInt();
|
||||
if (buffer.readableBytes() > 0) {
|
||||
exclusive = BufferHelper.readNullableBoolean(buffer);
|
||||
lastValue = BufferHelper.readNullableBoolean(buffer);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -141,6 +174,8 @@ public class SessionQueueQueryResponseMessage_V3 extends SessionQueueQueryRespon
|
|||
result = prime * result + (purgeOnNoConsumers ? 1231 : 1237);
|
||||
result = prime * result + routingType.hashCode();
|
||||
result = prime * result + maxConsumers;
|
||||
result = prime * result + (exclusive == null ? 0 : exclusive ? 1231 : 1237);
|
||||
result = prime * result + (lastValue == null ? 0 : lastValue ? 1231 : 1237);
|
||||
return result;
|
||||
}
|
||||
|
||||
|
@ -158,12 +193,14 @@ public class SessionQueueQueryResponseMessage_V3 extends SessionQueueQueryRespon
|
|||
buff.append(", purgeOnNoConsumers=" + purgeOnNoConsumers);
|
||||
buff.append(", routingType=" + routingType);
|
||||
buff.append(", maxConsumers=" + maxConsumers);
|
||||
buff.append(", exclusive=" + exclusive);
|
||||
buff.append(", lastValue=" + lastValue);
|
||||
return buff.toString();
|
||||
}
|
||||
|
||||
@Override
|
||||
public ClientSession.QueueQuery toQueueQuery() {
|
||||
return new QueueQueryImpl(isDurable(), isTemporary(), getConsumerCount(), getMessageCount(), getFilterString(), getAddress(), getName(), isExists(), isAutoCreateQueues(), getMaxConsumers(), isAutoCreated(), isPurgeOnNoConsumers(), getRoutingType());
|
||||
return new QueueQueryImpl(isDurable(), isTemporary(), getConsumerCount(), getMessageCount(), getFilterString(), getAddress(), getName(), isExists(), isAutoCreateQueues(), getMaxConsumers(), isAutoCreated(), isPurgeOnNoConsumers(), getRoutingType(), isExclusive(), isLastValue());
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -179,6 +216,10 @@ public class SessionQueueQueryResponseMessage_V3 extends SessionQueueQueryRespon
|
|||
return false;
|
||||
if (purgeOnNoConsumers != other.purgeOnNoConsumers)
|
||||
return false;
|
||||
if (exclusive != other.exclusive)
|
||||
return false;
|
||||
if (lastValue != other.lastValue)
|
||||
return false;
|
||||
if (routingType == null) {
|
||||
if (other.routingType != null)
|
||||
return false;
|
||||
|
|
|
@ -47,6 +47,10 @@ public class QueueQueryResult {
|
|||
|
||||
private int maxConsumers;
|
||||
|
||||
private Boolean exclusive;
|
||||
|
||||
private Boolean lastValue;
|
||||
|
||||
public QueueQueryResult(final SimpleString name,
|
||||
final SimpleString address,
|
||||
final boolean durable,
|
||||
|
@ -59,7 +63,9 @@ public class QueueQueryResult {
|
|||
final boolean autoCreated,
|
||||
final boolean purgeOnNoConsumers,
|
||||
final RoutingType routingType,
|
||||
final int maxConsumers) {
|
||||
final int maxConsumers,
|
||||
final Boolean exclusive,
|
||||
final Boolean lastValue) {
|
||||
this.durable = durable;
|
||||
|
||||
this.temporary = temporary;
|
||||
|
@ -85,6 +91,10 @@ public class QueueQueryResult {
|
|||
this.routingType = routingType;
|
||||
|
||||
this.maxConsumers = maxConsumers;
|
||||
|
||||
this.exclusive = exclusive;
|
||||
|
||||
this.lastValue = lastValue;
|
||||
}
|
||||
|
||||
public boolean isExists() {
|
||||
|
@ -142,4 +152,12 @@ public class QueueQueryResult {
|
|||
public void setAddress(SimpleString address) {
|
||||
this.address = address;
|
||||
}
|
||||
|
||||
public Boolean isExclusive() {
|
||||
return exclusive;
|
||||
}
|
||||
|
||||
public Boolean isLastValue() {
|
||||
return lastValue;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -171,8 +171,20 @@ public abstract class SessionContext {
|
|||
* @param routingType
|
||||
* @param filterString
|
||||
* @param durable
|
||||
* @param exclusive
|
||||
* @param lastValue
|
||||
* @throws ActiveMQException
|
||||
*/
|
||||
public abstract void createSharedQueue(SimpleString address,
|
||||
SimpleString queueName,
|
||||
RoutingType routingType,
|
||||
SimpleString filterString,
|
||||
boolean durable,
|
||||
Integer maxConsumers,
|
||||
Boolean purgeOnNoConsumers,
|
||||
Boolean exclusive,
|
||||
Boolean lastValue) throws ActiveMQException;
|
||||
|
||||
public abstract void createSharedQueue(SimpleString address,
|
||||
SimpleString queueName,
|
||||
RoutingType routingType,
|
||||
|
@ -199,6 +211,7 @@ public abstract class SessionContext {
|
|||
boolean temp,
|
||||
boolean autoCreated) throws ActiveMQException;
|
||||
|
||||
@Deprecated
|
||||
public abstract void createQueue(SimpleString address,
|
||||
RoutingType routingType,
|
||||
SimpleString queueName,
|
||||
|
@ -209,6 +222,18 @@ public abstract class SessionContext {
|
|||
boolean purgeOnNoConsumers,
|
||||
boolean autoCreated) throws ActiveMQException;
|
||||
|
||||
public abstract void createQueue(SimpleString address,
|
||||
RoutingType routingType,
|
||||
SimpleString queueName,
|
||||
SimpleString filterString,
|
||||
boolean durable,
|
||||
boolean temp,
|
||||
int maxConsumers,
|
||||
boolean purgeOnNoConsumers,
|
||||
boolean autoCreated,
|
||||
Boolean exclusive,
|
||||
Boolean lastVale) throws ActiveMQException;
|
||||
|
||||
public abstract ClientSession.QueueQuery queueQuery(SimpleString queueName) throws ActiveMQException;
|
||||
|
||||
public abstract void forceDelivery(ClientConsumer consumer, long sequence) throws ActiveMQException;
|
||||
|
|
|
@ -24,8 +24,10 @@ import java.util.Properties;
|
|||
import java.util.UUID;
|
||||
|
||||
import org.apache.activemq.artemis.api.core.Pair;
|
||||
import org.apache.activemq.artemis.api.core.QueueAttributes;
|
||||
import org.apache.activemq.artemis.api.core.SimpleString;
|
||||
import org.apache.activemq.artemis.jndi.JNDIStorable;
|
||||
import org.apache.activemq.artemis.api.core.ParameterisedAddress;
|
||||
|
||||
/**
|
||||
* ActiveMQ Artemis implementation of a JMS Destination.
|
||||
|
@ -249,6 +251,11 @@ public class ActiveMQDestination extends JNDIStorable implements Destination, Se
|
|||
*/
|
||||
private SimpleString simpleAddress;
|
||||
|
||||
/**
|
||||
* Queue parameters;
|
||||
*/
|
||||
private QueueAttributes queueAttributes;
|
||||
|
||||
/**
|
||||
* Needed for serialization backwards compatibility.
|
||||
*/
|
||||
|
@ -280,7 +287,10 @@ public class ActiveMQDestination extends JNDIStorable implements Destination, Se
|
|||
protected ActiveMQDestination(final SimpleString address,
|
||||
final TYPE type,
|
||||
final ActiveMQSession session) {
|
||||
this.simpleAddress = address;
|
||||
|
||||
if (address != null) {
|
||||
setSimpleAddress(address);
|
||||
}
|
||||
|
||||
this.thetype = type;
|
||||
|
||||
|
@ -319,8 +329,16 @@ public class ActiveMQDestination extends JNDIStorable implements Destination, Se
|
|||
if (address == null) {
|
||||
throw new IllegalArgumentException("address cannot be null");
|
||||
}
|
||||
this.address = address.toString();
|
||||
this.simpleAddress = address;
|
||||
if (ParameterisedAddress.isParameterised(address)) {
|
||||
ParameterisedAddress parameteredAddress = new ParameterisedAddress(address);
|
||||
this.simpleAddress = parameteredAddress.getAddress();
|
||||
this.address = parameteredAddress.getAddress().toString();
|
||||
this.queueAttributes = parameteredAddress.getQueueAttributes();
|
||||
} else {
|
||||
this.simpleAddress = address;
|
||||
this.address = address.toString();
|
||||
this.queueAttributes = null;
|
||||
}
|
||||
}
|
||||
|
||||
public void delete() throws JMSException {
|
||||
|
@ -351,6 +369,10 @@ public class ActiveMQDestination extends JNDIStorable implements Destination, Se
|
|||
return simpleAddress;
|
||||
}
|
||||
|
||||
public QueueAttributes getQueueAttributes() {
|
||||
return queueAttributes;
|
||||
}
|
||||
|
||||
public String getName() {
|
||||
return name != null ? name : getAddress();
|
||||
}
|
||||
|
|
|
@ -37,6 +37,7 @@ import javax.jms.TopicPublisher;
|
|||
import org.apache.activemq.artemis.api.core.ActiveMQException;
|
||||
import org.apache.activemq.artemis.api.core.ActiveMQInterruptedException;
|
||||
import org.apache.activemq.artemis.api.core.ActiveMQQueueExistsException;
|
||||
import org.apache.activemq.artemis.api.core.QueueAttributes;
|
||||
import org.apache.activemq.artemis.api.core.SimpleString;
|
||||
import org.apache.activemq.artemis.api.core.client.ClientMessage;
|
||||
import org.apache.activemq.artemis.api.core.client.ClientProducer;
|
||||
|
@ -412,7 +413,7 @@ public class ActiveMQMessageProducer implements MessageProducer, QueueSender, To
|
|||
// TODO is it right to use the address for the queue name here?
|
||||
clientSession.createTemporaryQueue(address, RoutingType.ANYCAST, address);
|
||||
} else {
|
||||
clientSession.createQueue(address, RoutingType.ANYCAST, address, null, true, true, query.getDefaultMaxConsumers(), query.isDefaultPurgeOnNoConsumers());
|
||||
createQueue(destination, RoutingType.ANYCAST, address, null, true, true, query.getDefaultMaxConsumers(), query.isDefaultPurgeOnNoConsumers(), query.isDefaultExclusive(), query.isDefaultLastValueQueue());
|
||||
}
|
||||
} else if (!destination.isQueue() && query.isAutoCreateAddresses()) {
|
||||
clientSession.createAddress(address, RoutingType.MULTICAST, true);
|
||||
|
@ -427,7 +428,7 @@ public class ActiveMQMessageProducer implements MessageProducer, QueueSender, To
|
|||
if (destination.isTemporary()) {
|
||||
clientSession.createTemporaryQueue(address, RoutingType.ANYCAST, address);
|
||||
} else {
|
||||
clientSession.createQueue(address, RoutingType.ANYCAST, address, null, true, true, query.getDefaultMaxConsumers(), query.isDefaultPurgeOnNoConsumers());
|
||||
createQueue(destination, RoutingType.ANYCAST, address, null, true, true, query.getDefaultMaxConsumers(), query.isDefaultPurgeOnNoConsumers(), query.isDefaultExclusive(), query.isDefaultLastValueQueue());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -535,6 +536,27 @@ public class ActiveMQMessageProducer implements MessageProducer, QueueSender, To
|
|||
}
|
||||
}
|
||||
|
||||
private void createQueue(ActiveMQDestination destination, RoutingType routingType, SimpleString queueName, SimpleString filter, boolean durable, boolean autoCreated, int maxConsumers, boolean purgeOnNoConsumers, Boolean exclusive, Boolean lastValue) throws ActiveMQException {
|
||||
QueueAttributes queueAttributes = destination.getQueueAttributes();
|
||||
if (queueAttributes == null) {
|
||||
clientSession.createQueue(destination.getSimpleAddress(), routingType, queueName, filter, durable, autoCreated, maxConsumers, purgeOnNoConsumers, exclusive, lastValue);
|
||||
} else {
|
||||
clientSession.createQueue(
|
||||
destination.getSimpleAddress(),
|
||||
routingType,
|
||||
queueName,
|
||||
filter,
|
||||
durable,
|
||||
autoCreated,
|
||||
queueAttributes.getMaxConsumers() == null ? maxConsumers : queueAttributes.getMaxConsumers(),
|
||||
queueAttributes.getPurgeOnNoConsumers() == null ? purgeOnNoConsumers : queueAttributes.getPurgeOnNoConsumers(),
|
||||
queueAttributes.getExclusive() == null ? exclusive : queueAttributes.getExclusive(),
|
||||
queueAttributes.getLastValue() == null ? lastValue : queueAttributes.getLastValue()
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
private static final class CompletionListenerWrapper implements SendAcknowledgementHandler {
|
||||
|
||||
private final CompletionListener completionListener;
|
||||
|
|
|
@ -52,6 +52,7 @@ import java.util.concurrent.ConcurrentHashMap;
|
|||
|
||||
import org.apache.activemq.artemis.api.core.ActiveMQException;
|
||||
import org.apache.activemq.artemis.api.core.ActiveMQQueueExistsException;
|
||||
import org.apache.activemq.artemis.api.core.QueueAttributes;
|
||||
import org.apache.activemq.artemis.api.core.SimpleString;
|
||||
import org.apache.activemq.artemis.api.core.client.ClientConsumer;
|
||||
import org.apache.activemq.artemis.api.core.client.ClientProducer;
|
||||
|
@ -318,7 +319,7 @@ public class ActiveMQSession implements QueueSession, TopicSession {
|
|||
if (jbd.isQueue() && response.isAutoCreateQueues()) {
|
||||
// perhaps just relying on the broker to do it is simplest (i.e. purgeOnNoConsumers)
|
||||
session.createAddress(jbd.getSimpleAddress(), RoutingType.ANYCAST, true);
|
||||
session.createQueue(jbd.getSimpleAddress(), RoutingType.ANYCAST, jbd.getSimpleAddress(), null, true, true, response.getDefaultMaxConsumers(), response.isDefaultPurgeOnNoConsumers());
|
||||
createQueue(jbd, RoutingType.ANYCAST, jbd.getSimpleAddress(), null, true, true, response.getDefaultMaxConsumers(), response.isDefaultPurgeOnNoConsumers(), response.isDefaultExclusive(), response.isDefaultLastValueQueue());
|
||||
} else if (!jbd.isQueue() && response.isAutoCreateAddresses()) {
|
||||
session.createAddress(jbd.getSimpleAddress(), RoutingType.MULTICAST, true);
|
||||
} else {
|
||||
|
@ -629,16 +630,16 @@ public class ActiveMQSession implements QueueSession, TopicSession {
|
|||
|
||||
queueName = ActiveMQDestination.createQueueNameForSubscription(durability == ConsumerDurability.DURABLE, connection.getClientID(), subscriptionName);
|
||||
|
||||
if (durability == ConsumerDurability.DURABLE) {
|
||||
try {
|
||||
session.createSharedQueue(dest.getSimpleAddress(), RoutingType.MULTICAST, queueName, coreFilterString, true);
|
||||
} catch (ActiveMQQueueExistsException ignored) {
|
||||
// We ignore this because querying and then creating the queue wouldn't be idempotent
|
||||
// we could also add a parameter to ignore existence what would require a bigger work around to avoid
|
||||
// compatibility.
|
||||
try {
|
||||
if (durability == ConsumerDurability.DURABLE) {
|
||||
createSharedQueue(dest, RoutingType.MULTICAST, queueName, coreFilterString, true, response.getDefaultMaxConsumers(), response.isDefaultPurgeOnNoConsumers(), response.isDefaultExclusive(), response.isDefaultLastValueQueue());
|
||||
} else {
|
||||
createSharedQueue(dest, RoutingType.MULTICAST, queueName, coreFilterString, false, response.getDefaultMaxConsumers(), response.isDefaultPurgeOnNoConsumers(), response.isDefaultExclusive(), response.isDefaultLastValueQueue());
|
||||
}
|
||||
} else {
|
||||
session.createSharedQueue(dest.getSimpleAddress(), queueName, coreFilterString, false);
|
||||
} catch (ActiveMQQueueExistsException ignored) {
|
||||
// We ignore this because querying and then creating the queue wouldn't be idempotent
|
||||
// we could also add a parameter to ignore existence what would require a bigger work around to avoid
|
||||
// compatibility.
|
||||
}
|
||||
|
||||
consumer = session.createConsumer(queueName, null, false);
|
||||
|
@ -699,7 +700,7 @@ public class ActiveMQSession implements QueueSession, TopicSession {
|
|||
if (!response.isExists() || !response.getQueueNames().contains(dest.getSimpleAddress())) {
|
||||
if (response.isAutoCreateQueues()) {
|
||||
try {
|
||||
session.createQueue(dest.getSimpleAddress(), RoutingType.ANYCAST, dest.getSimpleAddress(), null, true, true, response.getDefaultMaxConsumers(), response.isDefaultPurgeOnNoConsumers());
|
||||
createQueue(dest, RoutingType.ANYCAST, dest.getSimpleAddress(), null, true, true, response.getDefaultMaxConsumers(), response.isDefaultPurgeOnNoConsumers(), response.isDefaultExclusive(), response.isDefaultLastValueQueue());
|
||||
} catch (ActiveMQQueueExistsException e) {
|
||||
// The queue was created by another client/admin between the query check and send create queue packet
|
||||
}
|
||||
|
@ -733,7 +734,7 @@ public class ActiveMQSession implements QueueSession, TopicSession {
|
|||
|
||||
queueName = new SimpleString(UUID.randomUUID().toString());
|
||||
|
||||
session.createTemporaryQueue(dest.getSimpleAddress(), RoutingType.MULTICAST, queueName, coreFilterString);
|
||||
createTemporaryQueue(dest, RoutingType.MULTICAST, queueName, coreFilterString, response.getDefaultMaxConsumers(), response.isDefaultPurgeOnNoConsumers(), response.isDefaultExclusive(), response.isDefaultLastValueQueue());
|
||||
|
||||
consumer = session.createConsumer(queueName, null, false);
|
||||
|
||||
|
@ -756,7 +757,7 @@ public class ActiveMQSession implements QueueSession, TopicSession {
|
|||
|
||||
if (!subResponse.isExists()) {
|
||||
// durable subscription queues are not technically considered to be auto-created
|
||||
session.createQueue(dest.getSimpleAddress(), RoutingType.MULTICAST, queueName, coreFilterString, true, false, response.getDefaultMaxConsumers(), response.isDefaultPurgeOnNoConsumers());
|
||||
createQueue(dest, RoutingType.MULTICAST, queueName, coreFilterString, true, false, response.getDefaultMaxConsumers(), response.isDefaultPurgeOnNoConsumers(), response.isDefaultExclusive(), response.isDefaultLastValueQueue());
|
||||
} else {
|
||||
// Already exists
|
||||
if (subResponse.getConsumerCount() > 0) {
|
||||
|
@ -787,7 +788,7 @@ public class ActiveMQSession implements QueueSession, TopicSession {
|
|||
session.deleteQueue(queueName);
|
||||
|
||||
// Create the new one
|
||||
session.createQueue(dest.getSimpleAddress(), RoutingType.MULTICAST, queueName, coreFilterString, true, false, response.getDefaultMaxConsumers(), response.isDefaultPurgeOnNoConsumers());
|
||||
createQueue(dest, RoutingType.MULTICAST, queueName, coreFilterString, true, false, response.getDefaultMaxConsumers(), response.isDefaultPurgeOnNoConsumers(), response.isDefaultExclusive(), response.isDefaultLastValueQueue());
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -849,7 +850,7 @@ public class ActiveMQSession implements QueueSession, TopicSession {
|
|||
AddressQuery response = session.addressQuery(new SimpleString(activeMQDestination.getAddress()));
|
||||
if (!response.isExists()) {
|
||||
if (response.isAutoCreateQueues()) {
|
||||
session.createQueue(activeMQDestination.getSimpleAddress(), RoutingType.ANYCAST, activeMQDestination.getSimpleAddress(), null, true, true, response.getDefaultMaxConsumers(), response.isDefaultPurgeOnNoConsumers());
|
||||
createQueue(activeMQDestination, RoutingType.ANYCAST, activeMQDestination.getSimpleAddress(), null, true, true, response.getDefaultMaxConsumers(), response.isDefaultPurgeOnNoConsumers(), response.isDefaultExclusive(), response.isDefaultLastValueQueue());
|
||||
} else {
|
||||
throw new InvalidDestinationException("Destination " + activeMQDestination.getName() + " does not exist");
|
||||
}
|
||||
|
@ -1154,6 +1155,63 @@ public class ActiveMQSession implements QueueSession, TopicSession {
|
|||
}
|
||||
}
|
||||
|
||||
private void createTemporaryQueue(ActiveMQDestination destination, RoutingType routingType, SimpleString queueName, SimpleString filter, int maxConsumers, boolean purgeOnNoConsumers, Boolean exclusive, Boolean lastValue) throws ActiveMQException {
|
||||
QueueAttributes queueAttributes = destination.getQueueAttributes();
|
||||
if (queueAttributes == null) {
|
||||
session.createTemporaryQueue(destination.getSimpleAddress(), routingType, queueName, filter, maxConsumers, purgeOnNoConsumers, exclusive, lastValue);
|
||||
} else {
|
||||
session.createTemporaryQueue(
|
||||
destination.getSimpleAddress(),
|
||||
routingType,
|
||||
queueName,
|
||||
filter,
|
||||
queueAttributes.getMaxConsumers() == null ? maxConsumers : queueAttributes.getMaxConsumers(),
|
||||
queueAttributes.getPurgeOnNoConsumers() == null ? purgeOnNoConsumers : queueAttributes.getPurgeOnNoConsumers(),
|
||||
queueAttributes.getExclusive() == null ? exclusive : queueAttributes.getExclusive(),
|
||||
queueAttributes.getLastValue() == null ? lastValue : queueAttributes.getLastValue()
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
private void createSharedQueue(ActiveMQDestination destination, RoutingType routingType, SimpleString queueName, SimpleString filter, boolean durable, int maxConsumers, boolean purgeOnNoConsumers, Boolean exclusive, Boolean lastValue) throws ActiveMQException {
|
||||
QueueAttributes queueAttributes = destination.getQueueAttributes();
|
||||
if (queueAttributes == null) {
|
||||
session.createSharedQueue(destination.getSimpleAddress(), routingType, queueName, filter, durable, maxConsumers, purgeOnNoConsumers, exclusive, lastValue);
|
||||
} else {
|
||||
session.createSharedQueue(
|
||||
destination.getSimpleAddress(),
|
||||
routingType,
|
||||
queueName,
|
||||
filter,
|
||||
durable,
|
||||
queueAttributes.getMaxConsumers() == null ? maxConsumers : queueAttributes.getMaxConsumers(),
|
||||
queueAttributes.getPurgeOnNoConsumers() == null ? purgeOnNoConsumers : queueAttributes.getPurgeOnNoConsumers(),
|
||||
queueAttributes.getExclusive() == null ? exclusive : queueAttributes.getExclusive(),
|
||||
queueAttributes.getLastValue() == null ? lastValue : queueAttributes.getLastValue()
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
private void createQueue(ActiveMQDestination destination, RoutingType routingType, SimpleString queueName, SimpleString filter, boolean durable, boolean autoCreated, int maxConsumers, boolean purgeOnNoConsumers, Boolean exclusive, Boolean lastValue) throws ActiveMQException {
|
||||
QueueAttributes queueAttributes = destination.getQueueAttributes();
|
||||
if (queueAttributes == null) {
|
||||
session.createQueue(destination.getSimpleAddress(), routingType, queueName, filter, durable, autoCreated, maxConsumers, purgeOnNoConsumers, exclusive, lastValue);
|
||||
} else {
|
||||
session.createQueue(
|
||||
destination.getSimpleAddress(),
|
||||
routingType,
|
||||
queueName,
|
||||
filter,
|
||||
durable,
|
||||
autoCreated,
|
||||
queueAttributes.getMaxConsumers() == null ? maxConsumers : queueAttributes.getMaxConsumers(),
|
||||
queueAttributes.getPurgeOnNoConsumers() == null ? purgeOnNoConsumers : queueAttributes.getPurgeOnNoConsumers(),
|
||||
queueAttributes.getExclusive() == null ? exclusive : queueAttributes.getExclusive(),
|
||||
queueAttributes.getLastValue() == null ? lastValue : queueAttributes.getLastValue()
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
// Inner classes -------------------------------------------------
|
||||
|
||||
}
|
||||
|
|
|
@ -0,0 +1,63 @@
|
|||
/*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership.
|
||||
* The ASF licenses this file to You 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.apache.activemq.artemis.jms.client;
|
||||
|
||||
import static org.junit.Assert.assertEquals;
|
||||
import static org.junit.Assert.assertFalse;
|
||||
import static org.junit.Assert.assertNull;
|
||||
import static org.junit.Assert.assertTrue;
|
||||
|
||||
import org.junit.Test;
|
||||
|
||||
/**
|
||||
* Test Address queue parameters are correctly read.
|
||||
*/
|
||||
public class ActiveMQParameterTest {
|
||||
|
||||
@Test
|
||||
public void testQueueParameters() {
|
||||
ActiveMQDestination activeMQDestination = new ActiveMQQueue("jms.queue.foo?exclusive=true");
|
||||
assertTrue(activeMQDestination.getQueueAttributes().getExclusive());
|
||||
|
||||
assertEquals("jms.queue.foo", activeMQDestination.getAddress());
|
||||
|
||||
activeMQDestination = new ActiveMQQueue("jms.queue.foo?exclusive=false");
|
||||
assertFalse(activeMQDestination.getQueueAttributes().getExclusive());
|
||||
|
||||
activeMQDestination = new ActiveMQQueue("jms.queue.foo?last-value=true");
|
||||
assertTrue(activeMQDestination.getQueueAttributes().getLastValue());
|
||||
|
||||
activeMQDestination = new ActiveMQQueue("jms.queue.foo?last-value=false");
|
||||
assertFalse(activeMQDestination.getQueueAttributes().getLastValue());
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testMultipleQueueParameters() {
|
||||
ActiveMQDestination activeMQDestination = new ActiveMQQueue("jms.queue.foo?last-value=true&exclusive=true");
|
||||
assertEquals("jms.queue.foo", activeMQDestination.getAddress());
|
||||
assertTrue(activeMQDestination.getQueueAttributes().getLastValue());
|
||||
assertTrue(activeMQDestination.getQueueAttributes().getExclusive());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testNoQueueParameters() {
|
||||
ActiveMQDestination activeMQDestination = new ActiveMQQueue("jms.queue.foo");
|
||||
assertEquals("jms.queue.foo", activeMQDestination.getAddress());
|
||||
assertNull(activeMQDestination.getQueueAttributes());
|
||||
}
|
||||
}
|
|
@ -72,7 +72,7 @@ public class HornetQClientSessionContext extends ActiveMQSessionContext {
|
|||
public ClientSession.AddressQuery addressQuery(final SimpleString address) throws ActiveMQException {
|
||||
SessionBindingQueryResponseMessage response = (SessionBindingQueryResponseMessage) getSessionChannel().sendBlocking(new SessionBindingQueryMessage(address), PacketImpl.SESS_BINDINGQUERY_RESP);
|
||||
|
||||
return new AddressQueryImpl(response.isExists(), response.getQueueNames(), false, false, ActiveMQDefaultConfiguration.getDefaultPurgeOnNoConsumers(), ActiveMQDefaultConfiguration.getDefaultMaxQueueConsumers());
|
||||
return new AddressQueryImpl(response.isExists(), response.getQueueNames(), false, false, ActiveMQDefaultConfiguration.getDefaultPurgeOnNoConsumers(), ActiveMQDefaultConfiguration.getDefaultMaxQueueConsumers(), ActiveMQDefaultConfiguration.getDefaultExclusive(), ActiveMQDefaultConfiguration.getDefaultLastValue());
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
|
@ -35,6 +35,10 @@ public class CoreQueueConfiguration implements Serializable {
|
|||
|
||||
private String user = null;
|
||||
|
||||
private Boolean exclusive;
|
||||
|
||||
private Boolean lastValue;
|
||||
|
||||
private Integer maxConsumers = ActiveMQDefaultConfiguration.getDefaultMaxQueueConsumers();
|
||||
|
||||
private Boolean purgeOnNoConsumers = ActiveMQDefaultConfiguration.getDefaultPurgeOnNoConsumers();
|
||||
|
@ -64,6 +68,14 @@ public class CoreQueueConfiguration implements Serializable {
|
|||
return user;
|
||||
}
|
||||
|
||||
public Boolean isExclusive() {
|
||||
return exclusive;
|
||||
}
|
||||
|
||||
public Boolean isLastValue() {
|
||||
return lastValue;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param address the address to set
|
||||
*/
|
||||
|
@ -120,6 +132,16 @@ public class CoreQueueConfiguration implements Serializable {
|
|||
return this;
|
||||
}
|
||||
|
||||
public CoreQueueConfiguration setExclusive(Boolean exclusive) {
|
||||
this.exclusive = exclusive;
|
||||
return this;
|
||||
}
|
||||
|
||||
public CoreQueueConfiguration setLastValue(Boolean lastValue) {
|
||||
this.lastValue = lastValue;
|
||||
return this;
|
||||
}
|
||||
|
||||
public boolean getPurgeOnNoConsumers() {
|
||||
return purgeOnNoConsumers;
|
||||
}
|
||||
|
@ -147,6 +169,8 @@ public class CoreQueueConfiguration implements Serializable {
|
|||
result = prime * result + ((name == null) ? 0 : name.hashCode());
|
||||
result = prime * result + ((maxConsumers == null) ? 0 : maxConsumers.hashCode());
|
||||
result = prime * result + ((purgeOnNoConsumers == null) ? 0 : purgeOnNoConsumers.hashCode());
|
||||
result = prime * result + ((exclusive == null) ? 0 : exclusive.hashCode());
|
||||
result = prime * result + ((lastValue == null) ? 0 : lastValue.hashCode());
|
||||
return result;
|
||||
}
|
||||
|
||||
|
@ -187,6 +211,18 @@ public class CoreQueueConfiguration implements Serializable {
|
|||
} else if (!purgeOnNoConsumers.equals(other.purgeOnNoConsumers)) {
|
||||
return false;
|
||||
}
|
||||
if (exclusive == null) {
|
||||
if (other.exclusive != null)
|
||||
return false;
|
||||
} else if (!exclusive.equals(other.exclusive)) {
|
||||
return false;
|
||||
}
|
||||
if (lastValue == null) {
|
||||
if (other.lastValue != null)
|
||||
return false;
|
||||
} else if (!lastValue.equals(other.lastValue)) {
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -179,6 +179,10 @@ public final class FileConfigurationParser extends XMLConfigurationUtil {
|
|||
|
||||
private static final String LVQ_NODE_NAME = "last-value-queue";
|
||||
|
||||
private static final String DEFAULT_LVQ_NODE_NAME = "default-last-value-queue";
|
||||
|
||||
private static final String DEFAULT_EXCLUSIVE_NODE_NAME = "default-exclusive-queue";
|
||||
|
||||
private static final String REDISTRIBUTION_DELAY_NODE_NAME = "redistribution-delay";
|
||||
|
||||
private static final String SEND_TO_DLA_ON_NO_ROUTE = "send-to-dla-on-no-route";
|
||||
|
@ -989,8 +993,10 @@ public final class FileConfigurationParser extends XMLConfigurationUtil {
|
|||
Validators.ADDRESS_FULL_MESSAGE_POLICY_TYPE.validate(ADDRESS_FULL_MESSAGE_POLICY_NODE_NAME, value);
|
||||
AddressFullMessagePolicy policy = Enum.valueOf(AddressFullMessagePolicy.class, value);
|
||||
addressSettings.setAddressFullMessagePolicy(policy);
|
||||
} else if (LVQ_NODE_NAME.equalsIgnoreCase(name)) {
|
||||
addressSettings.setLastValueQueue(XMLUtil.parseBoolean(child));
|
||||
} else if (LVQ_NODE_NAME.equalsIgnoreCase(name) || DEFAULT_LVQ_NODE_NAME.equalsIgnoreCase(name)) {
|
||||
addressSettings.setDefaultLastValueQueue(XMLUtil.parseBoolean(child));
|
||||
} else if (DEFAULT_EXCLUSIVE_NODE_NAME.equalsIgnoreCase(name)) {
|
||||
addressSettings.setDefaultExclusiveQueue(XMLUtil.parseBoolean(child));
|
||||
} else if (MAX_DELIVERY_ATTEMPTS.equalsIgnoreCase(name)) {
|
||||
addressSettings.setMaxDeliveryAttempts(XMLUtil.parseInt(child));
|
||||
} else if (REDISTRIBUTION_DELAY_NODE_NAME.equalsIgnoreCase(name)) {
|
||||
|
@ -1090,6 +1096,8 @@ public final class FileConfigurationParser extends XMLConfigurationUtil {
|
|||
int maxConsumers = ActiveMQDefaultConfiguration.getDefaultMaxQueueConsumers();
|
||||
boolean purgeOnNoConsumers = ActiveMQDefaultConfiguration.getDefaultPurgeOnNoConsumers();
|
||||
String user = null;
|
||||
Boolean exclusive = null;
|
||||
Boolean lastValue = null;
|
||||
|
||||
NamedNodeMap attributes = node.getAttributes();
|
||||
for (int i = 0; i < attributes.getLength(); i++) {
|
||||
|
@ -1099,6 +1107,10 @@ public final class FileConfigurationParser extends XMLConfigurationUtil {
|
|||
Validators.MAX_QUEUE_CONSUMERS.validate(name, maxConsumers);
|
||||
} else if (item.getNodeName().equals("purge-on-no-consumers")) {
|
||||
purgeOnNoConsumers = Boolean.parseBoolean(item.getNodeValue());
|
||||
} else if (item.getNodeName().equals("exclusive")) {
|
||||
exclusive = Boolean.parseBoolean(item.getNodeValue());
|
||||
} else if (item.getNodeName().equals("last-value")) {
|
||||
lastValue = Boolean.parseBoolean(item.getNodeValue());
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1117,7 +1129,8 @@ public final class FileConfigurationParser extends XMLConfigurationUtil {
|
|||
}
|
||||
}
|
||||
|
||||
return new CoreQueueConfiguration().setAddress(address).setName(name).setFilterString(filterString).setDurable(durable).setMaxConsumers(maxConsumers).setPurgeOnNoConsumers(purgeOnNoConsumers).setUser(user);
|
||||
return new CoreQueueConfiguration().setAddress(address).setName(name).setFilterString(filterString).setDurable(durable).setMaxConsumers(maxConsumers).setPurgeOnNoConsumers(purgeOnNoConsumers).setUser(user)
|
||||
.setExclusive(exclusive).setLastValue(lastValue);
|
||||
}
|
||||
|
||||
protected CoreAddressConfiguration parseAddressConfiguration(final Node node) {
|
||||
|
|
|
@ -823,12 +823,21 @@ public class ActiveMQServerControlImpl extends AbstractControl implements Active
|
|||
String routingType,
|
||||
Integer maxConsumers,
|
||||
Boolean purgeOnNoConsumers) throws Exception {
|
||||
return updateQueue(name, routingType, maxConsumers, purgeOnNoConsumers, null);
|
||||
}
|
||||
|
||||
@Override
|
||||
public String updateQueue(String name,
|
||||
String routingType,
|
||||
Integer maxConsumers,
|
||||
Boolean purgeOnNoConsumers,
|
||||
Boolean exclusive) throws Exception {
|
||||
checkStarted();
|
||||
|
||||
clearIO();
|
||||
|
||||
try {
|
||||
final Queue queue = server.updateQueue(name, routingType != null ? RoutingType.valueOf(routingType) : null, maxConsumers, purgeOnNoConsumers);
|
||||
final Queue queue = server.updateQueue(name, routingType != null ? RoutingType.valueOf(routingType) : null, maxConsumers, purgeOnNoConsumers, exclusive);
|
||||
if (queue == null) {
|
||||
throw ActiveMQMessageBundle.BUNDLE.noSuchQueue(new SimpleString(name));
|
||||
}
|
||||
|
@ -2077,7 +2086,7 @@ public class ActiveMQServerControlImpl extends AbstractControl implements Active
|
|||
.add("redeliveryMultiplier", addressSettings.getRedeliveryMultiplier())
|
||||
.add("maxRedeliveryDelay", addressSettings.getMaxRedeliveryDelay())
|
||||
.add("redistributionDelay", addressSettings.getRedistributionDelay())
|
||||
.add("lastValueQueue", addressSettings.isLastValueQueue())
|
||||
.add("lastValueQueue", addressSettings.isDefaultLastValueQueue())
|
||||
.add("sendToDLAOnNoRoute", addressSettings.isSendToDLAOnNoRoute())
|
||||
.add("addressFullMessagePolicy", policy)
|
||||
.add("slowConsumerThreshold", addressSettings.getSlowConsumerThreshold())
|
||||
|
@ -2163,7 +2172,7 @@ public class ActiveMQServerControlImpl extends AbstractControl implements Active
|
|||
addressSettings.setDeadLetterAddress(DLA == null ? null : new SimpleString(DLA));
|
||||
addressSettings.setExpiryAddress(expiryAddress == null ? null : new SimpleString(expiryAddress));
|
||||
addressSettings.setExpiryDelay(expiryDelay);
|
||||
addressSettings.setLastValueQueue(lastValueQueue);
|
||||
addressSettings.setDefaultLastValueQueue(lastValueQueue);
|
||||
addressSettings.setMaxDeliveryAttempts(deliveryAttempts);
|
||||
addressSettings.setPageCacheMaxSize(pageMaxCacheSize);
|
||||
addressSettings.setMaxSizeBytes(maxSizeBytes);
|
||||
|
|
|
@ -381,6 +381,30 @@ public class QueueControlImpl extends AbstractControl implements QueueControl {
|
|||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isExclusive() {
|
||||
checkStarted();
|
||||
|
||||
clearIO();
|
||||
try {
|
||||
return queue.isExclusive();
|
||||
} finally {
|
||||
blockOnIO();
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isLastValue() {
|
||||
checkStarted();
|
||||
|
||||
clearIO();
|
||||
try {
|
||||
return queue.isLastValue();
|
||||
} finally {
|
||||
blockOnIO();
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<String, Object>[] listScheduledMessages() throws Exception {
|
||||
checkStarted();
|
||||
|
|
|
@ -60,7 +60,9 @@ public class QueueView extends ActiveMQAbstractView<QueueControl> {
|
|||
.add("messagesAcked", toString(queue.getMessagesAcknowledged()))
|
||||
.add("deliveringCount", toString(queue.getDeliveringCount()))
|
||||
.add("messagesKilled", toString(queue.getMessagesKilled()))
|
||||
.add("deliverDeliver", toString(q.isDirectDeliver()));
|
||||
.add("deliverDeliver", toString(q.isDirectDeliver()))
|
||||
.add("exclusive", toString(queue.isExclusive()))
|
||||
.add("lastValue", toString(queue.isLastValue()));
|
||||
return obj;
|
||||
}
|
||||
|
||||
|
@ -108,6 +110,10 @@ public class QueueView extends ActiveMQAbstractView<QueueControl> {
|
|||
return queue.getMessagesKilled();
|
||||
case "deliverDeliver":
|
||||
return q.isDirectDeliver();
|
||||
case "exclusive":
|
||||
return q.isExclusive();
|
||||
case "lastValue":
|
||||
return q.isLastValue();
|
||||
default:
|
||||
throw new IllegalArgumentException("Unsupported field, " + fieldName);
|
||||
}
|
||||
|
|
|
@ -27,7 +27,7 @@ public class QueueFilterPredicate extends ActiveMQFilterPredicate<QueueControl>
|
|||
enum Field {
|
||||
ID, NAME, CONSUMER_ID, QUEUE, ADDRESS, MAX_CONSUMERS, FILTER, MESSAGE_COUNT, CONSUMER_COUNT, DELIVERING_COUNT,
|
||||
MESSAGES_ADDED, MESSAGES_ACKED, RATE, ROUTING_TYPE, USER, AUTO_CREATED, DURABLE, PAUSED, TEMPORARY,
|
||||
PURGE_ON_NO_CONSUMERS, MESSAGES_KILLED, DIRECT_DELIVER
|
||||
PURGE_ON_NO_CONSUMERS, MESSAGES_KILLED, DIRECT_DELIVER, LAST_VALUE, EXCLUSIVE
|
||||
}
|
||||
|
||||
private Field f;
|
||||
|
@ -89,6 +89,10 @@ public class QueueFilterPredicate extends ActiveMQFilterPredicate<QueueControl>
|
|||
return matches(queue.isPurgeOnNoConsumers());
|
||||
case MESSAGES_KILLED:
|
||||
return matches(queue.getMessagesKilled());
|
||||
case EXCLUSIVE:
|
||||
return matches(queue.isExclusive());
|
||||
case LAST_VALUE:
|
||||
return matches(queue.isLastValue());
|
||||
default:
|
||||
return true;
|
||||
}
|
||||
|
|
|
@ -54,6 +54,10 @@ public interface QueueBindingInfo {
|
|||
|
||||
void setPurgeOnNoConsumers(boolean purgeOnNoConsumers);
|
||||
|
||||
boolean isExclusive();
|
||||
|
||||
void setExclusive(boolean exclusive);
|
||||
|
||||
byte getRoutingType();
|
||||
|
||||
void setRoutingType(byte routingType);
|
||||
|
|
|
@ -1272,7 +1272,7 @@ public abstract class AbstractJournalStorageManager extends CriticalComponentImp
|
|||
|
||||
SimpleString filterString = filter == null ? null : filter.getFilterString();
|
||||
|
||||
PersistentQueueBindingEncoding bindingEncoding = new PersistentQueueBindingEncoding(queue.getName(), binding.getAddress(), filterString, queue.getUser(), queue.isAutoCreated(), queue.getMaxConsumers(), queue.isPurgeOnNoConsumers(), queue.getRoutingType().getType());
|
||||
PersistentQueueBindingEncoding bindingEncoding = new PersistentQueueBindingEncoding(queue.getName(), binding.getAddress(), filterString, queue.getUser(), queue.isAutoCreated(), queue.getMaxConsumers(), queue.isPurgeOnNoConsumers(), queue.isExclusive(), queue.getRoutingType().getType());
|
||||
|
||||
readLock();
|
||||
try {
|
||||
|
|
|
@ -46,6 +46,8 @@ public class PersistentQueueBindingEncoding implements EncodingSupport, QueueBin
|
|||
|
||||
public boolean purgeOnNoConsumers;
|
||||
|
||||
public boolean exclusive;
|
||||
|
||||
public byte routingType;
|
||||
|
||||
public PersistentQueueBindingEncoding() {
|
||||
|
@ -68,6 +70,8 @@ public class PersistentQueueBindingEncoding implements EncodingSupport, QueueBin
|
|||
maxConsumers +
|
||||
", purgeOnNoConsumers=" +
|
||||
purgeOnNoConsumers +
|
||||
", exclusive=" +
|
||||
exclusive +
|
||||
", routingType=" +
|
||||
routingType +
|
||||
"]";
|
||||
|
@ -80,6 +84,7 @@ public class PersistentQueueBindingEncoding implements EncodingSupport, QueueBin
|
|||
final boolean autoCreated,
|
||||
final int maxConsumers,
|
||||
final boolean purgeOnNoConsumers,
|
||||
final boolean exclusive,
|
||||
final byte routingType) {
|
||||
this.name = name;
|
||||
this.address = address;
|
||||
|
@ -88,6 +93,7 @@ public class PersistentQueueBindingEncoding implements EncodingSupport, QueueBin
|
|||
this.autoCreated = autoCreated;
|
||||
this.maxConsumers = maxConsumers;
|
||||
this.purgeOnNoConsumers = purgeOnNoConsumers;
|
||||
this.exclusive = exclusive;
|
||||
this.routingType = routingType;
|
||||
}
|
||||
|
||||
|
@ -163,6 +169,16 @@ public class PersistentQueueBindingEncoding implements EncodingSupport, QueueBin
|
|||
this.purgeOnNoConsumers = purgeOnNoConsumers;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isExclusive() {
|
||||
return exclusive;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setExclusive(boolean exclusive) {
|
||||
this.exclusive = exclusive;
|
||||
}
|
||||
|
||||
@Override
|
||||
public byte getRoutingType() {
|
||||
return routingType;
|
||||
|
@ -203,6 +219,12 @@ public class PersistentQueueBindingEncoding implements EncodingSupport, QueueBin
|
|||
purgeOnNoConsumers = ActiveMQDefaultConfiguration.getDefaultPurgeOnNoConsumers();
|
||||
routingType = ActiveMQDefaultConfiguration.getDefaultRoutingType().getType();
|
||||
}
|
||||
|
||||
if (buffer.readableBytes() > 0) {
|
||||
exclusive = buffer.readBoolean();
|
||||
} else {
|
||||
exclusive = ActiveMQDefaultConfiguration.getDefaultExclusive();
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -215,6 +237,7 @@ public class PersistentQueueBindingEncoding implements EncodingSupport, QueueBin
|
|||
buffer.writeInt(maxConsumers);
|
||||
buffer.writeBoolean(purgeOnNoConsumers);
|
||||
buffer.writeByte(routingType);
|
||||
buffer.writeBoolean(exclusive);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -224,7 +247,8 @@ public class PersistentQueueBindingEncoding implements EncodingSupport, QueueBin
|
|||
SimpleString.sizeofNullableString(createMetadata()) +
|
||||
DataConstants.SIZE_INT +
|
||||
DataConstants.SIZE_BOOLEAN +
|
||||
DataConstants.SIZE_BYTE;
|
||||
DataConstants.SIZE_BYTE +
|
||||
DataConstants.SIZE_BOOLEAN;
|
||||
}
|
||||
|
||||
private SimpleString createMetadata() {
|
||||
|
|
|
@ -64,7 +64,8 @@ public interface PostOffice extends ActiveMQComponent {
|
|||
QueueBinding updateQueue(SimpleString name,
|
||||
RoutingType routingType,
|
||||
Integer maxConsumers,
|
||||
Boolean purgeOnNoConsumers) throws Exception;
|
||||
Boolean purgeOnNoConsumers,
|
||||
Boolean exclusive) throws Exception;
|
||||
|
||||
List<Queue> listQueuesForAddress(SimpleString address) throws Exception;
|
||||
|
||||
|
|
|
@ -464,7 +464,8 @@ public class PostOfficeImpl implements PostOffice, NotificationListener, Binding
|
|||
public QueueBinding updateQueue(SimpleString name,
|
||||
RoutingType routingType,
|
||||
Integer maxConsumers,
|
||||
Boolean purgeOnNoConsumers) throws Exception {
|
||||
Boolean purgeOnNoConsumers,
|
||||
Boolean exclusive) throws Exception {
|
||||
synchronized (addressLock) {
|
||||
final QueueBinding queueBinding = (QueueBinding) addressManager.getBinding(name);
|
||||
if (queueBinding == null) {
|
||||
|
@ -504,6 +505,10 @@ public class PostOfficeImpl implements PostOffice, NotificationListener, Binding
|
|||
changed = true;
|
||||
queue.setPurgeOnNoConsumers(purgeOnNoConsumers);
|
||||
}
|
||||
if (exclusive != null && queue.isExclusive() != exclusive.booleanValue()) {
|
||||
changed = true;
|
||||
queue.setExclusive(exclusive);
|
||||
}
|
||||
|
||||
if (changed) {
|
||||
final long txID = storageManager.generateID();
|
||||
|
|
|
@ -353,7 +353,7 @@ public class ServerSessionPacketHandler implements ChannelHandler {
|
|||
CreateQueueMessage_V2 request = (CreateQueueMessage_V2) packet;
|
||||
requiresResponse = request.isRequiresResponse();
|
||||
session.createQueue(request.getAddress(), request.getQueueName(), request.getRoutingType(), request.getFilterString(), request.isTemporary(), request.isDurable(), request.getMaxConsumers(), request.isPurgeOnNoConsumers(),
|
||||
request.isAutoCreated());
|
||||
request.isExclusive(), request.isLastValue(), request.isAutoCreated());
|
||||
if (requiresResponse) {
|
||||
response = new NullResponseMessage();
|
||||
}
|
||||
|
@ -371,7 +371,7 @@ public class ServerSessionPacketHandler implements ChannelHandler {
|
|||
case CREATE_SHARED_QUEUE_V2: {
|
||||
CreateSharedQueueMessage_V2 request = (CreateSharedQueueMessage_V2) packet;
|
||||
requiresResponse = request.isRequiresResponse();
|
||||
session.createSharedQueue(request.getAddress(), request.getQueueName(), request.getRoutingType(), request.isDurable(), request.getFilterString());
|
||||
session.createSharedQueue(request.getAddress(), request.getQueueName(), request.getRoutingType(), request.getFilterString(), request.isDurable(), request.getMaxConsumers(), request.isPurgeOnNoConsumers(), request.isExclusive(), request.isLastValue());
|
||||
if (requiresResponse) {
|
||||
response = new NullResponseMessage();
|
||||
}
|
||||
|
@ -417,13 +417,13 @@ public class ServerSessionPacketHandler implements ChannelHandler {
|
|||
if (!queueNames.isEmpty()) {
|
||||
final List<SimpleString> convertedQueueNames = request.convertQueueNames(clientVersion, queueNames);
|
||||
if (convertedQueueNames != queueNames) {
|
||||
result = new BindingQueryResult(result.isExists(), result.getAddressInfo(), convertedQueueNames, result.isAutoCreateQueues(), result.isAutoCreateAddresses(), result.isDefaultPurgeOnNoConsumers(), result.getDefaultMaxConsumers());
|
||||
result = new BindingQueryResult(result.isExists(), result.getAddressInfo(), convertedQueueNames, result.isAutoCreateQueues(), result.isAutoCreateAddresses(), result.isDefaultPurgeOnNoConsumers(), result.getDefaultMaxConsumers(), result.isDefaultExclusive(), result.isDefaultLastValue());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (channel.supports(PacketImpl.SESS_BINDINGQUERY_RESP_V4)) {
|
||||
response = new SessionBindingQueryResponseMessage_V4(result.isExists(), result.getQueueNames(), result.isAutoCreateQueues(), result.isAutoCreateAddresses(), result.isDefaultPurgeOnNoConsumers(), result.getDefaultMaxConsumers());
|
||||
response = new SessionBindingQueryResponseMessage_V4(result.isExists(), result.getQueueNames(), result.isAutoCreateQueues(), result.isAutoCreateAddresses(), result.isDefaultPurgeOnNoConsumers(), result.getDefaultMaxConsumers(), result.isDefaultExclusive(), result.isDefaultLastValue());
|
||||
} else if (channel.supports(PacketImpl.SESS_BINDINGQUERY_RESP_V3)) {
|
||||
response = new SessionBindingQueryResponseMessage_V3(result.isExists(), result.getQueueNames(), result.isAutoCreateQueues(), result.isAutoCreateAddresses());
|
||||
} else if (channel.supports(PacketImpl.SESS_BINDINGQUERY_RESP_V2)) {
|
||||
|
|
|
@ -333,6 +333,9 @@ public interface ActiveMQServer extends ServiceComponent {
|
|||
void createSharedQueue(SimpleString address, RoutingType routingType, SimpleString name, SimpleString filterString,
|
||||
SimpleString user, boolean durable) throws Exception;
|
||||
|
||||
void createSharedQueue(SimpleString address, RoutingType routingType, SimpleString name, SimpleString filterString,
|
||||
SimpleString user, boolean durable, int maxConsumers, boolean purgeOnNoConsumers, boolean exclusive, boolean lastValue) throws Exception;
|
||||
|
||||
Queue createQueue(SimpleString address, RoutingType routingType, SimpleString queueName, SimpleString filter,
|
||||
boolean durable, boolean temporary) throws Exception;
|
||||
|
||||
|
@ -351,10 +354,18 @@ public interface ActiveMQServer extends ServiceComponent {
|
|||
SimpleString user, boolean durable, boolean temporary, boolean autoCreated, Integer maxConsumers,
|
||||
Boolean purgeOnNoConsumers, boolean autoCreateAddress) throws Exception;
|
||||
|
||||
Queue createQueue(AddressInfo addressInfo, SimpleString queueName, SimpleString filter,
|
||||
SimpleString user, boolean durable, boolean temporary, boolean autoCreated, Integer maxConsumers,
|
||||
Boolean purgeOnNoConsumers, Boolean exclusive, Boolean lastValue, boolean autoCreateAddress) throws Exception;
|
||||
|
||||
Queue createQueue(SimpleString address, RoutingType routingType, SimpleString queueName, SimpleString filter,
|
||||
SimpleString user, boolean durable, boolean temporary, boolean ignoreIfExists, boolean transientQueue,
|
||||
boolean autoCreated, int maxConsumers, boolean purgeOnNoConsumers, boolean autoCreateAddress) throws Exception;
|
||||
|
||||
Queue createQueue(SimpleString address, RoutingType routingType, SimpleString queueName, SimpleString filter,
|
||||
SimpleString user, boolean durable, boolean temporary, boolean ignoreIfExists, boolean transientQueue,
|
||||
boolean autoCreated, int maxConsumers, boolean purgeOnNoConsumers, boolean exclusive, boolean lastValue, boolean autoCreateAddress) throws Exception;
|
||||
|
||||
@Deprecated
|
||||
Queue createQueue(SimpleString address, SimpleString queueName, SimpleString filter, boolean durable, boolean temporary) throws Exception;
|
||||
|
||||
|
@ -426,6 +437,12 @@ public interface ActiveMQServer extends ServiceComponent {
|
|||
Integer maxConsumers,
|
||||
Boolean purgeOnNoConsumers) throws Exception;
|
||||
|
||||
Queue updateQueue(String name,
|
||||
RoutingType routingType,
|
||||
Integer maxConsumers,
|
||||
Boolean purgeOnNoConsumers,
|
||||
Boolean exclusive) throws Exception;
|
||||
|
||||
/*
|
||||
* add a ProtocolManagerFactory to be used. Note if @see Configuration#isResolveProtocols is tur then this factory will
|
||||
* replace any factories with the same protocol
|
||||
|
|
|
@ -37,13 +37,19 @@ public class BindingQueryResult {
|
|||
|
||||
private final AddressInfo addressInfo;
|
||||
|
||||
private boolean defaultExclusive;
|
||||
|
||||
private boolean defaultLastValue;
|
||||
|
||||
public BindingQueryResult(final boolean exists,
|
||||
final AddressInfo addressInfo,
|
||||
final List<SimpleString> queueNames,
|
||||
final boolean autoCreateQueues,
|
||||
final boolean autoCreateAddresses,
|
||||
final boolean defaultPurgeOnNoConsumers,
|
||||
final int defaultMaxConsumers) {
|
||||
final int defaultMaxConsumers,
|
||||
final boolean defaultExclusive,
|
||||
final boolean defaultLastValue) {
|
||||
this.addressInfo = addressInfo;
|
||||
|
||||
this.exists = exists;
|
||||
|
@ -57,6 +63,10 @@ public class BindingQueryResult {
|
|||
this.defaultPurgeOnNoConsumers = defaultPurgeOnNoConsumers;
|
||||
|
||||
this.defaultMaxConsumers = defaultMaxConsumers;
|
||||
|
||||
this.defaultExclusive = defaultExclusive;
|
||||
|
||||
this.defaultLastValue = defaultLastValue;
|
||||
}
|
||||
|
||||
public boolean isExists() {
|
||||
|
@ -86,4 +96,12 @@ public class BindingQueryResult {
|
|||
public int getDefaultMaxConsumers() {
|
||||
return defaultMaxConsumers;
|
||||
}
|
||||
|
||||
public boolean isDefaultExclusive() {
|
||||
return defaultExclusive;
|
||||
}
|
||||
|
||||
public boolean isDefaultLastValue() {
|
||||
return defaultLastValue;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -68,6 +68,12 @@ public interface Queue extends Bindable,CriticalComponent {
|
|||
|
||||
void setPurgeOnNoConsumers(boolean value);
|
||||
|
||||
boolean isExclusive();
|
||||
|
||||
void setExclusive(boolean value);
|
||||
|
||||
boolean isLastValue();
|
||||
|
||||
int getMaxConsumers();
|
||||
|
||||
void setMaxConsumer(int maxConsumers);
|
||||
|
|
|
@ -37,6 +37,8 @@ public final class QueueConfig {
|
|||
private final boolean autoCreated;
|
||||
private final RoutingType routingType;
|
||||
private final int maxConsumers;
|
||||
private final boolean exclusive;
|
||||
private final boolean lastValue;
|
||||
private final boolean purgeOnNoConsumers;
|
||||
|
||||
public static final class Builder {
|
||||
|
@ -52,6 +54,8 @@ public final class QueueConfig {
|
|||
private boolean autoCreated;
|
||||
private RoutingType routingType;
|
||||
private int maxConsumers;
|
||||
private boolean exclusive;
|
||||
private boolean lastValue;
|
||||
private boolean purgeOnNoConsumers;
|
||||
|
||||
private Builder(final long id, final SimpleString name) {
|
||||
|
@ -70,6 +74,8 @@ public final class QueueConfig {
|
|||
this.autoCreated = true;
|
||||
this.routingType = ActiveMQDefaultConfiguration.getDefaultRoutingType();
|
||||
this.maxConsumers = ActiveMQDefaultConfiguration.getDefaultMaxQueueConsumers();
|
||||
this.exclusive = ActiveMQDefaultConfiguration.getDefaultExclusive();
|
||||
this.lastValue = ActiveMQDefaultConfiguration.getDefaultLastValue();
|
||||
this.purgeOnNoConsumers = ActiveMQDefaultConfiguration.getDefaultPurgeOnNoConsumers();
|
||||
validateState();
|
||||
}
|
||||
|
@ -122,6 +128,17 @@ public final class QueueConfig {
|
|||
return this;
|
||||
}
|
||||
|
||||
public Builder exclusive(final boolean exclusive) {
|
||||
this.exclusive = exclusive;
|
||||
return this;
|
||||
}
|
||||
|
||||
public Builder lastValue(final boolean lastValue) {
|
||||
this.lastValue = lastValue;
|
||||
return this;
|
||||
}
|
||||
|
||||
|
||||
public Builder purgeOnNoConsumers(final boolean purgeOnNoConsumers) {
|
||||
this.purgeOnNoConsumers = purgeOnNoConsumers;
|
||||
return this;
|
||||
|
@ -153,7 +170,7 @@ public final class QueueConfig {
|
|||
} else {
|
||||
pageSubscription = null;
|
||||
}
|
||||
return new QueueConfig(id, address, name, filter, pageSubscription, user, durable, temporary, autoCreated, routingType, maxConsumers, purgeOnNoConsumers);
|
||||
return new QueueConfig(id, address, name, filter, pageSubscription, user, durable, temporary, autoCreated, routingType, maxConsumers, exclusive, lastValue, purgeOnNoConsumers);
|
||||
}
|
||||
|
||||
}
|
||||
|
@ -197,6 +214,8 @@ public final class QueueConfig {
|
|||
final boolean autoCreated,
|
||||
final RoutingType routingType,
|
||||
final int maxConsumers,
|
||||
final boolean exclusive,
|
||||
final boolean lastValue,
|
||||
final boolean purgeOnNoConsumers) {
|
||||
this.id = id;
|
||||
this.address = address;
|
||||
|
@ -209,6 +228,8 @@ public final class QueueConfig {
|
|||
this.autoCreated = autoCreated;
|
||||
this.routingType = routingType;
|
||||
this.purgeOnNoConsumers = purgeOnNoConsumers;
|
||||
this.exclusive = exclusive;
|
||||
this.lastValue = lastValue;
|
||||
this.maxConsumers = maxConsumers;
|
||||
}
|
||||
|
||||
|
@ -256,6 +277,14 @@ public final class QueueConfig {
|
|||
return maxConsumers;
|
||||
}
|
||||
|
||||
public boolean isExclusive() {
|
||||
return exclusive;
|
||||
}
|
||||
|
||||
public boolean isLastValue() {
|
||||
return lastValue;
|
||||
}
|
||||
|
||||
public RoutingType deliveryMode() {
|
||||
return routingType;
|
||||
}
|
||||
|
@ -289,6 +318,10 @@ public final class QueueConfig {
|
|||
return false;
|
||||
if (maxConsumers != that.maxConsumers)
|
||||
return false;
|
||||
if (exclusive != that.exclusive)
|
||||
return false;
|
||||
if (lastValue != that.lastValue)
|
||||
return false;
|
||||
if (purgeOnNoConsumers != that.purgeOnNoConsumers)
|
||||
return false;
|
||||
return user != null ? user.equals(that.user) : that.user == null;
|
||||
|
@ -308,6 +341,8 @@ public final class QueueConfig {
|
|||
result = 31 * result + (autoCreated ? 1 : 0);
|
||||
result = 31 * result + routingType.getType();
|
||||
result = 31 * result + maxConsumers;
|
||||
result = 31 * result + (exclusive ? 1 : 0);
|
||||
result = 31 * result + (lastValue ? 1 : 0);
|
||||
result = 31 * result + (purgeOnNoConsumers ? 1 : 0);
|
||||
return result;
|
||||
}
|
||||
|
@ -326,6 +361,8 @@ public final class QueueConfig {
|
|||
+ ", autoCreated=" + autoCreated
|
||||
+ ", routingType=" + routingType
|
||||
+ ", maxConsumers=" + maxConsumers
|
||||
+ ", exclusive=" + exclusive
|
||||
+ ", lastValue=" + lastValue
|
||||
+ ", purgeOnNoConsumers=" + purgeOnNoConsumers + '}';
|
||||
}
|
||||
}
|
||||
|
|
|
@ -149,6 +149,18 @@ public interface ServerSession extends SecurityAuth {
|
|||
boolean purgeOnNoConsumers,
|
||||
boolean autoCreated) throws Exception;
|
||||
|
||||
Queue createQueue(SimpleString address,
|
||||
SimpleString name,
|
||||
RoutingType routingType,
|
||||
SimpleString filterString,
|
||||
boolean temporary,
|
||||
boolean durable,
|
||||
int maxConsumers,
|
||||
boolean purgeOnNoConsumers,
|
||||
Boolean exclusive,
|
||||
Boolean lastValue,
|
||||
boolean autoCreated) throws Exception;
|
||||
|
||||
Queue createQueue(SimpleString address,
|
||||
SimpleString name,
|
||||
RoutingType routingType,
|
||||
|
@ -164,6 +176,15 @@ public interface ServerSession extends SecurityAuth {
|
|||
boolean durable,
|
||||
boolean autoCreated) throws Exception;
|
||||
|
||||
Queue createQueue(AddressInfo addressInfo,
|
||||
SimpleString name,
|
||||
SimpleString filterString,
|
||||
boolean temporary,
|
||||
boolean durable,
|
||||
Boolean exclusive,
|
||||
Boolean lastValue,
|
||||
boolean autoCreated) throws Exception;
|
||||
|
||||
AddressInfo createAddress(SimpleString address,
|
||||
EnumSet<RoutingType> routingTypes,
|
||||
boolean autoCreated) throws Exception;
|
||||
|
@ -253,6 +274,16 @@ public interface ServerSession extends SecurityAuth {
|
|||
|
||||
boolean isClosed();
|
||||
|
||||
void createSharedQueue(SimpleString address,
|
||||
SimpleString name,
|
||||
RoutingType routingType,
|
||||
SimpleString filterString,
|
||||
boolean durable,
|
||||
Integer maxConsumers,
|
||||
Boolean purgeOnNoConsumers,
|
||||
Boolean exclusive,
|
||||
Boolean lastValue) throws Exception;
|
||||
|
||||
void createSharedQueue(SimpleString address,
|
||||
SimpleString name,
|
||||
RoutingType routingType,
|
||||
|
|
|
@ -825,6 +825,8 @@ public class ActiveMQServerImpl implements ActiveMQServer {
|
|||
boolean autoCreateAddresses = addressSettings.isAutoCreateAddresses();
|
||||
boolean defaultPurgeOnNoConsumers = addressSettings.isDefaultPurgeOnNoConsumers();
|
||||
int defaultMaxConsumers = addressSettings.getDefaultMaxConsumers();
|
||||
boolean defaultExclusive = addressSettings.isDefaultExclusiveQueue();
|
||||
boolean defaultLastValie = addressSettings.isDefaultLastValueQueue();
|
||||
|
||||
List<SimpleString> names = new ArrayList<>();
|
||||
|
||||
|
@ -833,7 +835,7 @@ public class ActiveMQServerImpl implements ActiveMQServer {
|
|||
SimpleString bindAddress = new SimpleString(realAddress);
|
||||
if (managementService != null) {
|
||||
if (bindAddress.equals(managementService.getManagementAddress())) {
|
||||
return new BindingQueryResult(true, null, names, autoCreateQeueus, autoCreateAddresses, defaultPurgeOnNoConsumers, defaultMaxConsumers);
|
||||
return new BindingQueryResult(true, null, names, autoCreateQeueus, autoCreateAddresses, defaultPurgeOnNoConsumers, defaultMaxConsumers, defaultExclusive, defaultLastValie);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -851,7 +853,7 @@ public class ActiveMQServerImpl implements ActiveMQServer {
|
|||
|
||||
AddressInfo info = getAddressInfo(bindAddress);
|
||||
|
||||
return new BindingQueryResult(info != null, info, names, autoCreateQeueus, autoCreateAddresses, defaultPurgeOnNoConsumers, defaultMaxConsumers);
|
||||
return new BindingQueryResult(info != null, info, names, autoCreateQeueus, autoCreateAddresses, defaultPurgeOnNoConsumers, defaultMaxConsumers, defaultExclusive, defaultLastValie);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -863,6 +865,8 @@ public class ActiveMQServerImpl implements ActiveMQServer {
|
|||
boolean autoCreateQueues = getAddressSettingsRepository().getMatch(name.toString()).isAutoCreateQueues();
|
||||
boolean defaultPurgeOnNoConsumers = getAddressSettingsRepository().getMatch(name.toString()).isDefaultPurgeOnNoConsumers();
|
||||
int defaultMaxConsumers = getAddressSettingsRepository().getMatch(name.toString()).getDefaultMaxConsumers();
|
||||
boolean defaultExclusiveQueue = getAddressSettingsRepository().getMatch(name.toString()).isDefaultExclusiveQueue();
|
||||
boolean defaultLastValueQueue = getAddressSettingsRepository().getMatch(name.toString()).isDefaultLastValueQueue();
|
||||
|
||||
QueueQueryResult response;
|
||||
|
||||
|
@ -877,14 +881,14 @@ public class ActiveMQServerImpl implements ActiveMQServer {
|
|||
|
||||
SimpleString filterString = filter == null ? null : filter.getFilterString();
|
||||
|
||||
response = new QueueQueryResult(name, binding.getAddress(), queue.isDurable(), queue.isTemporary(), filterString, queue.getConsumerCount(), queue.getMessageCount(), autoCreateQueues, true, queue.isAutoCreated(), queue.isPurgeOnNoConsumers(), queue.getRoutingType(), queue.getMaxConsumers());
|
||||
response = new QueueQueryResult(name, binding.getAddress(), queue.isDurable(), queue.isTemporary(), filterString, queue.getConsumerCount(), queue.getMessageCount(), autoCreateQueues, true, queue.isAutoCreated(), queue.isPurgeOnNoConsumers(), queue.getRoutingType(), queue.getMaxConsumers(), queue.isExclusive(), queue.isLastValue());
|
||||
} else if (name.equals(managementAddress)) {
|
||||
// make an exception for the management address (see HORNETQ-29)
|
||||
response = new QueueQueryResult(name, managementAddress, true, false, null, -1, -1, autoCreateQueues, true, false, false, RoutingType.MULTICAST, -1);
|
||||
response = new QueueQueryResult(name, managementAddress, true, false, null, -1, -1, autoCreateQueues, true, false, false, RoutingType.MULTICAST, -1, false, false);
|
||||
} else if (autoCreateQueues) {
|
||||
response = new QueueQueryResult(name, name, true, false, null, 0, 0, true, false, false, defaultPurgeOnNoConsumers, RoutingType.MULTICAST, defaultMaxConsumers);
|
||||
response = new QueueQueryResult(name, name, true, false, null, 0, 0, true, false, false, defaultPurgeOnNoConsumers, RoutingType.MULTICAST, defaultMaxConsumers, defaultExclusiveQueue, defaultLastValueQueue);
|
||||
} else {
|
||||
response = new QueueQueryResult(null, null, false, false, null, 0, 0, false, false, false, false, RoutingType.MULTICAST, 0);
|
||||
response = new QueueQueryResult(null, null, false, false, null, 0, 0, false, false, false, false, RoutingType.MULTICAST, 0, null, null);
|
||||
}
|
||||
|
||||
return response;
|
||||
|
@ -1672,9 +1676,25 @@ public class ActiveMQServerImpl implements ActiveMQServer {
|
|||
|
||||
@Override
|
||||
public Queue createQueue(AddressInfo addressInfo, SimpleString queueName, SimpleString filter, SimpleString user, boolean durable, boolean temporary, boolean autoCreated, Integer maxConsumers, Boolean purgeOnNoConsumers, boolean autoCreateAddress) throws Exception {
|
||||
return createQueue(addressInfo, queueName, filter, user, durable, temporary, false, false, autoCreated, maxConsumers, purgeOnNoConsumers, autoCreateAddress);
|
||||
AddressSettings as = getAddressSettingsRepository().getMatch(addressInfo == null ? queueName.toString() : addressInfo.getName().toString());
|
||||
return createQueue(addressInfo, queueName, filter, user, durable, temporary, false, false, autoCreated, maxConsumers, purgeOnNoConsumers, as.isDefaultExclusiveQueue(), as.isDefaultLastValueQueue(), autoCreateAddress);
|
||||
}
|
||||
|
||||
@Override
|
||||
public Queue createQueue(AddressInfo addressInfo, SimpleString queueName, SimpleString filter, SimpleString user, boolean durable, boolean temporary, boolean autoCreated, Integer maxConsumers, Boolean purgeOnNoConsumers, Boolean exclusive, Boolean lastValue, boolean autoCreateAddress) throws Exception {
|
||||
return createQueue(addressInfo, queueName, filter, user, durable, temporary, false, false, autoCreated, maxConsumers, purgeOnNoConsumers, exclusive, lastValue, autoCreateAddress);
|
||||
}
|
||||
|
||||
|
||||
@Override
|
||||
public Queue createQueue(SimpleString address, RoutingType routingType, SimpleString queueName, SimpleString filter,
|
||||
SimpleString user, boolean durable, boolean temporary, boolean ignoreIfExists, boolean transientQueue,
|
||||
boolean autoCreated, int maxConsumers, boolean purgeOnNoConsumers, boolean autoCreateAddress) throws Exception {
|
||||
AddressSettings as = getAddressSettingsRepository().getMatch(address == null ? queueName.toString() : address.toString());
|
||||
return createQueue(address, routingType, queueName, filter, user, durable, temporary, ignoreIfExists, transientQueue, autoCreated, maxConsumers, purgeOnNoConsumers, as.isDefaultExclusiveQueue(), as.isDefaultLastValueQueue(), autoCreateAddress);
|
||||
}
|
||||
|
||||
|
||||
@Deprecated
|
||||
@Override
|
||||
public Queue createQueue(final SimpleString address,
|
||||
|
@ -1692,6 +1712,21 @@ public class ActiveMQServerImpl implements ActiveMQServer {
|
|||
final SimpleString filterString,
|
||||
final SimpleString user,
|
||||
boolean durable) throws Exception {
|
||||
AddressSettings as = getAddressSettingsRepository().getMatch(address == null ? name.toString() : address.toString());
|
||||
createSharedQueue(address, routingType, name, filterString, user, durable, as.getDefaultMaxConsumers(), as.isDefaultPurgeOnNoConsumers(), as.isDefaultExclusiveQueue(), as.isDefaultLastValueQueue());
|
||||
}
|
||||
|
||||
@Override
|
||||
public void createSharedQueue(final SimpleString address,
|
||||
RoutingType routingType,
|
||||
final SimpleString name,
|
||||
final SimpleString filterString,
|
||||
final SimpleString user,
|
||||
boolean durable,
|
||||
int maxConsumers,
|
||||
boolean purgeOnNoConsumers,
|
||||
boolean exclusive,
|
||||
boolean lastValue) throws Exception {
|
||||
//force the old contract about address
|
||||
if (address == null) {
|
||||
throw new NullPointerException("address can't be null!");
|
||||
|
@ -1705,7 +1740,7 @@ public class ActiveMQServerImpl implements ActiveMQServer {
|
|||
}
|
||||
}
|
||||
|
||||
final Queue queue = createQueue(address, routingType, name, filterString, user, durable, !durable, true, !durable, false, Queue.MAX_CONSUMERS_UNLIMITED, false, true);
|
||||
final Queue queue = createQueue(address, routingType, name, filterString, user, durable, !durable, true, !durable, false, maxConsumers, purgeOnNoConsumers, exclusive, lastValue, true);
|
||||
|
||||
if (!queue.getAddress().equals(address)) {
|
||||
throw ActiveMQMessageBundle.BUNDLE.queueSubscriptionBelongsToDifferentAddress(name);
|
||||
|
@ -2480,16 +2515,19 @@ public class ActiveMQServerImpl implements ActiveMQServer {
|
|||
for (CoreQueueConfiguration config : queues) {
|
||||
SimpleString queueName = SimpleString.toSimpleString(config.getName());
|
||||
ActiveMQServerLogger.LOGGER.deployQueue(config.getName(), config.getAddress());
|
||||
|
||||
AddressSettings as = addressSettingsRepository.getMatch(config.getAddress());
|
||||
// determine if there is an address::queue match; update it if so
|
||||
if (locateQueue(queueName) != null && locateQueue(queueName).getAddress().toString().equals(config.getAddress())) {
|
||||
updateQueue(config.getName(), config.getRoutingType(), config.getMaxConsumers(), config.getPurgeOnNoConsumers());
|
||||
updateQueue(config.getName(), config.getRoutingType(), config.getMaxConsumers(), config.getPurgeOnNoConsumers(),
|
||||
config.isExclusive() == null ? as.isDefaultExclusiveQueue() : config.isExclusive());
|
||||
} else {
|
||||
// if the address::queue doesn't exist then create it
|
||||
try {
|
||||
createQueue(SimpleString.toSimpleString(config.getAddress()), config.getRoutingType(),
|
||||
queueName, SimpleString.toSimpleString(config.getFilterString()), SimpleString.toSimpleString(config.getUser()),
|
||||
config.isDurable(),false,false,false,false,config.getMaxConsumers(),config.getPurgeOnNoConsumers(),true);
|
||||
config.isDurable(),false,false,false,false,config.getMaxConsumers(),config.getPurgeOnNoConsumers(),
|
||||
config.isExclusive() == null ? as.isDefaultExclusiveQueue() : config.isExclusive(),
|
||||
config.isLastValue() == null ? as.isDefaultLastValueQueue() : config.isLastValue(), true);
|
||||
} catch (ActiveMQQueueExistsException e) {
|
||||
// the queue may exist on a *different* address
|
||||
ActiveMQServerLogger.LOGGER.warn(e.getMessage());
|
||||
|
@ -2668,6 +2706,8 @@ public class ActiveMQServerImpl implements ActiveMQServer {
|
|||
final boolean autoCreated,
|
||||
final int maxConsumers,
|
||||
final boolean purgeOnNoConsumers,
|
||||
final boolean exclusive,
|
||||
final boolean lastValue,
|
||||
final boolean autoCreateAddress) throws Exception {
|
||||
final QueueBinding binding = (QueueBinding) postOffice.getBinding(queueName);
|
||||
if (binding != null) {
|
||||
|
@ -2710,7 +2750,7 @@ public class ActiveMQServerImpl implements ActiveMQServer {
|
|||
throw ActiveMQMessageBundle.BUNDLE.invalidRoutingTypeForAddress(rt, info.getName().toString(), info.getRoutingTypes());
|
||||
}
|
||||
|
||||
final QueueConfig queueConfig = queueConfigBuilder.filter(filter).pagingManager(pagingManager).user(user).durable(durable).temporary(temporary).autoCreated(autoCreated).routingType(addrInfo.getRoutingType()).maxConsumers(maxConsumers).purgeOnNoConsumers(purgeOnNoConsumers).build();
|
||||
final QueueConfig queueConfig = queueConfigBuilder.filter(filter).pagingManager(pagingManager).user(user).durable(durable).temporary(temporary).autoCreated(autoCreated).routingType(addrInfo.getRoutingType()).maxConsumers(maxConsumers).purgeOnNoConsumers(purgeOnNoConsumers).exclusive(exclusive).lastValue(lastValue).build();
|
||||
|
||||
callBrokerPlugins(hasBrokerPlugins() ? plugin -> plugin.beforeCreateQueue(queueConfig) : null);
|
||||
|
||||
|
@ -2776,6 +2816,8 @@ public class ActiveMQServerImpl implements ActiveMQServer {
|
|||
final boolean autoCreated,
|
||||
final int maxConsumers,
|
||||
final boolean purgeOnNoConsumers,
|
||||
final boolean exclusive,
|
||||
final boolean lastValue,
|
||||
final boolean autoCreateAddress) throws Exception {
|
||||
|
||||
final QueueBinding binding = (QueueBinding) postOffice.getBinding(queueName);
|
||||
|
@ -2817,7 +2859,7 @@ public class ActiveMQServerImpl implements ActiveMQServer {
|
|||
throw ActiveMQMessageBundle.BUNDLE.invalidRoutingTypeForAddress(routingType, info.getName().toString(), info.getRoutingTypes());
|
||||
}
|
||||
|
||||
final QueueConfig queueConfig = queueConfigBuilder.filter(filter).pagingManager(pagingManager).user(user).durable(durable).temporary(temporary).autoCreated(autoCreated).routingType(routingType).maxConsumers(maxConsumers).purgeOnNoConsumers(purgeOnNoConsumers).build();
|
||||
final QueueConfig queueConfig = queueConfigBuilder.filter(filter).pagingManager(pagingManager).user(user).durable(durable).temporary(temporary).autoCreated(autoCreated).routingType(routingType).maxConsumers(maxConsumers).purgeOnNoConsumers(purgeOnNoConsumers).exclusive(exclusive).lastValue(lastValue).build();
|
||||
|
||||
callBrokerPlugins(hasBrokerPlugins() ? plugin -> plugin.beforeCreateQueue(queueConfig) : null);
|
||||
|
||||
|
@ -2873,8 +2915,16 @@ public class ActiveMQServerImpl implements ActiveMQServer {
|
|||
RoutingType routingType,
|
||||
Integer maxConsumers,
|
||||
Boolean purgeOnNoConsumers) throws Exception {
|
||||
return updateQueue(name, routingType, maxConsumers, purgeOnNoConsumers, null);
|
||||
}
|
||||
|
||||
final QueueBinding queueBinding = this.postOffice.updateQueue(new SimpleString(name), routingType, maxConsumers, purgeOnNoConsumers);
|
||||
@Override
|
||||
public Queue updateQueue(String name,
|
||||
RoutingType routingType,
|
||||
Integer maxConsumers,
|
||||
Boolean purgeOnNoConsumers,
|
||||
Boolean exclusive) throws Exception {
|
||||
final QueueBinding queueBinding = this.postOffice.updateQueue(new SimpleString(name), routingType, maxConsumers, purgeOnNoConsumers, exclusive);
|
||||
if (queueBinding != null) {
|
||||
final Queue queue = queueBinding.getQueue();
|
||||
return queue;
|
||||
|
|
|
@ -60,6 +60,7 @@ public class LastValueQueue extends QueueImpl {
|
|||
final boolean autoCreated,
|
||||
final RoutingType routingType,
|
||||
final Integer maxConsumers,
|
||||
final Boolean exclusive,
|
||||
final Boolean purgeOnNoConsumers,
|
||||
final ScheduledExecutorService scheduledExecutor,
|
||||
final PostOffice postOffice,
|
||||
|
@ -68,7 +69,7 @@ public class LastValueQueue extends QueueImpl {
|
|||
final ArtemisExecutor executor,
|
||||
final ActiveMQServer server,
|
||||
final QueueFactory factory) {
|
||||
super(persistenceID, address, name, filter, pageSubscription, user, durable, temporary, autoCreated, routingType, maxConsumers, purgeOnNoConsumers, scheduledExecutor, postOffice, storageManager, addressSettingsRepository, executor, server, factory);
|
||||
super(persistenceID, address, name, filter, pageSubscription, user, durable, temporary, autoCreated, routingType, maxConsumers, exclusive, purgeOnNoConsumers, scheduledExecutor, postOffice, storageManager, addressSettingsRepository, executor, server, factory);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -162,6 +163,11 @@ public class LastValueQueue extends QueueImpl {
|
|||
super.refRemoved(ref);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isLastValue() {
|
||||
return true;
|
||||
}
|
||||
|
||||
private class HolderReference implements MessageReference {
|
||||
|
||||
private final SimpleString prop;
|
||||
|
|
|
@ -150,6 +150,7 @@ public class PostOfficeJournalLoader implements JournalLoader {
|
|||
.autoCreated(queueBindingInfo.isAutoCreated())
|
||||
.purgeOnNoConsumers(queueBindingInfo.isPurgeOnNoConsumers())
|
||||
.maxConsumers(queueBindingInfo.getMaxConsumers())
|
||||
.exclusive(queueBindingInfo.isExclusive())
|
||||
.routingType(RoutingType.getType(queueBindingInfo.getRoutingType()));
|
||||
final Queue queue = queueFactory.createQueueWith(queueConfigBuilder.build());
|
||||
queue.setConsumersRefCount(new QueueManagerImpl(((PostOfficeImpl)postOffice).getServer(), queueBindingInfo.getQueueName()));
|
||||
|
|
|
@ -72,12 +72,11 @@ public class QueueFactoryImpl implements QueueFactory {
|
|||
|
||||
@Override
|
||||
public Queue createQueueWith(final QueueConfig config) {
|
||||
final AddressSettings addressSettings = addressSettingsRepository.getMatch(config.address().toString());
|
||||
final Queue queue;
|
||||
if (addressSettings.isLastValueQueue()) {
|
||||
queue = new LastValueQueue(config.id(), config.address(), config.name(), config.filter(), config.pageSubscription(), config.user(), config.isDurable(), config.isTemporary(), config.isAutoCreated(), config.deliveryMode(), config.maxConsumers(), config.isPurgeOnNoConsumers(), scheduledExecutor, postOffice, storageManager, addressSettingsRepository, executorFactory.getExecutor(), server, this);
|
||||
if (config.isLastValue()) {
|
||||
queue = new LastValueQueue(config.id(), config.address(), config.name(), config.filter(), config.pageSubscription(), config.user(), config.isDurable(), config.isTemporary(), config.isAutoCreated(), config.deliveryMode(), config.maxConsumers(), config.isExclusive(), config.isPurgeOnNoConsumers(), scheduledExecutor, postOffice, storageManager, addressSettingsRepository, executorFactory.getExecutor(), server, this);
|
||||
} else {
|
||||
queue = new QueueImpl(config.id(), config.address(), config.name(), config.filter(), config.pageSubscription(), config.user(), config.isDurable(), config.isTemporary(), config.isAutoCreated(), config.deliveryMode(), config.maxConsumers(), config.isPurgeOnNoConsumers(), scheduledExecutor, postOffice, storageManager, addressSettingsRepository, executorFactory.getExecutor(), server, this);
|
||||
queue = new QueueImpl(config.id(), config.address(), config.name(), config.filter(), config.pageSubscription(), config.user(), config.isDurable(), config.isTemporary(), config.isAutoCreated(), config.deliveryMode(), config.maxConsumers(), config.isExclusive(), config.isPurgeOnNoConsumers(), scheduledExecutor, postOffice, storageManager, addressSettingsRepository, executorFactory.getExecutor(), server, this);
|
||||
}
|
||||
|
||||
server.getCriticalAnalyzer().add(queue);
|
||||
|
@ -102,8 +101,8 @@ public class QueueFactoryImpl implements QueueFactory {
|
|||
AddressSettings addressSettings = addressSettingsRepository.getMatch(address.toString());
|
||||
|
||||
Queue queue;
|
||||
if (addressSettings.isLastValueQueue()) {
|
||||
queue = new LastValueQueue(persistenceID, address, name, filter, pageSubscription, user, durable, temporary, autoCreated, ActiveMQDefaultConfiguration.getDefaultRoutingType(), ActiveMQDefaultConfiguration.getDefaultMaxQueueConsumers(), ActiveMQDefaultConfiguration.getDefaultPurgeOnNoConsumers(), scheduledExecutor, postOffice, storageManager, addressSettingsRepository, executorFactory.getExecutor(), server, this);
|
||||
if (addressSettings.isDefaultLastValueQueue()) {
|
||||
queue = new LastValueQueue(persistenceID, address, name, filter, pageSubscription, user, durable, temporary, autoCreated, ActiveMQDefaultConfiguration.getDefaultRoutingType(), ActiveMQDefaultConfiguration.getDefaultMaxQueueConsumers(), ActiveMQDefaultConfiguration.getDefaultExclusive(), ActiveMQDefaultConfiguration.getDefaultPurgeOnNoConsumers(), scheduledExecutor, postOffice, storageManager, addressSettingsRepository, executorFactory.getExecutor(), server, this);
|
||||
} else {
|
||||
queue = new QueueImpl(persistenceID, address, name, filter, pageSubscription, user, durable, temporary, autoCreated, scheduledExecutor, postOffice, storageManager, addressSettingsRepository, executorFactory.getExecutor(), server, this);
|
||||
}
|
||||
|
|
|
@ -257,6 +257,8 @@ public class QueueImpl extends CriticalComponentImpl implements Queue {
|
|||
|
||||
private volatile int maxConsumers;
|
||||
|
||||
private volatile boolean exclusive;
|
||||
|
||||
private volatile boolean purgeOnNoConsumers;
|
||||
|
||||
private final AddressInfo addressInfo;
|
||||
|
@ -389,6 +391,29 @@ public class QueueImpl extends CriticalComponentImpl implements Queue {
|
|||
final ArtemisExecutor executor,
|
||||
final ActiveMQServer server,
|
||||
final QueueFactory factory) {
|
||||
this(id, address, name, filter, pageSubscription, user, durable, temporary, autoCreated, routingType, maxConsumers, null, purgeOnNoConsumers, scheduledExecutor, postOffice, storageManager, addressSettingsRepository, executor, server, factory);
|
||||
}
|
||||
|
||||
public QueueImpl(final long id,
|
||||
final SimpleString address,
|
||||
final SimpleString name,
|
||||
final Filter filter,
|
||||
final PageSubscription pageSubscription,
|
||||
final SimpleString user,
|
||||
final boolean durable,
|
||||
final boolean temporary,
|
||||
final boolean autoCreated,
|
||||
final RoutingType routingType,
|
||||
final Integer maxConsumers,
|
||||
final Boolean exclusive,
|
||||
final Boolean purgeOnNoConsumers,
|
||||
final ScheduledExecutorService scheduledExecutor,
|
||||
final PostOffice postOffice,
|
||||
final StorageManager storageManager,
|
||||
final HierarchicalRepository<AddressSettings> addressSettingsRepository,
|
||||
final ArtemisExecutor executor,
|
||||
final ActiveMQServer server,
|
||||
final QueueFactory factory) {
|
||||
super(server == null ? EmptyCriticalAnalyzer.getInstance() : server.getCriticalAnalyzer(), CRITICAL_PATHS);
|
||||
|
||||
this.id = id;
|
||||
|
@ -413,6 +438,8 @@ public class QueueImpl extends CriticalComponentImpl implements Queue {
|
|||
|
||||
this.maxConsumers = maxConsumers == null ? ActiveMQDefaultConfiguration.getDefaultMaxQueueConsumers() : maxConsumers;
|
||||
|
||||
this.exclusive = exclusive == null ? ActiveMQDefaultConfiguration.getDefaultExclusive() : exclusive;
|
||||
|
||||
this.purgeOnNoConsumers = purgeOnNoConsumers == null ? ActiveMQDefaultConfiguration.getDefaultPurgeOnNoConsumers() : purgeOnNoConsumers;
|
||||
|
||||
this.postOffice = postOffice;
|
||||
|
@ -463,7 +490,18 @@ public class QueueImpl extends CriticalComponentImpl implements Queue {
|
|||
return user;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isExclusive() {
|
||||
return exclusive;
|
||||
}
|
||||
|
||||
@Override
|
||||
public synchronized void setExclusive(boolean exclusive) {
|
||||
this.exclusive = exclusive;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isLastValue() {
|
||||
return false;
|
||||
}
|
||||
|
||||
|
@ -2190,6 +2228,10 @@ public class QueueImpl extends CriticalComponentImpl implements Queue {
|
|||
}
|
||||
}
|
||||
|
||||
if (exclusive) {
|
||||
consumer = consumerList.get(0).consumer;
|
||||
}
|
||||
|
||||
HandleStatus status = handle(ref, consumer);
|
||||
|
||||
if (status == HandleStatus.HANDLED) {
|
||||
|
@ -2237,7 +2279,7 @@ public class QueueImpl extends CriticalComponentImpl implements Queue {
|
|||
|
||||
// Only move onto the next position if the consumer on the current position was used.
|
||||
// When using group we don't need to load balance to the next position
|
||||
if (groupConsumer == null) {
|
||||
if (!exclusive && groupConsumer == null) {
|
||||
pos++;
|
||||
}
|
||||
|
||||
|
@ -2730,8 +2772,12 @@ public class QueueImpl extends CriticalComponentImpl implements Queue {
|
|||
}
|
||||
}
|
||||
|
||||
if (exclusive) {
|
||||
consumer = consumerList.get(0).consumer;
|
||||
}
|
||||
|
||||
// Only move onto the next position if the consumer on the current position was used.
|
||||
if (groupConsumer == null) {
|
||||
if (!exclusive && groupConsumer == null) {
|
||||
pos++;
|
||||
}
|
||||
|
||||
|
|
|
@ -559,7 +559,7 @@ public class ServerSessionImpl implements ServerSession, FailureListener {
|
|||
@Override
|
||||
public Queue createQueue(AddressInfo addressInfo, SimpleString name, SimpleString filterString, boolean temporary, boolean durable) throws Exception {
|
||||
AddressSettings as = server.getAddressSettingsRepository().getMatch(addressInfo.getName().toString());
|
||||
return createQueue(addressInfo, name, filterString, temporary, durable, as.getDefaultMaxConsumers(), as.isDefaultPurgeOnNoConsumers(), false);
|
||||
return createQueue(addressInfo, name, filterString, temporary, durable, as.getDefaultMaxConsumers(), as.isDefaultPurgeOnNoConsumers(), as.isDefaultExclusiveQueue(), as.isDefaultLastValueQueue(), false);
|
||||
}
|
||||
|
||||
public Queue createQueue(final AddressInfo addressInfo,
|
||||
|
@ -569,6 +569,8 @@ public class ServerSessionImpl implements ServerSession, FailureListener {
|
|||
final boolean durable,
|
||||
final int maxConsumers,
|
||||
final boolean purgeOnNoConsumers,
|
||||
final boolean exclusive,
|
||||
final boolean lastValue,
|
||||
final boolean autoCreated) throws Exception {
|
||||
final SimpleString unPrefixedName = removePrefix(name);
|
||||
|
||||
|
@ -583,7 +585,7 @@ public class ServerSessionImpl implements ServerSession, FailureListener {
|
|||
|
||||
server.checkQueueCreationLimit(getUsername());
|
||||
|
||||
Queue queue = server.createQueue(art, unPrefixedName, filterString, SimpleString.toSimpleString(getUsername()), durable, temporary, autoCreated, maxConsumers, purgeOnNoConsumers, server.getAddressSettingsRepository().getMatch(art.getName().toString()).isAutoCreateAddresses());
|
||||
Queue queue = server.createQueue(art, unPrefixedName, filterString, SimpleString.toSimpleString(getUsername()), durable, temporary, autoCreated, maxConsumers, purgeOnNoConsumers, exclusive, lastValue, server.getAddressSettingsRepository().getMatch(art.getName().toString()).isAutoCreateAddresses());
|
||||
|
||||
if (temporary) {
|
||||
// Temporary queue in core simply means the queue will be deleted if
|
||||
|
@ -622,7 +624,30 @@ public class ServerSessionImpl implements ServerSession, FailureListener {
|
|||
final int maxConsumers,
|
||||
final boolean purgeOnNoConsumers,
|
||||
final boolean autoCreated) throws Exception {
|
||||
return createQueue(new AddressInfo(address, routingType), name, filterString, temporary, durable, maxConsumers, purgeOnNoConsumers, autoCreated);
|
||||
AddressSettings as = server.getAddressSettingsRepository().getMatch(address.toString());
|
||||
return createQueue(new AddressInfo(address, routingType), name, filterString, temporary, durable, maxConsumers, purgeOnNoConsumers, as.isDefaultExclusiveQueue(), as.isDefaultLastValueQueue(), autoCreated);
|
||||
}
|
||||
|
||||
@Override
|
||||
public Queue createQueue(final SimpleString address,
|
||||
final SimpleString name,
|
||||
final RoutingType routingType,
|
||||
final SimpleString filterString,
|
||||
final boolean temporary,
|
||||
final boolean durable,
|
||||
final int maxConsumers,
|
||||
final boolean purgeOnNoConsumers,
|
||||
final Boolean exclusive,
|
||||
final Boolean lastValue,
|
||||
final boolean autoCreated) throws Exception {
|
||||
if (exclusive == null || lastValue == null) {
|
||||
AddressSettings as = server.getAddressSettingsRepository().getMatch(address.toString());
|
||||
return createQueue(new AddressInfo(address, routingType), name, filterString, temporary, durable, maxConsumers, purgeOnNoConsumers,
|
||||
exclusive == null ? as.isDefaultExclusiveQueue() : exclusive, lastValue == null ? as.isDefaultLastValueQueue() : lastValue, autoCreated);
|
||||
} else {
|
||||
return createQueue(new AddressInfo(address, routingType), name, filterString, temporary, durable, maxConsumers, purgeOnNoConsumers,
|
||||
exclusive, lastValue, autoCreated);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -640,7 +665,14 @@ public class ServerSessionImpl implements ServerSession, FailureListener {
|
|||
@Override
|
||||
public Queue createQueue(AddressInfo addressInfo, SimpleString name, SimpleString filterString, boolean temporary, boolean durable, boolean autoCreated) throws Exception {
|
||||
AddressSettings as = server.getAddressSettingsRepository().getMatch(addressInfo.getName().toString());
|
||||
return createQueue(addressInfo, name, filterString, temporary, durable, as.getDefaultMaxConsumers(), as.isDefaultPurgeOnNoConsumers(), autoCreated);
|
||||
return createQueue(addressInfo, name, filterString, temporary, durable, as.getDefaultMaxConsumers(), as.isDefaultPurgeOnNoConsumers(), as.isDefaultExclusiveQueue(), as.isDefaultLastValueQueue(), autoCreated);
|
||||
}
|
||||
|
||||
@Override
|
||||
public Queue createQueue(AddressInfo addressInfo, SimpleString name, SimpleString filterString, boolean temporary, boolean durable, Boolean exclusive, Boolean lastValue, boolean autoCreated) throws Exception {
|
||||
AddressSettings as = server.getAddressSettingsRepository().getMatch(addressInfo.getName().toString());
|
||||
return createQueue(addressInfo, name, filterString, temporary, durable, as.getDefaultMaxConsumers(), as.isDefaultPurgeOnNoConsumers(),
|
||||
exclusive == null ? as.isDefaultExclusiveQueue() : exclusive, lastValue == null ? as.isDefaultLastValueQueue() : lastValue, autoCreated);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -668,6 +700,31 @@ public class ServerSessionImpl implements ServerSession, FailureListener {
|
|||
return server.getAddressInfo(art.getName());
|
||||
}
|
||||
|
||||
@Override
|
||||
public void createSharedQueue(SimpleString address,
|
||||
SimpleString name,
|
||||
RoutingType routingType,
|
||||
SimpleString filterString,
|
||||
boolean durable,
|
||||
Integer maxConsumers,
|
||||
Boolean purgeOnNoConsumers,
|
||||
Boolean exclusive,
|
||||
Boolean lastValue) throws Exception {
|
||||
address = removePrefix(address);
|
||||
|
||||
securityCheck(address, name, durable ? CheckType.CREATE_DURABLE_QUEUE : CheckType.CREATE_NON_DURABLE_QUEUE, this);
|
||||
|
||||
server.checkQueueCreationLimit(getUsername());
|
||||
|
||||
AddressSettings as = server.getAddressSettingsRepository().getMatch(address.toString());
|
||||
|
||||
server.createSharedQueue(address, routingType, name, filterString, SimpleString.toSimpleString(getUsername()), durable,
|
||||
maxConsumers == null ? as.getDefaultMaxConsumers() : maxConsumers,
|
||||
purgeOnNoConsumers == null ? as.isDefaultPurgeOnNoConsumers() : purgeOnNoConsumers,
|
||||
exclusive == null ? as.isDefaultExclusiveQueue() : exclusive,
|
||||
lastValue == null ? as.isDefaultLastValueQueue() : lastValue);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void createSharedQueue(SimpleString address,
|
||||
final SimpleString name,
|
||||
|
@ -675,13 +732,7 @@ public class ServerSessionImpl implements ServerSession, FailureListener {
|
|||
boolean durable,
|
||||
final SimpleString filterString) throws Exception {
|
||||
|
||||
address = removePrefix(address);
|
||||
|
||||
securityCheck(address, name, CheckType.CREATE_NON_DURABLE_QUEUE, this);
|
||||
|
||||
server.checkQueueCreationLimit(getUsername());
|
||||
|
||||
server.createSharedQueue(address, routingType, name, filterString, SimpleString.toSimpleString(getUsername()), durable);
|
||||
createSharedQueue(address, name, routingType, filterString, durable, null, null, null, null);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
|
@ -124,7 +124,9 @@ public class AddressSettings implements Mergeable<AddressSettings>, Serializable
|
|||
|
||||
private Long expiryDelay = AddressSettings.DEFAULT_EXPIRY_DELAY;
|
||||
|
||||
private Boolean lastValueQueue = null;
|
||||
private Boolean defaultLastValueQueue = null;
|
||||
|
||||
private Boolean defaultExclusiveQueue = null;
|
||||
|
||||
private Long redistributionDelay = null;
|
||||
|
||||
|
@ -190,7 +192,8 @@ public class AddressSettings implements Mergeable<AddressSettings>, Serializable
|
|||
this.deadLetterAddress = other.deadLetterAddress;
|
||||
this.expiryAddress = other.expiryAddress;
|
||||
this.expiryDelay = other.expiryDelay;
|
||||
this.lastValueQueue = other.lastValueQueue;
|
||||
this.defaultLastValueQueue = other.defaultLastValueQueue;
|
||||
this.defaultExclusiveQueue = other.defaultExclusiveQueue;
|
||||
this.redistributionDelay = other.redistributionDelay;
|
||||
this.sendToDLAOnNoRoute = other.sendToDLAOnNoRoute;
|
||||
this.slowConsumerThreshold = other.slowConsumerThreshold;
|
||||
|
@ -352,12 +355,21 @@ public class AddressSettings implements Mergeable<AddressSettings>, Serializable
|
|||
return this;
|
||||
}
|
||||
|
||||
public boolean isLastValueQueue() {
|
||||
return lastValueQueue != null ? lastValueQueue : AddressSettings.DEFAULT_LAST_VALUE_QUEUE;
|
||||
public boolean isDefaultLastValueQueue() {
|
||||
return defaultLastValueQueue != null ? defaultLastValueQueue : AddressSettings.DEFAULT_LAST_VALUE_QUEUE;
|
||||
}
|
||||
|
||||
public AddressSettings setLastValueQueue(final boolean lastValueQueue) {
|
||||
this.lastValueQueue = lastValueQueue;
|
||||
public AddressSettings setDefaultLastValueQueue(final boolean defaultLastValueQueue) {
|
||||
this.defaultLastValueQueue = defaultLastValueQueue;
|
||||
return this;
|
||||
}
|
||||
|
||||
public boolean isDefaultExclusiveQueue() {
|
||||
return defaultExclusiveQueue != null ? defaultExclusiveQueue : ActiveMQDefaultConfiguration.getDefaultExclusive();
|
||||
}
|
||||
|
||||
public AddressSettings setDefaultExclusiveQueue(Boolean defaultExclusiveQueue) {
|
||||
this.defaultExclusiveQueue = defaultExclusiveQueue;
|
||||
return this;
|
||||
}
|
||||
|
||||
|
@ -691,7 +703,7 @@ public class AddressSettings implements Mergeable<AddressSettings>, Serializable
|
|||
|
||||
expiryDelay = BufferHelper.readNullableLong(buffer);
|
||||
|
||||
lastValueQueue = BufferHelper.readNullableBoolean(buffer);
|
||||
defaultLastValueQueue = BufferHelper.readNullableBoolean(buffer);
|
||||
|
||||
redistributionDelay = BufferHelper.readNullableLong(buffer);
|
||||
|
||||
|
@ -751,6 +763,10 @@ public class AddressSettings implements Mergeable<AddressSettings>, Serializable
|
|||
defaultQueueRoutingType = RoutingType.getType(buffer.readByte());
|
||||
|
||||
defaultAddressRoutingType = RoutingType.getType(buffer.readByte());
|
||||
|
||||
if (buffer.readableBytes() > 0) {
|
||||
defaultExclusiveQueue = BufferHelper.readNullableBoolean(buffer);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -769,7 +785,7 @@ public class AddressSettings implements Mergeable<AddressSettings>, Serializable
|
|||
SimpleString.sizeofNullableString(deadLetterAddress) +
|
||||
SimpleString.sizeofNullableString(expiryAddress) +
|
||||
BufferHelper.sizeOfNullableLong(expiryDelay) +
|
||||
BufferHelper.sizeOfNullableBoolean(lastValueQueue) +
|
||||
BufferHelper.sizeOfNullableBoolean(defaultLastValueQueue) +
|
||||
BufferHelper.sizeOfNullableLong(redistributionDelay) +
|
||||
BufferHelper.sizeOfNullableBoolean(sendToDLAOnNoRoute) +
|
||||
BufferHelper.sizeOfNullableLong(slowConsumerCheckPeriod) +
|
||||
|
@ -788,7 +804,8 @@ public class AddressSettings implements Mergeable<AddressSettings>, Serializable
|
|||
BufferHelper.sizeOfNullableInteger(defaultMaxConsumers) +
|
||||
BufferHelper.sizeOfNullableBoolean(defaultPurgeOnNoConsumers) +
|
||||
DataConstants.SIZE_BYTE +
|
||||
DataConstants.SIZE_BYTE;
|
||||
DataConstants.SIZE_BYTE +
|
||||
BufferHelper.sizeOfNullableBoolean(defaultExclusiveQueue);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -819,7 +836,7 @@ public class AddressSettings implements Mergeable<AddressSettings>, Serializable
|
|||
|
||||
BufferHelper.writeNullableLong(buffer, expiryDelay);
|
||||
|
||||
BufferHelper.writeNullableBoolean(buffer, lastValueQueue);
|
||||
BufferHelper.writeNullableBoolean(buffer, defaultLastValueQueue);
|
||||
|
||||
BufferHelper.writeNullableLong(buffer, redistributionDelay);
|
||||
|
||||
|
@ -862,6 +879,9 @@ public class AddressSettings implements Mergeable<AddressSettings>, Serializable
|
|||
buffer.writeByte(defaultQueueRoutingType == null ? -1 : defaultQueueRoutingType.getType());
|
||||
|
||||
buffer.writeByte(defaultAddressRoutingType == null ? -1 : defaultAddressRoutingType.getType());
|
||||
|
||||
BufferHelper.writeNullableBoolean(buffer, defaultExclusiveQueue);
|
||||
|
||||
}
|
||||
|
||||
/* (non-Javadoc)
|
||||
|
@ -876,7 +896,8 @@ public class AddressSettings implements Mergeable<AddressSettings>, Serializable
|
|||
result = prime * result + ((dropMessagesWhenFull == null) ? 0 : dropMessagesWhenFull.hashCode());
|
||||
result = prime * result + ((expiryAddress == null) ? 0 : expiryAddress.hashCode());
|
||||
result = prime * result + ((expiryDelay == null) ? 0 : expiryDelay.hashCode());
|
||||
result = prime * result + ((lastValueQueue == null) ? 0 : lastValueQueue.hashCode());
|
||||
result = prime * result + ((defaultLastValueQueue == null) ? 0 : defaultLastValueQueue.hashCode());
|
||||
result = prime * result + ((defaultExclusiveQueue == null) ? 0 : defaultExclusiveQueue.hashCode());
|
||||
result = prime * result + ((maxDeliveryAttempts == null) ? 0 : maxDeliveryAttempts.hashCode());
|
||||
result = prime * result + ((maxSizeBytes == null) ? 0 : maxSizeBytes.hashCode());
|
||||
result = prime * result + ((messageCounterHistoryDayLimit == null) ? 0 : messageCounterHistoryDayLimit.hashCode());
|
||||
|
@ -947,10 +968,15 @@ public class AddressSettings implements Mergeable<AddressSettings>, Serializable
|
|||
return false;
|
||||
} else if (!expiryDelay.equals(other.expiryDelay))
|
||||
return false;
|
||||
if (lastValueQueue == null) {
|
||||
if (other.lastValueQueue != null)
|
||||
if (defaultLastValueQueue == null) {
|
||||
if (other.defaultLastValueQueue != null)
|
||||
return false;
|
||||
} else if (!lastValueQueue.equals(other.lastValueQueue))
|
||||
} else if (!defaultLastValueQueue.equals(other.defaultLastValueQueue))
|
||||
return false;
|
||||
if (defaultExclusiveQueue == null) {
|
||||
if (other.defaultExclusiveQueue != null)
|
||||
return false;
|
||||
} else if (!defaultExclusiveQueue.equals(other.defaultExclusiveQueue))
|
||||
return false;
|
||||
if (maxDeliveryAttempts == null) {
|
||||
if (other.maxDeliveryAttempts != null)
|
||||
|
@ -1124,8 +1150,10 @@ public class AddressSettings implements Mergeable<AddressSettings>, Serializable
|
|||
expiryAddress +
|
||||
", expiryDelay=" +
|
||||
expiryDelay +
|
||||
", lastValueQueue=" +
|
||||
lastValueQueue +
|
||||
", defaultLastValueQueue=" +
|
||||
defaultLastValueQueue +
|
||||
", defaultExclusiveQueue=" +
|
||||
defaultExclusiveQueue +
|
||||
", maxDeliveryAttempts=" +
|
||||
maxDeliveryAttempts +
|
||||
", maxSizeBytes=" +
|
||||
|
|
|
@ -502,6 +502,8 @@
|
|||
</xsd:attribute>
|
||||
<xsd:attribute name="max-consumers" type="xsd:integer" use="optional"/>
|
||||
<xsd:attribute name="purge-on-no-consumers" type="xsd:boolean" use="optional"/>
|
||||
<xsd:attribute name="exclusive" type="xsd:boolean" use="optional"/>
|
||||
<xsd:attribute name="last-value" type="xsd:boolean" use="optional"/>
|
||||
</xsd:complexType>
|
||||
</xsd:element>
|
||||
</xsd:sequence>
|
||||
|
@ -2693,7 +2695,23 @@
|
|||
<xsd:element name="last-value-queue" type="xsd:boolean" default="false" maxOccurs="1" minOccurs="0">
|
||||
<xsd:annotation>
|
||||
<xsd:documentation>
|
||||
whether to treat the queue as a last value queue
|
||||
This is deprecated please use default-last-value-queue instead.
|
||||
</xsd:documentation>
|
||||
</xsd:annotation>
|
||||
</xsd:element>
|
||||
|
||||
<xsd:element name="default-last-value-queue" type="xsd:boolean" default="false" maxOccurs="1" minOccurs="0">
|
||||
<xsd:annotation>
|
||||
<xsd:documentation>
|
||||
whether to treat the queues under the address as a last value queues by default
|
||||
</xsd:documentation>
|
||||
</xsd:annotation>
|
||||
</xsd:element>
|
||||
|
||||
<xsd:element name="default-exclusive-queue" type="xsd:boolean" default="false" maxOccurs="1" minOccurs="0">
|
||||
<xsd:annotation>
|
||||
<xsd:documentation>
|
||||
whether to treat the queues under the address as exclusive queues by default
|
||||
</xsd:documentation>
|
||||
</xsd:annotation>
|
||||
</xsd:element>
|
||||
|
@ -3009,6 +3027,8 @@
|
|||
<xsd:attribute name="name" type="xsd:string" use="required"/>
|
||||
<xsd:attribute name="max-consumers" type="xsd:integer" use="optional"/>
|
||||
<xsd:attribute name="purge-on-no-consumers" type="xsd:boolean" use="optional"/>
|
||||
<xsd:attribute name="exclusive" type="xsd:boolean" use="optional"/>
|
||||
<xsd:attribute name="last-value" type="xsd:boolean" use="optional"/>
|
||||
</xsd:complexType>
|
||||
|
||||
<xsd:complexType name="addressType">
|
||||
|
|
|
@ -1311,6 +1311,21 @@ public class ScheduledDeliveryHandlerTest extends Assert {
|
|||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isLastValue() {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isExclusive() {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setExclusive(boolean exclusive) {
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void decDelivering(int size) {
|
||||
|
||||
|
|
|
@ -484,6 +484,8 @@
|
|||
</xsd:attribute>
|
||||
<xsd:attribute name="max-consumers" type="xsd:integer" use="optional"/>
|
||||
<xsd:attribute name="purge-on-no-consumers" type="xsd:boolean" use="optional"/>
|
||||
<xsd:attribute name="exclusive" type="xsd:boolean" use="optional"/>
|
||||
<xsd:attribute name="last-value" type="xsd:boolean" use="optional"/>
|
||||
</xsd:complexType>
|
||||
</xsd:element>
|
||||
</xsd:sequence>
|
||||
|
@ -2422,7 +2424,23 @@
|
|||
<xsd:element name="last-value-queue" type="xsd:boolean" default="false" maxOccurs="1" minOccurs="0">
|
||||
<xsd:annotation>
|
||||
<xsd:documentation>
|
||||
whether to treat the queue as a last value queue
|
||||
This is deprecated please use default-last-value-queue instead.
|
||||
</xsd:documentation>
|
||||
</xsd:annotation>
|
||||
</xsd:element>
|
||||
|
||||
<xsd:element name="default-last-value-queue" type="xsd:boolean" default="false" maxOccurs="1" minOccurs="0">
|
||||
<xsd:annotation>
|
||||
<xsd:documentation>
|
||||
whether to treat the queues under the address as a last value queues by default
|
||||
</xsd:documentation>
|
||||
</xsd:annotation>
|
||||
</xsd:element>
|
||||
|
||||
<xsd:element name="default-exclusive-queue" type="xsd:boolean" default="false" maxOccurs="1" minOccurs="0">
|
||||
<xsd:annotation>
|
||||
<xsd:documentation>
|
||||
whether to treat the queues under the address as exclusive queues by default
|
||||
</xsd:documentation>
|
||||
</xsd:annotation>
|
||||
</xsd:element>
|
||||
|
@ -2679,6 +2697,7 @@
|
|||
</xsd:simpleContent>
|
||||
</xsd:complexType>
|
||||
|
||||
|
||||
|
||||
<!-- 2.0 Addressing configuration -->
|
||||
|
||||
|
@ -2691,6 +2710,8 @@
|
|||
<xsd:attribute name="name" type="xsd:string" use="required"/>
|
||||
<xsd:attribute name="max-consumers" type="xsd:integer" use="optional"/>
|
||||
<xsd:attribute name="purge-on-no-consumers" type="xsd:boolean" use="optional"/>
|
||||
<xsd:attribute name="exclusive" type="xsd:boolean" use="optional"/>
|
||||
<xsd:attribute name="last-value" type="xsd:boolean" use="optional"/>
|
||||
</xsd:complexType>
|
||||
|
||||
<xsd:complexType name="addressType">
|
||||
|
|
|
@ -43,7 +43,7 @@ public class JMSLVQTest extends JMSClientTestSupport {
|
|||
|
||||
@Override
|
||||
protected void addConfiguration(ActiveMQServer server) {
|
||||
server.getAddressSettingsRepository().addMatch(LVQ_QUEUE_NAME, new AddressSettings().setLastValueQueue(true));
|
||||
server.getAddressSettingsRepository().addMatch(LVQ_QUEUE_NAME, new AddressSettings().setDefaultLastValueQueue(true));
|
||||
}
|
||||
@Override
|
||||
protected void createAddressAndQueues(ActiveMQServer server) throws Exception {
|
||||
|
|
|
@ -74,7 +74,7 @@ public class MultipleProducersTest extends JMSTestBase {
|
|||
addressSettings.setDeadLetterAddress(expiryQueue);
|
||||
addressSettings.setRedeliveryDelay(0);
|
||||
addressSettings.setMessageCounterHistoryDayLimit(2);
|
||||
addressSettings.setLastValueQueue(false);
|
||||
addressSettings.setDefaultLastValueQueue(false);
|
||||
addressSettings.setMaxDeliveryAttempts(10);
|
||||
addressSettings.setMaxSizeBytes(1048576);
|
||||
addressSettings.setPageCacheMaxSize(5);
|
||||
|
|
|
@ -99,7 +99,7 @@ public class SessionCreateAndDeleteQueueTest extends ActiveMQTestBase {
|
|||
|
||||
@Test
|
||||
public void testAddressSettingUSed() throws Exception {
|
||||
server.getAddressSettingsRepository().addMatch(address.toString(), new AddressSettings().setLastValueQueue(true));
|
||||
server.getAddressSettingsRepository().addMatch(address.toString(), new AddressSettings().setDefaultLastValueQueue(true));
|
||||
ClientSession session = createSessionFactory(locator).createSession(false, true, true);
|
||||
SimpleString filterString = new SimpleString("x=y");
|
||||
session.createQueue(address, queueName, filterString, false);
|
||||
|
|
|
@ -59,7 +59,7 @@ public class UpdateQueueTest extends ActiveMQTestBase {
|
|||
prod.send(session.createTextMessage("message " + i));
|
||||
}
|
||||
|
||||
server.updateQueue(ADDRESS.toString(), RoutingType.ANYCAST, 1, false);
|
||||
server.updateQueue(ADDRESS.toString(), RoutingType.ANYCAST, 1, false, false);
|
||||
|
||||
conn.close();
|
||||
factory.close();
|
||||
|
|
|
@ -0,0 +1,319 @@
|
|||
/*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership.
|
||||
* The ASF licenses this file to You 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.apache.activemq.artemis.tests.integration.jms.client;
|
||||
|
||||
import javax.jms.Connection;
|
||||
import javax.jms.ConnectionFactory;
|
||||
import javax.jms.Destination;
|
||||
import javax.jms.JMSConsumer;
|
||||
import javax.jms.JMSContext;
|
||||
import javax.jms.JMSProducer;
|
||||
import javax.jms.MessageConsumer;
|
||||
import javax.jms.MessageProducer;
|
||||
import javax.jms.Queue;
|
||||
import javax.jms.Session;
|
||||
import javax.jms.TextMessage;
|
||||
import javax.jms.Topic;
|
||||
|
||||
import org.apache.activemq.artemis.api.core.RoutingType;
|
||||
import org.apache.activemq.artemis.api.core.SimpleString;
|
||||
import org.apache.activemq.artemis.jms.client.ActiveMQDestination;
|
||||
import org.apache.activemq.artemis.tests.util.JMSTestBase;
|
||||
import org.junit.Before;
|
||||
import org.junit.Test;
|
||||
|
||||
/**
|
||||
* Exclusive Test
|
||||
*/
|
||||
public class ExclusiveTest extends JMSTestBase {
|
||||
|
||||
private SimpleString queueName = SimpleString.toSimpleString("jms.exclusive.queue");
|
||||
|
||||
@Override
|
||||
@Before
|
||||
public void setUp() throws Exception {
|
||||
super.setUp();
|
||||
server.createQueue(queueName, RoutingType.ANYCAST, queueName, null, null, true, false, false, false, false, -1, false, true, false,true);
|
||||
}
|
||||
|
||||
|
||||
protected ConnectionFactory getCF() throws Exception {
|
||||
return cf;
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testExclusiveQueueConsumer() throws Exception {
|
||||
ConnectionFactory fact = getCF();
|
||||
Connection connection = fact.createConnection();
|
||||
|
||||
try {
|
||||
|
||||
Session session = connection.createSession(false, Session.CLIENT_ACKNOWLEDGE);
|
||||
|
||||
Destination queue = session.createQueue(queueName.toString());
|
||||
MessageProducer producer = session.createProducer(queue);
|
||||
|
||||
MessageConsumer consumer1 = session.createConsumer(queue);
|
||||
MessageConsumer consumer2 = session.createConsumer(queue);
|
||||
MessageConsumer consumer3 = session.createConsumer(queue);
|
||||
|
||||
connection.start();
|
||||
|
||||
for (int j = 0; j < 100; j++) {
|
||||
TextMessage message = session.createTextMessage();
|
||||
|
||||
message.setText("Message" + j);
|
||||
|
||||
producer.send(message);
|
||||
}
|
||||
|
||||
|
||||
//All msgs should go to the first consumer
|
||||
for (int j = 0; j < 100; j++) {
|
||||
TextMessage tm = (TextMessage) consumer1.receive(10000);
|
||||
|
||||
assertNotNull(tm);
|
||||
|
||||
assertEquals("Message" + j, tm.getText());
|
||||
|
||||
tm = (TextMessage) consumer2.receiveNoWait();
|
||||
assertNull(tm);
|
||||
tm = (TextMessage) consumer3.receiveNoWait();
|
||||
assertNull(tm);
|
||||
}
|
||||
} finally {
|
||||
connection.close();
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testExclusiveWithJMS2Producer() throws Exception {
|
||||
ConnectionFactory fact = getCF();
|
||||
JMSContext ctx = addContext(getCF().createContext(JMSContext.SESSION_TRANSACTED));
|
||||
|
||||
try {
|
||||
JMSProducer producer = ctx.createProducer();
|
||||
Destination queue = ctx.createQueue(queueName.toString());
|
||||
|
||||
JMSConsumer consumer1 = ctx.createConsumer(queue);
|
||||
JMSConsumer consumer2 = ctx.createConsumer(queue);
|
||||
JMSConsumer consumer3 = ctx.createConsumer(queue);
|
||||
|
||||
ctx.start();
|
||||
|
||||
for (int j = 0; j < 100; j++) {
|
||||
TextMessage message = ctx.createTextMessage("Message" + j);
|
||||
|
||||
producer.send(queue, message);
|
||||
}
|
||||
|
||||
ctx.commit();
|
||||
|
||||
//All msgs should go to the first consumer
|
||||
for (int j = 0; j < 100; j++) {
|
||||
TextMessage tm = (TextMessage) consumer1.receive(10000);
|
||||
|
||||
assertNotNull(tm);
|
||||
|
||||
tm.acknowledge();
|
||||
|
||||
assertEquals("Message" + j, tm.getText());
|
||||
|
||||
tm = (TextMessage) consumer2.receiveNoWait();
|
||||
assertNull(tm);
|
||||
tm = (TextMessage) consumer3.receiveNoWait();
|
||||
assertNull(tm);
|
||||
}
|
||||
|
||||
ctx.commit();
|
||||
} finally {
|
||||
ctx.close();
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testExclusiveQueueConsumerSettingUsingAddressQueueParameters() throws Exception {
|
||||
ConnectionFactory fact = getCF();
|
||||
Connection connection = fact.createConnection();
|
||||
|
||||
try {
|
||||
|
||||
Session session = connection.createSession(false, Session.CLIENT_ACKNOWLEDGE);
|
||||
|
||||
Queue queue = session.createQueue("random?exclusive=true");
|
||||
assertEquals("random", queue.getQueueName());
|
||||
|
||||
ActiveMQDestination a = (ActiveMQDestination) queue;
|
||||
assertTrue(a.getQueueAttributes().getExclusive());
|
||||
|
||||
MessageProducer producer = session.createProducer(queue);
|
||||
|
||||
MessageConsumer consumer1 = session.createConsumer(queue);
|
||||
MessageConsumer consumer2 = session.createConsumer(queue);
|
||||
MessageConsumer consumer3 = session.createConsumer(queue);
|
||||
|
||||
connection.start();
|
||||
|
||||
for (int j = 0; j < 100; j++) {
|
||||
TextMessage message = session.createTextMessage();
|
||||
|
||||
message.setText("Message" + j);
|
||||
|
||||
producer.send(message);
|
||||
}
|
||||
|
||||
|
||||
//All msgs should go to the first consumer
|
||||
for (int j = 0; j < 100; j++) {
|
||||
TextMessage tm = (TextMessage) consumer1.receive(10000);
|
||||
|
||||
assertNotNull(tm);
|
||||
|
||||
assertEquals("Message" + j, tm.getText());
|
||||
|
||||
tm = (TextMessage) consumer2.receiveNoWait();
|
||||
assertNull(tm);
|
||||
tm = (TextMessage) consumer3.receiveNoWait();
|
||||
assertNull(tm);
|
||||
}
|
||||
} finally {
|
||||
connection.close();
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testExclusiveQueueConsumerFailover() throws Exception {
|
||||
ConnectionFactory fact = getCF();
|
||||
Connection connection = fact.createConnection();
|
||||
|
||||
try {
|
||||
|
||||
Session session = connection.createSession(false, Session.CLIENT_ACKNOWLEDGE);
|
||||
|
||||
Destination queue = session.createQueue(queueName.toString());
|
||||
MessageProducer producer = session.createProducer(queue);
|
||||
|
||||
MessageConsumer consumer1 = session.createConsumer(queue);
|
||||
MessageConsumer consumer2 = session.createConsumer(queue);
|
||||
MessageConsumer consumer3 = session.createConsumer(queue);
|
||||
|
||||
connection.start();
|
||||
|
||||
for (int j = 0; j < 100; j++) {
|
||||
TextMessage message = session.createTextMessage();
|
||||
|
||||
message.setText("Message" + j);
|
||||
|
||||
producer.send(message);
|
||||
}
|
||||
|
||||
|
||||
//All msgs should go to the first consumer
|
||||
for (int j = 0; j < 50; j++) {
|
||||
TextMessage tm = (TextMessage) consumer1.receive(10000);
|
||||
|
||||
assertNotNull(tm);
|
||||
|
||||
assertEquals("Message" + j, tm.getText());
|
||||
|
||||
tm = (TextMessage) consumer2.receiveNoWait();
|
||||
assertNull(tm);
|
||||
tm = (TextMessage) consumer3.receiveNoWait();
|
||||
assertNull(tm);
|
||||
}
|
||||
consumer1.close();
|
||||
|
||||
//All msgs should now go to the next consumer only, without any errors or exceptions
|
||||
for (int j = 50; j < 100; j++) {
|
||||
TextMessage tm = (TextMessage) consumer2.receive(10000);
|
||||
|
||||
assertNotNull(tm);
|
||||
|
||||
assertEquals("Message" + j, tm.getText());
|
||||
|
||||
tm = (TextMessage) consumer3.receiveNoWait();
|
||||
assertNull(tm);
|
||||
}
|
||||
} finally {
|
||||
connection.close();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@Test
|
||||
public void testExclusiveTopicSharedConsumerFailover() throws Exception {
|
||||
ConnectionFactory fact = getCF();
|
||||
Connection connection = fact.createConnection();
|
||||
|
||||
try {
|
||||
|
||||
Session session = connection.createSession(false, Session.CLIENT_ACKNOWLEDGE);
|
||||
|
||||
Destination topic = session.createTopic("mytopic");
|
||||
MessageProducer producer = session.createProducer(topic);
|
||||
|
||||
String subscriptionName = "sharedsub";
|
||||
Topic topicConsumer = session.createTopic("mytopic?exclusive=true");
|
||||
MessageConsumer consumer1 = session.createSharedDurableConsumer(topicConsumer, subscriptionName);
|
||||
MessageConsumer consumer2 = session.createSharedDurableConsumer(topicConsumer, subscriptionName);
|
||||
MessageConsumer consumer3 = session.createSharedDurableConsumer(topicConsumer, subscriptionName);
|
||||
|
||||
connection.start();
|
||||
|
||||
for (int j = 0; j < 100; j++) {
|
||||
TextMessage message = session.createTextMessage();
|
||||
|
||||
message.setText("Message" + j);
|
||||
|
||||
producer.send(message);
|
||||
}
|
||||
|
||||
|
||||
//All msgs should go to the first consumer
|
||||
for (int j = 0; j < 50; j++) {
|
||||
TextMessage tm = (TextMessage) consumer1.receive(10000);
|
||||
|
||||
assertNotNull(tm);
|
||||
|
||||
assertEquals("Message" + j, tm.getText());
|
||||
|
||||
tm = (TextMessage) consumer2.receiveNoWait();
|
||||
assertNull(tm);
|
||||
tm = (TextMessage) consumer3.receiveNoWait();
|
||||
assertNull(tm);
|
||||
}
|
||||
consumer1.close();
|
||||
|
||||
//All msgs should now go to the next consumer only, without any errors or exceptions
|
||||
for (int j = 50; j < 100; j++) {
|
||||
TextMessage tm = (TextMessage) consumer2.receive(10000);
|
||||
|
||||
assertNotNull(tm);
|
||||
|
||||
assertEquals("Message" + j, tm.getText());
|
||||
|
||||
tm = (TextMessage) consumer3.receiveNoWait();
|
||||
assertNull(tm);
|
||||
}
|
||||
|
||||
|
||||
} finally {
|
||||
connection.close();
|
||||
}
|
||||
}
|
||||
|
||||
}
|
|
@ -0,0 +1,145 @@
|
|||
/*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership.
|
||||
* The ASF licenses this file to You 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.apache.activemq.artemis.tests.integration.jms.client;
|
||||
|
||||
import javax.jms.Connection;
|
||||
import javax.jms.ConnectionFactory;
|
||||
import javax.jms.MessageConsumer;
|
||||
import javax.jms.MessageProducer;
|
||||
import javax.jms.Queue;
|
||||
import javax.jms.Session;
|
||||
import javax.jms.TextMessage;
|
||||
import javax.jms.Topic;
|
||||
|
||||
import org.apache.activemq.artemis.api.core.Message;
|
||||
import org.apache.activemq.artemis.jms.client.ActiveMQConnectionFactory;
|
||||
import org.apache.activemq.artemis.jms.client.ActiveMQDestination;
|
||||
import org.apache.activemq.artemis.tests.util.JMSTestBase;
|
||||
import org.junit.Before;
|
||||
import org.junit.Test;
|
||||
|
||||
/**
|
||||
* LVQ Test
|
||||
*/
|
||||
public class LVQTest extends JMSTestBase {
|
||||
|
||||
@Override
|
||||
@Before
|
||||
public void setUp() throws Exception {
|
||||
super.setUp();
|
||||
}
|
||||
|
||||
|
||||
protected ConnectionFactory getCF() throws Exception {
|
||||
return cf;
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testLastValueQueueUsingAddressQueueParameters() throws Exception {
|
||||
ActiveMQConnectionFactory fact = (ActiveMQConnectionFactory) getCF();
|
||||
|
||||
//Set the consumer window size to 0 to not buffer any messages client side.
|
||||
fact.setConsumerWindowSize(0);
|
||||
Connection connection = fact.createConnection();
|
||||
|
||||
try {
|
||||
|
||||
Session session = connection.createSession(false, Session.CLIENT_ACKNOWLEDGE);
|
||||
|
||||
Queue queue = session.createQueue("random?last-value=true");
|
||||
assertEquals("random", queue.getQueueName());
|
||||
|
||||
ActiveMQDestination a = (ActiveMQDestination) queue;
|
||||
assertTrue(a.getQueueAttributes().getLastValue());
|
||||
|
||||
MessageProducer producer = session.createProducer(queue);
|
||||
MessageConsumer consumer1 = session.createConsumer(queue);
|
||||
|
||||
connection.start();
|
||||
for (int j = 0; j < 100; j++) {
|
||||
TextMessage message = session.createTextMessage();
|
||||
|
||||
message.setText("Message" + j);
|
||||
message.setStringProperty(Message.HDR_LAST_VALUE_NAME.toString(), "key");
|
||||
producer.send(message);
|
||||
}
|
||||
|
||||
//Last message only should go to the consumer
|
||||
TextMessage tm = (TextMessage) consumer1.receive(10000);
|
||||
|
||||
assertNotNull(tm);
|
||||
|
||||
assertEquals("Message99", tm.getText());
|
||||
|
||||
} finally {
|
||||
connection.close();
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testLastValueQueueTopicConsumerUsingAddressQueueParameters() throws Exception {
|
||||
ActiveMQConnectionFactory fact = (ActiveMQConnectionFactory) getCF();
|
||||
|
||||
//Set the consumer window size to 0 to not buffer any messages client side.
|
||||
fact.setConsumerWindowSize(0);
|
||||
Connection connection = fact.createConnection();
|
||||
|
||||
try {
|
||||
|
||||
Session session = connection.createSession(false, Session.CLIENT_ACKNOWLEDGE);
|
||||
|
||||
Topic topic = session.createTopic("topic?last-value=true");
|
||||
assertEquals("topic", topic.getTopicName());
|
||||
|
||||
ActiveMQDestination a = (ActiveMQDestination) topic;
|
||||
assertTrue(a.getQueueAttributes().getLastValue());
|
||||
|
||||
MessageProducer producer = session.createProducer(topic);
|
||||
MessageConsumer consumer1 = session.createConsumer(topic);
|
||||
MessageConsumer consumer2 = session.createConsumer(topic);
|
||||
|
||||
connection.start();
|
||||
for (int j = 0; j < 100; j++) {
|
||||
TextMessage message = session.createTextMessage();
|
||||
|
||||
message.setText("Message" + j);
|
||||
message.setStringProperty(Message.HDR_LAST_VALUE_NAME.toString(), "key");
|
||||
producer.send(message);
|
||||
}
|
||||
|
||||
|
||||
|
||||
//Last message only should go to the consumer.
|
||||
TextMessage tm = (TextMessage) consumer1.receive(10000);
|
||||
|
||||
assertNotNull(tm);
|
||||
|
||||
assertEquals("Message99", tm.getText());
|
||||
|
||||
//Last message only should go to the other consumer as well.
|
||||
TextMessage tm2 = (TextMessage) consumer2.receive(10000);
|
||||
|
||||
assertNotNull(tm2);
|
||||
|
||||
assertEquals("Message99", tm2.getText());
|
||||
|
||||
} finally {
|
||||
connection.close();
|
||||
}
|
||||
}
|
||||
|
||||
}
|
|
@ -135,6 +135,16 @@ public class ActiveMQServerControlUsingCoreTest extends ActiveMQServerControlTes
|
|||
return (String) proxy.invokeOperation("updateQueue", name, routingType, maxConsumers, purgeOnNoConsumers);
|
||||
}
|
||||
|
||||
@Override
|
||||
public String updateQueue(@Parameter(name = "name", desc = "Name of the queue") String name,
|
||||
@Parameter(name = "routingType", desc = "The routing type used for this address, MULTICAST or ANYCAST") String routingType,
|
||||
@Parameter(name = "maxConsumers", desc = "The maximum number of consumers allowed on this queue at any one time") Integer maxConsumers,
|
||||
@Parameter(name = "purgeOnNoConsumers", desc = "Delete this queue when the last consumer disconnects") Boolean purgeOnNoConsumers,
|
||||
@Parameter(name = "exclusive", desc = "If the queue should route exclusively to one consumer") Boolean exclusive)
|
||||
throws Exception {
|
||||
return (String) proxy.invokeOperation("updateQueue", name, routingType, maxConsumers, purgeOnNoConsumers, exclusive);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void deleteAddress(@Parameter(name = "name", desc = "The name of the address") String name) throws Exception {
|
||||
proxy.invokeOperation("deleteAddress", name);
|
||||
|
|
|
@ -101,6 +101,16 @@ public class QueueControlUsingCoreTest extends QueueControlTest {
|
|||
return (Boolean) proxy.retrieveAttributeValue("purgeOnNoConsumers");
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isExclusive() {
|
||||
return (Boolean) proxy.retrieveAttributeValue("exclusive");
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isLastValue() {
|
||||
return (Boolean) proxy.retrieveAttributeValue("lastValue");
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getDeliveringCount() {
|
||||
return (Integer) proxy.retrieveAttributeValue("deliveringCount", Integer.class);
|
||||
|
|
|
@ -170,7 +170,7 @@ public class LVQRecoveryTest extends ActiveMQTestBase {
|
|||
server = createServer(true, configuration);
|
||||
server.start();
|
||||
|
||||
qs = new AddressSettings().setLastValueQueue(true);
|
||||
qs = new AddressSettings().setDefaultLastValueQueue(true);
|
||||
server.getAddressSettingsRepository().addMatch(address.toString(), qs);
|
||||
// then we create a client as normal
|
||||
locator = createInVMNonHALocator().setBlockOnAcknowledge(true).setAckBatchSize(0);
|
||||
|
@ -188,7 +188,7 @@ public class LVQRecoveryTest extends ActiveMQTestBase {
|
|||
// start the server
|
||||
server.start();
|
||||
|
||||
server.getAddressSettingsRepository().addMatch(address.toString(), new AddressSettings().setLastValueQueue(true));
|
||||
server.getAddressSettingsRepository().addMatch(address.toString(), new AddressSettings().setDefaultLastValueQueue(true));
|
||||
// then we create a client as normal
|
||||
locator.close();
|
||||
locator = createInVMNonHALocator().setBlockOnAcknowledge(true).setAckBatchSize(0);
|
||||
|
|
|
@ -648,7 +648,7 @@ public class LVQTest extends ActiveMQTestBase {
|
|||
// start the server
|
||||
server.start();
|
||||
|
||||
server.getAddressSettingsRepository().addMatch(address.toString(), new AddressSettings().setLastValueQueue(true));
|
||||
server.getAddressSettingsRepository().addMatch(address.toString(), new AddressSettings().setDefaultLastValueQueue(true));
|
||||
// then we create a client as normalServer
|
||||
ServerLocator locator = createNettyNonHALocator().setBlockOnAcknowledge(true).setAckBatchSize(0);
|
||||
|
||||
|
|
|
@ -917,6 +917,12 @@ public class MessageHeaderTest extends MessageHeaderTestBase {
|
|||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void createSharedQueue(SimpleString address, RoutingType routingType, SimpleString queueName, SimpleString filter,
|
||||
boolean durable, Integer maxConsumers, Boolean purgeOnNoConsumers, Boolean exclusive, Boolean lastValue) throws ActiveMQException {
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* Creates a <em>non-temporary</em> queue.
|
||||
*
|
||||
|
@ -1018,6 +1024,13 @@ public class MessageHeaderTest extends MessageHeaderTestBase {
|
|||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void createQueue(SimpleString address, RoutingType routingType, SimpleString queueName, SimpleString filter, boolean durable,
|
||||
boolean autoCreated, int maxConsumers, boolean purgeOnNoConsumers, Boolean exclusive, Boolean lastValue)
|
||||
throws ActiveMQException {
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* Creates a <em>non-temporary</em>queue.
|
||||
*
|
||||
|
@ -1048,6 +1061,13 @@ public class MessageHeaderTest extends MessageHeaderTestBase {
|
|||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void createQueue(String address, RoutingType routingType, String queueName, String filter, boolean durable,
|
||||
boolean autoCreated,
|
||||
int maxConsumers, boolean purgeOnNoConsumers, Boolean exclusive, Boolean lastValue) throws ActiveMQException {
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* Creates a <em>temporary</em> queue.
|
||||
*
|
||||
|
@ -1074,6 +1094,13 @@ public class MessageHeaderTest extends MessageHeaderTestBase {
|
|||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void createTemporaryQueue(SimpleString address, RoutingType routingType, SimpleString queueName, SimpleString filter,
|
||||
int maxConsumers, boolean purgeOnNoConsumers, Boolean exclusive, Boolean lastValue)
|
||||
throws ActiveMQException {
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* Creates a <em>temporary</em> queue with a filter.
|
||||
*
|
||||
|
|
|
@ -47,6 +47,23 @@ public class FakeQueue extends CriticalComponentImpl implements Queue {
|
|||
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isExclusive() {
|
||||
// no-op
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setExclusive(boolean value) {
|
||||
// no-op
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isLastValue() {
|
||||
// no-op
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setMaxConsumer(int maxConsumers) {
|
||||
|
||||
|
|
|
@ -46,7 +46,8 @@ public class FakePostOffice implements PostOffice {
|
|||
public QueueBinding updateQueue(SimpleString name,
|
||||
RoutingType routingType,
|
||||
Integer maxConsumers,
|
||||
Boolean purgeOnNoConsumers) throws Exception {
|
||||
Boolean purgeOnNoConsumers,
|
||||
Boolean exclusive) throws Exception {
|
||||
return null;
|
||||
}
|
||||
|
||||
|
|
Loading…
Reference in New Issue