Skip to content

Conversation

@JamieB-gu
Copy link
Contributor

@JamieB-gu JamieB-gu commented Dec 8, 2025

A simple version of this type was introduced to see if we would find it useful (#10361). We've started to use it more widely, so this change adds some ergonomic improvements to make it easier to work with. There are three parts to this, as detailed below.

This keeps the convenience functions ok and error for constructing Result, but it's possible these are no longer necessary as the Ok and Err classes could be constructed directly. An update to this may be considered in a future change.

Note: "Hide whitespace" may be useful for reviewing this change.

kind Becomes ok

The kind property, which was previously of type 'ok' | 'error', has been replaced with an ok property of type boolean. This makes code that checks this property less verbose, and it's similar to the ok property found on the Response type in the Fetch API1. I believe this was originally suggested by @mxdvl

Before:

if (result.kind === 'ok') {
    console.log(result.value);
} else {
    console.error(result.error);
}

After:

if (result.ok) {
    console.log(result.value);
} else {
    console.error(result.error);
}

New Methods

map

Before:

if (result.kind === 'error') {
    return result;
}

return doSomething(result.value);

After:

return result.map(doSomething);

flatMap

Before:

if (result.kind === 'error') {
    return result;
}

return doSomethingThatCouldFail(result.value);

After:

return result.flatMap(doSomethingThatCouldFail);

mapError

Before:

if (result.kind === 'error') {
    return error(`New error message: ${result.error}`);
}

After:

return result.mapError(err => `New error message: ${err}`);

okOrThrow And errorOrThrow Become Methods

Previously these were functions, but they have now become methods alongside the others described above. They've also been renamed to better suit the method approach.

Before:

const value = okOrThrow(doSomething(data), 'Expected this to succeed');
const error = errorOrThrow(
    doSomething(data),
    'Expected this to fail',
);

After:

const value = doSomething(data).getOrThrow('Expected this to succeed');
const error = doSomething(data).getErrorOrThrow(
    'Expected this to fail',
);

Footnotes

  1. https://developer.mozilla.org/en-US/docs/Web/API/Response/ok

A simple version of this type was introduced to see if we would find it
useful. We've started to use it more widely, so this change adds some
ergonomic improvements to make it easier to work with. There are three
parts to this, as detailed below.

This keeps the convenience functions `ok` and `error` for constructing
`Result`, but it's possible these are no longer necessary as the `Ok`
and `Err` classes could be constructed directly. An update to this may
be considered in a future change.

`kind` Becomes `ok`
-------------------

The `kind` property, which was previously of type `'ok' | 'error'`,
has been replaced with an `ok` property of type `boolean`. This makes
code that checks this property less verbose, and it's similar to the
`ok` property found on the `Response` type in the Fetch API.

**Before:**

```ts
if (result.kind === 'ok') {
    console.log(result.value);
} else {
    console.error(result.error);
}
```

**After:**

```ts
if (result.ok) {
    console.log(result.value);
} else {
    console.error(result.error);
}
```

New Methods
-----------

1. `map`

**Before:**

```ts
if (result.kind === 'error') {
    return result;
}

return doSomething(result.value);
```

**After:**

```ts
return result.map(doSomething);
```

2. flatMap

**Before:**

```ts
if (result.kind === 'error') {
    return result;
}

return doSomethingThatCouldFail(result.value);
```

**After:**

```ts
return result.flatMap(doSomethingThatCouldFail);
```

3. `mapError`

**Before:**

```ts
if (result.kind === 'error') {
    return error(`New error message: ${result.error}`);
}
```

**After:**

```ts
return result.mapError(err => `New error message: ${err}`);
```

`okOrThrow` And `errorOrThrow` Become Methods
---------------------------------------------

Previously these were functions, but they have now become methods
alongside the others described above. They've also been renamed to
better suit the method approach.

**Before:**

```ts
const value = okOrThrow(doSomething(data), 'Expected this to succeed');
const error = errorOrThrow(
    doSomething(data),
    'Expected this to fail',
);
```

**After:**

```ts
const value = doSomething(data).getOrThrow('Expected this to succeed');
const error = doSomething(data).getErrorOrThrow(
    'Expected this to fail',
);
```
@JamieB-gu JamieB-gu added this to the Health milestone Dec 8, 2025
@JamieB-gu JamieB-gu self-assigned this Dec 8, 2025
@JamieB-gu JamieB-gu added the maintenance Departmental tracking: maintenance work, not a fix or a feature label Dec 8, 2025
@mxdvl
Copy link
Contributor

mxdvl commented Dec 8, 2025

I’m definitely partial to an ok, but I first witnessed it in “Error Handling with Result Type” by Jake Trent

@github-actions
Copy link

github-actions bot commented Dec 10, 2025

@JamieB-gu JamieB-gu marked this pull request as ready for review December 10, 2025 12:59
@JamieB-gu JamieB-gu requested a review from a team as a code owner December 10, 2025 12:59
@github-actions
Copy link

Hello 👋! When you're ready to run Chromatic, please apply the run_chromatic label to this PR.

You will need to reapply the label each time you want to run Chromatic.

Click here to see the Chromatic project.

@JamieB-gu JamieB-gu added the run_chromatic Runs chromatic when label is applied label Dec 10, 2025
@github-actions github-actions bot removed the run_chromatic Runs chromatic when label is applied label Dec 10, 2025
Copy link
Contributor

@ioannakok ioannakok left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Great work! 🥳

@AshCorr
Copy link
Member

AshCorr commented Dec 12, 2025

Rare @mxdvl sighting 💜

I like the new syntax, it feels a lot more like the syntax I'm used to with Result types in other languages.

@JamieB-gu JamieB-gu merged commit e243c2f into main Dec 15, 2025
26 checks passed
@JamieB-gu JamieB-gu deleted the refactor-result-type branch December 15, 2025 11:22
@gu-prout
Copy link

gu-prout bot commented Dec 15, 2025

Seen on PROD (merged by @JamieB-gu 10 minutes and 8 seconds ago) Please check your changes!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

maintenance Departmental tracking: maintenance work, not a fix or a feature Seen-on-PROD

Projects

None yet

Development

Successfully merging this pull request may close these issues.

5 participants