ThreadFactory usage in Java

Can someone briefly explain on HOW and WHEN to use a ThreadFactory? An example with and without using ThreadFactory might be really helpful to understand the differences.

Thanks!

Problem with Java ThreadFactory

IN my app I use a threadpool with a custom ThreadFactory. My code looks like: pool = Executors.newScheduledThreadPool(10, new TF()); class TF implements ThreadFactory { AtomicInteger count = new Atomi

Java – ThreadFactory memory leak?

This code: while (true) { new ThreadFactory() { @Override public Thread newThread(Runnable r) { return null; } }; } make the JVM go out of memory very quickly. Why?

Java: How does ThreadFactory handles Threads?

I’m currently using the default ThreadFactory and I’m not satisfied with it’s performance and queueing of tasks. As I searched about ThreadFactory, I want to consider it’s implementation. My question

Java ThreadFactory how to create ThreadCreationException for testing in JUnit

Trying to create a unit test (borderline integration testing) using ThreadFactory, and just wondering how do I ‘force’ Java/JVM to not being able to create more threads ? In other words how do I call

How Java’s ThreadPoolExecutor uses custom ThreadFactory?

The ThreadPoolExecutor class allows to give a custom ThreadFactory to create new threads. However, I do not understand how these threads are used within sun’s implementation of ThreadPoolExecutor. Thi

approach to null all references to objects created by a Java ThreadFactory

I have a Java ThreadFactory implementation spawning runnable thread subclass objects in my Android application. This application requires that all spawned threads are addressable before a certain even

How do I customize all the names of the child threads of a ThreadFactory in Java?

If I am extending an existing ThreadFactory implementation, how would I go able ensuring that all threads created would have the same prefix? I’m sick and tired of looking at Thread-9 in my logs and w

newCachedThreadPool with ThreadFactory

I am implement a thread pool for my application and I want to use newCachedThreadPool along with ThreadFactory, and I wonder what I wrote below is correct. 1.The idea of using newCachedThreadPool is t

Limit Java RAM usage?

we use Java for our project www.aerospaceresearch.net/constellation and use Java diretcly out of an uninstalled java bin-folder. We have some troubles with ram usage of this java differing between OS

newSingleThreadExecutor and sequentially when ThreadFactory is used

I am trying to understand something about the newSingleThreadExecutor – how is said below it executes the tasks sequentially, when no ThreadFactory mentioned. public static ExecutorService newSingleTh

Answers

The factory pattern is a creational design pattern used in software development to encapsulate the processes involved in the creation of objects.

Let’s assume we have some worker threads for different tasks and want them with special names (say for debugging purposes). So we could implement a ThreadFactory:

public class WorkerThreadFactory implements ThreadFactory {
   private int counter = 0;
   private String prefix = "";

   public WorkerThreadFactory(String prefix) {
     this.prefix = prefix;
   }

   public Thread newThread(Runnable r) {
     return new Thread(r, prefix + "-" + counter++);
   }
}

If you had such a requirement, it would be pretty difficult to implement it without a factory or builder pattern.


ThreadFactory is part of the Java API because it is used by other classes too. So the example above shows why we should use ‘a factory to create Threads’ in some occasions but, of course, there is absolutely no need to implement java.util.concurrent.ThreadFactory to accomplish this task.

Here’s one possible usage. If you have an executor service which executes your runnable tasks in multithreaded fashion and once in a while your thread die from an uncaught exception. Let’s assume that you wan’t to log all these exceptions. ThreadFactory solves this problem:

ExecutorService executor = Executors.newSingleThreadExecutor(new LoggingThreadFactory());

executor.submit(new Runnable() {
   @Override
   public void run() {
      someObject.someMethodThatThrowsRuntimeException();
   }
});

LoggingThreadFactory can be implemented like this one:

public class LoggingThreadFactory implements ThreadFactory
{

    @Override
    public Thread newThread(Runnable r)
    {
        Thread t = new Thread(r);

        t.setUncaughtExceptionHandler(new Thread.UncaughtExceptionHandler()
        {
            @Override
            public void uncaughtException(Thread t, Throwable e)
            {
                LoggerFactory.getLogger(t.getName()).error(e.getMessage(), e);
            }
        });

        return t;
    }
}

As mentioned by “InsertNickHere”, you’ll have to understand the Factory Pattern.

A good example for a use of a ThreadFactory is the ThreadPoolExecutor: The Executor will create Threads if necessary and take care of the pooling. If you want to step in at the creation process and give special names to the created Threads, or assign them to a ThreadGroup, you can create a ThreadFactory for that purpose and give it to the Executor.

It’s a little bit IoC-style.

IMHO the single most important function of a ThreadFactory is naming threads something useful. Having threads in a stacktrace named pool-1-thread-2 or worse Thread-12 is a complete pain when diagnosing problems.

Of course, having a ThreadGroup, daemon status and priority are all useful too.

Some inner workings

The topic is covered quite well except for some inner works that are not easily visible. While creating a thread w/ the constructor the newly created thread inherits current threads:

  • ThreadGroup (unless supplied or System.getSecurityManager().getThreadGroup() returns arbitrary ThreadGroup) – The thread group on its right own can be important in some cases and can result in improper thread termination/interruption. The ThreadGroup will stand as default exception handler.
  • ContextClassLoader – in managed environment that should not be a great issue since the environment shall switch the CCL, but if you are to implement that – keep it mind. Leaking the caller’s CCL is quite bad, so is the thread group (esp. if the threadGroup is some subclass and not direct java.lang.ThreadGroup – need to override ThreadGroup.uncaughtException)
  • AccessControlContext – here, there is virtually nothing to be done (except starting in a dedicated thread) since the field is for internal usage only, and few even suspect the existence of.
  • stack size (usually it’s unspecified but it can a -fun- thing to get a thread w/ very narrow stack size, based on the caller)
  • priority – most people do know about and tend to set it (more or less)
  • daemon status – usually that’s not very important and easily noticable (if the application just disappears)
  • Lastly: the thread inherits caller’s InheritableThreadLocal – which may (or may not) lead to some implications. Again nothing can be done about, besides spawning the thread into a dedicated thread.

Depending on the application the points above may have no effect at all but in some cases, some of them can lead to Class/Resources leaks that are hard to detect and exhibit not deterministic behavior.


That would make an extra long post but so…

below is some (hopefully) reusable code for ThreadFactory implementation, it can be used in managed environments to ensure proper ThreadGroup (which can limit priority or interrupt threads), ContextClassLoader, stacksize and so on are set (and/or can be configured) and not leaked. If there is any interest I can show how to deal w/ inherited ThreadLocals or the inherited acc (which essentially can leak the calling classloader)

package bestsss.util;

import java.lang.Thread.UncaughtExceptionHandler;
import java.security.AccessControlContext;
import java.security.AccessController;
import java.security.PrivilegedAction;
import java.util.concurrent.ThreadFactory;
import java.util.concurrent.atomic.AtomicLong;

public class ThreadFactoryX implements ThreadFactory{
    //thread properties
    long stackSize;
    String pattern;
    ClassLoader ccl;
    ThreadGroup group;
    int priority;
    UncaughtExceptionHandler exceptionHandler;
    boolean daemon;

    private boolean configured;

    private boolean wrapRunnable;//if acc is present wrap or keep it
    protected final AccessControlContext acc;

    //thread creation counter
    protected final AtomicLong counter = new AtomicLong();

    public ThreadFactoryX(){        
        final Thread t = Thread.currentThread();
        ClassLoader loader;
    AccessControlContext acc = null;
    try{
        loader =  t.getContextClassLoader();
        if (System.getSecurityManager()!=null){
            acc = AccessController.getContext();//keep current permissions             
            acc.checkPermission(new RuntimePermission("setContextClassLoader"));
        }
    }catch(SecurityException _skip){
        //no permission
        loader =null;
        acc = null;
    }

    this.ccl = loader;
    this.acc = acc;
    this.priority = t.getPriority();    
    this.daemon = true;//Executors have it false by default

    this.wrapRunnable = true;//by default wrap if acc is present (+SecurityManager)

    //default pattern - caller className
    StackTraceElement[] stack =  new Exception().getStackTrace();    
    pattern(stack.length>1?getOuterClassName(stack[1].getClassName()):"ThreadFactoryX", true);     
    }

    public ThreadFactory finishConfig(){
        configured = true;
        counter.addAndGet(0);//write fence "w/o" volatile
        return this;
    }

    public long getCreatedThreadsCount(){
        return counter.get();
    }

    protected void assertConfigurable(){
        if (configured)
            throw new IllegalStateException("already configured");
    }

    private static String getOuterClassName(String className){
        int idx = className.lastIndexOf('.')+1;
        className = className.substring(idx);//remove package
        idx = className.indexOf('$');
        if (idx<=0){
            return className;//handle classes starting w/ $
        }       
        return className.substring(0,idx);//assume inner class

    }

    @Override
    public Thread newThread(Runnable r) {
        configured = true;
        final Thread t = new Thread(group, wrapRunnable(r), composeName(r), stackSize);
        t.setPriority(priority);
        t.setDaemon(daemon);
        t.setUncaughtExceptionHandler(exceptionHandler);//securityException only if in the main group, shall be safe here
        //funny moment Thread.getUncaughtExceptionHandler() has a race.. badz (can throw NPE)

        applyCCL(t);
        return t;
    }

    private void applyCCL(final Thread t) {
        if (ccl!=null){//use factory creator ACC for setContextClassLoader
            AccessController.doPrivileged(new PrivilegedAction<Object>(){
                @Override
                public Object run() {
                    t.setContextClassLoader(ccl);
                    return null;
                }                               
            }, acc);        
        }
    }
    private Runnable wrapRunnable(final Runnable r){
        if (acc==null || !wrapRunnable){
            return r;
        }
        Runnable result = new Runnable(){
            public void run(){
                AccessController.doPrivileged(new PrivilegedAction<Object>(){
                    @Override
                    public Object run() {
                        r.run();
                        return null;
                    }                               
                }, acc);
            }
        };
        return result;      
    }


    protected String composeName(Runnable r) {
        return String.format(pattern, counter.incrementAndGet(), System.currentTimeMillis());
    }   


    //standard setters allowing chaining, feel free to add normal setXXX    
    public ThreadFactoryX pattern(String patten, boolean appendFormat){
        assertConfigurable();
        if (appendFormat){
            patten+=": %d @ %tF %<tT";//counter + creation time
        }
        this.pattern = patten;
        return this;
    }


    public ThreadFactoryX daemon(boolean daemon){
        assertConfigurable();
        this.daemon = daemon;
        return this;
    }

    public ThreadFactoryX priority(int priority){
        assertConfigurable();
        if (priority<Thread.MIN_PRIORITY || priority>Thread.MAX_PRIORITY){//check before actual creation
            throw new IllegalArgumentException("priority: "+priority);
        }
        this.priority = priority;
        return this;
    }

    public ThreadFactoryX stackSize(long stackSize){
        assertConfigurable();
        this.stackSize = stackSize;
        return this;
    }


    public ThreadFactoryX threadGroup(ThreadGroup group){
        assertConfigurable();
        this.group= group;
        return this;        
    }

    public ThreadFactoryX exceptionHandler(UncaughtExceptionHandler exceptionHandler){
        assertConfigurable();
        this.exceptionHandler= exceptionHandler;
        return this;                
    }

    public ThreadFactoryX wrapRunnable(boolean wrapRunnable){
        assertConfigurable();
        this.wrapRunnable= wrapRunnable;
        return this;                        
    }

    public ThreadFactoryX ccl(ClassLoader ccl){
        assertConfigurable();
        this.ccl = ccl;
        return this;
    }
}

Also some very simple usage:

ThreadFactory factory = new TreadFactoryX().priority(3).stackSize(0).wrapRunnable(false).pattern("Socket workers", true).
daemon(false).finishConfig();

Take a look at VerboseThreads (implements ThreadFactory) from jcabi-log. This implementation makes Threads that log exceptions when they are being thrown out of them. Very useful class when you need to see when and why your threads die.

It is always a good practice to use custom thread factory. The default factories are not much of use. You should use a custom factory for the following reasons:

  1. To have custom thread names
  2. To choose between thread types
  3. To choose Thread Priority
  4. To handle uncaught exceptions

Check this post: http://wilddiary.com/understanding-java-threadfactory-creating-custom-thread-factories/

ThreadFactory is an interface with a single method public abstract java.lang.Thread newThread(java.lang.Runnable arg0);

Its usage depends on your requirement. Suppose you want a particular functionality to always create Daemon threads. You can easily achieve this with ThreadFactory.

The below code is just for telling the fundamental. It is not doing any specific functionality.

package TestClasses;
import java.util.concurrent.ThreadFactory;
public class ThreadFactoryEx implements ThreadFactory{
    @Override
    public Thread newThread(Runnable r) {
        Thread t = new Thread(r);
        t.setDaemon(true);
        return t;
    }
}

package TestClasses;
import java.util.concurrent.ThreadPoolExecutor;
public class RunnableEx implements Runnable{
    @Override
    public void run() {
        // TODO Auto-generated method stub
        for (int i = 0; i < 5; i++) {
            System.out.println("in a loop" + i + "times");
        }
    }
}


package TestClasses;

import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;

public class Thread1 {
    public static void main(String[] args) {
        ExecutorService exe = Executors.newCachedThreadPool(new ThreadFactoryEx());
        for (int i = 0; i < 4; i++) {
            exe.execute(new RunnableEx());
        }
    }
}

ThreadFactory usage in Java

An object that creates new threads on demand. Using thread factories removes hardwiring of calls to new Thread, enabling applications to use special thread subclasses, priorities, etc.

The simplest implementation of this interface is just:

class SimpleThreadFactory implements ThreadFactory {
   public Thread newThread(Runnable r) {
     return new Thread(r);
   }
 }

DefaultThreadFactory of ThreadPoolExecutor.java

static class DefaultThreadFactory implements ThreadFactory {
        private static final AtomicInteger poolNumber = new AtomicInteger(1);
        private final ThreadGroup group;
        private final AtomicInteger threadNumber = new AtomicInteger(1);
        private final String namePrefix;

        DefaultThreadFactory() {
            SecurityManager s = System.getSecurityManager();
            group = (s != null) ? s.getThreadGroup() :
                                  Thread.currentThread().getThreadGroup();
            namePrefix = "pool-" +
                          poolNumber.getAndIncrement() +
                         "-thread-";
        }

        public Thread newThread(Runnable r) {
            Thread t = new Thread(group, r,
                                  namePrefix + threadNumber.getAndIncrement(),
                                  0);
            if (t.isDaemon())
                t.setDaemon(false);
            if (t.getPriority() != Thread.NORM_PRIORITY)
                t.setPriority(Thread.NORM_PRIORITY);
            return t;
        }
    }

Source