View Javadoc
1   /*
2    * Copyright 2022 The Netty Project
3    *
4    * The Netty Project licenses this file to you under the Apache License,
5    * version 2.0 (the "License"); you may not use this file except in compliance
6    * with the License. You may obtain a copy of the License at:
7    *
8    *   https://www.apache.org/licenses/LICENSE-2.0
9    *
10   * Unless required by applicable law or agreed to in writing, software
11   * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
12   * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
13   * License for the specific language governing permissions and limitations
14   * under the License.
15   */
16  package io.netty5.buffer.api;
17  
18  import io.netty5.buffer.api.ComponentIterator.Next;
19  import io.netty5.util.SafeCloseable;
20  
21  /**
22   * A facade for iterating the readable or writable components of a {@link Buffer}.
23   *
24   * <strong>Note:</strong> the {@linkplain ComponentIterator iterator object} must be
25   * {@linkplain ComponentIterator#close() closed} after use.
26   * The easiest way to ensure this, is to use a try-with-resources clause.
27   * <p>
28   * The typical code pattern for using this API looks like the following:
29   * <pre>{@code
30   *      try (var iteration = buffer.forEachReadable()) {
31   *          for (var c = iteration.first(); c != null; c = c.next()) {
32   *              ByteBuffer componentBuffer = c.readableBuffer();
33   *              // ...
34   *          }
35   *      }
36   * }</pre>
37   * Note the use of the {@code var} keyword for local variables, which are required for correctly expressing the
38   * generic types used in the iteration.
39   * Following this code pattern will ensure that the components, and their parent buffer, will be correctly
40   * life-cycled.
41   *
42   * @param <T> A type that implements {@link Next}, and either {@link ReadableComponent} or {@link WritableComponent}.
43   * @see Buffer#forEachReadable()
44   * @see Buffer#forEachWritable()
45   */
46  public interface ComponentIterator<T extends Next> extends SafeCloseable {
47      /**
48       * Get the first component of the iteration, or {@code null} if there are no components.
49       * <p>
50       * The object returned will implement both {@link Next}, and one of the {@link ReadableComponent} or
51       * {@link WritableComponent} interfaces.
52       *
53       * @return The first component of the iteration, or {@code null} if there are no components.
54       */
55      T first();
56  
57      /**
58       * This interface exposes external iteration on components.
59       */
60      interface Next {
61          /**
62           * Get the next component of the iteration, or {@code null} if there are no more components.
63           * <p>
64           * The returned object, if any, will be of the same type as this object, and would typically be assigned to the
65           * same variable.
66           * <p>
67           * Iteration is only valid while the {@link ComponentIterator} is open.
68           * Calling this method after the associated component iterator has been
69           * {@linkplain ComponentIterator#close() closed} may result in undefined behaviour.
70           *
71           * @return The next component in the iteration, or {@code null} if there are no more components.
72           * @param <N> A type that implements {@link Next}, and one of the {@link ReadableComponent} or
73           * {@link WritableComponent} interfaces.
74           */
75          <N extends Next> N next();
76      }
77  }