/* See LICENSE for licensing and NOTICE for copyright. */
package org.ldaptive.concurrent;
import java.util.Arrays;
import java.util.List;
import java.util.concurrent.ExecutorService;
import org.ldaptive.Connection;
import org.ldaptive.SearchOperation;
import org.ldaptive.SearchRequest;
import org.ldaptive.SearchResult;
import org.ldaptive.cache.Cache;
import org.ldaptive.handler.OperationExceptionHandler;
import org.ldaptive.handler.OperationResponseHandler;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
/**
* Base class for concurrent search executors.
*
* @author Middleware Services
*/
public abstract class AbstractSearchExecutor extends SearchRequest
{
/** Logger for this class. */
protected final Logger logger = LoggerFactory.getLogger(getClass());
/** To submit operations to. */
private final ExecutorService service;
/** Handler to handle search exceptions. */
private OperationExceptionHandler<SearchRequest, SearchResult> searchExceptionHandler;
/** Handlers to handle search responses. */
private OperationResponseHandler<SearchRequest, SearchResult>[] searchResponseHandlers;
/** Cache to use when performing searches. */
private Cache<SearchRequest> searchCache;
/**
* Creates a new abstract search executor.
*
* @param es executor service
*/
public AbstractSearchExecutor(final ExecutorService es)
{
if (es == null) {
throw new NullPointerException("ExecutorService cannot be null");
}
service = es;
}
/**
* Returns the executor service for this search executor.
*
* @return executor service
*/
protected ExecutorService getExecutorService()
{
return service;
}
/**
* Returns the search exception handler.
*
* @return search exception handler
*/
public OperationExceptionHandler<SearchRequest, SearchResult> getSearchExceptionHandler()
{
return searchExceptionHandler;
}
/**
* Sets the search exception handler.
*
* @param handler search exception handler
*/
public void setSearchExceptionHandler(final OperationExceptionHandler<SearchRequest, SearchResult> handler)
{
searchExceptionHandler = handler;
}
/**
* Returns the search response handlers.
*
* @return search response handlers
*/
public OperationResponseHandler<SearchRequest, SearchResult>[] getSearchResponseHandlers()
{
return searchResponseHandlers;
}
/**
* Sets the search response handlers.
*
* @param handlers search response handlers
*/
@SuppressWarnings("unchecked")
public void setSearchResponseHandlers(final OperationResponseHandler<SearchRequest, SearchResult>... handlers)
{
searchResponseHandlers = handlers;
}
/**
* Returns the search cache.
*
* @return cache
*/
public Cache<SearchRequest> getSearchCache()
{
return searchCache;
}
/**
* Sets the search cache.
*
* @param cache to set
*/
public void setSearchCache(final Cache<SearchRequest> cache)
{
searchCache = cache;
}
/** Shuts down the executor service. See {@link ExecutorService#shutdown()}. */
public void shutdown()
{
service.shutdown();
}
/**
* Immediately shuts down the executor service. See {@link ExecutorService#shutdownNow()}.
*
* @return list of tasks that never executed
*/
public List<Runnable> shutdownNow()
{
return service.shutdownNow();
}
/**
* Creates a new search operation configured with the properties on this search executor.
*
* @param conn to pass to the search operation
*
* @return search operation
*/
protected SearchOperation createSearchOperation(final Connection conn)
{
final SearchOperation op = new SearchOperation(conn);
if (searchExceptionHandler != null) {
op.setOperationExceptionHandler(searchExceptionHandler);
}
if (searchResponseHandlers != null) {
op.setOperationResponseHandlers(searchResponseHandlers);
}
if (searchCache != null) {
op.setCache(searchCache);
}
return op;
}
@Override
protected void finalize()
throws Throwable
{
try {
shutdown();
} finally {
super.finalize();
}
}
@Override
public String toString()
{
return
String.format(
"[%s@%d::service=%s, searchExceptionHandler=%s, " +
"searchResponseHandlers=%s, searchCache=%s]",
getClass().getName(),
hashCode(),
service,
searchExceptionHandler,
Arrays.toString(searchResponseHandlers),
searchCache);
}
}