From 5bae96b1199db4531995962e5e077d8d7a41ae2d Mon Sep 17 00:00:00 2001 From: Jakub Toth Date: Thu, 8 Jun 2017 17:31:33 +0200 Subject: [PATCH] Binding2 runtime - Codecs impl - context - part2 * derived parts * fixed base parts Change-Id: Ib46351557a42e914bba3c4a34abf2ef94ec9bb80 Signed-off-by: Jakub Toth (cherry picked from commit 764468fe46154f4d60cbcaa102ac59bd648be653) --- .../impl/context/AugmentationNodeContext.java | 49 +++++ .../impl/context/ChoiceNodeCodecContext.java | 208 ++++++++++++++++++ .../context/NotificationCodecContext.java | 59 +++++ .../impl/context/UnionValueOptionContext.java | 140 ++++++++++++ .../dom/codec/impl/context/ValueContext.java | 81 +++++++ .../base/DataContainerCodecPrototype.java | 11 +- .../context/base/LeafNodeCodecContext.java | 2 +- .../impl/value/EncapsulatedValueCodec.java | 12 +- 8 files changed, 550 insertions(+), 12 deletions(-) create mode 100644 binding2/mdsal-binding2-dom-codec/src/main/java/org/opendaylight/mdsal/binding/javav2/dom/codec/impl/context/AugmentationNodeContext.java create mode 100644 binding2/mdsal-binding2-dom-codec/src/main/java/org/opendaylight/mdsal/binding/javav2/dom/codec/impl/context/ChoiceNodeCodecContext.java create mode 100644 binding2/mdsal-binding2-dom-codec/src/main/java/org/opendaylight/mdsal/binding/javav2/dom/codec/impl/context/NotificationCodecContext.java create mode 100644 binding2/mdsal-binding2-dom-codec/src/main/java/org/opendaylight/mdsal/binding/javav2/dom/codec/impl/context/UnionValueOptionContext.java create mode 100644 binding2/mdsal-binding2-dom-codec/src/main/java/org/opendaylight/mdsal/binding/javav2/dom/codec/impl/context/ValueContext.java diff --git a/binding2/mdsal-binding2-dom-codec/src/main/java/org/opendaylight/mdsal/binding/javav2/dom/codec/impl/context/AugmentationNodeContext.java b/binding2/mdsal-binding2-dom-codec/src/main/java/org/opendaylight/mdsal/binding/javav2/dom/codec/impl/context/AugmentationNodeContext.java new file mode 100644 index 0000000000..767cfbc1b6 --- /dev/null +++ b/binding2/mdsal-binding2-dom-codec/src/main/java/org/opendaylight/mdsal/binding/javav2/dom/codec/impl/context/AugmentationNodeContext.java @@ -0,0 +1,49 @@ +/* + * Copyright (c) 2017 Pantheon Technologies s.r.o. and others. All rights reserved. + * + * This program and the accompanying materials are made available under the + * terms of the Eclipse Public License v1.0 which accompanies this distribution, + * and is available at http://www.eclipse.org/legal/epl-v10.html + */ +package org.opendaylight.mdsal.binding.javav2.dom.codec.impl.context; + +import com.google.common.annotations.Beta; +import com.google.common.base.Preconditions; +import javax.annotation.Nonnull; +import org.opendaylight.mdsal.binding.javav2.dom.codec.impl.context.base.DataContainerCodecPrototype; +import org.opendaylight.mdsal.binding.javav2.dom.codec.impl.context.base.TreeNodeCodecContext; +import org.opendaylight.mdsal.binding.javav2.spec.base.TreeNode; +import org.opendaylight.mdsal.binding.javav2.spec.structural.Augmentation; +import org.opendaylight.yangtools.yang.data.api.schema.AugmentationNode; +import org.opendaylight.yangtools.yang.data.api.schema.NormalizedNode; +import org.opendaylight.yangtools.yang.model.api.AugmentationSchema; + +/** + * Context for prototype of augmentation node. + */ +@Beta +public final class AugmentationNodeContext> + extends TreeNodeCodecContext { + + /** + * Prepare context for augmentation node from prototype. + * + * @param prototype + * - codec prototype of augmentation node + */ + public AugmentationNodeContext(final DataContainerCodecPrototype prototype) { + super(prototype); + } + + @Nonnull + @Override + public D deserialize(@Nonnull final NormalizedNode normalizedNode) { + Preconditions.checkArgument(normalizedNode instanceof AugmentationNode); + return createBindingProxy((AugmentationNode) normalizedNode); + } + + @Override + protected Object deserializeObject(final NormalizedNode normalizedNode) { + return deserialize(normalizedNode); + } +} diff --git a/binding2/mdsal-binding2-dom-codec/src/main/java/org/opendaylight/mdsal/binding/javav2/dom/codec/impl/context/ChoiceNodeCodecContext.java b/binding2/mdsal-binding2-dom-codec/src/main/java/org/opendaylight/mdsal/binding/javav2/dom/codec/impl/context/ChoiceNodeCodecContext.java new file mode 100644 index 0000000000..ea6cd4395f --- /dev/null +++ b/binding2/mdsal-binding2-dom-codec/src/main/java/org/opendaylight/mdsal/binding/javav2/dom/codec/impl/context/ChoiceNodeCodecContext.java @@ -0,0 +1,208 @@ +/* + * Copyright (c) 2017 Pantheon Technologies s.r.o. and others. All rights reserved. + * + * This program and the accompanying materials are made available under the + * terms of the Eclipse Public License v1.0 which accompanies this distribution, + * and is available at http://www.eclipse.org/legal/epl-v10.html + */ +package org.opendaylight.mdsal.binding.javav2.dom.codec.impl.context; + +import com.google.common.annotations.Beta; +import com.google.common.base.Optional; +import com.google.common.base.Preconditions; +import com.google.common.collect.ImmutableMap; +import com.google.common.collect.Iterables; +import java.util.HashMap; +import java.util.HashSet; +import java.util.Map; +import java.util.Map.Entry; +import java.util.Set; +import javax.annotation.Nonnull; +import org.opendaylight.mdsal.binding.javav2.dom.codec.impl.context.base.DataContainerCodecContext; +import org.opendaylight.mdsal.binding.javav2.dom.codec.impl.context.base.DataContainerCodecPrototype; +import org.opendaylight.mdsal.binding.javav2.dom.codec.impl.context.base.NodeCodecContext; +import org.opendaylight.mdsal.binding.javav2.runtime.reflection.BindingReflections; +import org.opendaylight.mdsal.binding.javav2.spec.base.Instantiable; +import org.opendaylight.mdsal.binding.javav2.spec.base.TreeArgument; +import org.opendaylight.mdsal.binding.javav2.spec.base.TreeNode; +import org.opendaylight.yangtools.yang.data.api.YangInstanceIdentifier; +import org.opendaylight.yangtools.yang.data.api.YangInstanceIdentifier.NodeIdentifier; +import org.opendaylight.yangtools.yang.data.api.schema.ChoiceNode; +import org.opendaylight.yangtools.yang.data.api.schema.NormalizedNode; +import org.opendaylight.yangtools.yang.data.api.schema.NormalizedNodeContainer; +import org.opendaylight.yangtools.yang.data.impl.schema.SchemaUtils; +import org.opendaylight.yangtools.yang.model.api.AugmentationSchema; +import org.opendaylight.yangtools.yang.model.api.ChoiceCaseNode; +import org.opendaylight.yangtools.yang.model.api.ChoiceSchemaNode; +import org.opendaylight.yangtools.yang.model.api.DataSchemaNode; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +/** + * Context for prototype of choice node codec. + * + * @param + * - type of tree node + */ +@Beta +public class ChoiceNodeCodecContext extends DataContainerCodecContext { + + private static final Logger LOG = LoggerFactory.getLogger(ChoiceNodeCodecContext.class); + + private final ImmutableMap> byYangCaseChild; + private final ImmutableMap, DataContainerCodecPrototype> byClass; + private final ImmutableMap, DataContainerCodecPrototype> byCaseChildClass; + + /** + * Prepare context for choice node from prototype and all case children of choice class. + * + * @param prototype + * - codec prototype of choice node + */ + public ChoiceNodeCodecContext(final DataContainerCodecPrototype prototype) { + super(prototype); + final Map> byYangCaseChildBuilder = + new HashMap<>(); + final Map, DataContainerCodecPrototype> byClassBuilder = new HashMap<>(); + final Map, DataContainerCodecPrototype> byCaseChildClassBuilder = new HashMap<>(); + final Set> potentialSubstitutions = new HashSet<>(); + // Walks all cases for supplied choice in current runtime context + for (final Class caze : factory().getRuntimeContext().getCases(getBindingClass())) { + // We try to load case using exact match thus name + // and original schema must equals + final DataContainerCodecPrototype cazeDef = loadCase(caze); + // If we have case definition, this case is instantiated + // at current location and thus is valid in context of parent choice + if (cazeDef != null) { + byClassBuilder.put(cazeDef.getBindingClass(), cazeDef); + // Updates collection of case children + @SuppressWarnings("unchecked") + final Class> cazeCls = (Class>) caze; + for (final Class cazeChild : BindingReflections.getChildrenClasses(cazeCls)) { + byCaseChildClassBuilder.put(cazeChild, cazeDef); + } + // Updates collection of YANG instance identifier to case + for (final DataSchemaNode cazeChild : cazeDef.getSchema().getChildNodes()) { + if (cazeChild.isAugmenting()) { + final AugmentationSchema augment = + SchemaUtils.findCorrespondingAugment(cazeDef.getSchema(), cazeChild); + if (augment != null) { + byYangCaseChildBuilder.put(SchemaUtils.getNodeIdentifierForAugmentation(augment), cazeDef); + continue; + } + } + byYangCaseChildBuilder.put(NodeIdentifier.create(cazeChild.getQName()), cazeDef); + } + } else { + /* + * If case definition is not available, we store it for later check if it could be used as + * substitution of existing one. + */ + potentialSubstitutions.add(caze); + } + } + + final Map, DataContainerCodecPrototype> bySubstitutionBuilder = new HashMap<>(); + /* + * Walks all cases which are not directly instantiated and tries to match them to instantiated cases - + * represent same data as instantiated case, only case name or schema path is different. This is + * required due property of binding specification, that if choice is in grouping schema path location + * is lost, and users may use incorrect case class using copy builders. + */ + for (final Class substitution : potentialSubstitutions) { + for (final Entry, DataContainerCodecPrototype> real : byClassBuilder.entrySet()) { + if (BindingReflections.isSubstitutionFor(substitution, real.getKey())) { + bySubstitutionBuilder.put(substitution, real.getValue()); + break; + } + } + } + byClassBuilder.putAll(bySubstitutionBuilder); + byYangCaseChild = ImmutableMap.copyOf(byYangCaseChildBuilder); + byClass = ImmutableMap.copyOf(byClassBuilder); + byCaseChildClass = ImmutableMap.copyOf(byCaseChildClassBuilder); + } + + @SuppressWarnings("unchecked") + @Nonnull + @Override + public DataContainerCodecContext streamChild(@Nonnull final Class childClass) { + final DataContainerCodecPrototype child = byClass.get(childClass); + return (DataContainerCodecContext) childNonNull(child, childClass, "Supplied class %s is not valid case", childClass).get(); + } + + @SuppressWarnings("unchecked") + @Override + public Optional> + possibleStreamChild(@Nonnull final Class childClass) { + final DataContainerCodecPrototype child = byClass.get(childClass); + if (child != null) { + return Optional.of((DataContainerCodecContext) child.get()); + } + return Optional.absent(); + } + + Iterable> getCaseChildrenClasses() { + return byCaseChildClass.keySet(); + } + + private DataContainerCodecPrototype loadCase(final Class childClass) { + final Optional childSchema = + factory().getRuntimeContext().getCaseSchemaDefinition(getSchema(), childClass); + if (childSchema.isPresent()) { + return DataContainerCodecPrototype.from(childClass, childSchema.get(), factory()); + } + + LOG.debug("Supplied class %s is not valid case in schema %s", childClass, getSchema()); + return null; + } + + @Nonnull + @Override + public NodeCodecContext yangPathArgumentChild(final YangInstanceIdentifier.PathArgument arg) { + final DataContainerCodecPrototype cazeProto; + if (arg instanceof YangInstanceIdentifier.NodeIdentifierWithPredicates) { + cazeProto = byYangCaseChild.get(new NodeIdentifier(arg.getNodeType())); + } else { + cazeProto = byYangCaseChild.get(arg); + } + + return childNonNull(cazeProto, arg, "Argument %s is not valid child of %s", arg, getSchema()).get() + .yangPathArgumentChild(arg); + } + + @SuppressWarnings("unchecked") + @Nonnull + @Override + public D deserialize(@Nonnull final NormalizedNode data) { + Preconditions.checkArgument(data instanceof ChoiceNode); + final NormalizedNodeContainer> casted = + (NormalizedNodeContainer>) data; + final NormalizedNode first = Iterables.getFirst(casted.getValue(), null); + + if (first == null) { + return null; + } + final DataContainerCodecPrototype caze = byYangCaseChild.get(first.getIdentifier()); + return (D) caze.get().deserialize(data); + } + + @Override + protected Object deserializeObject(final NormalizedNode normalizedNode) { + return deserialize(normalizedNode); + } + + @Nonnull + @Override + public TreeArgument deserializePathArgument(@Nonnull final YangInstanceIdentifier.PathArgument arg) { + Preconditions.checkArgument(getDomPathArgument().equals(arg)); + return null; + } + + @Nonnull + @Override + public YangInstanceIdentifier.PathArgument serializePathArgument(@Nonnull final TreeArgument arg) { + return getDomPathArgument(); + } +} diff --git a/binding2/mdsal-binding2-dom-codec/src/main/java/org/opendaylight/mdsal/binding/javav2/dom/codec/impl/context/NotificationCodecContext.java b/binding2/mdsal-binding2-dom-codec/src/main/java/org/opendaylight/mdsal/binding/javav2/dom/codec/impl/context/NotificationCodecContext.java new file mode 100644 index 0000000000..eb04792cac --- /dev/null +++ b/binding2/mdsal-binding2-dom-codec/src/main/java/org/opendaylight/mdsal/binding/javav2/dom/codec/impl/context/NotificationCodecContext.java @@ -0,0 +1,59 @@ +/* + * Copyright (c) 2017 Pantheon Technologies s.r.o. and others. All rights reserved. + * + * This program and the accompanying materials are made available under the + * terms of the Eclipse Public License v1.0 which accompanies this distribution, + * and is available at http://www.eclipse.org/legal/epl-v10.html + */ +package org.opendaylight.mdsal.binding.javav2.dom.codec.impl.context; + +import com.google.common.annotations.Beta; +import com.google.common.base.Preconditions; +import javax.annotation.Nonnull; +import org.opendaylight.mdsal.binding.javav2.dom.codec.impl.context.base.DataContainerCodecPrototype; +import org.opendaylight.mdsal.binding.javav2.dom.codec.impl.context.base.TreeNodeCodecContext; +import org.opendaylight.mdsal.binding.javav2.spec.base.Notification; +import org.opendaylight.mdsal.binding.javav2.spec.base.TreeNode; +import org.opendaylight.yangtools.yang.data.api.schema.ContainerNode; +import org.opendaylight.yangtools.yang.data.api.schema.NormalizedNode; +import org.opendaylight.yangtools.yang.data.api.schema.NormalizedNodeContainer; +import org.opendaylight.yangtools.yang.model.api.NotificationDefinition; + +/** + * Context for prototype of notification. + * + * @param + * - type of tree node + */ +@SuppressWarnings("rawtypes") +@Beta +public final class NotificationCodecContext + extends TreeNodeCodecContext { + + /** + * Prepare context for notification from prototype. + * + * @param key + * - binding class + * @param schema + * - schema of notification + * @param factory + * - codec context factory + */ + public NotificationCodecContext(final Class key, final NotificationDefinition schema, + final CodecContextFactory factory) { + super(DataContainerCodecPrototype.from(key, schema, factory)); + } + + @Nonnull + @Override + public D deserialize(@Nonnull final NormalizedNode data) { + Preconditions.checkState(data instanceof ContainerNode); + return createBindingProxy((NormalizedNodeContainer) data); + } + + @Override + protected Object deserializeObject(final NormalizedNode normalizedNode) { + return deserialize(normalizedNode); + } +} diff --git a/binding2/mdsal-binding2-dom-codec/src/main/java/org/opendaylight/mdsal/binding/javav2/dom/codec/impl/context/UnionValueOptionContext.java b/binding2/mdsal-binding2-dom-codec/src/main/java/org/opendaylight/mdsal/binding/javav2/dom/codec/impl/context/UnionValueOptionContext.java new file mode 100644 index 0000000000..9daf43edfa --- /dev/null +++ b/binding2/mdsal-binding2-dom-codec/src/main/java/org/opendaylight/mdsal/binding/javav2/dom/codec/impl/context/UnionValueOptionContext.java @@ -0,0 +1,140 @@ +/* + * Copyright (c) 2017 Pantheon Technologies s.r.o. and others. All rights reserved. + * + * This program and the accompanying materials are made available under the + * terms of the Eclipse Public License v1.0 which accompanies this distribution, + * and is available at http://www.eclipse.org/legal/epl-v10.html + */ +package org.opendaylight.mdsal.binding.javav2.dom.codec.impl.context; + +import com.google.common.annotations.Beta; +import com.google.common.base.Preconditions; +import com.google.common.base.Throwables; +import java.lang.invoke.MethodHandle; +import java.lang.invoke.MethodHandles; +import java.lang.invoke.MethodType; +import java.lang.reflect.Method; +import org.opendaylight.mdsal.binding.javav2.dom.codec.impl.value.EncapsulatedValueCodec; +import org.opendaylight.yangtools.concepts.Codec; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +/** + * Context for serializing input value of union type and deserializing objects to binding. + * + */ +@Beta +public class UnionValueOptionContext { + + private static final Logger LOG = LoggerFactory.getLogger(UnionValueOptionContext.class); + + private static final MethodType OBJECT_TYPE = MethodType.methodType(Object.class, Object.class); + + private final Class bindingType; + private final Codec codec; + private final MethodHandle getter; + private final MethodHandle unionCtor; + + /** + * Prepare union as binding object and codec for this object, make a direct method handle of getting union + * type and constructor of union type for initializing it. + * + * @param unionType + * - union as binding object + * @param valueType + * - returned type of union + * @param getter + * - method for getting union type + * @param codec + * - codec for serialize/deserialize type of union + */ + public UnionValueOptionContext(final Class unionType, final Class valueType, final Method getter, + final Codec codec) { + this.bindingType = Preconditions.checkNotNull(valueType); + this.codec = Preconditions.checkNotNull(codec); + + try { + this.getter = MethodHandles.publicLookup().unreflect(getter).asType(OBJECT_TYPE); + } catch (final IllegalAccessException e) { + throw new IllegalStateException("Failed to access method " + getter, e); + } + + try { + this.unionCtor = MethodHandles.publicLookup() + .findConstructor(unionType, MethodType.methodType(void.class, valueType)).asType(OBJECT_TYPE); + } catch (IllegalAccessException | NoSuchMethodException e) { + throw new IllegalStateException( + String.format("Failed to access constructor for %s in type %s", valueType, unionType), e); + } + } + + /** + * Serialize input based on prepared codec. + * + * @param input + * - object to serialize + * @return serialized objetc + */ + public Object serialize(final Object input) { + final Object baValue = getValueFrom(input); + return baValue == null ? null : codec.serialize(baValue); + } + + /** + * Deserialize input object via prepared codec for invoking new object of union as binding. + * + * @param input + * - input object for deserializing + * @return deserialized union binding type object + */ + public Object deserializeUnion(final Object input) { + // Side-step potential exceptions by checking the type if it is available + if (codec instanceof EncapsulatedValueCodec && !((EncapsulatedValueCodec) codec).canAcceptObject(input)) { + return null; + } + + final Object value; + try { + value = codec.deserialize(input); + } catch (final Exception e) { + LOG.debug("Codec {} failed to deserialize input {}", codec, input, e); + return null; + } + + try { + return unionCtor.invokeExact(value); + } catch (final ClassCastException e) { + // This case can happen. e.g. NOOP_CODEC + LOG.debug("Failed to instantiate {} for input {} value {}", bindingType, input, value, e); + return null; + } catch (final Throwable e) { + throw new IllegalArgumentException("Failed to construct union for value " + value, e); + } + } + + private Object getValueFrom(final Object input) { + try { + return getter.invokeExact(input); + } catch (final Throwable e) { + throw Throwables.propagate(e); + } + } + + @Override + public int hashCode() { + return bindingType.hashCode(); + } + + @Override + public boolean equals(final Object obj) { + if (this == obj) { + return true; + } + if (!(obj instanceof UnionValueOptionContext)) { + return false; + } + + final UnionValueOptionContext other = (UnionValueOptionContext) obj; + return bindingType.equals(other.bindingType); + } +} diff --git a/binding2/mdsal-binding2-dom-codec/src/main/java/org/opendaylight/mdsal/binding/javav2/dom/codec/impl/context/ValueContext.java b/binding2/mdsal-binding2-dom-codec/src/main/java/org/opendaylight/mdsal/binding/javav2/dom/codec/impl/context/ValueContext.java new file mode 100644 index 0000000000..1698867d0a --- /dev/null +++ b/binding2/mdsal-binding2-dom-codec/src/main/java/org/opendaylight/mdsal/binding/javav2/dom/codec/impl/context/ValueContext.java @@ -0,0 +1,81 @@ +/* + * Copyright (c) 2017 Pantheon Technologies s.r.o. and others. All rights reserved. + * + * This program and the accompanying materials are made available under the + * terms of the Eclipse Public License v1.0 which accompanies this distribution, + * and is available at http://www.eclipse.org/legal/epl-v10.html + */ +package org.opendaylight.mdsal.binding.javav2.dom.codec.impl.context; + +import com.google.common.annotations.Beta; +import com.google.common.base.Preconditions; +import com.google.common.base.Throwables; +import java.lang.invoke.MethodHandle; +import java.lang.invoke.MethodHandles; +import java.lang.invoke.MethodType; +import org.opendaylight.mdsal.binding.javav2.dom.codec.impl.context.base.LeafNodeCodecContext; +import org.opendaylight.yangtools.concepts.Codec; + +/** + * Context for serialize/deserialize leaf. + */ +@Beta +public final class ValueContext { + + private static final MethodType OBJECT_METHOD = MethodType.methodType(Object.class, Object.class); + private final Codec codec; + private final MethodHandle getter; + private final Class identifier; + private final String getterName; + + /** + * Prepare codec of leaf value and getter of binding leaf object for getting leaf. + * + * @param identifier + * - binding class + * @param leaf + * - leaf codec context + */ + public ValueContext(final Class identifier, final LeafNodeCodecContext leaf) { + getterName = leaf.getGetter().getName(); + try { + getter = MethodHandles.publicLookup().unreflect(identifier.getMethod(getterName)).asType(OBJECT_METHOD); + } catch (IllegalAccessException | NoSuchMethodException | SecurityException e) { + throw new IllegalStateException(String.format("Cannot find method %s in class %s", getterName, identifier), e); + } + this.identifier = identifier; + codec = leaf.getValueCodec(); + } + + /** + * Get object via invoking getter with input and serializes it by prepared codec of leaf. + * + * @param obj + * - input object + * @return serialized invoked object + */ + public Object getAndSerialize(final Object obj) { + final Object value; + try { + value = getter.invokeExact(obj); + } catch (final Throwable e) { + throw Throwables.propagate(e); + } + + Preconditions.checkArgument(value != null, + "All keys must be specified for %s. Missing key is %s. Supplied key is %s", + identifier, getterName, obj); + return codec.serialize(value); + } + + /** + * Deserialize input object by prepared codec. + * + * @param obj + * - input object + * @return deserialized object + */ + public Object deserialize(final Object obj) { + return codec.deserialize(obj); + } +} diff --git a/binding2/mdsal-binding2-dom-codec/src/main/java/org/opendaylight/mdsal/binding/javav2/dom/codec/impl/context/base/DataContainerCodecPrototype.java b/binding2/mdsal-binding2-dom-codec/src/main/java/org/opendaylight/mdsal/binding/javav2/dom/codec/impl/context/base/DataContainerCodecPrototype.java index 2a531bbc0c..f36464da8f 100644 --- a/binding2/mdsal-binding2-dom-codec/src/main/java/org/opendaylight/mdsal/binding/javav2/dom/codec/impl/context/base/DataContainerCodecPrototype.java +++ b/binding2/mdsal-binding2-dom-codec/src/main/java/org/opendaylight/mdsal/binding/javav2/dom/codec/impl/context/base/DataContainerCodecPrototype.java @@ -57,12 +57,12 @@ public final class DataContainerCodecPrototype implements NodeContextSupplier } @SuppressWarnings({ "unchecked", "rawtypes" }) - static DataContainerCodecPrototype from(final Class cls, final T schema, + public static DataContainerCodecPrototype from(final Class cls, final T schema, final CodecContextFactory factory) { return new DataContainerCodecPrototype(cls, NodeIdentifier.create(schema.getQName()), schema, factory); } - static DataContainerCodecPrototype rootPrototype(final CodecContextFactory factory) { + public static DataContainerCodecPrototype rootPrototype(final CodecContextFactory factory) { final SchemaContext schema = factory.getRuntimeContext().getSchemaContext(); final NodeIdentifier arg = NodeIdentifier.create(schema.getQName()); return new DataContainerCodecPrototype<>(TreeRoot.class, arg, schema, factory); @@ -74,12 +74,13 @@ public final class DataContainerCodecPrototype implements NodeContextSupplier return new DataContainerCodecPrototype(augClass, arg, schema, factory); } - static DataContainerCodecPrototype from(final Class augClass, final NotificationDefinition schema, final CodecContextFactory factory) { + public static DataContainerCodecPrototype from(final Class augClass, + final NotificationDefinition schema, final CodecContextFactory factory) { final PathArgument arg = NodeIdentifier.create(schema.getQName()); return new DataContainerCodecPrototype<>(augClass, arg, schema, factory); } - protected T getSchema() { + public T getSchema() { return schema; } @@ -91,7 +92,7 @@ public final class DataContainerCodecPrototype implements NodeContextSupplier return factory; } - protected Class getBindingClass() { + public Class getBindingClass() { return bindingClass; } diff --git a/binding2/mdsal-binding2-dom-codec/src/main/java/org/opendaylight/mdsal/binding/javav2/dom/codec/impl/context/base/LeafNodeCodecContext.java b/binding2/mdsal-binding2-dom-codec/src/main/java/org/opendaylight/mdsal/binding/javav2/dom/codec/impl/context/base/LeafNodeCodecContext.java index 9a88075ebf..3645fbcb88 100644 --- a/binding2/mdsal-binding2-dom-codec/src/main/java/org/opendaylight/mdsal/binding/javav2/dom/codec/impl/context/base/LeafNodeCodecContext.java +++ b/binding2/mdsal-binding2-dom-codec/src/main/java/org/opendaylight/mdsal/binding/javav2/dom/codec/impl/context/base/LeafNodeCodecContext.java @@ -149,7 +149,7 @@ public final class LeafNodeCodecContext extends NodeCodecCon return this; } - final Method getGetter() { + public final Method getGetter() { return getter; } diff --git a/binding2/mdsal-binding2-dom-codec/src/main/java/org/opendaylight/mdsal/binding/javav2/dom/codec/impl/value/EncapsulatedValueCodec.java b/binding2/mdsal-binding2-dom-codec/src/main/java/org/opendaylight/mdsal/binding/javav2/dom/codec/impl/value/EncapsulatedValueCodec.java index 8727eadddc..959fcb5f39 100644 --- a/binding2/mdsal-binding2-dom-codec/src/main/java/org/opendaylight/mdsal/binding/javav2/dom/codec/impl/value/EncapsulatedValueCodec.java +++ b/binding2/mdsal-binding2-dom-codec/src/main/java/org/opendaylight/mdsal/binding/javav2/dom/codec/impl/value/EncapsulatedValueCodec.java @@ -24,7 +24,7 @@ import org.opendaylight.mdsal.binding.javav2.dom.codec.impl.value.ValueTypeCodec * types, which are same as in NormalizedNode model. */ @Beta -final class EncapsulatedValueCodec extends ReflectionBasedCodec implements SchemaUnawareCodec { +public final class EncapsulatedValueCodec extends ReflectionBasedCodec implements SchemaUnawareCodec { private static final Lookup LOOKUP = MethodHandles.publicLookup(); private static final MethodType OBJ_METHOD = MethodType.methodType(Object.class, Object.class); @@ -59,24 +59,24 @@ final class EncapsulatedValueCodec extends ReflectionBasedCodec implements Schem * @param value Value to be checked * @return True if the value can be encapsulated */ - boolean canAcceptObject(final Object value) { + public boolean canAcceptObject(final Object value) { return valueType.isInstance(value); } @Override - public Object deserialize(Object input) { + public Object deserialize(final Object input) { try { return constructor.invokeExact(input); - } catch (Throwable e) { + } catch (final Throwable e) { throw Throwables.propagate(e); } } @Override - public Object serialize(Object input) { + public Object serialize(final Object input) { try { return getter.invokeExact(input); - } catch (Throwable e) { + } catch (final Throwable e) { throw Throwables.propagate(e); } } -- 2.36.6