An example: Imagine an application server which has a pool of worker threads. They will be kept alive until application server termination. A deployed web application uses a staticThreadLocal in one of its classes in order to store some thread-local data, an instance of another class (lets call it SomeClass) of the web application. This is done within the worker thread (e.g. this action originates from a HTTP request).
Important: By definition, a reference to a ThreadLocalvalue is kept until the "owning" thread dies or if the ThreadLocal itself is no longer reachable.
If the web application fails to clear the reference to the ThreadLocalon shutdown, bad things will happen: Because the worker thread will usually never die and the reference to the ThreadLocal is static, the ThreadLocal value still references the instance of SomeClass, a web application's class - even if the web application has been stopped!
As a consequence, the web application's classloader cannot be garbage collected, which means that all classes (and all static data) of the web application remain loaded (this affects the PermGen memory pool as well as the heap). Every redeployment iteration of the web application will increase permgen (and heap) usage.
Threads should never be killed, they should only be notified/interrupted in order to terminate gently by itself. Also, threads are expensive to create and often shared across multiple applications within the same container - but this is implementation-specific. However, some application servers drop all threads of a stopped web application (depending on the product/configuration), or renew its threads periodically in order to prevent such leaks.
In this case the only references to the ThreadLocal are in the static final field of a class that has now become a target for GC, and the reference from the worker threads. However, the references from the worker threads to the ThreadLocal are WeakReferences!
The values of a ThreadLocal are not weak references, however. So, if you have references in the values of a ThreadLocal to application classes, then these will maintain a reference to the ClassLoader and prevent GC. However, if your ThreadLocal values are just integers or strings or some other basic object type (e.g., a standard collection of the above), then there should not be a problem (they will only prevent GC of the boot/system classloader, which is never going to happen anyway).
It is still good practice to explicitly clean up a ThreadLocal when you are done with it, but in the case of the cited log4j bug the sky was definitely not falling
When we run this, we can see that the CustomClassLoader is indeed not garbage collected (as the thread local in the main thread has a reference to a Foo instance that was loaded by our custom classloader):
However, when we change the ThreadLocal to instead contain a reference to a simple Integer rather than a Foo instance:
Then we see that the custom classloader is now garbage collected (as the thread local on the main thread only has a reference to an integer loaded by the system classloader):
if you make the mistake of creating a new ThreadLocal instances over and over again (instead of using a static variable to hold a singleton instance), the thread local values won't get overwritten, and will accumulate in each thread's threadlocals map. This could result in a serious leak.
Assuming that you are talking about thread locals that are created / used during a webapp's processing of an HTTP request, then one way to avoid the thread local leaks is to register a ServletRequestListener with your webapp's ServletContext and implement the listener's requestDestroyed method to cleanup the thread locals for the current thread.
One common use of ThreadLocal is when you want to access some non thread-safe objects in threads without using synchronization mechanisms like synchronized block and locks. These variables will not share states among different threads, so there is no synchronization problem; while at the same since each thread will have only one instance of the ThreadLocal object, it saves memory.
publicclassThreadId {
// Atomic integer containing the next thread ID to be assigned
// Thread local variable containing each thread's ID
privatestaticfinalThreadLocal threadId =
newThreadLocal() {
@OverrideprotectedInteger initialValue() {
returnnextId.getAndIncrement();
}
};
// Returns the current thread's unique ID, assigning it if necessary
publicstaticintget() {
returnthreadId.get();
}
}
If you do not clean up when you're done, any references it holds to classes loaded as part of a deployed webapp will remain in the permanent heap and will never get garbage collected. Redeploying/undeploying the webapp will not clean up each Thread's reference to your webapp's class(es) since the Thread is not something owned by your webapp. Each successive deployment will create a new instance of the class which will never be garbage collected.
You will end up with out of memory exceptions due to java.lang.OutOfMemoryError: PermGen space
Starting with tomcat 6.0.25, the manager webapp has a new "Find Leaks" button. When triggered, it displays a list of webapps (their context path) that have been stopped (this includes undeployed and redeployed ones) but whose classloader failed to be GCed.
Many people use Filters to initialize and remove ThreadLocal variables. You can initialize ThreadLocal in filter, put some expensive object as ThreadLocal and once request has been processed remove it from ThreadLocal as shown in below example:
public class MyCounter {
private int count = 0;
public void increment() {
count++;
}
public int getCount() {
return count;
}
}
public class MyThreadLocal extends ThreadLocal<MyCounter> {
}
public class LeakingServlet extends HttpServlet {
private static MyThreadLocal myThreadLocal = new MyThreadLocal();
protected void doGet(HttpServletRequest request,
HttpServletResponse response) throws ServletException, IOException {
MyCounter counter = myThreadLocal.get();
if (counter == null) {
counter = new MyCounter();
myThreadLocal.set(counter);
}
response.getWriter().println(
"The current thread served this servlet " + counter.getCount()
+ " times");
counter.increment();
}
}
Normally, as the thread dies on end of execution, the objects stored in ThreadLocals are no longer referenced and the garbage collector takes care of removing such objects:
Each thread holds an implicit reference to its copy of a thread-local variable as long as the thread is alive and the ThreadLocal instance is accessible; after a thread goes away, all of its copies of thread-local instances are subject to garbage collection (unless other references to these copies exist).
But when the thread has been fetched from a thread pool, it does not die, but instead is returned to the pool. Since the thread is still alive, so are the referenced ThreadLocals. This manifests both as memory leaks and "leaking" of values from one request to another when the same ThreadLocal is used and the thread handling the request/task was used before.
https://veerasundar.com/blog/2010/11/java-thread-local-how-to-use-and-code-sample/ Consider you have a Servlet which calls some business methods. You have a requirement to generate a unique transaction id for each and every request this servlet process and you need to pass this transaction id to the business methods, for logging purpose. One solution would be passing this transaction id as a parameter to all the business methods.
X.ThreadLocal - leak when app redeployment https://plumbr.io/blog/locked-threads/how-to-shoot-yourself-in-foot-with-threadlocals It is often the easiest way to render a stateful class thread-safe. And encapsulate non-thread-safe classes so that they can safely be used in multithreaded environments. In addition to simplicity, using ThreadLocal to store a per-thread-singleton or per-thread context information has a valuable information included – by using a ThreadLocal, it’s clear that the object stored in the ThreadLocal is not shared between threads, simplifying the task of determining whether a class is thread-safe or not. Which
ThreadLocal gives you the opportunity to use the variables without explicitly passing them down through the method invocation chain. Which could be useful on certain occasions. But you guys out there who have created a n-layer architecture to abstract away different communication interfaces. And then grab HttpServletRequest from ThreadLocals in your DAO objects … what were you smoking when making this decision? It took a few hours and a second pair of eyes when we were digging up this particular case. But anyhow – be careful when using the powers of globalization. You end up creating unexpected dependencies within your code. And as you might remember – this is not a wise thing to do.
It is darn easy to introduce a memory leak to your code when using a ThreadLocal. Which serves as a nice demonstration about the complexities surrounding classloaders. If you are deploying your code in an application server then your application classes are loaded/unloaded with a different classloader than the one used by the application server itself. Which is not bad per se. But now considering that modern application servers also pool threads instead of creating a new one on each HttpRequest, we have built the foundation to a problem.
If one of the application classes stores a value in ThreadLocal variable and doesn’t remove it after the task at hand is completed, a copy of that Object will remain with the Thread (from the application server thread pool). Since lifespan of the pooled Thread surpasses that of the application, it will prevent the object and thus a ClassLoader being responsible for loading the application from being garbage collected. And we have created a leak, which has a chance to surface in a good old java.lang.OutOfMemoryError: PermGen space form.
ThreadLocal in Java is a mechanism to provide separate copy of shared object to every Thread. So that they no longer shared between multiple Threads and remain thread-safe.ThreadLocal variables are stored in a special map called ThreadLocalMap which is designed to hold thread local objects, it uses WeakReferences for keys. Since every Thread has strong reference to there copy of ThreadLocal variables, they are not garbage collected until Thread is Alive and this is what creates memory leak in a typical J2EE web application
In web server and application server like Tomcat or WebLogic, web-app is loaded by a different ClassLoader than which is used by Server itself. This ClassLoader loads and unloads classes from web application. Web servers also maintains ThreadPool, which is collection of worker thread, to server HTTP requests. Now if one of the Servlet or any other Java class from web application creates a ThreadLocal variable during requestprocessing and doesn't remove it after that, copy of that Object will remain with worker Thread and since life-span of worker Thread is more than web app itself, it will prevent the object and ClassLoader, which uploaded the web app, from being garbage collected. This will create a memory leak in Server. Now if you do this couple of time you may see java.lang.OutOfMemoryError: PermGen space . Now this brings an important question, is it possible to to use ThreadLocal variable safely in a managed environment? Answer is Yes,, but that requires a careful usage of ThreadLocal variable and making sure to remove the object from ThreadLocal once done.
How to use ThreadLocal safely in Java Web application
Many people use Filters to initialize and remove ThreadLocal variables. You can initialize ThreadLocal in filter, put some expensive object as ThreadLocal and once request has been processed remove it from ThreadLocal as shown in below example:
ThreadLocal
On basic level ThreadLocal provides Thread Confinement which is extension of local variable. while local variable only accessible on block they are declared, ThreadLocal are visible only in Single Thread. No two Thread can see each others ThreadLocal variable.
We want to have separate instances(private copy) of a class so that there will not be any conflict among multiple threads. Each instance will be unique for each thread. This is nothing but a way of implementing threadsafety.
Thread Local can be considered as a scope of access, like a request scope or session scope. It’s athread scope. You can set any object in Thread Local and this object will be global and local to the specific thread which is accessing this object.
Values stored in Thread Local are global to the thread, meaning that they can be accessed from anywhere inside that thread. If a thread calls methods from several classes, then all the methods can see the Thread Local variable set by other methods (because they are executing in same thread). The value need not be passed explicitly. It’s like how you use global variables.
Values stored in Thread Local are local to the thread, meaning that each thread will have it’s own Thread Local variable. One thread can not access/modify other thread’s Thread Local variables.
1) ThreadLocal are fantastic to implement Per Thread Singleton classes or per thread context information like transaction id.
2) You can wrap any non Thread Safe object in ThreadLocal and suddenly its uses becomes Thread-safe, as its only being used by Thread Safe. One of the classic example of ThreadLocal is sharing SimpleDateForamt. SinceSimpleDateFormat is not thread safe, having a global formatter may not work but having per Thread formatter will certainly work.
3) ThreadLocal provides another way to extend Thread. If you want to preserve or carry information from one method call to another you can carry it by using ThreadLocal. This can provide immense flexibility as you don't need to modify any method.
3. Each thread holds an exclusive copy of ThreadLocal variable which becomes eligible to Garbage collection after thread finished or died, normally or due to any Exception, Given those ThreadLocal variable doesn't have any other live references.
4. ThreadLocal variables in Java are generally private static fields in Classes and maintain its state inside Thread.
A typical example of using ThreadLocal would be as an alternative to an object or resource pool, when we don't mind creating one object per thread. Let's consider the example of a pool of Calendar instances. In an application that does a lot of date manipulation, Calendar classes may be a good candidates for pooling because:
Creating a Calendar is non-trivial (various calculations and accesses to localisation resources need to be made each time one is created);
There's no actual requirement to shareCalendars between threads or have fewer calendars than threads.
Consider you have a Servlet which calls some business methods. You have a requirement to generate a unique transaction id for each and every request this servlet process and you need to pass this transaction id to the business methods, for logging purpose. One solution would be passing this transaction id as a parameter to all the business methods. But this is not a good solution as the code is redundant and unnecessary.
To solve that, you can use Thread Local. You can generate a transaction id (either in servlet or better in a filter) and set it in the Thread Local. After this, what ever the business method, that this servlet calls, can access the transaction id from the thread local.
An instance of the object is frequently needed by a given thread;
The application pools threads, such as in a typical server (if every time the thread-local is used it is from a new thread, then a new object will still be created on each call!);
It doesn't matter that Thread A will never share an instance with Thread B;
Random number generators (provided a per-thread sequence was acceptable); XML parsers or other cases where creating an instance involves going through slightly non-trival code to 'choose a registered service provider'; Per-thread information such as profiling data which will be periodically collated.
Note that it is generally better not to re-use objects that are trivial to construct and finalize.
Example using ThreadLocal to re-use Calendar objects
public class CalendarFactory {
private ThreadLocal<Calendar> calendarRef = new ThreadLocal<Calendar>() {
protected Calendar initialValue() {
return new GregorianCalendar();
}
};
private static CalendarFactory instance = new CalendarFactory();
public static CalendarFactory getFactory() { return instance; }
public Calendar getCalendar() {
return calendarRef.get();
}
// Don't let outsiders create new factories directly
private CalendarFactory() {}
}
ThreadLocalRandom It can be used to generate random numbers specific to parallel threads. Seed for random number will be unique for each thread.
ThreadLocalRandom.current().nextInt( 1, 3);
InheritableThreadLocal
The InheritableThreadLocal class is a subclass of ThreadLocal. Instead of each thread having its own value inside a ThreadLocal, the InheritableThreadLocal grants access to values to a thread and all child threads created by that thread.
http://www.appneta.com/blog/introduction-to-javas-threadlocal-storage/ ThreadLocal is implemented by having a Map (a ThreadLocalMap) as field (with WeakReference entry) within each Thread instance. (There are actually 2 maps; the second one is used for InheritabeleThreadLocal, but let’s not complicate the picture). The keys of those maps are the corresponding ThreadLocals themselves. Therefore, when a set/get is called on a ThreadLocal, it looks at the current thread, find the map, and look up the value with “this” ThreadLocal instance.
Still confused? I certainly am. Let’s look at a real example.
Code running in Thread 1 calls set() on ThreadLocal instance “A” with value “123″
Code running in Thread 2 calls set() on ThreadLocal instance “A” with value “234″
Code running in Thread 1 calls set() on ThreadLocal instance “B” with value “345″
And this is the end result:
Thread 1 (the instance)’s field ThreadLocalMap (m1) has 2 entries:
Key
Value
ThreadLocal A
“123″
ThreadLocal B
“345″
Thread 2 (the instance)’s field ThreadLocalMap (m2) has 1 entry:
Key
Value
ThreadLocal A
“234″
Now if some code logic in Thread 1 calls get() on ThreadLocal instance “A”, the ThreadLocal logic will lookup the current Thread, which is instance Thread 1, then access the field ThreadLocalMap of that Thread instance, which is m1, it can then lookup the value by using m1.get(this), with “this” as ThreadLocal and the result is “123″
Always clean up/reset your threadlocal after you have finished your “unit of operation”! Even though the current code might be simple enough to bypass the cleanups, it might be adapted and integrated into servlets/thread pooling later on!
* The next hash code to be given out. Updated atomically. Starts at
* zero.
*/
privatestaticAtomicIntegernextHashCode=
newAtomicInteger();
Returns the value in the current thread's copy of this thread-local variable. If the variable has no value for the current thread, it is first initialized to the value returned by an invocation of the initialValue method.
publicTget(){
Threadt=Thread.currentThread();
ThreadLocalMapmap=getMap(t);
if(map!=null){
ThreadLocalMap.Entrye=map.getEntry(this);
if(e!=null){
@SuppressWarnings("unchecked")
Tresult=(T)e.value;
returnresult;
}
}
returnsetInitialValue();
}
privateTsetInitialValue(){
Tvalue=initialValue();
Threadt=Thread.currentThread();
ThreadLocalMapmap=getMap(t);
if(map!=null)
map.set(this,value);
else
createMap(t,value);
returnvalue;
}
publicvoidset(Tvalue){
Threadt=Thread.currentThread();
ThreadLocalMapmap=getMap(t);
if(map!=null)
map.set(this,value);
else
createMap(t,value);
}
publicvoidremove(){
ThreadLocalMapm=getMap(Thread.currentThread());
if(m!=null)
m.remove(this);
}
* Get the map associated with a ThreadLocal. Overridden in
ThreadLocalMap is a customized hash map suitable only for maintaining thread local values. No operations are exported outside of the ThreadLocal class. The class is package private to allow declaration of fields in class Thread. To help deal with very large and long-lived usages, the hash table entries use WeakReferences for keys. However, since reference queues are not used, stale entries are guaranteed to be removed only when the table starts running out of space.
staticclass{
* The entries in this hash map extend WeakReference, using
* its main ref field as the key (which is always a
* ThreadLocal object). Note that null keys (i.e. entry.get()
* == null) mean that the key is no longer referenced, so the
* entry can be expunged from table. Such entries are referred to
http://howtodoinjava.com/2014/12/24/when-and-how-to-use-thread-local-variables/
When to use ThreadLocal?
For example, consider you are working on a eCommerce application. You have a requirement to generate a unique transaction id for each and every customer request this controller process and you need to pass this transaction id to the business methods in manager/DAO classes for logging purpose. One solution could be passing this transaction id as a parameter to all the business methods. But this is not a good solution as the code is redundant and unnecessary.
To solve that, here you can use ThreadLocal variable. You can generate a transaction id in controller OR any pre-processor interceptor; and set this transaction id in the ThreadLocal. After this, whatever the methods, that this controller calls, they all can access this transaction id from the threadlocal.
classDemoTask implementsRunnable {
// Atomic integer containing the next thread ID to be assigned
// Thread local variable containing each thread's ID
privatestaticfinalThreadLocal<Integer> threadId =
newThreadLocal<Integer>() {
@Override
protectedInteger initialValue() {
returnnextId.getAndIncrement();
}
};
// Returns the current thread's unique ID, assigning it if necessary
publicintgetThreadId() {
returnthreadId.get();
}
// Returns the current thread's starting timestamp
privatestaticfinalThreadLocal<Date> startDate =
newThreadLocal<Date>() {
protectedDate initialValue() {
returnnewDate();
}
};
}
In wabapp server, it may be keep a thread pool, so a ThreadLocal var should be removed before response to the client, since current thread may be reused by next request. Also, if you do not clean up when you’re done, any references it holds to classes loaded as part of a deployed webapp will remain in the permanent heap and will never get garbage collected.