Skip to content

Commit 197afdd

Browse files
authored
Merge pull request #990 from Simulant87/984-refactor-cognitive-complexity-populateMap
Refactor JSONObject populateMap() per SonarQube
2 parents 1bdaacc + 5063d31 commit 197afdd

File tree

1 file changed

+67
-39
lines changed

1 file changed

+67
-39
lines changed

src/main/java/org/json/JSONObject.java

Lines changed: 67 additions & 39 deletions
Original file line numberDiff line numberDiff line change
@@ -1780,46 +1780,30 @@ private void populateMap(Object bean, Set<Object> objectsRecord, JSONParserConfi
17801780

17811781
Method[] methods = includeSuperClass ? klass.getMethods() : klass.getDeclaredMethods();
17821782
for (final Method method : methods) {
1783-
final int modifiers = method.getModifiers();
1784-
if (Modifier.isPublic(modifiers)
1785-
&& !Modifier.isStatic(modifiers)
1786-
&& method.getParameterTypes().length == 0
1787-
&& !method.isBridge()
1788-
&& method.getReturnType() != Void.TYPE
1789-
&& isValidMethodName(method.getName())) {
1790-
final String key = getKeyNameFromMethod(method);
1791-
if (key != null && !key.isEmpty()) {
1792-
try {
1793-
final Object result = method.invoke(bean);
1794-
if (result != null || jsonParserConfiguration.isUseNativeNulls()) {
1795-
// check cyclic dependency and throw error if needed
1796-
// the wrap and populateMap combination method is
1797-
// itself DFS recursive
1798-
if (objectsRecord.contains(result)) {
1799-
throw recursivelyDefinedObjectException(key);
1800-
}
1801-
1802-
objectsRecord.add(result);
1803-
1804-
testValidity(result);
1805-
this.map.put(key, wrap(result, objectsRecord));
1806-
1807-
objectsRecord.remove(result);
1808-
1809-
// we don't use the result anywhere outside of wrap
1810-
// if it's a resource we should be sure to close it
1811-
// after calling toString
1812-
if (result instanceof Closeable) {
1813-
try {
1814-
((Closeable) result).close();
1815-
} catch (IOException ignore) {
1816-
}
1817-
}
1783+
final String key = getKeyNameFromMethod(method);
1784+
if (key != null && !key.isEmpty()) {
1785+
try {
1786+
final Object result = method.invoke(bean);
1787+
if (result != null || jsonParserConfiguration.isUseNativeNulls()) {
1788+
// check cyclic dependency and throw error if needed
1789+
// the wrap and populateMap combination method is
1790+
// itself DFS recursive
1791+
if (objectsRecord.contains(result)) {
1792+
throw recursivelyDefinedObjectException(key);
18181793
}
1819-
} catch (IllegalAccessException ignore) {
1820-
} catch (IllegalArgumentException ignore) {
1821-
} catch (InvocationTargetException ignore) {
1794+
1795+
objectsRecord.add(result);
1796+
1797+
testValidity(result);
1798+
this.map.put(key, wrap(result, objectsRecord));
1799+
1800+
objectsRecord.remove(result);
1801+
1802+
closeClosable(result);
18221803
}
1804+
} catch (IllegalAccessException ignore) {
1805+
} catch (IllegalArgumentException ignore) {
1806+
} catch (InvocationTargetException ignore) {
18231807
}
18241808
}
18251809
}
@@ -1830,6 +1814,10 @@ private static boolean isValidMethodName(String name) {
18301814
}
18311815

18321816
private static String getKeyNameFromMethod(Method method) {
1817+
if (!isValidMethod(method)) {
1818+
return null;
1819+
}
1820+
18331821
final int ignoreDepth = getAnnotationDepth(method, JSONPropertyIgnore.class);
18341822
if (ignoreDepth > 0) {
18351823
final int forcedNameDepth = getAnnotationDepth(method, JSONPropertyName.class);
@@ -1840,7 +1828,7 @@ private static String getKeyNameFromMethod(Method method) {
18401828
}
18411829
}
18421830
JSONPropertyName annotation = getAnnotation(method, JSONPropertyName.class);
1843-
if (annotation != null && annotation.value() != null && !annotation.value().isEmpty()) {
1831+
if (annotationValueNotEmpty(annotation)) {
18441832
return annotation.value();
18451833
}
18461834
String key;
@@ -1866,6 +1854,46 @@ private static String getKeyNameFromMethod(Method method) {
18661854
return key;
18671855
}
18681856

1857+
/**
1858+
* checks if the annotation is not null and the {@link JSONPropertyName#value()} is not null and is not empty.
1859+
* @param annotation the annotation to check
1860+
* @return true if the annotation and the value is not null and not empty, false otherwise.
1861+
*/
1862+
private static boolean annotationValueNotEmpty(JSONPropertyName annotation) {
1863+
return annotation != null && annotation.value() != null && !annotation.value().isEmpty();
1864+
}
1865+
1866+
/**
1867+
* Checks if the method is valid for the {@link #populateMap(Object, Set, JSONParserConfiguration)} use case
1868+
* @param method the Method to check
1869+
* @return true, if valid, false otherwise.
1870+
*/
1871+
private static boolean isValidMethod(Method method) {
1872+
final int modifiers = method.getModifiers();
1873+
return Modifier.isPublic(modifiers)
1874+
&& !Modifier.isStatic(modifiers)
1875+
&& method.getParameterTypes().length == 0
1876+
&& !method.isBridge()
1877+
&& method.getReturnType() != Void.TYPE
1878+
&& isValidMethodName(method.getName());
1879+
}
1880+
1881+
/**
1882+
* calls {@link Closeable#close()} on the input, if it is an instance of Closable.
1883+
* @param input the input to close, if possible.
1884+
*/
1885+
private static void closeClosable(Object input) {
1886+
// we don't use the result anywhere outside of wrap
1887+
// if it's a resource we should be sure to close it
1888+
// after calling toString
1889+
if (input instanceof Closeable) {
1890+
try {
1891+
((Closeable) input).close();
1892+
} catch (IOException ignore) {
1893+
}
1894+
}
1895+
}
1896+
18691897
/**
18701898
* Searches the class hierarchy to see if the method or it's super
18711899
* implementations and interfaces has the annotation.

0 commit comments

Comments
 (0)