Skip to content
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

feat: Add a function that combines multiple results and returns an object #610

Open
wants to merge 1 commit into
base: master
Choose a base branch
from

Conversation

Karibash
Copy link

Hi @supermacro ,

First of all, I would like to thank you for creating such a wonderful library. I have been using neverthrow in a production environment for about a year and I am very satisfied with it.

In this PR, I am adding a function that combines multiple Results, passed as an object, into a single Result. This can be very useful for functional programming as shown below:

const createTaskId: (id: string) => Result<TaskId, Error>;
const createTaskContent: (content: string) => Result<TaskContent, Error>;

const task = Result.struct({
  id: createTaskId('id'),
  content: createTaskContent('content'),
});

To do the same thing with the current API, you need to use map as shown below. This requires you to remember which data is in which position in the array, which is not very convenient.

const createTaskId: (id: string) => Result<TaskId, Error>;
const createTaskContent: (content: string) => Result<TaskContent, Error>;

const values = Result.combineWithAllErrors([
  createTaskId('id'),
  createTaskContent('content'),
]);

const task = values.map(([id, content]) => ({ id, content }));

Copy link

changeset-bot bot commented Nov 12, 2024

🦋 Changeset detected

Latest commit: 595c76a

The changes in this PR will be included in the next version bump.

This PR includes changesets to release 1 package
Name Type
neverthrow Minor

Not sure what this means? Click here to learn what changesets are.

Click here if you're a maintainer who wants to add another changeset to this PR

@macksal
Copy link
Contributor

macksal commented Nov 26, 2024

Faced this exact pattern before, and using ResultAsync.combine is very awkward. +1 for the feature.

My one question is, does this really need to be a different method, or would it be possible to just overload combine/combineWithAllErrors to accept either an array or an object and return the appropriate type?

I am thinking of the combineLatest function in rxjs which has that exact overload. Pass an array of observables, get an observable of arrays. Pass an object of observables, get an observable of objects.

We could have similarly (for Result.combine):

  • pass an array of results, get a result of array
  • pass an object of results, get a result of object

overloads can be messy, but I'm more favourable of them in library code where the user is more likely to see these two cases as equivalent, and it avoids the need for them to remember any difference in behaviour between the two if they are truly analogous.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants