From 7005c7f15e01dec9cd2954a08ad140289bc266e8 Mon Sep 17 00:00:00 2001 From: Florian Hotze Date: Sun, 1 Dec 2024 12:28:25 +0100 Subject: [PATCH] ConfigDescriptionParameter & Input: Add null annotations & improve JavaDoc (#4465) * Add null annotations to org.openhab.core.automation.type.Input * Add null annotations to org.openhab.core.config.core.ConfigDescriptionParameter Signed-off-by: Florian Hotze --- .../openhab/core/automation/type/Input.java | 49 +++--- .../core/ConfigDescriptionParameter.java | 160 +++++++++--------- .../openhab/core/config/core/ConfigUtil.java | 5 +- .../internal/validation/PatternValidator.java | 5 +- ...EnrichedConfigDescriptionParameterDTO.java | 7 +- 5 files changed, 118 insertions(+), 108 deletions(-) diff --git a/bundles/org.openhab.core.automation/src/main/java/org/openhab/core/automation/type/Input.java b/bundles/org.openhab.core.automation/src/main/java/org/openhab/core/automation/type/Input.java index 273f93434..668567883 100644 --- a/bundles/org.openhab.core.automation/src/main/java/org/openhab/core/automation/type/Input.java +++ b/bundles/org.openhab.core.automation/src/main/java/org/openhab/core/automation/type/Input.java @@ -14,6 +14,8 @@ package org.openhab.core.automation.type; import java.util.Set; +import org.eclipse.jdt.annotation.NonNullByDefault; +import org.eclipse.jdt.annotation.Nullable; import org.openhab.core.automation.Module; import org.openhab.core.automation.Rule; @@ -32,20 +34,26 @@ import org.openhab.core.automation.Rule; * "temperature", for example. The value "*" means that all possible types are acceptable. The type is used to determine * which {@link Output} can be connected to this {@link Input}. *
  • label (optional) - short description (one word) of the {@link Input}
  • - *
  • description (optional) - long user friendly description of the {@link Input}
  • + *
  • description (optional) - long user-friendly description of the {@link Input}
  • + *
  • tags (optional) - add additional restrictions to connections between {@code Input}s and {@link Output}s. The + * input tags must be subset of the output tags to succeed the connection.
  • + *
  • required (optional) - defines if the {@link Input} is required or optional. The default value is false.
  • + *
  • reference (optional) - refers to the input of parent module type or null. If this input is part of the system + * module the reference should be null.
  • *
  • default value (optional) - the string representation of the default value of the {@link Input}. It must be * compatible with the type of the {@link Input}
  • - *
  • required (optional) - defines if the {@link Input} is required or optional. The default value is false.
  • * * * @author Yordan Mihaylov - Initial contribution + * @author Florian Hotze - Add null annotations */ +@NonNullByDefault public class Input { /** * Specifies a unique name of the {@code Input} in scope of the {@link Module}. */ - private String name; + private @NonNullByDefault({}) String name; /** * Specifies the acceptable data type for this {@link Input}. The value could be any string that makes sense for the @@ -53,25 +61,25 @@ public class Input { * value "*" means that all possible types are acceptable. The type is used to determine which {@link Output} can be * connected to this {@link Input} instance. */ - private String type; + private @NonNullByDefault({}) String type; /** * Keeps a single word description of the {@code Input}. */ - private String label; + private @Nullable String label; /** - * Keeps the user friendly description of the {@code Input}. + * Keeps the user-friendly description of the {@code Input}. */ - private String description; + private @Nullable String description; /** * Determines if the {@code Input} is required or optional. */ private boolean required = false; - private Set tags; - private String reference; - private String defaultValue; + private @Nullable Set tags; + private @Nullable String reference; + private @Nullable String defaultValue; /** * Default constructor for deserialization e.g. by Gson. @@ -98,12 +106,12 @@ public class Input { * @param name unique name of the {@code Input} in scope of the module. * @param type the acceptable data type for this {@link Input}. * @param label a single word description of the {@code Input}. - * @param description user friendly description of the {@code Input}. - * @param tags are associated with the {@code Input}. The tags adds additional restrictions to connections + * @param description user-friendly description of the {@code Input}. + * @param tags are associated with the {@code Input}. The tags add additional restrictions to connections * between {@code Input}s and {@link Output}s. The input tags must be subset of the output tags * to succeed the connection. * For example: When we want to connect input to output and both have same java.lang.double data - * type. The the output has assign "temperature" and "celsius" tags then the input must have at + * type. The output has assign "temperature" and "celsius" tags then the input must have at * least one of these output's tags (i.e. "temperature") to connect this {@code Input} to the * selected output. * @param required determines if the {@code Input} is required or optional. @@ -113,8 +121,8 @@ public class Input { * must be the type the Input. * @throws IllegalArgumentException If one of the name or type parameters is null. */ - public Input(String name, String type, String label, String description, Set tags, boolean required, - String reference, String defaultValue) { + public Input(String name, String type, @Nullable String label, @Nullable String description, + @Nullable Set tags, boolean required, @Nullable String reference, @Nullable String defaultValue) { if (name == null) { throw new IllegalArgumentException("The name of the input must not be NULL!"); } @@ -145,16 +153,16 @@ public class Input { * * @return label of the Input. */ - public String getLabel() { + public @Nullable String getLabel() { return label; } /** * Gets the long description of the Input. * - * @return user friendly description of the Input. + * @return user-friendly description of the Input. */ - public String getDescription() { + public @Nullable String getDescription() { return description; } @@ -188,6 +196,7 @@ public class Input { * @return tags associated with this Input. */ public Set getTags() { + Set tags = this.tags; return tags != null ? tags : Set.of(); } @@ -197,7 +206,7 @@ public class Input { * * @return reference to data source. */ - public String getReference() { + public @Nullable String getReference() { return reference; } @@ -207,7 +216,7 @@ public class Input { * * @return the string representation of the default value of this {@link Input}. */ - public String getDefaultValue() { + public @Nullable String getDefaultValue() { return defaultValue; } diff --git a/bundles/org.openhab.core.config.core/src/main/java/org/openhab/core/config/core/ConfigDescriptionParameter.java b/bundles/org.openhab.core.config.core/src/main/java/org/openhab/core/config/core/ConfigDescriptionParameter.java index aea9ca011..8676ad369 100644 --- a/bundles/org.openhab.core.config.core/src/main/java/org/openhab/core/config/core/ConfigDescriptionParameter.java +++ b/bundles/org.openhab.core.config.core/src/main/java/org/openhab/core/config/core/ConfigDescriptionParameter.java @@ -18,6 +18,9 @@ import java.util.Collections; import java.util.List; import java.util.Set; +import org.eclipse.jdt.annotation.NonNullByDefault; +import org.eclipse.jdt.annotation.Nullable; + import com.google.gson.annotations.SerializedName; /** @@ -38,7 +41,9 @@ import com.google.gson.annotations.SerializedName; * getter to return primitive types * @author Thomas Höfer - Added unit * @author Laurent Garnier - Removed constraint on unit value + * @author Florian Hotze - Add null annotations */ +@NonNullByDefault public class ConfigDescriptionParameter { /** @@ -73,27 +78,27 @@ public class ConfigDescriptionParameter { } - private String name; - private Type type; + private @NonNullByDefault({}) String name; + private @NonNullByDefault({}) Type type; - private String groupName; + private @Nullable String groupName; - private BigDecimal min; - private BigDecimal max; - private BigDecimal step; - private String pattern; + private @Nullable BigDecimal min; + private @Nullable BigDecimal max; + private @Nullable BigDecimal step; + private @Nullable String pattern; private boolean required = false; private boolean readOnly = false; private boolean multiple = false; - private Integer multipleLimit; - private String unit; - private String unitLabel; + private @Nullable Integer multipleLimit; + private @Nullable String unit; + private @Nullable String unitLabel; - private String context; + private @Nullable String context; @SerializedName("default") - private String defaultValue; - private String label; - private String description; + private @Nullable String defaultValue; + private @Nullable String label; + private @Nullable String description; private List options = new ArrayList<>(); private List filterCriteria = new ArrayList<>(); @@ -116,29 +121,23 @@ public class ConfigDescriptionParameter { /** * Creates a new instance of this class with the specified parameters. * - * @param name the name of the configuration parameter (must neither be null - * nor empty) - * @param type the data type of the configuration parameter (nullable) + * @param name the name of the configuration parameter (must not be empty) + * @param type the data type of the configuration parameter * @param minimum the minimal value for numeric types, or the minimal length of - * strings, or the minimal number of selected options (nullable) + * strings, or the minimal number of selected options * @param maximum the maximal value for numeric types, or the maximal length of - * strings, or the maximal number of selected options (nullable) - * @param stepsize the value granularity for a numeric value (nullable) - * @param pattern the regular expression for a text type (nullable) + * strings, or the maximal number of selected options + * @param stepsize the value granularity for a numeric value + * @param pattern the regular expression for a text type * @param required specifies whether the value is required * @param readOnly specifies whether the value is read-only * @param multiple specifies whether multiple selections of options are allowed - * @param context the context of the configuration parameter (can be null or - * empty) - * @param defaultValue the default value of the configuration parameter (can be null) - * @param label a human readable label for the configuration parameter (can be - * null or empty) - * @param description a human readable description for the configuration parameter - * (can be null or empty) - * @param filterCriteria a list of filter criteria for values of a dynamic selection - * list (nullable) + * @param context the context of the configuration parameter (can be empty) + * @param defaultValue the default value of the configuration parameter + * @param label a human-readable label for the configuration parameter (can be empty) + * @param description a human-readable description for the configuration parameter (can be empty) + * @param filterCriteria a list of filter criteria for values of a dynamic selection list * @param options a list of element definitions of a static selection list - * (nullable) * @param groupName a string used to group parameters together into logical blocks * so that the UI can display them together * @param advanced specifies if this is an advanced parameter. An advanced @@ -151,10 +150,11 @@ public class ConfigDescriptionParameter { * can enter values other than those in the list * @param multipleLimit specifies the maximum number of options that can be selected * when multiple is true - * @param unit specifies the unit of measurements for the configuration parameter (nullable) + * @param unit specifies the unit of measurements for the configuration parameter * @param unitLabel specifies the unit label for the configuration parameter. This attribute can also be used to * provide * natural language units as iterations, runs, etc. + * @param verify specifies whether the parameter should be considered dangerous * @throws IllegalArgumentException *
      *
    • if the name is null or empty, or the type is null
    • @@ -166,11 +166,14 @@ public class ConfigDescriptionParameter { * @deprecated Use {@link ConfigDescriptionParameterBuilder} instead. */ @Deprecated - ConfigDescriptionParameter(String name, Type type, BigDecimal minimum, BigDecimal maximum, BigDecimal stepsize, - String pattern, Boolean required, Boolean readOnly, Boolean multiple, String context, String defaultValue, - String label, String description, List options, List filterCriteria, - String groupName, Boolean advanced, Boolean limitToOptions, Integer multipleLimit, String unit, - String unitLabel, Boolean verify) throws IllegalArgumentException { + ConfigDescriptionParameter(String name, Type type, @Nullable BigDecimal minimum, @Nullable BigDecimal maximum, + @Nullable BigDecimal stepsize, @Nullable String pattern, @Nullable Boolean required, + @Nullable Boolean readOnly, @Nullable Boolean multiple, @Nullable String context, + @Nullable String defaultValue, @Nullable String label, @Nullable String description, + @Nullable List options, @Nullable List filterCriteria, + @Nullable String groupName, @Nullable Boolean advanced, @Nullable Boolean limitToOptions, + @Nullable Integer multipleLimit, @Nullable String unit, @Nullable String unitLabel, + @Nullable Boolean verify) throws IllegalArgumentException { if ((name == null) || (name.isEmpty())) { throw new IllegalArgumentException("The name must neither be null nor empty!"); } @@ -233,7 +236,7 @@ public class ConfigDescriptionParameter { /** * Returns the name of the configuration parameter. * - * @return the name of the configuration parameter (neither null, nor empty) + * @return the name of the configuration parameter (not empty) */ public String getName() { return this.name; @@ -242,7 +245,7 @@ public class ConfigDescriptionParameter { /** * Returns the data type of the configuration parameter. * - * @return the data type of the configuration parameter (not null) + * @return the data type of the configuration parameter */ public Type getType() { return this.type; @@ -250,17 +253,17 @@ public class ConfigDescriptionParameter { /** * @return the minimal value for numeric types, or the minimal length of - * strings, or the minimal number of selected options (nullable) + * strings, or the minimal number of selected options */ - public BigDecimal getMinimum() { + public @Nullable BigDecimal getMinimum() { return min; } /** * @return the maximal value for numeric types, or the maximal length of - * strings, or the maximal number of selected options (nullable) + * strings, or the maximal number of selected options */ - public BigDecimal getMaximum() { + public @Nullable BigDecimal getMaximum() { return max; } @@ -269,23 +272,23 @@ public class ConfigDescriptionParameter { *

      * By setting the step size to 0, any granularity is allowed, i.e. any number of decimals is accepted. * - * @return the value granularity for a numeric value (nullable) + * @return the value granularity for a numeric value */ - public BigDecimal getStepSize() { + public @Nullable BigDecimal getStepSize() { return step; } /** - * @return the regular expression for a text type (nullable) + * @return the regular expression for a text type */ - public String getPattern() { + public @Nullable String getPattern() { return pattern; } /** * @return true if the value is required, otherwise false. */ - public Boolean isReadOnly() { + public boolean isReadOnly() { return readOnly; } @@ -293,14 +296,14 @@ public class ConfigDescriptionParameter { * @return true if multiple selections of options are allowed, otherwise * false. */ - public Boolean isMultiple() { + public boolean isMultiple() { return multiple; } /** * @return the maximum number of options that can be selected from the options list */ - public Integer getMultipleLimit() { + public @Nullable Integer getMultipleLimit() { return multipleLimit; } @@ -347,10 +350,9 @@ public class ConfigDescriptionParameter { * - location: A latitude,longitude[,altitude] GPS location. A user-interface would probably render a world map for * selection. * - * @return the context of the configuration parameter (could be null or - * empty) + * @return the context of the configuration parameter (could be empty) */ - public String getContext() { + public @Nullable String getContext() { return this.context; } @@ -362,35 +364,34 @@ public class ConfigDescriptionParameter { * false */ public boolean isRequired() { - return this.required; + return required; } /** * Returns the default value of the configuration parameter. * - * @return the default value of the configuration parameter (could be null) + * @return the default value of the configuration parameter */ - public String getDefault() { - return this.defaultValue; + public @Nullable String getDefault() { + return defaultValue; } /** - * Returns a human readable label for the configuration parameter. + * Returns a human-readable label for the configuration parameter. * - * @return a human readable label for the configuration parameter (could be - * null or empty) + * @return a human-readable label for the configuration parameter (could be empty) */ - public String getLabel() { - return this.label; + public @Nullable String getLabel() { + return label; } /** - * Returns a the group for this configuration parameter. + * Returns the group for this configuration parameter. * - * @return a group for the configuration parameter (could be null or empty) + * @return a group for the configuration parameter (could be empty) */ - public String getGroupName() { - return this.groupName; + public @Nullable String getGroupName() { + return groupName; } /** @@ -400,7 +401,7 @@ public class ConfigDescriptionParameter { * @return true if the value is limited to the options list */ public boolean getLimitToOptions() { - return this.limitToOptions; + return limitToOptions; } /** @@ -409,17 +410,16 @@ public class ConfigDescriptionParameter { * @return true if the value is an advanced option */ public boolean isAdvanced() { - return this.advanced; + return advanced; } /** - * Returns a human readable description for the configuration parameter. + * Returns a human-readable description for the configuration parameter. * - * @return a human readable description for the configuration parameter - * (could be null or empty) + * @return a human-readable description for the configuration parameter (could be empty) */ - public String getDescription() { - return this.description; + public @Nullable String getDescription() { + return description; } /** @@ -428,7 +428,7 @@ public class ConfigDescriptionParameter { * @return static selection list for the value of this parameter */ public List getOptions() { - return this.options; + return options; } /** @@ -440,24 +440,24 @@ public class ConfigDescriptionParameter { * @return list of filter criteria for a dynamically created selection list */ public List getFilterCriteria() { - return this.filterCriteria; + return filterCriteria; } /** * Returns the unit of measurements of this parameter. * - * @return the unit of measurements of this parameter (could be null) + * @return the unit of measurements of this parameter */ - public String getUnit() { + public @Nullable String getUnit() { return unit; } /** * Returns the unit label of this parameter. * - * @return the unit label of this parameter (could be null) + * @return the unit label of this parameter */ - public String getUnitLabel() { + public @Nullable String getUnitLabel() { return unitLabel; } @@ -467,7 +467,7 @@ public class ConfigDescriptionParameter { * * @return true if the parameter requires verification in the UI */ - public Boolean isVerifyable() { + public boolean isVerifyable() { return verify; } diff --git a/bundles/org.openhab.core.config.core/src/main/java/org/openhab/core/config/core/ConfigUtil.java b/bundles/org.openhab.core.config.core/src/main/java/org/openhab/core/config/core/ConfigUtil.java index d99c83149..294b8617a 100644 --- a/bundles/org.openhab.core.config.core/src/main/java/org/openhab/core/config/core/ConfigUtil.java +++ b/bundles/org.openhab.core.config.core/src/main/java/org/openhab/core/config/core/ConfigUtil.java @@ -68,7 +68,10 @@ public class ConfigUtil { } static @Nullable Object getDefaultValueAsCorrectType(String parameterName, Type parameterType, - String defaultValue) { + @Nullable String defaultValue) { + if (defaultValue == null) { + return null; + } try { switch (parameterType) { case TEXT: diff --git a/bundles/org.openhab.core.config.core/src/main/java/org/openhab/core/config/core/internal/validation/PatternValidator.java b/bundles/org.openhab.core.config.core/src/main/java/org/openhab/core/config/core/internal/validation/PatternValidator.java index a0b288661..c52c8537f 100644 --- a/bundles/org.openhab.core.config.core/src/main/java/org/openhab/core/config/core/internal/validation/PatternValidator.java +++ b/bundles/org.openhab.core.config.core/src/main/java/org/openhab/core/config/core/internal/validation/PatternValidator.java @@ -29,11 +29,12 @@ final class PatternValidator implements ConfigDescriptionParameterValidator { @Override public @Nullable ConfigValidationMessage validate(ConfigDescriptionParameter parameter, @Nullable Object value) { - if (value == null || parameter.getType() != Type.TEXT || parameter.getPattern() == null) { + String pattern = parameter.getPattern(); + if (value == null || parameter.getType() != Type.TEXT || pattern == null) { return null; } - if (!((String) value).matches(parameter.getPattern())) { + if (!((String) value).matches(pattern)) { MessageKey messageKey = MessageKey.PATTERN_VIOLATED; return new ConfigValidationMessage(parameter.getName(), messageKey.defaultMessage, messageKey.key, String.valueOf(value), parameter.getPattern()); diff --git a/bundles/org.openhab.core.io.rest.core/src/main/java/org/openhab/core/io/rest/core/config/EnrichedConfigDescriptionParameterDTO.java b/bundles/org.openhab.core.io.rest.core/src/main/java/org/openhab/core/io/rest/core/config/EnrichedConfigDescriptionParameterDTO.java index 88afee855..8a3ac461e 100644 --- a/bundles/org.openhab.core.io.rest.core/src/main/java/org/openhab/core/io/rest/core/config/EnrichedConfigDescriptionParameterDTO.java +++ b/bundles/org.openhab.core.io.rest.core/src/main/java/org/openhab/core/io/rest/core/config/EnrichedConfigDescriptionParameterDTO.java @@ -18,8 +18,6 @@ import java.util.List; import java.util.Set; import java.util.stream.Stream; -import org.eclipse.jdt.annotation.NonNullByDefault; -import org.eclipse.jdt.annotation.Nullable; import org.openhab.core.config.core.ConfigDescriptionParameter.Type; import org.openhab.core.config.core.dto.ConfigDescriptionParameterDTO; import org.openhab.core.config.core.dto.FilterCriteriaDTO; @@ -31,16 +29,15 @@ import org.openhab.core.config.core.dto.ParameterOptionDTO; * * @author Christoph Weitkamp - Initial contribution */ -@NonNullByDefault public class EnrichedConfigDescriptionParameterDTO extends ConfigDescriptionParameterDTO { private static final String DEFAULT_LIST_DELIMITER = ","; - public @Nullable Collection defaultValues; + public Collection defaultValues; public EnrichedConfigDescriptionParameterDTO(String name, Type type, BigDecimal minimum, BigDecimal maximum, BigDecimal stepsize, String pattern, Boolean required, Boolean readOnly, Boolean multiple, String context, - @Nullable String defaultValue, String label, String description, List options, + String defaultValue, String label, String description, List options, List filterCriteria, String groupName, Boolean advanced, Boolean limitToOptions, Integer multipleLimit, String unit, String unitLabel, Boolean verify) { super(name, type, minimum, maximum, stepsize, pattern, required, readOnly, multiple, context, defaultValue,