Simplify code using Java 8 features
[mdsal.git] / binding / mdsal-binding-generator-api / src / main / java / org / opendaylight / mdsal / binding / model / api / YangSourceDefinition.java
1 /*
2  * Copyright (c) 2018 Pantheon Technologies, s.r.o. and others.  All rights reserved.
3  *
4  * This program and the accompanying materials are made available under the
5  * terms of the Eclipse Public License v1.0 which accompanies this distribution,
6  * and is available at http://www.eclipse.org/legal/epl-v10.html
7  */
8 package org.opendaylight.mdsal.binding.model.api;
9
10 import static com.google.common.base.Preconditions.checkArgument;
11 import static java.util.Objects.requireNonNull;
12
13 import com.google.common.annotations.Beta;
14 import com.google.common.collect.ImmutableList;
15 import java.util.Collection;
16 import java.util.List;
17 import java.util.Optional;
18 import java.util.stream.Collectors;
19 import org.eclipse.jdt.annotation.NonNullByDefault;
20 import org.opendaylight.yangtools.yang.model.api.DocumentedNode;
21 import org.opendaylight.yangtools.yang.model.api.Module;
22 import org.opendaylight.yangtools.yang.model.api.SchemaNode;
23 import org.opendaylight.yangtools.yang.model.api.meta.DeclaredStatement;
24 import org.opendaylight.yangtools.yang.model.api.meta.EffectiveStatement;
25 import org.opendaylight.yangtools.yang.model.api.stmt.ModuleEffectiveStatement;
26 import org.opendaylight.yangtools.yang.model.api.stmt.ModuleStatement;
27
28 /**
29  * DTO capturing the YANG source definition which lead to a {@link GeneratedType} being emitted.
30  *
31  * @author Robert Varga
32  */
33 @Beta
34 @NonNullByDefault
35 public abstract class YangSourceDefinition {
36     public static final class Multiple extends YangSourceDefinition {
37         private final List<? extends SchemaNode> nodes;
38
39         Multiple(final ModuleEffectiveStatement module, final Collection<? extends SchemaNode> nodes) {
40             super(module);
41             this.nodes = ImmutableList.copyOf(nodes);
42         }
43
44         /**
45          * Return the defining SchemaNodes. Each node is guaranteed to implement {@link EffectiveStatement} and have
46          * a corresponding declared statement.
47          *
48          * @return defining SchemaNodes, guaranteed to be non-empty
49          */
50         public List<? extends SchemaNode> getNodes() {
51             return nodes.stream().filter(node -> node instanceof EffectiveStatement
52                 && ((EffectiveStatement<?, ?>) node).getDeclared() != null).collect(Collectors.toList());
53         }
54     }
55
56     public static final class Single extends YangSourceDefinition {
57         private final DocumentedNode node;
58
59         Single(final ModuleEffectiveStatement module, final DocumentedNode node) {
60             super(module);
61             this.node = requireNonNull(node);
62         }
63
64         /**
65          * Return the defining DocumentedNode. The node is guaranteed to implement {@link EffectiveStatement} and have
66          * a corresponding declared statement.
67          *
68          * @return defining SchemaNodes, guaranteed to be non-empty
69          */
70         public DocumentedNode getNode() {
71             return node;
72         }
73     }
74
75     private final ModuleEffectiveStatement module;
76
77     private YangSourceDefinition(final ModuleEffectiveStatement module) {
78         this.module = requireNonNull(module);
79     }
80
81     public static Optional<YangSourceDefinition> of(final Module module) {
82         if (module instanceof ModuleEffectiveStatement) {
83             final ModuleEffectiveStatement effective = (ModuleEffectiveStatement) module;
84             final ModuleStatement declared = effective.getDeclared();
85             if (declared != null) {
86                 return Optional.of(new Single(effective, module));
87             }
88         }
89         return Optional.empty();
90     }
91
92     public static Optional<YangSourceDefinition> of(final Module module, final SchemaNode node) {
93         if (module instanceof ModuleEffectiveStatement) {
94             final ModuleEffectiveStatement effective = (ModuleEffectiveStatement) module;
95             if (node instanceof EffectiveStatement) {
96                 final DeclaredStatement<?> declared = ((EffectiveStatement<?, ?>) node).getDeclared();
97                 if (declared != null) {
98                     return Optional.of(new Single(effective, node));
99                 }
100             }
101         }
102         return Optional.empty();
103     }
104
105     public static Optional<YangSourceDefinition> of(final Module module, final Collection<? extends SchemaNode> nodes) {
106         checkArgument(!nodes.isEmpty());
107
108         if (module instanceof ModuleEffectiveStatement) {
109             final ModuleEffectiveStatement effective = (ModuleEffectiveStatement) module;
110             final boolean anyDeclared = nodes.stream().anyMatch(node ->
111                 node instanceof EffectiveStatement && ((EffectiveStatement<?, ?>) node).getDeclared() != null);
112             if (anyDeclared) {
113                 return Optional.of(new Multiple(effective, nodes));
114             }
115         }
116         return Optional.empty();
117     }
118
119     /**
120      * Return the defining YANG module.
121      *
122      * @return Defining YANG module.
123      */
124     public final ModuleEffectiveStatement getModule() {
125         return module;
126     }
127 }