/** * Copyright (c) 2000-present Liferay, Inc. All rights reserved. * * This library is free software; you can redistribute it and/or modify it under * the terms of the GNU Lesser General Public License as published by the Free * Software Foundation; either version 2.1 of the License, or (at your option) * any later version. * * This library is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS * FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more * details. */ package com.liferay.portal.increment; import com.liferay.portal.kernel.concurrent.BatchablePipe; import com.liferay.portal.kernel.increment.Increment; import com.liferay.portal.kernel.messaging.proxy.ProxyModeThreadLocal; import com.liferay.portal.kernel.util.ClassLoaderUtil; import com.liferay.portal.kernel.util.NamedThreadFactory; import com.liferay.portal.kernel.util.StringBundler; import com.liferay.portal.kernel.util.StringPool; import java.io.Serializable; import java.lang.reflect.Method; import java.util.concurrent.ExecutorService; import java.util.concurrent.SynchronousQueue; import java.util.concurrent.ThreadPoolExecutor; import java.util.concurrent.ThreadPoolExecutor.DiscardPolicy; import java.util.concurrent.TimeUnit; import java.util.concurrent.atomic.AtomicInteger; /** * @author Shuyang Zhou */ public class BufferedIncrementProcessor { public BufferedIncrementProcessor( BufferedIncrementConfiguration bufferedIncrementConfiguration, Method method) { _bufferedIncrementConfiguration = bufferedIncrementConfiguration; ThreadPoolExecutor threadPoolExecutor = new ThreadPoolExecutor( 0, _bufferedIncrementConfiguration.getThreadpoolMaxSize(), _bufferedIncrementConfiguration.getThreadpoolKeepAliveTime(), TimeUnit.SECONDS, new SynchronousQueue<Runnable>()); threadPoolExecutor.setRejectedExecutionHandler(new DiscardPolicy()); Class<?>[] parameterTypes = method.getParameterTypes(); StringBundler sb = new StringBundler(parameterTypes.length * 2 + 5); sb.append("BufferedIncrement-"); Class<?> clazz = method.getDeclaringClass(); sb.append(clazz.getSimpleName()); sb.append(StringPool.PERIOD); sb.append(method.getName()); sb.append(StringPool.OPEN_PARENTHESIS); for (Class<?> parameterType : parameterTypes) { sb.append(parameterType.getSimpleName()); sb.append(StringPool.COMMA); } sb.setIndex(sb.index() - 1); sb.append(StringPool.CLOSE_PARENTHESIS); threadPoolExecutor.setThreadFactory( new NamedThreadFactory( sb.toString(), Thread.NORM_PRIORITY, ClassLoaderUtil.getContextClassLoader())); _executorService = threadPoolExecutor; } public void destroy() { _executorService.shutdown(); } @SuppressWarnings("rawtypes") public void process(BufferedIncreasableEntry bufferedIncreasableEntry) { if (_batchablePipe.put(bufferedIncreasableEntry)) { Runnable runnable = new BufferedIncrementRunnable( _bufferedIncrementConfiguration, _batchablePipe, _queueLengthTracker, Thread.currentThread()); if (ProxyModeThreadLocal.isForceSync()) { runnable.run(); } else { _executorService.execute(runnable); } } } private final BatchablePipe<Serializable, Increment<?>> _batchablePipe = new BatchablePipe<>(); private final BufferedIncrementConfiguration _bufferedIncrementConfiguration; private final ExecutorService _executorService; private final AtomicInteger _queueLengthTracker = new AtomicInteger(); }