mirror of
https://github.com/corda/corda.git
synced 2024-12-21 22:07:55 +00:00
Minor: move ErrorOr into the core module and tweak its API a bit. Add a Path div operator.
This commit is contained in:
parent
d8d639f192
commit
34ee44b532
@ -1,40 +0,0 @@
|
||||
package com.r3corda.client.mock
|
||||
|
||||
class ErrorOr<out A> private constructor(
|
||||
val value: A?,
|
||||
val error: Exception?
|
||||
) {
|
||||
constructor(value: A): this(value, null)
|
||||
constructor(error: Exception): this(null, error)
|
||||
|
||||
fun <T> match(onValue: (A) -> T, onError: (Exception) -> T): T {
|
||||
if (value != null) {
|
||||
return onValue(value)
|
||||
} else {
|
||||
return onError(error!!)
|
||||
}
|
||||
}
|
||||
|
||||
fun getValueOrThrow(): A {
|
||||
if (value != null) {
|
||||
return value
|
||||
} else {
|
||||
throw error!!
|
||||
}
|
||||
}
|
||||
|
||||
// Functor
|
||||
fun <B> map(function: (A) -> B): ErrorOr<B> {
|
||||
return ErrorOr(value?.let(function), error)
|
||||
}
|
||||
|
||||
// Applicative
|
||||
fun <B, C> combine(other: ErrorOr<B>, function: (A, B) -> C): ErrorOr<C> {
|
||||
return ErrorOr(value?.let { a -> other.value?.let { b -> function(a, b) } }, error ?: other.error)
|
||||
}
|
||||
|
||||
// Monad
|
||||
fun <B> bind(function: (A) -> ErrorOr<B>): ErrorOr<B> {
|
||||
return value?.let(function) ?: ErrorOr<B>(error!!)
|
||||
}
|
||||
}
|
@ -1,5 +1,7 @@
|
||||
package com.r3corda.client.mock
|
||||
|
||||
import com.r3corda.client.mock.Generator.Companion.choice
|
||||
import com.r3corda.core.ErrorOr
|
||||
import java.util.*
|
||||
|
||||
/**
|
||||
@ -54,7 +56,7 @@ class Generator<out A>(val generate: (Random) -> ErrorOr<A>) {
|
||||
companion object {
|
||||
fun <A> pure(value: A) = Generator { ErrorOr(value) }
|
||||
fun <A> impure(valueClosure: () -> A) = Generator { ErrorOr(valueClosure()) }
|
||||
fun <A> fail(error: Exception) = Generator<A> { ErrorOr(error) }
|
||||
fun <A> fail(error: Exception) = Generator<A> { ErrorOr.of(error) }
|
||||
|
||||
// Alternative
|
||||
fun <A> choice(generators: List<Generator<A>>) = intRange(0, generators.size - 1).bind { generators[it] }
|
||||
@ -85,10 +87,11 @@ class Generator<out A>(val generate: (Random) -> ErrorOr<A>) {
|
||||
val result = mutableListOf<A>()
|
||||
for (generator in generators) {
|
||||
val element = generator.generate(it)
|
||||
if (element.value != null) {
|
||||
result.add(element.value)
|
||||
val v = element.value
|
||||
if (v != null) {
|
||||
result.add(v)
|
||||
} else {
|
||||
return@Generator ErrorOr(element.error!!)
|
||||
return@Generator ErrorOr.of(element.error!!)
|
||||
}
|
||||
}
|
||||
ErrorOr(result)
|
||||
@ -99,11 +102,12 @@ class Generator<out A>(val generate: (Random) -> ErrorOr<A>) {
|
||||
fun <A> Generator.Companion.oneOf(list: List<A>) = intRange(0, list.size - 1).map { list[it] }
|
||||
|
||||
fun <A> Generator<A>.generateOrFail(random: Random, numberOfTries: Int = 1): A {
|
||||
var error: Exception? = null
|
||||
var error: Throwable? = null
|
||||
for (i in 0 .. numberOfTries - 1) {
|
||||
val result = generate(random)
|
||||
if (result.value != null) {
|
||||
return result.value
|
||||
val v = result.value
|
||||
if (v != null) {
|
||||
return v
|
||||
} else {
|
||||
error = result.error
|
||||
}
|
||||
@ -146,8 +150,9 @@ fun <A> Generator.Companion.replicatePoisson(meanSize: Double, generator: Genera
|
||||
ErrorOr(Unit)
|
||||
}
|
||||
}
|
||||
if (errorOr.error != null) {
|
||||
return@Generator ErrorOr(errorOr.error)
|
||||
val e = errorOr.error
|
||||
if (e != null) {
|
||||
return@Generator ErrorOr.of(e)
|
||||
}
|
||||
}
|
||||
ErrorOr(result)
|
||||
|
@ -219,3 +219,44 @@ fun extractZipFile(zipPath: Path, toPath: Path) {
|
||||
// TODO: Generic csv printing utility for clases.
|
||||
|
||||
val Throwable.rootCause: Throwable get() = Throwables.getRootCause(this)
|
||||
|
||||
/** Allows you to write code like: Paths.get("someDir") / "subdir" / "filename" but using the Paths API to avoid platform separator problems. */
|
||||
operator fun Path.div(other: String): Path = resolve(other)
|
||||
|
||||
/** Representation of an operation that may have thrown an error. */
|
||||
data class ErrorOr<out A> private constructor(val value: A?, val error: Throwable?) {
|
||||
constructor(value: A) : this(value, null)
|
||||
|
||||
companion object {
|
||||
/** Runs the given lambda and wraps the result. */
|
||||
inline fun <T> catch(body: () -> T): ErrorOr<T> = try { ErrorOr(body()) } catch (t: Throwable) { ErrorOr.of(t) }
|
||||
fun of(t: Throwable) = ErrorOr(null, t)
|
||||
}
|
||||
|
||||
fun <T> match(onValue: (A) -> T, onError: (Throwable) -> T): T {
|
||||
if (value != null) {
|
||||
return onValue(value)
|
||||
} else {
|
||||
return onError(error!!)
|
||||
}
|
||||
}
|
||||
|
||||
fun getOrThrow(): A {
|
||||
if (value != null) {
|
||||
return value
|
||||
} else {
|
||||
throw error!!
|
||||
}
|
||||
}
|
||||
|
||||
// Functor
|
||||
fun <B> map(function: (A) -> B) = ErrorOr(value?.let(function), error)
|
||||
|
||||
// Applicative
|
||||
fun <B, C> combine(other: ErrorOr<B>, function: (A, B) -> C): ErrorOr<C> {
|
||||
return ErrorOr(value?.let { a -> other.value?.let { b -> function(a, b) } }, error ?: other.error)
|
||||
}
|
||||
|
||||
// Monad
|
||||
fun <B> bind(function: (A) -> ErrorOr<B>) = value?.let(function) ?: ErrorOr.of(error!!)
|
||||
}
|
Loading…
Reference in New Issue
Block a user