use of org.apache.activemq.artemis.core.paging.cursor.PageSubscriptionCounter in project activemq-artemis by apache.
the class Page method close.
/**
* sendEvent means it's a close happening from a major event such moveNext.
* While reading the cache we don't need (and shouldn't inform the backup
*/
public synchronized void close(boolean sendEvent) throws Exception {
if (sendEvent && storageManager != null) {
storageManager.pageClosed(storeName, pageId);
}
if (pageCache != null) {
pageCache.close();
// leave it to the soft cache to decide when to release it now
pageCache = null;
}
file.close();
Set<PageSubscriptionCounter> counters = getPendingCounters();
if (counters != null) {
for (PageSubscriptionCounter counter : counters) {
counter.cleanupNonTXCounters(this.getPageId());
}
}
}
use of org.apache.activemq.artemis.core.paging.cursor.PageSubscriptionCounter in project activemq-artemis by apache.
the class PostOfficeJournalLoader method recoverPendingPageCounters.
/**
* This method will recover the counters after failures making sure the page counter doesn't get out of sync
*
* @param pendingNonTXPageCounter
* @throws Exception
*/
@Override
public void recoverPendingPageCounters(List<PageCountPending> pendingNonTXPageCounter) throws Exception {
// We need a structure of the following
// Address -> PageID -> QueueID -> List<PageCountPending>
// The following loop will sort the records according to the hierarchy we need
Transaction txRecoverCounter = new TransactionImpl(storageManager);
Map<SimpleString, Map<Long, Map<Long, List<PageCountPending>>>> perAddressMap = generateMapsOnPendingCount(queues, pendingNonTXPageCounter, txRecoverCounter);
for (Map.Entry<SimpleString, Map<Long, Map<Long, List<PageCountPending>>>> addressPageMapEntry : perAddressMap.entrySet()) {
PagingStore store = pagingManager.getPageStore(addressPageMapEntry.getKey());
Map<Long, Map<Long, List<PageCountPending>>> perPageMap = addressPageMapEntry.getValue();
// We have already generated this before, so it can't be null
assert (perPageMap != null);
for (Long pageId : perPageMap.keySet()) {
Map<Long, List<PageCountPending>> perQueue = perPageMap.get(pageId);
// This can't be true!
assert (perQueue != null);
if (store.checkPageFileExists(pageId.intValue())) {
// on this case we need to recalculate the records
Page pg = store.createPage(pageId.intValue());
pg.open();
List<PagedMessage> pgMessages = pg.read(storageManager);
Map<Long, AtomicInteger> countsPerQueueOnPage = new HashMap<>();
Map<Long, AtomicLong> sizePerQueueOnPage = new HashMap<>();
for (PagedMessage pgd : pgMessages) {
if (pgd.getTransactionID() <= 0) {
for (long q : pgd.getQueueIDs()) {
AtomicInteger countQ = countsPerQueueOnPage.get(q);
AtomicLong sizeQ = sizePerQueueOnPage.get(q);
if (countQ == null) {
countQ = new AtomicInteger(0);
countsPerQueueOnPage.put(q, countQ);
}
if (sizeQ == null) {
sizeQ = new AtomicLong(0);
sizePerQueueOnPage.put(q, sizeQ);
}
countQ.incrementAndGet();
if (pgd.getPersistentSize() > 0) {
sizeQ.addAndGet(pgd.getPersistentSize());
}
}
}
}
for (Map.Entry<Long, List<PageCountPending>> entry : perQueue.entrySet()) {
for (PageCountPending record : entry.getValue()) {
logger.debug("Deleting pg tempCount " + record.getID());
storageManager.deletePendingPageCounter(txRecoverCounter.getID(), record.getID());
}
PageSubscriptionCounter counter = store.getCursorProvider().getSubscription(entry.getKey()).getCounter();
AtomicInteger value = countsPerQueueOnPage.get(entry.getKey());
AtomicLong sizeValue = sizePerQueueOnPage.get(entry.getKey());
if (value == null) {
logger.debug("Page " + entry.getKey() + " wasn't open, so we will just ignore");
} else {
logger.debug("Replacing counter " + value.get());
counter.increment(txRecoverCounter, value.get(), sizeValue.get());
}
}
} else {
// on this case the page file didn't exist, we just remove all the records since the page is already gone
logger.debug("Page " + pageId + " didn't exist on address " + addressPageMapEntry.getKey() + ", so we are just removing records");
for (List<PageCountPending> records : perQueue.values()) {
for (PageCountPending record : records) {
logger.debug("Removing pending page counter " + record.getID());
storageManager.deletePendingPageCounter(txRecoverCounter.getID(), record.getID());
txRecoverCounter.setContainsPersistent();
}
}
}
}
}
txRecoverCounter.commit();
}
use of org.apache.activemq.artemis.core.paging.cursor.PageSubscriptionCounter in project activemq-artemis by apache.
the class PagingCounterTest method testPrepareCounter.
@Test
public void testPrepareCounter() throws Exception {
Xid xid = newXID();
Queue queue = server.createQueue(new SimpleString("A1"), RoutingType.ANYCAST, new SimpleString("A1"), null, true, false);
PageSubscriptionCounter counter = locateCounter(queue);
StorageManager storage = server.getStorageManager();
Transaction tx = new TransactionImpl(xid, server.getStorageManager(), 300);
for (int i = 0; i < 2000; i++) {
counter.increment(tx, 1, 1000);
}
assertEquals(0, counter.getValue());
tx.prepare();
storage.waitOnOperations();
assertEquals(0, counter.getValue());
server.stop();
server = newActiveMQServer();
server.start();
storage = server.getStorageManager();
queue = server.locateQueue(new SimpleString("A1"));
assertNotNull(queue);
counter = locateCounter(queue);
tx = server.getResourceManager().removeTransaction(xid);
assertNotNull(tx);
assertEquals(0, counter.getValue());
tx.commit(false);
storage.waitOnOperations();
assertEquals(2000, counter.getValue());
}
use of org.apache.activemq.artemis.core.paging.cursor.PageSubscriptionCounter in project activemq-artemis by apache.
the class PagingCounterTest method testCounter.
@Test
public void testCounter() throws Exception {
ClientSessionFactory sf = createSessionFactory(sl);
ClientSession session = sf.createSession();
try {
server.addAddressInfo(new AddressInfo(new SimpleString("A1"), RoutingType.ANYCAST));
Queue queue = server.createQueue(new SimpleString("A1"), RoutingType.ANYCAST, new SimpleString("A1"), null, true, false);
PageSubscriptionCounter counter = locateCounter(queue);
StorageManager storage = server.getStorageManager();
Transaction tx = new TransactionImpl(server.getStorageManager());
counter.increment(tx, 1, 1000);
assertEquals(0, counter.getValue());
assertEquals(0, counter.getPersistentSize());
tx.commit();
storage.waitOnOperations();
assertEquals(1, counter.getValue());
assertEquals(1000, counter.getPersistentSize());
} finally {
sf.close();
session.close();
}
}
use of org.apache.activemq.artemis.core.paging.cursor.PageSubscriptionCounter in project activemq-artemis by apache.
the class PagingCounterTest method testCleanupCounter.
@Test
public void testCleanupCounter() throws Exception {
ClientSessionFactory sf = createSessionFactory(sl);
ClientSession session = sf.createSession();
try {
server.addAddressInfo(new AddressInfo(new SimpleString("A1"), RoutingType.ANYCAST));
Queue queue = server.createQueue(new SimpleString("A1"), RoutingType.ANYCAST, new SimpleString("A1"), null, true, false);
PageSubscriptionCounter counter = locateCounter(queue);
StorageManager storage = server.getStorageManager();
Transaction tx = new TransactionImpl(server.getStorageManager());
for (int i = 0; i < 2100; i++) {
counter.increment(tx, 1, 1000);
if (i % 200 == 0) {
tx.commit();
storage.waitOnOperations();
assertEquals(i + 1, counter.getValue());
assertEquals((i + 1) * 1000, counter.getPersistentSize());
tx = new TransactionImpl(server.getStorageManager());
}
}
tx.commit();
storage.waitOnOperations();
assertEquals(2100, counter.getValue());
assertEquals(2100 * 1000, counter.getPersistentSize());
server.stop();
server = newActiveMQServer();
server.start();
queue = server.locateQueue(new SimpleString("A1"));
assertNotNull(queue);
counter = locateCounter(queue);
assertEquals(2100, counter.getValue());
assertEquals(2100 * 1000, counter.getPersistentSize());
} finally {
sf.close();
session.close();
}
}
Aggregations