-
Notifications
You must be signed in to change notification settings - Fork 451
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Accumulate
DSL for Raise
(open for discussion)
#2881
Conversation
By the way, I tried to make this work without the intermediate |
Kover Report
|
Isn't this just |
Interesting 🤔 This looks very similar to |
else -> raise(EmptyValue.unbox(e)) | ||
): List<B> = | ||
accumulateErrors(semigroup) { | ||
map { accumulate { block(it) } }.map { it.value } |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Unfortunate, this introduces a second iteration over the Iterable
.
DRAFT? |
I'm closing this in favor of #2880. I think this is just too complicated as an API to expose. |
When/if we have union types, this idea could be great since, it seems, the "idiomatic" way to represent errors would be returning such a union. Smart casts could even make this nicer, with a simple |
@kyay10 this was proposed by @Intex32, but it's currently not working properly with contracts yet 😞 I.e. Union would be amazing to have, and would allow us to spice up a lot of the APIs. I think we should really revisit this when we have those features. |
This creates a "sub-DSL" within
Raise
to express scopes in which errors should be accumulated, instead of the regular fail-first approach. The idea is that insideaccumulateErrors
you "protect" each potentially-failing computation withaccumulate
.The problem here is potential data dependencies. To fight these, the result of
accumulate
is not directlyA
, butAccumulate.Value<A>
, a "box" which remembers whether the computation it comes from failed or not. If at some point we try to unwrap a failed computation, that means we cannot proceed further with accumulation, and we just return whatever errors we had found.As a comparison with other FP abstractions,
Accumulate
implements selective functors, because it's allowed to choose how to continue based on whether a computation failed or not, but not based on the data you obtained (that requires monads).