You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

Result.java 6.1KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190
  1. /*
  2. * Copyright 2000-2016 Vaadin Ltd.
  3. *
  4. * Licensed under the Apache License, Version 2.0 (the "License"); you may not
  5. * use this file except in compliance with the License. You may obtain a copy of
  6. * the License at
  7. *
  8. * http://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 under
  14. * the License.
  15. */
  16. package com.vaadin.data;
  17. import java.io.Serializable;
  18. import java.util.Objects;
  19. import java.util.Optional;
  20. import com.vaadin.server.SerializableConsumer;
  21. import com.vaadin.server.SerializableFunction;
  22. import com.vaadin.server.SerializableSupplier;
  23. /**
  24. * Represents the result of an operation that might fail, such as type
  25. * conversion. A result may contain either a value, signifying a successful
  26. * operation, or an error message in case of a failure.
  27. * <p>
  28. * Result instances are created using the factory methods {@link #ok(R)} and
  29. * {@link #error(String)}, denoting success and failure respectively.
  30. * <p>
  31. * Unless otherwise specified, {@code Result} method arguments cannot be null.
  32. *
  33. * @param <R>
  34. * the result value type
  35. */
  36. public interface Result<R> extends Serializable {
  37. /**
  38. * Returns a successful result wrapping the given value.
  39. *
  40. * @param <R>
  41. * the result value type
  42. * @param value
  43. * the result value, can be null
  44. * @return a successful result
  45. */
  46. public static <R> Result<R> ok(R value) {
  47. return new SimpleResult<>(value, null);
  48. }
  49. /**
  50. * Returns a failure result wrapping the given error message.
  51. *
  52. * @param <R>
  53. * the result value type
  54. * @param message
  55. * the error message
  56. * @return a failure result
  57. */
  58. public static <R> Result<R> error(String message) {
  59. Objects.requireNonNull(message, "message cannot be null");
  60. return new SimpleResult<>(null, message);
  61. }
  62. /**
  63. * Returns a Result representing the result of invoking the given supplier.
  64. * If the supplier returns a value, returns a {@code Result.ok} of the
  65. * value; if an exception is thrown, returns the message in a
  66. * {@code Result.error}.
  67. *
  68. * @param <R>
  69. * the result value type
  70. * @param supplier
  71. * the supplier to run
  72. * @param onError
  73. * the function to provide the error message
  74. * @return the result of invoking the supplier
  75. */
  76. public static <R> Result<R> of(SerializableSupplier<R> supplier,
  77. SerializableFunction<Exception, String> onError) {
  78. Objects.requireNonNull(supplier, "supplier cannot be null");
  79. Objects.requireNonNull(onError, "onError cannot be null");
  80. try {
  81. return ok(supplier.get());
  82. } catch (Exception e) {
  83. return error(onError.apply(e));
  84. }
  85. }
  86. /**
  87. * If this Result has a value, returns a Result of applying the given
  88. * function to the value. Otherwise, returns a Result bearing the same error
  89. * as this one. Note that any exceptions thrown by the mapping function are
  90. * not wrapped but allowed to propagate.
  91. *
  92. * @param <S>
  93. * the type of the mapped value
  94. * @param mapper
  95. * the mapping function
  96. * @return the mapped result
  97. */
  98. public default <S> Result<S> map(SerializableFunction<R, S> mapper) {
  99. return flatMap(value -> ok(mapper.apply(value)));
  100. }
  101. /**
  102. * If this Result has a value, applies the given Result-returning function
  103. * to the value. Otherwise, returns a Result bearing the same error as this
  104. * one. Note that any exceptions thrown by the mapping function are not
  105. * wrapped but allowed to propagate.
  106. *
  107. * @param <S>
  108. * the type of the mapped value
  109. * @param mapper
  110. * the mapping function
  111. * @return the mapped result
  112. */
  113. public <S> Result<S> flatMap(SerializableFunction<R, Result<S>> mapper);
  114. /**
  115. * Invokes either the first callback or the second one, depending on whether
  116. * this Result denotes a success or a failure, respectively.
  117. *
  118. * @param ifOk
  119. * the function to call if success
  120. * @param ifError
  121. * the function to call if failure
  122. */
  123. public void handle(SerializableConsumer<R> ifOk,
  124. SerializableConsumer<String> ifError);
  125. /**
  126. * Applies the {@code consumer} if result is not an error.
  127. *
  128. * @param consumer
  129. * consumer to apply in case it's not an error
  130. */
  131. public default void ifOk(SerializableConsumer<R> consumer) {
  132. handle(consumer, error -> {
  133. });
  134. }
  135. /**
  136. * Applies the {@code consumer} if result is an error.
  137. *
  138. * @param consumer
  139. * consumer to apply in case it's an error
  140. */
  141. public default void ifError(SerializableConsumer<String> consumer) {
  142. handle(value -> {
  143. }, consumer);
  144. }
  145. /**
  146. * Checks if the result denotes an error.
  147. *
  148. * @return <code>true</code> if the result denotes an error,
  149. * <code>false</code> otherwise
  150. */
  151. public boolean isError();
  152. /**
  153. * Returns an Optional of the result message, or an empty Optional if none.
  154. *
  155. * @return the optional message
  156. */
  157. public Optional<String> getMessage();
  158. /**
  159. * Return the value, if the result denotes success, otherwise throw an
  160. * exception to be created by the provided supplier.
  161. *
  162. * @param <X>
  163. * Type of the exception to be thrown
  164. * @param exceptionProvider
  165. * The provider which will return the exception to be thrown
  166. * based on the given error message
  167. * @return the value
  168. * @throws X
  169. * if this result denotes an error
  170. */
  171. public <X extends Throwable> R getOrThrow(
  172. SerializableFunction<String, ? extends X> exceptionProvider)
  173. throws X;
  174. }