Skip to content

Commit

Permalink
Issue checkstyle#9280: New property 'accessModifiers' as substitution…
Browse files Browse the repository at this point in the history
… of 'scope' and 'excludeScope' in JavadocVariableCheck
  • Loading branch information
kkoutsilis committed Dec 24, 2024
1 parent 8e5396f commit 4aae949
Show file tree
Hide file tree
Showing 22 changed files with 244 additions and 210 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -19,15 +19,19 @@

package com.puppycrawl.tools.checkstyle.checks.javadoc;

import com.puppycrawl.tools.checkstyle.api.Scope;
import com.puppycrawl.tools.checkstyle.utils.CheckUtil;
import java.util.Arrays;
import java.util.Optional;
import java.util.regex.Pattern;

import com.puppycrawl.tools.checkstyle.StatelessCheck;
import com.puppycrawl.tools.checkstyle.api.AbstractCheck;
import com.puppycrawl.tools.checkstyle.api.DetailAST;
import com.puppycrawl.tools.checkstyle.api.FileContents;
import com.puppycrawl.tools.checkstyle.api.Scope;
import com.puppycrawl.tools.checkstyle.api.TextBlock;
import com.puppycrawl.tools.checkstyle.api.TokenTypes;
import com.puppycrawl.tools.checkstyle.checks.naming.AccessModifierOption;
import com.puppycrawl.tools.checkstyle.utils.ScopeUtil;

/**
Expand All @@ -36,22 +40,17 @@
* </div>
* <ul>
* <li>
* Property {@code excludeScope} - Specify the visibility scope where Javadoc
* comments are not checked.
* Type is {@code com.puppycrawl.tools.checkstyle.api.Scope}.
* Default value is {@code null}.
* Property {@code accessModifiers} - Access modifiers of methods where parameters are
* checked.
* Type is {@code com.puppycrawl.tools.checkstyle.checks.naming.AccessModifierOption[]}.
* Default value is {@code public, protected, package, private}.
* </li>
* <li>
* Property {@code ignoreNamePattern} - Specify the regexp to define variable names to ignore.
* Type is {@code java.util.regex.Pattern}.
* Default value is {@code null}.
* </li>
* <li>
* Property {@code scope} - Specify the visibility scope where Javadoc comments are checked.
* Type is {@code com.puppycrawl.tools.checkstyle.api.Scope}.
* Default value is {@code private}.
* </li>
* <li>
* Property {@code tokens} - tokens to check
* Type is {@code java.lang.String[]}.
* Validation type is {@code tokenSet}.
Expand Down Expand Up @@ -84,35 +83,28 @@ public class JavadocVariableCheck
* A key is pointing to the warning message text in "messages.properties"
* file.
*/
public static final String MSG_JAVADOC_MISSING = "javadoc.missing";

/** Specify the visibility scope where Javadoc comments are checked. */
private Scope scope = Scope.PRIVATE;

/** Specify the visibility scope where Javadoc comments are not checked. */
private Scope excludeScope;
public static final String MSG_JAVADOC_MISSING = "javadoc.missing";
/** Access modifiers of methods where parameters are checked. */
private AccessModifierOption[] accessModifiers = {
AccessModifierOption.PUBLIC,
AccessModifierOption.PROTECTED,
AccessModifierOption.PACKAGE,
AccessModifierOption.PRIVATE,
};

/** Specify the regexp to define variable names to ignore. */
private Pattern ignoreNamePattern;

/**
* Setter to specify the visibility scope where Javadoc comments are checked.
*
* @param scope a scope.
* @since 3.0
*/
public void setScope(Scope scope) {
this.scope = scope;
}

