X-Git-Url: https://git.opendaylight.org/gerrit/gitweb?a=blobdiff_plain;ds=sidebyside;f=yang%2Fyang-data-impl%2Fsrc%2Fmain%2Fjava%2Forg%2Fopendaylight%2Fyangtools%2Fyang%2Fdata%2Fimpl%2Fschema%2FInstanceIdToNodes.java;h=8590557411cde7e07f639c1199650a61837c1df6;hb=970923b5f47f7507ec78021965fa5df1a878af48;hp=cb109bef5111124a1a2d4e5a240f313dc9bd9e33;hpb=faaf2c84f0f1304e0f8837992014557c47dd9379;p=yangtools.git diff --git a/yang/yang-data-impl/src/main/java/org/opendaylight/yangtools/yang/data/impl/schema/InstanceIdToNodes.java b/yang/yang-data-impl/src/main/java/org/opendaylight/yangtools/yang/data/impl/schema/InstanceIdToNodes.java index cb109bef51..8590557411 100644 --- a/yang/yang-data-impl/src/main/java/org/opendaylight/yangtools/yang/data/impl/schema/InstanceIdToNodes.java +++ b/yang/yang-data-impl/src/main/java/org/opendaylight/yangtools/yang/data/impl/schema/InstanceIdToNodes.java @@ -7,32 +7,34 @@ */ package org.opendaylight.yangtools.yang.data.impl.schema; -import com.google.common.base.Optional; -import com.google.common.base.Preconditions; -import com.google.common.collect.FluentIterable; -import java.util.Collections; +import static com.google.common.base.Preconditions.checkArgument; +import static com.google.common.base.Preconditions.checkState; + +import com.google.common.collect.Iterables; +import java.util.Iterator; import java.util.List; -import java.util.Map.Entry; +import java.util.Optional; import javax.xml.transform.dom.DOMSource; -import org.opendaylight.yangtools.concepts.Identifiable; +import org.eclipse.jdt.annotation.NonNull; +import org.eclipse.jdt.annotation.Nullable; +import org.opendaylight.yangtools.concepts.AbstractSimpleIdentifiable; import org.opendaylight.yangtools.yang.common.QName; -import org.opendaylight.yangtools.yang.data.api.ModifyAction; -import org.opendaylight.yangtools.yang.data.api.YangInstanceIdentifier; import org.opendaylight.yangtools.yang.data.api.YangInstanceIdentifier.NodeIdentifier; import org.opendaylight.yangtools.yang.data.api.YangInstanceIdentifier.PathArgument; -import org.opendaylight.yangtools.yang.data.api.schema.AnyXmlNode; +import org.opendaylight.yangtools.yang.data.api.schema.AnydataNode; +import org.opendaylight.yangtools.yang.data.api.schema.DOMSourceAnyxmlNode; import org.opendaylight.yangtools.yang.data.api.schema.NormalizedNode; import org.opendaylight.yangtools.yang.data.api.schema.UnkeyedListEntryNode; import org.opendaylight.yangtools.yang.data.api.schema.UnkeyedListNode; -import org.opendaylight.yangtools.yang.data.impl.schema.builder.api.AttributesBuilder; import org.opendaylight.yangtools.yang.data.impl.schema.builder.api.CollectionNodeBuilder; -import org.opendaylight.yangtools.yang.data.impl.schema.builder.api.NormalizedNodeAttrBuilder; -import org.opendaylight.yangtools.yang.model.api.AnyXmlSchemaNode; -import org.opendaylight.yangtools.yang.model.api.AugmentationSchema; +import org.opendaylight.yangtools.yang.data.impl.schema.builder.api.NormalizedNodeBuilder; +import org.opendaylight.yangtools.yang.model.api.AnydataSchemaNode; +import org.opendaylight.yangtools.yang.model.api.AnyxmlSchemaNode; +import org.opendaylight.yangtools.yang.model.api.AugmentationSchemaNode; import org.opendaylight.yangtools.yang.model.api.AugmentationTarget; -import org.opendaylight.yangtools.yang.model.api.ChoiceCaseNode; +import org.opendaylight.yangtools.yang.model.api.CaseSchemaNode; import org.opendaylight.yangtools.yang.model.api.ChoiceSchemaNode; -import org.opendaylight.yangtools.yang.model.api.ContainerSchemaNode; +import org.opendaylight.yangtools.yang.model.api.ContainerLike; import org.opendaylight.yangtools.yang.model.api.DataNodeContainer; import org.opendaylight.yangtools.yang.model.api.DataSchemaNode; import org.opendaylight.yangtools.yang.model.api.LeafListSchemaNode; @@ -43,70 +45,48 @@ import org.opendaylight.yangtools.yang.model.api.ListSchemaNode; * Base strategy for converting an instance identifier into a normalized node structure. * Use provided static methods for generic YangInstanceIdentifier -> NormalizedNode translation in ImmutableNodes. */ -abstract class InstanceIdToNodes implements Identifiable { - - private final T identifier; - - @Override - public final T getIdentifier() { - return identifier; - } - - protected InstanceIdToNodes(final T identifier) { - this.identifier = identifier; +abstract class InstanceIdToNodes extends AbstractSimpleIdentifiable { + InstanceIdToNodes(final T identifier) { + super(identifier); } /** - * Build a strategy for the next path argument + * Build a strategy for the next path argument. * * @param child child identifier * @return transformation strategy for a specific child */ - abstract InstanceIdToNodes getChild(final PathArgument child); + abstract @Nullable InstanceIdToNodes getChild(PathArgument child); /** - * - * Convert instance identifier into a NormalizedNode structure + * Convert instance identifier into a NormalizedNode structure. * * @param instanceId Instance identifier to transform into NormalizedNodes * @param deepestChild Optional normalized node to be inserted as the last child * @param operation Optional modify operation to be set on the last child * @return NormalizedNode structure corresponding to submitted instance ID */ - abstract NormalizedNode create(YangInstanceIdentifier instanceId, Optional> deepestChild, Optional> operation); + abstract @NonNull NormalizedNode create(PathArgument first, Iterator others, + Optional deepestChild); abstract boolean isMixin(); - public void addModifyOpIfPresent(final Optional> operation, final AttributesBuilder builder) { - if(operation.isPresent()) { - builder.withAttributes(Collections.singletonMap(operation.get().getKey(), modifyOperationToXmlString(operation.get().getValue()))); - } - } - - public static String modifyOperationToXmlString(final ModifyAction operation) { - return operation.name().toLowerCase(); - } - - private final static class UnkeyedListMixinNormalization extends InstanceIdToCompositeNodes { - + private static final class UnkeyedListMixinNormalization extends InstanceIdToCompositeNodes { private final UnkeyedListItemNormalization innerNode; - public UnkeyedListMixinNormalization(final ListSchemaNode list) { + UnkeyedListMixinNormalization(final ListSchemaNode list) { super(NodeIdentifier.create(list.getQName())); this.innerNode = new UnkeyedListItemNormalization(list); } @Override - protected CollectionNodeBuilder createBuilder(final PathArgument compositeNode) { + CollectionNodeBuilder createBuilder(final PathArgument compositeNode) { return Builders.unkeyedListBuilder().withNodeIdentifier(getIdentifier()); } @Override - public InstanceIdToNodes getChild(final PathArgument child) { - if (child.getNodeType().equals(getIdentifier().getNodeType())) { - return innerNode; - } - return null; + InstanceIdToNodes getChild(final PathArgument child) { + return child.getNodeType().equals(getIdentifier().getNodeType()) ? innerNode : null; } @Override @@ -115,73 +95,92 @@ abstract class InstanceIdToNodes implements Identifiable } } - private static class AnyXmlNormalization extends InstanceIdToNodes { - - protected AnyXmlNormalization(final AnyXmlSchemaNode schema) { + private abstract static class AbstractOpaqueNormalization extends InstanceIdToNodes { + AbstractOpaqueNormalization(final DataSchemaNode schema) { super(NodeIdentifier.create(schema.getQName())); } @Override - public InstanceIdToNodes getChild(final PathArgument child) { + final InstanceIdToNodes getChild(final PathArgument child) { return null; } @Override - public NormalizedNode create(final YangInstanceIdentifier instanceId, final Optional> deepestChild, final Optional> operation) { - if(deepestChild.isPresent()) { - Preconditions.checkState(deepestChild instanceof AnyXmlNode); - final NormalizedNodeAttrBuilder anyXmlBuilder = - Builders.anyXmlBuilder().withNodeIdentifier(getIdentifier()).withValue(((AnyXmlNode) deepestChild).getValue()); - addModifyOpIfPresent(operation, anyXmlBuilder); - return anyXmlBuilder.build(); - } + final boolean isMixin() { + return false; + } + } - final NormalizedNodeAttrBuilder builder = - Builders.anyXmlBuilder().withNodeIdentifier(getIdentifier()); - addModifyOpIfPresent(operation, builder); - return builder.build(); + private static final class AnydataNormalization extends AbstractOpaqueNormalization { + AnydataNormalization(final AnydataSchemaNode schema) { + super(schema); } @Override - boolean isMixin() { - return false; + NormalizedNode create(final PathArgument first, final Iterator others, + final Optional deepestChild) { + checkState(deepestChild.isPresent(), "Cannot instantiate anydata node without a value"); + final NormalizedNode child = deepestChild.get(); + checkState(child instanceof AnydataNode, "Invalid child %s", child); + return createAnydata((AnydataNode) child); + } + + private AnydataNode createAnydata(final AnydataNode child) { + return Builders.anydataBuilder(child.bodyObjectModel()).withValue(child.body()) + .withNodeIdentifier(getIdentifier()).build(); } } - private static Optional findChildSchemaNode(final DataNodeContainer parent, final QName child) { - DataSchemaNode potential = parent.getDataChildByName(child); - if (potential == null) { - final Iterable choices = FluentIterable.from(parent.getChildNodes()).filter(ChoiceSchemaNode.class); - potential = findChoice(choices, child); + private static final class AnyXmlNormalization extends AbstractOpaqueNormalization { + AnyXmlNormalization(final AnyxmlSchemaNode schema) { + super(schema); + } + + @Override + NormalizedNode create(final PathArgument first, final Iterator others, + final Optional deepestChild) { + final NormalizedNodeBuilder builder = + Builders.anyXmlBuilder() + .withNodeIdentifier(getIdentifier()); + if (deepestChild.isPresent()) { + final NormalizedNode child = deepestChild.get(); + checkState(child instanceof DOMSourceAnyxmlNode, "Invalid child %s", child); + builder.withValue(((DOMSourceAnyxmlNode) child).body()); + } + + return builder.build(); } - return Optional.fromNullable(potential); } - static InstanceIdToNodes fromSchemaAndQNameChecked(final DataNodeContainer schema, final QName child) { + private static Optional findChildSchemaNode(final DataNodeContainer parent, final QName child) { + final Optional potential = parent.findDataChildByName(child); + return potential.isPresent() ? potential : Optional.ofNullable( + findChoice(Iterables.filter(parent.getChildNodes(), ChoiceSchemaNode.class), child)); + } + + static @Nullable InstanceIdToNodes fromSchemaAndQNameChecked(final DataNodeContainer schema, final QName child) { final Optional potential = findChildSchemaNode(schema, child); - Preconditions.checkArgument(potential.isPresent(), - "Supplied QName %s is not valid according to schema %s, potential children nodes: %s", child, schema, schema.getChildNodes()); + checkArgument(potential.isPresent(), + "Supplied QName %s is not valid according to schema %s, potential children nodes: %s", child, schema, + schema.getChildNodes()); final DataSchemaNode result = potential.get(); // We try to look up if this node was added by augmentation - if ((schema instanceof DataSchemaNode) && result.isAugmenting()) { + if (schema instanceof DataSchemaNode && result.isAugmenting()) { return fromAugmentation(schema, (AugmentationTarget) schema, result); } return fromDataSchemaNode(result); } - private static ChoiceSchemaNode findChoice(final Iterable choices, final QName child) { - ChoiceSchemaNode foundChoice = null; - choiceLoop: + private static @Nullable ChoiceSchemaNode findChoice(final Iterable choices, final QName child) { for (final ChoiceSchemaNode choice : choices) { - for (final ChoiceCaseNode caze : choice.getCases()) { + for (final CaseSchemaNode caze : choice.getCases()) { if (findChildSchemaNode(caze, child).isPresent()) { - foundChoice = choice; - break choiceLoop; + return choice; } } } - return foundChoice; + return null; } /** @@ -192,27 +191,20 @@ abstract class InstanceIdToNodes implements Identifiable * otherwise returns a SchemaPathUtil for child as * call for {@link #fromDataSchemaNode(org.opendaylight.yangtools.yang.model.api.DataSchemaNode)}. */ - private static InstanceIdToNodes fromAugmentation(final DataNodeContainer parent, - final AugmentationTarget parentAug, final DataSchemaNode child) { - AugmentationSchema augmentation = null; - for (final AugmentationSchema aug : parentAug.getAvailableAugmentations()) { - final DataSchemaNode potential = aug.getDataChildByName(child.getQName()); - if (potential != null) { - augmentation = aug; - break; + private static @Nullable InstanceIdToNodes fromAugmentation(final DataNodeContainer parent, + final AugmentationTarget parentAug, final DataSchemaNode child) { + for (final AugmentationSchemaNode aug : parentAug.getAvailableAugmentations()) { + final Optional potential = aug.findDataChildByName(child.getQName()); + if (potential.isPresent()) { + return new InstanceIdToCompositeNodes.AugmentationNormalization(aug, parent); } - - } - if (augmentation != null) { - return new InstanceIdToCompositeNodes.AugmentationNormalization(augmentation, parent); - } else { - return fromDataSchemaNode(child); } + return fromDataSchemaNode(child); } - static InstanceIdToNodes fromDataSchemaNode(final DataSchemaNode potential) { - if (potential instanceof ContainerSchemaNode) { - return new InstanceIdToCompositeNodes.ContainerTransformation((ContainerSchemaNode) potential); + static @Nullable InstanceIdToNodes fromDataSchemaNode(final DataSchemaNode potential) { + if (potential instanceof ContainerLike) { + return new InstanceIdToCompositeNodes.ContainerTransformation((ContainerLike) potential); } else if (potential instanceof ListSchemaNode) { return fromListSchemaNode((ListSchemaNode) potential); } else if (potential instanceof LeafSchemaNode) { @@ -221,8 +213,10 @@ abstract class InstanceIdToNodes implements Identifiable return new InstanceIdToCompositeNodes.ChoiceNodeNormalization((ChoiceSchemaNode) potential); } else if (potential instanceof LeafListSchemaNode) { return fromLeafListSchemaNode((LeafListSchemaNode) potential); - } else if (potential instanceof AnyXmlSchemaNode) { - return new AnyXmlNormalization((AnyXmlSchemaNode) potential); + } else if (potential instanceof AnydataSchemaNode) { + return new AnydataNormalization((AnydataSchemaNode) potential); + } else if (potential instanceof AnyxmlSchemaNode) { + return new AnyXmlNormalization((AnyxmlSchemaNode) potential); } return null; } @@ -232,18 +226,12 @@ abstract class InstanceIdToNodes implements Identifiable if (keyDefinition == null || keyDefinition.isEmpty()) { return new UnkeyedListMixinNormalization(potential); } - if (potential.isUserOrdered()) { - return new InstanceIdToCompositeNodes.OrderedMapMixinNormalization(potential); - } - return new InstanceIdToCompositeNodes.UnorderedMapMixinNormalization(potential); + return potential.isUserOrdered() ? new InstanceIdToCompositeNodes.OrderedMapMixinNormalization(potential) + : new InstanceIdToCompositeNodes.UnorderedMapMixinNormalization(potential); } private static InstanceIdToNodes fromLeafListSchemaNode(final LeafListSchemaNode potential) { - if (potential.isUserOrdered()) { - return new InstanceIdToCompositeNodes.OrderedLeafListMixinNormalization(potential); - } - return new InstanceIdToCompositeNodes.UnorderedLeafListMixinNormalization(potential); + return potential.isUserOrdered() ? new InstanceIdToCompositeNodes.OrderedLeafListMixinNormalization(potential) + : new InstanceIdToCompositeNodes.UnorderedLeafListMixinNormalization(potential); } - - }