View Javadoc
1   package io.atlassian.fugue.extensions.step;
2   
3   import java.util.Optional;
4   import java.util.function.Function;
5   import java.util.function.Predicate;
6   import java.util.function.Supplier;
7   
8   /**
9    * The first step of the {@link Optional} type.
10   * <p>
11   * This class is not intended to be contructed manually, and should only be used
12   * as part of a {@link Steps} chain, started by {@link Steps#begin(Optional)}
13   *
14   * @param <A> The type of the first defined value
15   * @see Steps for usage examples
16   * @see Optional
17   * @since 4.7.0
18   */
19  @SuppressWarnings("OptionalUsedAsFieldOrParameterType") public final class OptionalStep1<A> {
20  
21    private final Optional<A> optional1;
22  
23    OptionalStep1(Optional<A> optional1) {
24      this.optional1 = optional1;
25    }
26  
27    /**
28     * Apply the provided function with the previous Step results.
29     * <p>
30     * Internally this will perform a {@link Optional#flatMap(Function)} and the
31     * result will become the next step value.
32     *
33     * @param functor The functor to be applied as a flatMap with the previous
34     * step
35     * @param <B> The right hand side type of the next step result
36     * @return The next step class
37     */
38    public <B> OptionalStep2<A, B> then(Function<? super A, Optional<B>> functor) {
39      Optional<B> option2 = optional1.flatMap(functor);
40      return new OptionalStep2<>(optional1, option2);
41    }
42  
43    /**
44     * Apply the provided supplier with the previous Step results.
45     * <p>
46     * Internally this will perform a {@link Optional#flatMap(Function)} and the
47     * supplier will become the next step value.
48     * <p>
49     * This is different to {@link #then(Function)} in that the previous step
50     * results are not provided for the new step evaluation.
51     *
52     * @param supplier The supplier to provide the result of the flatMap with the
53     * previous step.
54     * @param <B> The type of the next step result
55     * @return The next step class
56     */
57    public <B> OptionalStep2<A, B> then(Supplier<Optional<B>> supplier) {
58      Optional<B> Optional = optional1.flatMap(value1 -> supplier.get());
59      return new OptionalStep2<>(optional1, Optional);
60    }
61  
62    /**
63     * Apply the provided predicate with the previous step results.
64     *
65     * @param predicate The check that must be satisfied by contained values
66     * @return This step class with either the same last step value, or changed to
67     * empty
68     */
69    public OptionalStep1<A> filter(Predicate<? super A> predicate) {
70      Optional<A> filterOptional1 = optional1.filter(predicate);
71      return new OptionalStep1<>(filterOptional1);
72    }
73  
74    /**
75     * Terminating step expression, that will provide the previous steps to this
76     * function and return the result as a <code>of</code>
77     *
78     * @param functor The yield function to map on previous values
79     * @param <Z> The type for the returned result
80     * @return An Optional containing this result or empty
81     */
82    public <Z> Optional<Z> yield(Function<? super A, Z> functor) {
83      return optional1.map(functor);
84    }
85  
86  }