/**
*
* Copyright 2004 Protique Ltd
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*
**/
package org.activemq.io.util;
import java.util.ArrayList;
import java.util.List;
import junit.framework.TestCase;
import org.activemq.message.ActiveMQMessage;
import EDU.oswego.cs.dl.util.concurrent.Semaphore;
import EDU.oswego.cs.dl.util.concurrent.SynchronizedBoolean;
/**
* MemoryBoundedQueueTest
*
* @version $Revision: 1.1.1.1 $
*/
public class MemoryBoundedQueueTest extends TestCase {
protected static final int TEST_INSTANCE_SIZE = 2048;
private static final int TEST_ENQUEUE_SIZE = TEST_INSTANCE_SIZE / 2;
protected static final String QUEUE_NAME = "TestQueue";
private final int TOTAL_LOAD = 100000;
private final int NUMBER_CONSUMERS = 20;
private Semaphore stoppedSemaphore = new Semaphore(1-NUMBER_CONSUMERS);
private MemoryBoundedObjectManager memoryManager;
private MemoryBoundedQueueManager queueManager;
protected boolean supportJMSPriority=false;
protected MemoryBoundedObjectManager getMemoryManager() {
if (memoryManager == null) {
memoryManager = new MemoryBoundedObjectManager("testmanager", 1024 * 1024, supportJMSPriority);
}
return memoryManager;
}
protected MemoryBoundedQueueManager getQueueManager() {
if (queueManager == null) {
queueManager = new MemoryBoundedQueueManager(getMemoryManager());
}
return queueManager;
}
private class Dequeue implements Runnable {
private MemoryBoundedQueue queue;
private int localCount;
Dequeue(MemoryBoundedQueue q, int num, int localCount) {
this.queue = q;
this.localCount = localCount;
}
public void run() {
try {
int internalCount = 0;
while (internalCount < localCount) {
Thread.yield();
MemoryManageable obj = queue.dequeue();
if (obj == null) {
break;
}
internalCount++;
}
} catch (InterruptedException ie) {
ie.printStackTrace();
} finally {
stoppedSemaphore.release();
}
}
}
public void testLoad() throws Exception {
final MemoryBoundedQueue queue = getQueueManager().getMemoryBoundedQueue(QUEUE_NAME);
getMemoryManager().setValueLimit(TEST_INSTANCE_SIZE * NUMBER_CONSUMERS);
final List list = new ArrayList(NUMBER_CONSUMERS);
int numberOfMessages = TOTAL_LOAD / NUMBER_CONSUMERS;
for (int i = 0;i < NUMBER_CONSUMERS;i++) {
Dequeue dq = new Dequeue(queue, i, numberOfMessages);
list.add(dq);
Thread t = new Thread(dq);
t.setPriority(Thread.NORM_PRIORITY - 1);
t.start();
}
for (int i = 0;i < TOTAL_LOAD;i++) {
ActiveMQMessage msg = new ActiveMQMessage();
msg.setMemoryUsage(TEST_INSTANCE_SIZE);
queue.enqueue(msg);
}
try {
// Assert that all the consumers stopped.
assertTrue(stoppedSemaphore.attempt(1000*30));
}
catch (InterruptedException ie) {
ie.printStackTrace();
}
//Thread.sleep(250);
assertEquals(0, getMemoryManager().getTotalMemoryUsedSize());
queue.close();
}
public void testClear() {
final MemoryBoundedQueue queue = getQueueManager().getMemoryBoundedQueue(QUEUE_NAME);
getMemoryManager().setValueLimit(TEST_INSTANCE_SIZE);
ActiveMQMessage msg = new ActiveMQMessage();
queue.enqueue(msg);
queue.clear();
assertTrue(queue.size() == 0);
queue.close();
}
public void testDequeue() throws Exception {
final MemoryBoundedQueue queue = getQueueManager().getMemoryBoundedQueue(QUEUE_NAME);
getMemoryManager().setValueLimit(TEST_INSTANCE_SIZE * 100);
ActiveMQMessage msg = new ActiveMQMessage();
queue.enqueue(msg);
Object result = queue.dequeue();
assertTrue(result == msg);
queue.close();
}
public void testClose() {
/** @todo: Insert test code here. Use assertEquals(), for example. */
final MemoryBoundedQueue queue = getQueueManager().getMemoryBoundedQueue(QUEUE_NAME);
getMemoryManager().setValueLimit(TEST_ENQUEUE_SIZE);
final SynchronizedBoolean success = new SynchronizedBoolean(false);
final MemoryBoundedQueue q1 = getQueueManager().getMemoryBoundedQueue(QUEUE_NAME);
assertTrue(queue == q1);
Thread t = new Thread(new Runnable() {
public void run() {
try {
Thread.sleep(250);
queue.dequeue();
}
catch (Exception e) {
e.printStackTrace();
}
synchronized (success) {
success.set(true);
success.notify();
}
}
});
t.start();
queue.close();
try {
synchronized (success) {
if (!success.get()) {
success.wait(2000);
}
}
}
catch (Throwable e) {
e.printStackTrace();
}
assertTrue(success.get());
MemoryBoundedQueue q2 = getQueueManager().getMemoryBoundedQueue(QUEUE_NAME);
assertTrue(queue != q2);
}
public void testDequeueNoWait() throws Exception {
final MemoryBoundedQueue queue = getQueueManager().getMemoryBoundedQueue(QUEUE_NAME);
Object obj = queue.dequeueNoWait();
assertTrue(obj == null);
queue.close();
}
public void testEnqueueFirst() throws Exception {
final MemoryBoundedQueue queue = getQueueManager().getMemoryBoundedQueue(QUEUE_NAME);
assertTrue(getMemoryManager().getTotalMemoryUsedSize() == 0);
Object mutex = new Object();
getMemoryManager().setValueLimit(TEST_INSTANCE_SIZE * 100);
for (int i = 0;i < 10;i++) {
queue.enqueue(new ActiveMQMessage());
}
ActiveMQMessage test = new ActiveMQMessage();
test.setJMSMessageID("FIRST");
queue.enqueueFirst(test);
Object obj = queue.dequeue();
assertTrue(obj == test);
queue.close();
}
public void testEnqueueNoBlock() {
MemoryBoundedQueue queue = getQueueManager().getMemoryBoundedQueue(QUEUE_NAME);
getMemoryManager().setValueLimit(TEST_ENQUEUE_SIZE);
ActiveMQMessage msg = new ActiveMQMessage();
queue.enqueueNoBlock(msg);
assertTrue(true);
queue.close();
}
public void testIsEmpty() {
int size = 10;
MemoryBoundedQueue queue = getQueueManager().getMemoryBoundedQueue(QUEUE_NAME);
for (int i = 0;i < size;i++) {
queue.enqueue(new ActiveMQMessage());
}
queue.clear();
assertTrue(queue.isEmpty());
queue.close();
}
public void testRemove() {
MemoryBoundedQueue queue = getQueueManager().getMemoryBoundedQueue(QUEUE_NAME);
ActiveMQMessage msg = new ActiveMQMessage();
queue.enqueue(msg);
assertTrue(queue.remove(msg));
queue.close();
}
public void testSize() {
int size = 10;
MemoryBoundedQueue queue = getQueueManager().getMemoryBoundedQueue(QUEUE_NAME);
for (int i = 0;i < size;i++) {
queue.enqueue(new ActiveMQMessage());
}
assertTrue(queue.size() == size);
queue.close();
}
public void testRemovePacket(){
int size = 100;
MemoryBoundedQueue queue = getQueueManager().getMemoryBoundedQueue(QUEUE_NAME);
List list = new ArrayList(size);
for (int i = 0;i < size;i++) {
ActiveMQMessage msg = new ActiveMQMessage();
msg.setJMSMessageID(""+i);
list.add(msg);
queue.enqueue(msg);
}
for (int i =0; i < size; i++){
queue.remove((ActiveMQMessage)list.get(i));
}
assertTrue(queue.size() == 0);
queue.close();
}
public void testRemovePacketById(){
int size = 100;
MemoryBoundedQueue queue = getQueueManager().getMemoryBoundedQueue(QUEUE_NAME);
List list = new ArrayList(size);
for (int i = 0;i < size;i++) {
ActiveMQMessage msg = new ActiveMQMessage();
msg.setJMSMessageID(""+i);
list.add(msg);
queue.enqueue(msg);
}
for (int i =0; i < size; i++){
ActiveMQMessage p = (ActiveMQMessage)list.get(i);
MemoryManageable removed = queue.remove(p.getJMSMessageID());
assertTrue(removed != null);
assertTrue(removed == p);
}
assertTrue(queue.size() == 0);
queue.close();
}
}