com.liferay.portal.spring.aop.RetryAdvice Maven / Gradle / Ivy
/**
* 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.spring.aop;
import com.liferay.petra.string.StringBundler;
import com.liferay.portal.kernel.aop.AopMethodInvocation;
import com.liferay.portal.kernel.aop.ChainableMethodAdvice;
import com.liferay.portal.kernel.log.Log;
import com.liferay.portal.kernel.log.LogFactoryUtil;
import com.liferay.portal.kernel.service.RetryAcceptor;
import com.liferay.portal.kernel.spring.aop.Property;
import com.liferay.portal.kernel.spring.aop.Retry;
import com.liferay.portal.util.PropsValues;
import java.lang.annotation.Annotation;
import java.lang.reflect.Method;
import java.util.HashMap;
import java.util.Map;
/**
* @author Matthew Tambara
*/
public class RetryAdvice extends ChainableMethodAdvice {
@Override
public Object createMethodContext(
Class> targetClass, Method method,
Map, Annotation> annotations) {
Retry retry = (Retry)annotations.get(Retry.class);
if (retry == null) {
return null;
}
int retries = retry.retries();
if (retries < 0) {
retries = PropsValues.RETRY_ADVICE_MAX_RETRIES;
}
Map properties = new HashMap<>();
for (Property property : retry.properties()) {
properties.put(property.name(), property.value());
}
Class extends RetryAcceptor> clazz = retry.acceptor();
try {
RetryAcceptor retryAcceptor = clazz.newInstance();
return new RetryContext(retryAcceptor, properties, retries);
}
catch (ReflectiveOperationException reflectiveOperationException) {
_log.error(reflectiveOperationException);
return null;
}
}
@Override
public Object invoke(
AopMethodInvocation aopMethodInvocation, Object[] arguments)
throws Throwable {
RetryContext retryContext =
aopMethodInvocation.getAdviceMethodContext();
RetryAcceptor retryAcceptor = retryContext._retryAcceptor;
Map properties = retryContext._properties;
int retries = retryContext._retries;
int totalRetries = retries;
if (retries >= 0) {
retries++;
}
Object returnValue = null;
Throwable throwable1 = null;
while ((retries < 0) || (retries-- > 0)) {
try {
returnValue = aopMethodInvocation.proceed(arguments);
if (!retryAcceptor.acceptResult(returnValue, properties)) {
return returnValue;
}
if (_log.isWarnEnabled() && (retries != 0)) {
String number = String.valueOf(retries);
if (retries < 0) {
number = "unlimited";
}
_log.warn(
StringBundler.concat(
"Retry on ", aopMethodInvocation, " for ", number,
" more times due to result ", returnValue));
}
}
catch (Throwable throwable2) {
throwable1 = throwable2;
if (!retryAcceptor.acceptException(throwable2, properties)) {
throw throwable2;
}
if (_log.isWarnEnabled() && (retries != 0)) {
String number = String.valueOf(retries);
if (retries < 0) {
number = "unlimited";
}
_log.warn(
StringBundler.concat(
"Retry on ", aopMethodInvocation, " for ", number,
" more times due to exception ", throwable1),
throwable1);
}
}
}
if (throwable1 != null) {
if (_log.isWarnEnabled()) {
_log.warn(
StringBundler.concat(
"Give up retrying on ", aopMethodInvocation, " after ",
totalRetries,
" retries and rethrow last retry's exception ",
throwable1),
throwable1);
}
throw throwable1;
}
if (_log.isWarnEnabled()) {
_log.warn(
StringBundler.concat(
"Give up retrying on ", aopMethodInvocation, " after ",
totalRetries,
" retries and returning the last retry's result ",
returnValue));
}
return returnValue;
}
private static final Log _log = LogFactoryUtil.getLog(RetryAdvice.class);
private static class RetryContext {
private RetryContext(
RetryAcceptor retryAcceptor, Map properties,
int retries) {
_retryAcceptor = retryAcceptor;
_properties = properties;
_retries = retries;
}
private final Map _properties;
private final int _retries;
private final RetryAcceptor _retryAcceptor;
}
} © 2015 - 2025 Weber Informatics LLC | Privacy Policy