2 * Copyright (c) 2014 Cisco Systems, Inc. and others. All rights reserved.
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
8 package org.opendaylight.yangtools.yang.binding;
10 import java.io.Closeable;
11 import java.io.Flushable;
12 import java.io.IOException;
16 * Event Stream Writer for Binding Representation.
18 * <h3>Emmiting Event Stream</h3>
21 * <li><code>container</code> - Container node representation, start event is
22 * emitted using {@link #startContainerNode(Class, int)} and node end event is
23 * emitted using {@link #endNode()}. Container node is implementing
24 * {@link DataObject} interface.
26 * <li><code>list</code> - YANG list statement has two representation in event
27 * stream - unkeyed list and map. Unkeyed list is YANG list which did not
31 * <li><code>Map</code> - Map start event is emitted using
32 * {@link #startMapNode(Class, int)} and is ended using {@link #endNode()}. Each map
33 * entry start is emitted using {@link #startMapEntryNode(Identifier, int)} with Map of keys
34 * and finished using {@link #endNode()}.</li>
35 * <li><code>UnkeyedList</code> - Unkeyed list represent list without keys,
36 * unkeyed list start is emitted using {@link #startUnkeyedList(Class, int)} list
37 * end is emitted using {@link #endNode()}. Each list item is emitted using
38 * {@link #startUnkeyedListItem(int)} and ended using {@link #endNode()}.</li>
40 * <li><code>leaf</code> - Leaf node event is emitted using
41 * {@link #leafNode(String, Object)}. {@link #endNode()} MUST be not emitted for
43 * <li><code>leaf-list</code> - Leaf list start is emitted using
44 * {@link #startLeafSet(String, int)}. Leaf list end is emitted using
45 * {@link #endNode()}. Leaf list entries are emitted using
46 * {@link #leafSetEntryNode(Object)}.
47 * <li><code>anyxml - Anyxml node event is emitted using
48 * {@link #leafNode(String, Object)}. {@link #endNode()} MUST be not emitted
49 * for anyxml node.</code></li>
50 * <li><code>choice</code> Choice node event is emitted by
51 * {@link #startChoiceNode(Class, int)} event and must be immediately followed by
52 * {@link #startCase(Class, int)} event. Choice node is finished by emitting an
53 * {@link #endNode()} event.</li>
55 * <code>case</code> - Case node may be emitted only inside choice node by
56 * invoking {@link #startCase(Class, int)}. Case node is finished be emitting an
57 * {@link #endNode()} event.</li>
59 * <code>augment</code> - Represents augmentation, augmentation node is started
60 * by invoking {@link #startAugmentationNode(Class)} and
61 * finished by invoking {@link #endNode()}.</li>
64 * <h3>Implementation notes</h3> This interface is not intended to be implemented by users of generated Binding DTOs
65 * but to be used by utilities, which needs to emit NormalizedNode model from Binding DTOs.
68 * This interface is intended as API definition of facade for real Event / Stream Writer, without explicitly requiring
69 * stream writer and related interfaces to be imported by all generated Binding DTOs.
72 * Existence of this interface in base Java Binding package is required to support runtime generation of users of this
73 * interface in OSGI and OSGI-like environment, since this package is only package which is imported by all generated
74 * Binding DTOs and wired in OSGI.
76 public interface BindingStreamEventWriter extends Closeable, Flushable {
79 * Methods in this interface allow users to hint the underlying implementation about the sizing of container-like
80 * constructors (leafLists, containers, etc.). These hints may be taken into account by a particular implementation
81 * to improve performance, but clients are not required to provide hints. This constant should be used by clients
82 * who either do not have the sizing information, or do not wish to divulge it (for whatever reasons).
83 * Implementations are free to ignore these hints completely, but if they do use them, they are expected to be
84 * resilient in face of missing and mismatched hints, which is to say the user can specify startLeafSet(..., 1)
85 * and then call leafNode() 15 times.
88 * The acceptable hint values are non-negative integers and this constant, all other values will result, based on
89 * implementation preference, in the hint being completely ignored or IllegalArgumentException being thrown.
91 int UNKNOWN_SIZE = -1;
94 * Emits a leaf node event with supplied value.
97 * name of node as defined in schema, namespace and revision are
98 * derived from parent node.
100 * Value of leaf node.
101 * @throws IllegalArgumentException
102 * If emitted leaf node has invalid value in current context or
103 * was emitted multiple times.
104 * @throws IllegalStateException
105 * If node was emitted inside <code>map</code>,
106 * <code>choice</code> <code>unkeyed list</code> node.
107 * @throws IOException if an underlying IO error occurs
109 void leafNode(String localName, Object value) throws IOException;
112 * Emits a start of leaf set (leaf-list). Emits start of leaf set, during writing leaf set event, only
113 * {@link #leafSetEntryNode(Object)} calls are valid. Leaf set event is finished by calling {@link #endNode()}.
116 * name of node as defined in schema, namespace and revision are
117 * derived from parent node.
118 * @param childSizeHint
119 * Non-negative count of expected direct child nodes or
120 * {@link #UNKNOWN_SIZE} if count is unknown. This is only hint
121 * and should not fail writing of child events, if there are more
123 * @throws IllegalArgumentException
124 * If emitted leaf node is invalid in current context or was
125 * emitted multiple times.
126 * @throws IllegalStateException
127 * If node was emitted inside <code>map</code>,
128 * <code>choice</code> <code>unkeyed list</code> node.
129 * @throws IOException if an underlying IO error occurs
131 void startLeafSet(String localName, int childSizeHint) throws IOException;
134 * Emits a start of leaf set (leaf-list).
137 * Emits start of leaf set, during writing leaf set event, only
138 * {@link #leafSetEntryNode(Object)} calls are valid. Leaf set event is
139 * finished by calling {@link #endNode()}.
142 * name of node as defined in schema, namespace and revision are
143 * derived from parent node.
144 * @param childSizeHint
145 * Non-negative count of expected direct child nodes or
146 * {@link #UNKNOWN_SIZE} if count is unknown. This is only hint
147 * and should not fail writing of child events, if there are more
149 * @throws IllegalArgumentException
150 * If emitted leaf node is invalid in current context or was
151 * emitted multiple times.
152 * @throws IllegalStateException
153 * If node was emitted inside <code>map</code>,
154 * <code>choice</code> <code>unkeyed list</code> node.
155 * @throws IOException if an underlying IO error occurs
157 void startOrderedLeafSet(String localName, int childSizeHint) throws IOException;
160 * Emits a leaf set entry node.
163 * Value of leaf set entry node.
164 * @throws IllegalArgumentException
165 * If emitted leaf node has invalid value.
166 * @throws IllegalStateException
167 * If node was emitted outside <code>leaf set</code> node.
168 * @throws IOException if an underlying IO error occurs
170 void leafSetEntryNode(Object value) throws IOException;
173 * Emits start of new container. End of container event is emitted by invoking {@link #endNode()}.
176 * Valid sub-events are:
178 * <li>{@link #leafNode(String, Object)}</li>
179 * <li>{@link #startContainerNode(Class, int)}</li>
180 * <li>{@link #startChoiceNode(Class, int)}</li>
181 * <li>{@link #startLeafSet(String, int)}</li>
182 * <li>{@link #startMapNode(Class, int)}</li>
183 * <li>{@link #startUnkeyedList(Class, int)}</li>
184 * <li>{@link #startAugmentationNode(Class)}</li>
188 * name of node as defined in schema, namespace and revision are
189 * derived from parent node.
190 * @param childSizeHint
191 * Non-negative count of expected direct child nodes or
192 * {@link #UNKNOWN_SIZE} if count is unknown. This is only hint
193 * and should not fail writing of child events, if there are more
195 * @throws IllegalArgumentException
196 * If emitted node is invalid in current context or was emitted
198 * @throws IllegalStateException
199 * If node was emitted inside <code>map</code>,
200 * <code>choice</code> <code>unkeyed list</code> node.
201 * @throws IOException if an underlying IO error occurs
203 void startContainerNode(Class<? extends DataObject> container, int childSizeHint) throws IOException;
206 * Emits start of unkeyed list node event.
209 * End of unkeyed list event is emitted by invoking {@link #endNode()}.
210 * Valid subevents is only {@link #startUnkeyedListItem(int)}. All other
211 * methods will throw {@link IllegalArgumentException}.
214 * name of node as defined in schema, namespace and revision are
215 * derived from parent node.
216 * @param childSizeHint
217 * Non-negative count of expected direct child nodes or
218 * {@link #UNKNOWN_SIZE} if count is unknown. This is only hint
219 * and should not fail writing of child events, if there are more
221 * @throws IllegalArgumentException
222 * If emitted node is invalid in current context or was emitted
224 * @throws IllegalStateException
225 * If node was emitted inside <code>map</code>,
226 * <code>choice</code> <code>unkeyed list</code> node.
227 * @throws IOException if an underlying IO error occurs
229 void startUnkeyedList(Class<? extends DataObject> localName, int childSizeHint) throws IOException;
232 * Emits start of new unkeyed list item.
235 * Unkeyed list item event is finished by invoking {@link #endNode()}. Valid
238 * <li>{@link #leafNode(String, Object)}</li>
239 * <li>{@link #startContainerNode(Class, int)}</li>
240 * <li>{@link #startChoiceNode(Class, int)}</li>
241 * <li>{@link #startLeafSet(String, int)}</li>
242 * <li>{@link #startMapNode(Class, int)}</li>
243 * <li>{@link #startUnkeyedList(Class, int)}</li>
244 * <li>{@link #startAugmentationNode(Class)}</li>
247 * @param childSizeHint
248 * Non-negative count of expected direct child nodes or
249 * {@link #UNKNOWN_SIZE} if count is unknown. This is only hint
250 * and should not fail writing of child events, if there are more
252 * @throws IllegalStateException
253 * If node was emitted outside <code>unkeyed list</code> node.
254 * @throws IOException if an underlying IO error occurs
256 void startUnkeyedListItem(int childSizeHint) throws IOException;
259 * Emits start of unordered map node event.
262 * End of map node event is emitted by invoking {@link #endNode()}. Valid
263 * subevent is only {@link #startMapEntryNode(Identifier, int)}. All other methods will
264 * throw {@link IllegalArgumentException}.
266 * @param mapEntryType
267 * Class of list item, which has defined key.
268 * @param childSizeHint
269 * Non-negative count of expected direct child nodes or
270 * {@link #UNKNOWN_SIZE} if count is unknown. This is only hint
271 * and should not fail writing of child events, if there are more
273 * @throws IllegalArgumentException
274 * If emitted node is invalid in current context or was emitted
276 * @throws IllegalStateException
277 * If node was emitted inside <code>map</code>,
278 * <code>choice</code> <code>unkeyed list</code> node.
279 * @throws IOException if an underlying IO error occurs
281 <T extends DataObject & Identifiable<?>> void startMapNode(Class<T> mapEntryType, int childSizeHint)
285 * Emits start of ordered map node event.
288 * End of map node event is emitted by invoking {@link #endNode()}. Valid
289 * subevent is only {@link #startMapEntryNode(Identifier, int)}. All other methods will
290 * throw {@link IllegalArgumentException}.
292 * @param mapEntryType
293 * Class of list item, which has defined key.
294 * @param childSizeHint
295 * Non-negative count of expected direct child nodes or
296 * {@link #UNKNOWN_SIZE} if count is unknown. This is only hint
297 * and should not fail writing of child events, if there are more
299 * @throws IllegalArgumentException
300 * If emitted node is invalid in current context or was emitted
302 * @throws IllegalStateException
303 * If node was emitted inside <code>map</code>,
304 * <code>choice</code> <code>unkeyed list</code> node.
305 * @throws IOException if an underlying IO error occurs
307 <T extends DataObject & Identifiable<?>> void startOrderedMapNode(Class<T> mapEntryType, int childSizeHint)
311 * Emits start of map entry.
314 * End of map entry event is emitted by invoking {@link #endNode()}.
317 * Valid sub-events are:
319 * <li>{@link #leafNode(String, Object)}</li>
320 * <li>{@link #startContainerNode(Class, int)}</li>
321 * <li>{@link #startChoiceNode(Class, int)}</li>
322 * <li>{@link #startLeafSet(String, int)}</li>
323 * <li>{@link #startMapNode(Class, int)}</li>
324 * <li>{@link #startUnkeyedList(Class, int)}</li>
325 * <li>{@link #startAugmentationNode(Class)}</li>
329 * Key of map entry node
330 * @param childSizeHint
331 * Non-negative count of expected direct child nodes or
332 * {@link #UNKNOWN_SIZE} if count is unknown. This is only hint
333 * and should not fail writing of child events, if there are more
335 * @throws IllegalArgumentException
336 * If key contains incorrect value.
337 * @throws IllegalStateException
338 * If node was emitted outside <code>map entry</code> node.
339 * @throws IOException if an underlying IO error occurs
341 void startMapEntryNode(Identifier<?> keyValues, int childSizeHint) throws IOException;
344 * Emits start of choice node.
347 * Valid sub-event in {@link #startCase(Class, int)}, which selects case
348 * which should be written.
352 * @param childSizeHint
353 * Non-negative count of expected direct child nodes or
354 * {@link #UNKNOWN_SIZE} if count is unknown. This is only hint
355 * and should not fail writing of child events, if there are more
357 * @throws IllegalStateException
358 * If node was emitted inside <code>map</code>, <code>choice</code>,
359 * <code>unkeyed list</code> node.
360 * @throws IOException if an underlying IO error occurs
362 void startChoiceNode(Class<? extends DataContainer> choice, int childSizeHint) throws IOException;
365 * Starts a case node.
368 * Valid sub-events are:
370 * <li>{@link #leafNode(String, Object)}</li>
371 * <li>{@link #startContainerNode(Class, int)}</li>
372 * <li>{@link #startChoiceNode(Class, int)}</li>
373 * <li>{@link #startLeafSet(String, int)}</li>
374 * <li>{@link #startMapNode(Class, int)}</li>
375 * <li>{@link #startUnkeyedList(Class, int)}</li>
376 * <li>{@link #startAugmentationNode(Class)}</li>
379 * @param caze Case class
380 * @throws IOException if an underlying IO error occurs
382 void startCase(Class<? extends DataObject> caze, int childSizeHint) throws IOException;
385 * Emits start of augmentation node.
388 * End of augmentation event is emitted by invoking {@link #endNode()}.
391 * Valid sub-events are:
394 * <li>{@link #leafNode(String, Object)}</li>
395 * <li>{@link #startContainerNode(Class, int)}</li>
396 * <li>{@link #startChoiceNode(Class, int)}</li>
397 * <li>{@link #startLeafSet(String, int)}</li>
398 * <li>{@link #startMapNode(Class, int)}</li>
399 * <li>{@link #startUnkeyedList(Class, int)}</li>
403 * Note this is only method, which does not require childSizeHint, since
404 * maximum value is always size of <code>possibleChildren</code>.
406 * @param augmentationType augmentation class
407 * @throws IllegalArgumentException
408 * If augmentation is invalid in current context.
409 * @throws IOException if an underlying IO error occurs
411 void startAugmentationNode(Class<? extends Augmentation<?>> augmentationType) throws IOException;
414 * Emits anyxml node event.
416 * @param name node name
417 * @param value node value
418 * @throws IllegalStateException
419 * If node was emitted inside <code>map</code>,
420 * <code>choice</code> <code>unkeyed list</code> node.
421 * @throws IOException if an underlying IO error occurs
423 void anyxmlNode(String name, Object value) throws IOException;
426 * Emits end event for node.
428 * @throws IllegalStateException If there is no open node.
429 * @throws IOException if an underlying IO error occurs
431 void endNode() throws IOException;
434 void flush() throws IOException;
437 void close() throws IOException;