/**
* Setter to specify the visibility scope where Javadoc comments are not checked.
* Setter to access modifiers of methods where parameters are checked.
*
* @param excludeScope a scope.
* @since 3.4
* @param accessModifiers access modifiers of methods which should be checked.
* @since 11.0.0
*/
public void setExcludeScope(Scope excludeScope) {
this.excludeScope = excludeScope;
public void setAccessModifiers(AccessModifierOption... accessModifiers) {
this.accessModifiers =
Arrays.copyOf(accessModifiers, accessModifiers.length);
}

/**
Expand Down Expand Up @@ -176,6 +168,17 @@ private boolean isIgnored(DetailAST ast) {
|| "serialVersionUID".equals(name);
}

/**
* Checks whether a method has the correct access modifier to be checked.
*
* @param accessModifier the access modifier of the method.
* @return whether the method matches the expected access modifier.
*/
private boolean matchAccessModifiers(final AccessModifierOption accessModifier) {
return Arrays.stream(accessModifiers)
.anyMatch(modifier -> modifier == accessModifier);
}

/**
* Whether we should check this node.
*
Expand All @@ -185,14 +188,73 @@ private boolean isIgnored(DetailAST ast) {
private boolean shouldCheck(final DetailAST ast) {
boolean result = false;
if (!ScopeUtil.isInCodeBlock(ast) && !isIgnored(ast)) {
final Scope customScope = ScopeUtil.getScope(ast);
final Scope surroundingScope = ScopeUtil.getSurroundingScope(ast);
result = customScope.isIn(scope) && surroundingScope.isIn(scope)
&& (excludeScope == null
|| !customScope.isIn(excludeScope)
|| !surroundingScope.isIn(excludeScope));
final AccessModifierOption accessModifier = getAccessModifier(ast);
final AccessModifierOption surroundingAccessModifier = getSurroundingAccessModifier(ast);
final AccessModifierOption effectiveAccessModifier = getEffectiveModifierOption(surroundingAccessModifier, accessModifier);
result = Optional.of(matchAccessModifiers(effectiveAccessModifier)).orElse(false);
}
return result;
}

/**
* Returns the access modifier of the given AST.
* In case of an invalid access modifier, null is returned.
*
* @param ast the AST to get the access modifier from.
* @return the access modifier of the given AST.
*/
private static AccessModifierOption getAccessModifier(DetailAST ast) {
AccessModifierOption accessModifier;
try {
accessModifier = CheckUtil.getAccessModifierFromModifiersToken(ast);
}
catch (IllegalArgumentException e) {
accessModifier = null;
}
return accessModifier;
}

/**
* Returns the access modifier of the surrounding scope of the given AST.
* In case of an invalid access modifier, null is returned.
*
* @param ast the AST to get the surrounding access modifier from.
* @return the access modifier of the surrounding scope of the given AST.
*/
private static AccessModifierOption getSurroundingAccessModifier(DetailAST ast) {
AccessModifierOption surroundingAccessModifier;
try {
surroundingAccessModifier = CheckUtil.getSurroundingAccessModifier(ast);
} catch (IllegalArgumentException e) {
surroundingAccessModifier = null;
}
return surroundingAccessModifier;
}

/**
* Returns the effective access modifier.
*
* @param surroundingAccessModifier the access modifier of the surrounding scope.
* @param accessModifier the access modifier of the current scope.
* @return the effective access modifier.
*/
private static AccessModifierOption getEffectiveModifierOption(AccessModifierOption surroundingAccessModifier, AccessModifierOption accessModifier) {
final AccessModifierOption effectiveAccessModifier;
if (surroundingAccessModifier != null && accessModifier != null) {
effectiveAccessModifier = surroundingAccessModifier.isIn(accessModifier)
? accessModifier
: surroundingAccessModifier;
}
else if (accessModifier == null && surroundingAccessModifier == null) {
effectiveAccessModifier = null;

}
else if ( accessModifier == null){
effectiveAccessModifier = surroundingAccessModifier;
}
else {
effectiveAccessModifier = accessModifier;
}
return effectiveAccessModifier;
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -52,6 +52,17 @@ private String getName() {
return name().toLowerCase(Locale.ENGLISH);
}

/**
* Checks if this access modifier is a sub access modifier of another access modifier.
* Example: PUBLIC is a sub access modifier of PRIVATE.
*
* @param accessModifierOption a {@code AccessModifierOption} value
* @return if {@code this} is a sub access modifier of {@code accessModifierOption}.
*/
public boolean isIn(AccessModifierOption accessModifierOption) {
return compareTo(accessModifierOption) <= 0;
}

/**
* Factory method which returns an AccessModifier instance that corresponds to the
* given access modifier name represented as a {@link String}.
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -8,18 +8,15 @@
Checks that a variable has a Javadoc comment. Ignores {@code serialVersionUID} fields.
&lt;/div&gt;</description>
<properties>
<property name="excludeScope" type="com.puppycrawl.tools.checkstyle.api.Scope">
<description>Specify the visibility scope where Javadoc
comments are not checked.</description>
<property default-value="public, protected, package, private"
name="accessModifiers"
type="com.puppycrawl.tools.checkstyle.checks.naming.AccessModifierOption[]">
<description>Access modifiers of methods where parameters are
checked.</description>
</property>
<property name="ignoreNamePattern" type="java.util.regex.Pattern">
<description>Specify the regexp to define variable names to ignore.</description>
</property>
<property default-value="private"
name="scope"
type="com.puppycrawl.tools.checkstyle.api.Scope">
<description>Specify the visibility scope where Javadoc comments are checked.</description>
</property>
<property default-value="ENUM_CONSTANT_DEF"
name="tokens"
type="java.lang.String[]"
Expand Down
Loading

0 comments on commit 4aae949

Please sign in to comment.