import java.util.Collection;
import java.util.Locale;
import java.util.Optional;
-import java.util.Set;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
+import org.eclipse.jdt.annotation.NonNull;
import org.opendaylight.yangtools.yang.binding.Augmentable;
+import org.opendaylight.yangtools.yang.binding.DataContainer;
import org.opendaylight.yangtools.yang.binding.Identifiable;
import org.opendaylight.yangtools.yang.common.QName;
import org.opendaylight.yangtools.yang.common.QNameModule;
@Beta
public final class BindingMapping {
- public static final String VERSION = "0.6";
+ public static final @NonNull String VERSION = "0.6";
- public static final Set<String> JAVA_RESERVED_WORDS = ImmutableSet.of(
+ public static final ImmutableSet<String> JAVA_RESERVED_WORDS = ImmutableSet.of(
// https://docs.oracle.com/javase/specs/jls/se9/html/jls-3.html#jls-3.9
"abstract", "assert", "boolean", "break", "byte", "case", "catch", "char", "class", "const", "continue",
"default", "do", "double", "else", "enum", "extends", "final", "finally", "float", "for", "goto", "if",
// https://docs.oracle.com/javase/specs/jls/se9/html/jls-3.html#jls-3.10.7
"null");
- public static final String DATA_ROOT_SUFFIX = "Data";
- public static final String RPC_SERVICE_SUFFIX = "Service";
- public static final String NOTIFICATION_LISTENER_SUFFIX = "Listener";
- public static final String QNAME_STATIC_FIELD_NAME = "QNAME";
- public static final String PACKAGE_PREFIX = "org.opendaylight.yang.gen.v1";
- public static final String AUGMENTATION_FIELD = "augmentation";
+ public static final @NonNull String DATA_ROOT_SUFFIX = "Data";
+ public static final @NonNull String RPC_SERVICE_SUFFIX = "Service";
+ public static final @NonNull String NOTIFICATION_LISTENER_SUFFIX = "Listener";
+ public static final @NonNull String QNAME_STATIC_FIELD_NAME = "QNAME";
+ public static final @NonNull String PACKAGE_PREFIX = "org.opendaylight.yang.gen.v1";
+ public static final @NonNull String AUGMENTATION_FIELD = "augmentation";
private static final Splitter CAMEL_SPLITTER = Splitter.on(CharMatcher.anyOf(" _.-/").precomputed())
.omitEmptyStrings().trimResults();
private static final String QUOTED_DOT = Matcher.quoteReplacement(".");
private static final Splitter DOT_SPLITTER = Splitter.on('.');
- public static final String MODULE_INFO_CLASS_NAME = "$YangModuleInfoImpl";
- public static final String MODULE_INFO_QNAMEOF_METHOD_NAME = "qnameOf";
- public static final String MODEL_BINDING_PROVIDER_CLASS_NAME = "$YangModelBindingProvider";
+ public static final @NonNull String MODULE_INFO_CLASS_NAME = "$YangModuleInfoImpl";
+ public static final @NonNull String MODULE_INFO_QNAMEOF_METHOD_NAME = "qnameOf";
+ public static final @NonNull String MODEL_BINDING_PROVIDER_CLASS_NAME = "$YangModelBindingProvider";
/**
* Name of {@link Augmentable#augmentation(Class)}.
*/
- public static final String AUGMENTABLE_AUGMENTATION_NAME = "augmentation";
+ public static final @NonNull String AUGMENTABLE_AUGMENTATION_NAME = "augmentation";
/**
* Name of {@link Identifiable#key()}.
*/
- public static final String IDENTIFIABLE_KEY_NAME = "key";
+ public static final @NonNull String IDENTIFIABLE_KEY_NAME = "key";
- public static final String RPC_INPUT_SUFFIX = "Input";
- public static final String RPC_OUTPUT_SUFFIX = "Output";
+ /**
+ * Name of {@link DataContainer#implementedInterface()}.
+ */
+ public static final @NonNull String DATA_CONTAINER_IMPLEMENTED_INTERFACE_NAME = "implementedInterface";
+
+ /**
+ * Prefix for getter methods working on top of boolean.
+ */
+ public static final @NonNull String BOOLEAN_GETTER_PREFIX = "is";
+
+ /**
+ * Prefix for normal getter methods.
+ */
+ public static final @NonNull String GETTER_PREFIX = "get";
+
+ /**
+ * Prefix for non-null default wrapper methods. These methods always wrap a corresponding normal getter.
+ */
+ public static final @NonNull String NONNULL_PREFIX = "nonnull";
+
+ public static final @NonNull String RPC_INPUT_SUFFIX = "Input";
+ public static final @NonNull String RPC_OUTPUT_SUFFIX = "Output";
private static final Interner<String> PACKAGE_INTERNER = Interners.newWeakInterner();
throw new UnsupportedOperationException("Utility class should not be instantiated");
}
- public static String getRootPackageName(final QName module) {
+ public static @NonNull String getRootPackageName(final QName module) {
return getRootPackageName(module.getModule());
}
- public static String getRootPackageName(final QNameModule module) {
- checkArgument(module != null, "Module must not be null");
- checkArgument(module.getRevision() != null, "Revision must not be null");
- checkArgument(module.getNamespace() != null, "Namespace must not be null");
- final StringBuilder packageNameBuilder = new StringBuilder();
-
- packageNameBuilder.append(BindingMapping.PACKAGE_PREFIX);
- packageNameBuilder.append('.');
+ public static @NonNull String getRootPackageName(final QNameModule module) {
+ final StringBuilder packageNameBuilder = new StringBuilder().append(BindingMapping.PACKAGE_PREFIX).append('.');
String namespace = module.getNamespace().toString();
namespace = COLON_SLASH_SLASH.matcher(namespace).replaceAll(QUOTED_DOT);
// right characters.
final String rev = optRev.get().toString();
checkArgument(rev.length() == 10, "Unsupported revision %s", rev);
- packageNameBuilder.append("rev");
- packageNameBuilder.append(rev.substring(2, 4)).append(rev.substring(5, 7)).append(rev.substring(8));
+ packageNameBuilder.append("rev").append(rev, 2, 4).append(rev, 5, 7).append(rev.substring(8));
} else {
// No-revision packages are special
packageNameBuilder.append("norev");
return normalizePackageName(packageNameBuilder.toString());
}
- public static String normalizePackageName(final String packageName) {
- if (packageName == null) {
- return null;
- }
-
+ public static @NonNull String normalizePackageName(final String packageName) {
final StringBuilder builder = new StringBuilder();
boolean first = true;
- for (String p : DOT_SPLITTER.split(packageName.toLowerCase())) {
+ for (String p : DOT_SPLITTER.split(packageName.toLowerCase(Locale.ENGLISH))) {
if (first) {
first = false;
} else {
return PACKAGE_INTERNER.intern(builder.toString());
}
- public static String getClassName(final String localName) {
- checkArgument(localName != null, "Name should not be null.");
+ public static @NonNull String getClassName(final String localName) {
return toFirstUpper(toCamelCase(localName));
}
- public static String getClassName(final QName name) {
- checkArgument(name != null, "Name should not be null.");
+ public static @NonNull String getClassName(final QName name) {
return toFirstUpper(toCamelCase(name.getLocalName()));
}
- public static String getMethodName(final String yangIdentifier) {
- checkArgument(yangIdentifier != null,"Identifier should not be null");
+ public static @NonNull String getMethodName(final String yangIdentifier) {
return toFirstLower(toCamelCase(yangIdentifier));
}
- public static String getMethodName(final QName name) {
- checkArgument(name != null, "Name should not be null.");
+ public static @NonNull String getMethodName(final QName name) {
return getMethodName(name.getLocalName());
}
- public static String getGetterSuffix(final QName name) {
- checkArgument(name != null, "Name should not be null.");
+ public static @NonNull String getGetterPrefix(final boolean isBoolean) {
+ return isBoolean ? BOOLEAN_GETTER_PREFIX : GETTER_PREFIX;
+ }
+
+ public static @NonNull String getGetterMethodName(final String localName, final boolean isBoolean) {
+ return getGetterPrefix(isBoolean) + toFirstUpper(getPropertyName(localName));
+ }
+
+ public static @NonNull String getGetterMethodName(final QName name, final boolean isBoolean) {
+ return getGetterPrefix(isBoolean) + getGetterSuffix(name);
+ }
+
+ public static boolean isGetterMethodName(final String methodName) {
+ return methodName.startsWith(GETTER_PREFIX) || methodName.startsWith(BOOLEAN_GETTER_PREFIX);
+ }
+
+ public static @NonNull String getGetterMethodForNonnull(final String methodName) {
+ checkArgument(isNonnullMethodName(methodName));
+ return GETTER_PREFIX + methodName.substring(NONNULL_PREFIX.length());
+ }
+
+ public static @NonNull String getNonnullMethodName(final String localName) {
+ return NONNULL_PREFIX + toFirstUpper(getPropertyName(localName));
+ }
+
+ public static boolean isNonnullMethodName(final String methodName) {
+ return methodName.startsWith(NONNULL_PREFIX);
+ }
+
+ public static @NonNull String getGetterSuffix(final QName name) {
final String candidate = toFirstUpper(toCamelCase(name.getLocalName()));
return "Class".equals(candidate) ? "XmlClass" : candidate;
}
- public static String getPropertyName(final String yangIdentifier) {
+ public static @NonNull String getPropertyName(final String yangIdentifier) {
final String potential = toFirstLower(toCamelCase(yangIdentifier));
if ("class".equals(potential)) {
return "xmlClass";
return potential;
}
- private static String toCamelCase(final String rawString) {
- checkArgument(rawString != null, "String should not be null");
- Iterable<String> components = CAMEL_SPLITTER.split(rawString);
+ private static @NonNull String toCamelCase(final String rawString) {
StringBuilder builder = new StringBuilder();
- for (String comp : components) {
+ for (String comp : CAMEL_SPLITTER.split(rawString)) {
builder.append(toFirstUpper(comp));
}
return checkNumericPrefix(builder.toString());
}
- private static String checkNumericPrefix(final String rawString) {
- if (rawString == null || rawString.isEmpty()) {
- return rawString;
- }
- char firstChar = rawString.charAt(0);
- if (firstChar >= '0' && firstChar <= '9') {
- return "_" + rawString;
- } else {
+ private static @NonNull String checkNumericPrefix(final String rawString) {
+ if (rawString.isEmpty()) {
return rawString;
}
+ final char firstChar = rawString.charAt(0);
+ return firstChar >= '0' && firstChar <= '9' ? "_" + rawString : rawString;
}
/**
- * Returns the {@link String} {@code s} with an {@link Character#isUpperCase(char) upper case} first character. This
- * function is null-safe.
+ * Returns the {@link String} {@code s} with an {@link Character#isUpperCase(char) upper case} first character.
*
- * @param str the string that should get an upper case first character. May be <code>null</code>.
- * @return the {@link String} {@code str} with an upper case first character or <code>null</code> if the input
- * {@link String} {@code str} was <code>null</code>.
+ * @param str the string that should get an upper case first character.
+ * @return the {@link String} {@code str} with an upper case first character.
*/
- public static String toFirstUpper(final String str) {
- if (str == null || str.length() == 0) {
+ private static @NonNull String toFirstUpper(final @NonNull String str) {
+ if (str.isEmpty()) {
return str;
}
if (Character.isUpperCase(str.charAt(0))) {
return str;
}
if (str.length() == 1) {
- return str.toUpperCase();
+ return str.toUpperCase(Locale.ENGLISH);
}
- return str.substring(0, 1).toUpperCase() + str.substring(1);
+ return str.substring(0, 1).toUpperCase(Locale.ENGLISH) + str.substring(1);
}
/**
*
* @param str the string that should get an lower case first character. May be <code>null</code>.
* @return the {@link String} {@code str} with an lower case first character or <code>null</code> if the input
- * {@link String} {@code str} was <code>null</code>.
+ * {@link String} {@code str} was empty.
*/
- private static String toFirstLower(final String str) {
- if (str == null || str.length() == 0) {
+ private static @NonNull String toFirstLower(final @NonNull String str) {
+ if (str.isEmpty()) {
return str;
}
if (Character.isLowerCase(str.charAt(0))) {
return str;
}
if (str.length() == 1) {
- return str.toLowerCase();
+ return str.toLowerCase(Locale.ENGLISH);
}
- return str.substring(0, 1).toLowerCase() + str.substring(1);
+ return str.substring(0, 1).toLowerCase(Locale.ENGLISH) + str.substring(1);
+ }
+
+ /**
+ * Returns the {@link String} {@code s} with a '$' character as suffix.
+ *
+ * @param qname RPC QName
+ * @return The RPC method name as determined by considering the localname against the JLS.
+ * @throws NullPointerException if {@code qname} is null
+ */
+ public static @NonNull String getRpcMethodName(final @NonNull QName qname) {
+ final String methodName = getMethodName(qname);
+ return JAVA_RESERVED_WORDS.contains(methodName) ? methodName + "$" : methodName;
}
/**