All Downloads are FREE. Search and download functionalities are using the official Maven repository.

bitronix.tm.TransactionManagerServices Maven / Gradle / Ivy

There is a newer version: 62
Show newest version
/*
 * Copyright (C) 2006-2013 Bitronix Software (http://www.bitronix.be)
 *
 * 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 bitronix.tm;

import bitronix.tm.internal.LogDebugCheck;
import bitronix.tm.journal.DiskJournal;
import bitronix.tm.journal.Journal;
import bitronix.tm.journal.NullJournal;
import bitronix.tm.recovery.Recoverer;
import bitronix.tm.resource.ResourceLoader;
import bitronix.tm.timer.TaskScheduler;
import bitronix.tm.twopc.executor.AsyncExecutor;
import bitronix.tm.twopc.executor.Executor;
import bitronix.tm.twopc.executor.SyncExecutor;
import bitronix.tm.utils.ClassLoaderUtils;
import bitronix.tm.utils.DefaultExceptionAnalyzer;
import bitronix.tm.utils.ExceptionAnalyzer;
import bitronix.tm.utils.InitializationException;

import java.util.concurrent.atomic.AtomicReference;
import java.util.concurrent.locks.Lock;
import java.util.concurrent.locks.ReentrantLock;
import java.util.logging.Level;

/**
 * Container for all BTM services.
 * 

The different services available are: {@link BitronixTransactionManager}, {@link BitronixTransactionSynchronizationRegistry} * {@link Configuration}, {@link Journal}, {@link TaskScheduler}, {@link ResourceLoader}, {@link Recoverer} and {@link Executor}. * They are used in all places of the TM so they must be globally reachable.

* * @author Ludovic Orban */ public class TransactionManagerServices { private static final java.util.logging.Logger log = java.util.logging.Logger.getLogger(TransactionManagerServices.class.toString()); private static final Lock transactionManagerLock = new ReentrantLock(); private static final AtomicReference transactionSynchronizationRegistryRef = new AtomicReference<>(); private static final AtomicReference configurationRef = new AtomicReference<>(); private static final AtomicReference journalRef = new AtomicReference<>(); private static final AtomicReference taskSchedulerRef = new AtomicReference<>(); private static final AtomicReference resourceLoaderRef = new AtomicReference<>(); private static final AtomicReference recovererRef = new AtomicReference<>(); private static final AtomicReference executorRef = new AtomicReference<>(); private static final AtomicReference exceptionAnalyzerRef = new AtomicReference<>(); private static volatile BitronixTransactionManager transactionManager; /** * Constructor TransactionManagerServices creates a new TransactionManagerServices instance. */ private TransactionManagerServices() { //No config required } /** * Create an initialized transaction manager. * * @return the transaction manager. */ public static BitronixTransactionManager getTransactionManager() { transactionManagerLock.lock(); try { if (transactionManager == null) { transactionManager = new BitronixTransactionManager(); } return transactionManager; } finally { transactionManagerLock.unlock(); } } /** * Create the JTA 1.1 TransactionSynchronizationRegistry. * * @return the TransactionSynchronizationRegistry. */ public static BitronixTransactionSynchronizationRegistry getTransactionSynchronizationRegistry() { BitronixTransactionSynchronizationRegistry transactionSynchronizationRegistry = transactionSynchronizationRegistryRef.get(); if (transactionSynchronizationRegistry == null) { transactionSynchronizationRegistry = new BitronixTransactionSynchronizationRegistry(); if (!transactionSynchronizationRegistryRef.compareAndSet(null, transactionSynchronizationRegistry)) { transactionSynchronizationRegistry = transactionSynchronizationRegistryRef.get(); } } return transactionSynchronizationRegistry; } /** * Create the transactions journal. * * @return the transactions journal. */ public static Journal getJournal() { Journal journal = journalRef.get(); if (journal == null) { String configuredJournal = getConfiguration().getJournal(); if ("null".equals(configuredJournal) || null == configuredJournal) { journal = new NullJournal(); } else if ("disk".equals(configuredJournal)) { journal = new DiskJournal(); } else { try { Class clazz = ClassLoaderUtils.loadClass(configuredJournal); journal = (Journal) clazz.getDeclaredConstructor() .newInstance(); } catch (Exception ex) { throw new InitializationException("invalid journal implementation '" + configuredJournal + "'", ex); } } if (LogDebugCheck.isDebugEnabled()) { log.finer("using journal " + configuredJournal); } if (!journalRef.compareAndSet(null, journal)) { journal = journalRef.get(); } } return journal; } /** * Create the configuration of all the components of the transaction manager. * * @return the global configuration. */ public static Configuration getConfiguration() { Configuration configuration = configurationRef.get(); if (configuration == null) { configuration = new Configuration(); if (!configurationRef.compareAndSet(null, configuration)) { configuration = configurationRef.get(); } } return configuration; } /** * Create the task scheduler. * * @return the task scheduler. */ public static TaskScheduler getTaskScheduler() { TaskScheduler taskScheduler = taskSchedulerRef.get(); if (taskScheduler == null) { taskScheduler = new TaskScheduler(); if (!taskSchedulerRef.compareAndSet(null, taskScheduler)) { taskScheduler = taskSchedulerRef.get(); } else { taskScheduler.start(); } } return taskScheduler; } /** * Create the resource loader. * * @return the resource loader. */ public static ResourceLoader getResourceLoader() { ResourceLoader resourceLoader = resourceLoaderRef.get(); if (resourceLoader == null) { resourceLoader = new ResourceLoader(); if (!resourceLoaderRef.compareAndSet(null, resourceLoader)) { resourceLoader = resourceLoaderRef.get(); } } return resourceLoader; } /** * Create the transaction recoverer. * * @return the transaction recoverer. */ public static Recoverer getRecoverer() { Recoverer recoverer = recovererRef.get(); if (recoverer == null) { recoverer = new Recoverer(); if (!recovererRef.compareAndSet(null, recoverer)) { recoverer = recovererRef.get(); } } return recoverer; } /** * Create the 2PC executor. * * @return the 2PC executor. */ public static Executor getExecutor() { Executor executor = executorRef.get(); if (executor == null) { if (getConfiguration().isAsynchronous2Pc()) { if (LogDebugCheck.isDebugEnabled()) { log.finer("using AsyncExecutor"); } executor = new AsyncExecutor(); } else { if (LogDebugCheck.isDebugEnabled()) { log.finer("using SyncExecutor"); } executor = new SyncExecutor(); } if (!executorRef.compareAndSet(null, executor)) { executor.shutdown(); executor = executorRef.get(); } } return executor; } /** * Create the exception analyzer. * * @return the exception analyzer. */ @SuppressWarnings("unchecked") public static ExceptionAnalyzer getExceptionAnalyzer() { ExceptionAnalyzer analyzer = exceptionAnalyzerRef.get(); if (analyzer == null) { String exceptionAnalyzerName = getConfiguration().getExceptionAnalyzer(); analyzer = new DefaultExceptionAnalyzer(); if (exceptionAnalyzerName != null) { try { analyzer = (ExceptionAnalyzer) ClassLoaderUtils.loadClass(exceptionAnalyzerName) .getDeclaredConstructor() .newInstance(); } catch (Exception ex) { log.log(Level.WARNING, "failed to initialize custom exception analyzer, using default one instead", ex); } } if (!exceptionAnalyzerRef.compareAndSet(null, analyzer)) { analyzer.shutdown(); analyzer = exceptionAnalyzerRef.get(); } } return analyzer; } /** * Check if the transaction manager has started. * * @return true if the transaction manager has started. */ public static boolean isTransactionManagerRunning() { return transactionManager != null; } /** * Check if the task scheduler has started. * * @return true if the task scheduler has started. */ public static boolean isTaskSchedulerRunning() { return taskSchedulerRef.get() != null; } /** * Clear services references. Called at the end of the shutdown procedure. */ protected static synchronized void clear() { transactionManager = null; transactionSynchronizationRegistryRef.set(null); configurationRef.set(null); journalRef.set(null); taskSchedulerRef.set(null); resourceLoaderRef.set(null); recovererRef.set(null); executorRef.set(null); exceptionAnalyzerRef.set(null); } }




© 2015 - 2024 Weber Informatics LLC | Privacy Policy