javax.enterprise.concurrent.ManagedExecutors Maven / Gradle / Ivy
Go to download
Show more of this group Show more artifacts with this name
Show all versions of javax.enterprise.concurrent-api Show documentation
Show all versions of javax.enterprise.concurrent-api Show documentation
JSR 236:Concurrency Utilities for Java EE
/**
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
*
* Copyright (c) 2010-2012 Oracle and/or its affiliates. All rights reserved.
*
* The contents of this file are subject to the terms of either the GNU
* General Public License Version 2 only ("GPL") or the Common Development
* and Distribution License("CDDL") (collectively, the "License"). You
* may not use this file except in compliance with the License. You can
* obtain a copy of the License at
* https://glassfish.dev.java.net/public/CDDL+GPL_1_1.html
* or packager/legal/LICENSE.txt. See the License for the specific
* language governing permissions and limitations under the License.
*
* When distributing the software, include this License Header Notice in each
* file and include the License file at packager/legal/LICENSE.txt.
*
* GPL Classpath Exception:
* Oracle designates this particular file as subject to the "Classpath"
* exception as provided by Oracle in the GPL Version 2 section of the License
* file that accompanied this code.
*
* Modifications:
* If applicable, add the following below the License Header, with the fields
* enclosed by brackets [] replaced by your own identifying information:
* "Portions Copyright [year] [name of copyright owner]"
*
* Contributor(s):
* If you wish your version of this file to be governed by only the CDDL or
* only the GPL Version 2, indicate your decision by adding "[Contributor]
* elects to include this software in this distribution under the [CDDL or GPL
* Version 2] license." If you don't indicate a single choice of license, a
* recipient has the option to distribute your version of this file under
* either the CDDL, the GPL Version 2 or to extend the choice of license to
* its licensees as provided above. However, if you add GPL Version 2 code
* and therefore, elected the GPL Version 2 license, then the option applies
* only if the new code is made subject to such option by the copyright
* holder.
*/
package javax.enterprise.concurrent;
import java.util.HashMap;
import java.util.Locale;
import java.util.Map;
import java.util.concurrent.Callable;
/**
* Utility methods for classes defined in this package.
*
* @since 1.0
*/
public class ManagedExecutors {
/**
* Not suppose to create instances of this class
*/
private ManagedExecutors() {};
final static String NULL_TASK_ERROR_MSG = "Task cannot be null";
/**
* Utility method for checking the {@code isShutdown()} value of the current
* thread if it is a {@link ManageableThread} created from
* {@link ManagedThreadFactory#newThread(java.lang.Runnable) ManagedThreadFactory.newThread() }.
*
* @return Returns the {@code isShutdown()} value if the current thread is a
* {@code ManageableThread} created by {@code ManagedThreadFactory}, or
* false if the current thread is not a {@code ManageableThread}.
*
*/
public static boolean isCurrentThreadShutdown() {
Thread currThread = Thread.currentThread();
if (currThread instanceof ManageableThread) {
return ((ManageableThread) currThread).isShutdown();
}
return false;
}
/**
* Returns a {@link Runnable} object that also implements {@link ManagedTask}
* interface so it can receive notification of lifecycle events with the
* provided {@link ManagedTaskListener} when the task is submitted
* to a {@link ManagedExecutorService} or a {@link ManagedScheduledExecutorService}.
*
* Example:
*
* Runnable task = ...;
* ManagedTaskListener myTaskListener = ...;
* ManagedExecutorService executor = ...;
*
* Runnable taskWithListener = ManagedExecutors.managedTask(task, myTaskListener);
* executor.submit(taskWithListener);
*
* @param task the task to have the given ManagedTaskListener associated with
* @param taskListener (optional) the {@code ManagedTaskListener} to receive
* lifecycle events notification when the task is submitted. If {@code task}
* implements {@code ManagedTask}, and {@code taskListener} is not
* {@code null}, the {@code ManagedTaskListener} interface methods of the
* task will not be called.
* @return a Runnable object
* @throws IllegalArgumentException if {@code task} is {@code null}
*/
public static Runnable managedTask(Runnable task, ManagedTaskListener taskListener)
throws IllegalArgumentException {
return managedTask(task, null, taskListener);
}
/**
* Returns a {@link Runnable} object that also implements {@link ManagedTask}
* interface so it can receive notification of lifecycle events with the
* provided {@link ManagedTaskListener} and to provide additional execution
* properties when the task is submitted to a {@link ManagedExecutorService} or a
* {@link ManagedScheduledExecutorService}.
*
* @param task the task to have the given ManagedTaskListener associated with
* @param taskListener (optional) the {@code ManagedTaskListener} to receive
* lifecycle events notification when the task is submitted. If {@code task}
* implements {@code ManagedTask}, and {@code taskListener} is not
* {@code null}, the {@code ManagedTaskListener} interface methods of the
* task will not be called.
* @param executionProperties (optional) execution properties to provide additional hints
* to {@link ManagedExecutorService} or {@link ManagedScheduledExecutorService}
* when the task is submitted.
* If {@code task} implements {@code ManagedTask} with non-empty
* execution properties, the {@code Runnable} returned will contain the union
* of the execution properties specified in the {@code task} and the {@code executionProperties}
* argument, with the latter taking precedence if the same property key is
* specified in both.
* After the method is called, further changes to the {@code Map}
* object will not be reflected in the {@code Runnable} returned by this method.
* @return a Runnable object
* @throws IllegalArgumentException if {@code task} is {@code null}
*/
public static Runnable managedTask(Runnable task, Map executionProperties, ManagedTaskListener taskListener)
throws IllegalArgumentException {
if (task == null) {
throw new IllegalArgumentException(NULL_TASK_ERROR_MSG);
}
return new RunnableAdapter(task, executionProperties, taskListener);
}
/**
* Returns a {@link Callable} object that also implements {@link ManagedTask}
* interface so it can receive notification of lifecycle events with the
* provided {@link ManagedTaskListener} when the task is submitted
* to a {@link ManagedExecutorService} or a {@link ManagedScheduledExecutorService}.
*
* @param task the task to have the given ManagedTaskListener associated with
* @param taskListener (optional) the {@code ManagedTaskListener} to receive
* lifecycle events notification when the task is submitted. If {@code task}
* implements {@code ManagedTask}, and {@code taskListener} is not
* {@code null}, the {@code ManagedTaskListener} interface methods of the
* task will not be called.
* @return a Callable object
* @throws IllegalArgumentException if {@code task} is {@code null}
*/
public static Callable managedTask(Callable task, ManagedTaskListener taskListener)
throws IllegalArgumentException {
return managedTask(task, null, taskListener);
}
/**
* Returns a {@link Callable} object that also implements {@link ManagedTask}
* interface so it can receive notification of lifecycle events with the
* provided {@link ManagedTaskListener} and to provide additional execution
* properties when the task is submitted to a {@link ManagedExecutorService} or a
* {@link ManagedScheduledExecutorService}.
*
* @param task the task to have the given ManagedTaskListener associated with
* @param taskListener (optional) the {@code ManagedTaskListener} to receive
* lifecycle events notification when the task is submitted. If {@code task}
* implements {@code ManagedTask}, and {@code taskListener} is not
* {@code null}, the {@code ManagedTaskListener} interface methods of the
* task will not be called.
* @param executionProperties (optional) execution properties to provide additional hints
* to {@link ManagedExecutorService} or {@link ManagedScheduledExecutorService}
* when the task is submitted.
* If {@code task} implements {@code ManagedTask} with non-empty
* execution properties, the {@code Runnable} returned will contain the union
* of the execution properties specified in the {@code task} and the {@code executionProperties}
* argument, with the latter taking precedence if the same property key is
* specified in both.
* After the method is called, further changes to the {@code Map}
* object will not be reflected in the {@code Callable} returned by this method.
* @return a Callable object
* @throws IllegalArgumentException if {@code task} is {@code null}
*/
public static Callable managedTask(Callable task, Map executionProperties, ManagedTaskListener taskListener)
throws IllegalArgumentException {
if (task == null) {
throw new IllegalArgumentException(NULL_TASK_ERROR_MSG);
}
return new CallableAdapter(task, executionProperties, taskListener);
}
/**
* Adapter for Runnable to include ManagedTask interface methods
*/
static final class RunnableAdapter extends Adapter implements Runnable {
final Runnable task;
public RunnableAdapter(Runnable task, Map executionProperties, ManagedTaskListener taskListener) {
super(taskListener, executionProperties,
task instanceof ManagedTask? (ManagedTask)task: null);
this.task = task;
}
@Override
public void run() {
task.run();
}
}
/**
* Adapter for Callable to include ManagedTask interface methods
*/
static final class CallableAdapter extends Adapter implements Callable {
final Callable task;
public CallableAdapter(Callable task, Map executionProperties, ManagedTaskListener taskListener) {
super(taskListener, executionProperties,
task instanceof ManagedTask? (ManagedTask)task: null);
this.task = task;
}
@Override
public V call() throws Exception {
return task.call();
}
}
static class Adapter implements ManagedTask {
protected final ManagedTaskListener taskListener;
protected final Map executionProperties;
// If the Runnable or Callable to be wrapped also implements the
// ManagedTask interface, save it here to provide pieces of information
// that are not supplied by the provided ManagedTaskListener or
// executionProperties.
protected final ManagedTask managedTask;
public Adapter(ManagedTaskListener taskListener, Map executionProperties, ManagedTask managedTask) {
this.taskListener = taskListener;
this.managedTask = managedTask;
this.executionProperties =
initExecutionProperties(managedTask == null? null: managedTask.getExecutionProperties(),
executionProperties);
}
@Override
public ManagedTaskListener getManagedTaskListener() {
if (taskListener != null) {
return taskListener;
}
if (managedTask != null) {
return managedTask.getManagedTaskListener();
}
return null;
}
@Override
public Map getExecutionProperties() {
if (executionProperties != null) {
return executionProperties;
}
return null;
}
private Map initExecutionProperties(Map base, Map override) {
if (base == null && override == null) {
return null;
}
Map props = new HashMap<>();
if (base != null) {
props.putAll(base);
}
if (override != null) {
props.putAll(override);
}
return props;
}
}
}