# How to use MDC with thread pools in Java?

In Java, MDC (Mapped Diagnostic Context) is a feature provided by logging frameworks like Log4j and Logback. It allows you to associate key-value pairs with the current thread's execution context, which can be very useful in multi-threaded environments, including scenarios involving thread pools.

Using MDC with thread pools involves setting and clearing MDC values appropriately before and after executing tasks in the thread pool. This ensures that each task executed by a thread in the pool has its specific MDC values, preventing interference between threads.

Here's how you can use MDC with thread pools in Java:

## 1. **Initialize MDC values before submitting tasks to the thread pool**

Before submitting tasks to the thread pool, set the MDC values that you want to associate with the executing threads. For example:

```java
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.slf4j.MDC;

public class Task implements Runnable {
    private static final Logger LOGGER = LoggerFactory.getLogger(Task.class);

    private String requestId;

    public Task(String requestId) {
        this.requestId = requestId;
    }

    @Override
    public void run() {
        // Set MDC values for the current thread
        MDC.put("requestId", requestId);

        // Perform your task logic
        LOGGER.info("Processing request: {}", requestId);

        // Clear MDC values to avoid interference with other tasks
        MDC.clear();
    }
}
```

## 2. **Submit tasks to the thread pool**

Once you have the tasks created with their associated MDC values, you can submit them to the thread pool for execution. Make sure to use an appropriate thread pool implementation, such as `ExecutorService`, to manage the threads.

```java
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;

public class Main {
    public static void main(String[] args) {
        // Create a thread pool with a fixed number of threads
        int numThreads = 5;
        ExecutorService threadPool = Executors.newFixedThreadPool(numThreads);

        // Submit tasks with different requestId values
        for (int i = 1; i <= 10; i++) {
            String requestId = "REQ_" + i;
            threadPool.submit(new Task(requestId));
        }

        // Shutdown the thread pool when no more tasks need to be submitted
        threadPool.shutdown();
    }
}
```

In this example, we are creating a thread pool with five threads and submitting ten tasks, each with a different `requestId`. The `Task` class sets the `requestId` as an MDC value for the current thread and logs the processing of each request. After the task is completed, we clear the MDC values to prevent interference with other tasks.

By using MDC with thread pools, you can ensure that each task in the pool has its specific MDC values, providing a better context for log messages and easier debugging in multi-threaded applications.

To learn more about logging, visit [Better Stack Community](https://betterstack.com/community/guides/logging/).