diff --git a/pom.xml b/pom.xml
index 7667a9891..a039b2e29 100644
--- a/pom.xml
+++ b/pom.xml
@@ -1138,7 +1138,7 @@
.*.checks.indentation.ElseHandler75100
.*.checks.indentation.AbstractExpressionHandler9197
.*.checks.indentation.ForHandler7595
- .*.checks.indentation.HandlerFactory7781
+ .*.checks.indentation.HandlerFactory81100
.*.checks.indentation.ImportHandler5087
.*.checks.indentation.IndentationCheck10093
.*.checks.indentation.IndexHandler10075
diff --git a/src/main/java/com/puppycrawl/tools/checkstyle/Utils.java b/src/main/java/com/puppycrawl/tools/checkstyle/Utils.java
index 4f4d24b11..3ade1fc75 100644
--- a/src/main/java/com/puppycrawl/tools/checkstyle/Utils.java
+++ b/src/main/java/com/puppycrawl/tools/checkstyle/Utils.java
@@ -24,7 +24,9 @@ import com.puppycrawl.tools.checkstyle.api.TokenTypes;
import org.apache.commons.beanutils.ConversionException;
import java.io.File;
+import java.lang.reflect.Constructor;
import java.lang.reflect.Field;
+import java.lang.reflect.InvocationTargetException;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.util.ResourceBundle;
@@ -336,4 +338,35 @@ public final class Utils {
public static boolean isCommentType(String type) {
return isCommentType(getTokenId(type));
}
+
+ /**
+ * @param targetClass from which constructor is returned
+ * @param parameterTypes of constructor
+ * @return constructor of targetClass or {@link IllegalStateException} if any exception occurs
+ * @see Class#getConstructor(Class[])
+ */
+ public static Constructor> getConstructor(Class> targetClass, Class>... parameterTypes) {
+ try {
+ return targetClass.getConstructor(parameterTypes);
+ }
+ catch (NoSuchMethodException ex) {
+ throw new IllegalStateException(ex);
+ }
+ }
+
+ /**
+ * @param constructor to invoke
+ * @param parameters to pass to constructor
+ * @param type of constructor
+ * @return new instance of class or {@link IllegalStateException} if any exception occurs
+ * @see Constructor#newInstance(Object...)
+ */
+ public static T invokeConstructor(Constructor constructor, Object... parameters) {
+ try {
+ return constructor.newInstance(parameters);
+ }
+ catch (InstantiationException | IllegalAccessException | InvocationTargetException ex) {
+ throw new IllegalStateException(ex);
+ }
+ }
}
diff --git a/src/main/java/com/puppycrawl/tools/checkstyle/checks/indentation/HandlerFactory.java b/src/main/java/com/puppycrawl/tools/checkstyle/checks/indentation/HandlerFactory.java
index cec1e7305..186ed7fb0 100644
--- a/src/main/java/com/puppycrawl/tools/checkstyle/checks/indentation/HandlerFactory.java
+++ b/src/main/java/com/puppycrawl/tools/checkstyle/checks/indentation/HandlerFactory.java
@@ -20,14 +20,12 @@
package com.puppycrawl.tools.checkstyle.checks.indentation;
import com.google.common.collect.Maps;
+import com.puppycrawl.tools.checkstyle.Utils;
import com.puppycrawl.tools.checkstyle.api.DetailAST;
import com.puppycrawl.tools.checkstyle.api.TokenTypes;
import java.lang.reflect.Constructor;
-import java.lang.reflect.InvocationTargetException;
import java.util.Map;
import java.util.Set;
-import org.apache.commons.logging.Log;
-import org.apache.commons.logging.LogFactory;
/**
* Factory for handlers. Looks up constructor via reflection.
@@ -35,9 +33,6 @@ import org.apache.commons.logging.LogFactory;
* @author jrichard
*/
public class HandlerFactory {
- /** Logger for indentation check. */
- private static final Log LOG = LogFactory.getLog(HandlerFactory.class);
-
/**
* Registered handlers.
*/
@@ -90,19 +85,12 @@ public class HandlerFactory {
* the handler to register
*/
private void register(int type, Class> handlerClass) {
- try {
- final Constructor> ctor = handlerClass
- .getConstructor(new Class[] {IndentationCheck.class,
- DetailAST.class, // current AST
- AbstractExpressionHandler.class, // parent
- });
- typeHandlers.put(type, ctor);
- }
- catch (final NoSuchMethodException | SecurityException e) {
- final String message = "couldn't find ctor for " + handlerClass;
- LOG.debug(message, e);
- throw new RuntimeException(message);
- }
+ final Constructor> ctor = Utils.getConstructor(handlerClass,
+ IndentationCheck.class,
+ DetailAST.class, // current AST
+ AbstractExpressionHandler.class // parent
+ );
+ typeHandlers.put(type, ctor);
}
/**
@@ -154,26 +142,11 @@ public class HandlerFactory {
}
AbstractExpressionHandler expHandler = null;
- try {
- final Constructor> handlerCtor =
- typeHandlers.get(ast.getType());
- if (handlerCtor != null) {
- expHandler = (AbstractExpressionHandler) handlerCtor.newInstance(
- indentCheck, ast, parent);
- }
- }
- catch (final InstantiationException | InvocationTargetException e) {
- final String message = "couldn't instantiate constructor for " + ast;
- LOG.debug(message, e);
- throw new RuntimeException(message);
- }
- catch (final IllegalAccessException e) {
- final String message = "couldn't access constructor for " + ast;
- LOG.debug(message, e);
- throw new RuntimeException(message);
- }
- if (expHandler == null) {
- throw new RuntimeException("no handler for type " + ast.getType());
+ final Constructor> handlerCtor =
+ typeHandlers.get(ast.getType());
+ if (handlerCtor != null) {
+ expHandler = (AbstractExpressionHandler) Utils.invokeConstructor(
+ handlerCtor, indentCheck, ast, parent);
}
return expHandler;
}
diff --git a/src/test/java/com/puppycrawl/tools/checkstyle/UtilsTest.java b/src/test/java/com/puppycrawl/tools/checkstyle/UtilsTest.java
index 2dbf60e78..70452d279 100644
--- a/src/test/java/com/puppycrawl/tools/checkstyle/UtilsTest.java
+++ b/src/test/java/com/puppycrawl/tools/checkstyle/UtilsTest.java
@@ -26,9 +26,12 @@ import static com.puppycrawl.tools.checkstyle.Utils.fileExtensionMatches;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertTrue;
+import static org.junit.Assert.fail;
+import java.lang.reflect.Constructor;
import java.io.File;
import java.io.IOException;
+import java.util.Dictionary;
import org.apache.commons.beanutils.ConversionException;
import org.junit.Test;
@@ -124,4 +127,44 @@ public class UtilsTest {
boolean result = Utils.isPatternValid("some[invalidPattern");
assertFalse(result);
}
+
+ @Test
+ public void testGetExistingConstructor() throws NoSuchMethodException {
+ Constructor> constructor = Utils.getConstructor(String.class, String.class);
+
+ assertEquals(String.class.getConstructor(String.class), constructor);
+ }
+
+ @Test
+ public void testGetNonExistingConstructor() throws NoSuchMethodException {
+ try {
+ Utils.getConstructor(Math.class);
+ fail();
+ }
+ catch (IllegalStateException expected) {
+ assertEquals(NoSuchMethodException.class, expected.getCause().getClass());
+ }
+ }
+
+ @Test
+ public void testInvokeConstructor() throws NoSuchMethodException {
+ Constructor constructor = String.class.getConstructor(String.class);
+
+ String constructedString = Utils.invokeConstructor(constructor, "string");
+
+ assertEquals("string", constructedString);
+ }
+
+ @Test
+ public void testInvokeConstructorThatFails() throws NoSuchMethodException {
+ Constructor constructor = Dictionary.class.getConstructor();
+
+ try {
+ Utils.invokeConstructor(constructor);
+ fail();
+ }
+ catch (IllegalStateException expected) {
+ assertEquals(InstantiationException.class, expected.getCause().getClass());
+ }
+ }
}