I am using InheritableThreadLocal
in my Servlet
Class. So that It will available from it's child threads. Is that evil using InheritableThreadLocal
in thread pool executors? . Such as servlet thread pool.
My Questions.
1) Why should we avoid using InheritableThreadLocals
in servlets?
2) Is this memory leak possible in InheritableThreadLocal
?
3) Is there any alternative for InheritableThreadLocal
?.
4) What happens if the thread will be reused , the value stored in threadlocal
will not be cleared?
My Real Time Scenario
public class UserAccessFilter implements javax.servlet.Filter {
static final InheritableThreadLocal<String> currentRequestURI = new InheritableThreadLocal<String>();
public void doFilter(ServletRequest req, ServletResponse resp , FilterChain fc) throws IOException, ServletException{
String uri = request.getRequestURI();
fc.doFilter(request, response);
}
}
public class MailServlet extends HttpServlet{
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
String mailCount = req.getParameter("mailCount");
if(mailCount != null && !"".equals(mailCount) && mailCount.matches("[0-9]+")){
MailThread mailThread = new MailThread("[email protected]", generateToAddress(Integer.parseInt(mailCount))); //NO I18N
Thread t = new Thread(mailThread);
t.start();
}
resp.getWriter().println("Mail Servlet.............."); //NO I18N
}
}
class MailThread implements Runnable{
private String from;
private String to;
public MailThread(String from , String to){
this.from = from;
this.to = to;
}
@Override
public void run() {
sendMail();
}
public void sendMail(){
//I want this uri from child threads. I can't pass this value to this constructor.
String uri = currentRequestURI.get();
//Do Mail Operations
}
}
Filter --> Servlet A --> Child Thread ---> Mail Thread (Here I am getting the value setted in filter) .
Most common use of thread local is when you have some object that is not thread-safe, but you want to avoid synchronizing access to that object using synchronized keyword/block. Instead, give each thread its own instance of the object to work with.
Java ThreadLocal is used to create thread local variables. We know that all threads of an Object share it's variables, so the variable is not thread safe. We can use synchronization for thread safety but if we want to avoid synchronization, we can use ThreadLocal variables.
The ThreadLocal class is used to create thread local variables which can only be read and written by the same thread. For example, if two threads are accessing code having reference to same threadLocal variable then each thread will not see any modification to threadLocal variable done by other thread.
ThreadLocal instances are typically private static fields in classes that wish to associate state with a thread (e.g., a user ID or transaction ID). The use of ThreadLocal objects requires care in classes whose objects are required to be executed by multiple threads in a thread pool.
Why should we avoid using InheritableThreadLocals in servlets?
They represent a potential path for leaking information from one request to another. The "problem" is that requests are handled by a pool of threads. When on request is completed, the next request that a thread handles is likely to be for a different user. But if you forget to clear the thread local state on finishing the first request, there is a potential that it might be used by the second one.
Is a memory leak possible in InheritableThreadLocal?
Yes ... sort of. If we assume that the worker pool is bounded, the thread local state of any thread is likely to be overwritten, clearing the memory leak. At worst the problem is a bounded memory leak ... bounded by the number of threads in the pool.
The information leakage problem is more concerning.
Is there any alternative for InheritableThreadLocal?
Setting attributes in the request or response object is better.
What happens if the thread will be reused, the value stored in threadlocal will not be cleared.
It won't be cleared. THAT is the problem!
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With