Сила <Т | ноль | undefined> тип параметра функции

В настоящее время мы применяем строгие проверки null в старой кодовой базе и сами создали помощника.

type Maybe<T> = T | null | undefined

Мы реализовали пару вспомогательных функций, они могут выглядеть так:

function isSafe<T>(val: Maybe<T>): val is T {
    // ...
}

Ссылка на игровую площадку

Работает как шарм, улучшение, которое я хотел бы, состоит в том, чтобы предотвратить передачу значений, не являющихся возможными, в качестве параметра, потому что с этим типом можно было бы вызвать isSafe('hi'), что не может быть null, что является случай для каждой переменной, которая не заключена в Maybe.

Предотвращение подобных вызовов устранило бы недоразумения, поскольку я ожидаю, что переменные, которые передаются в isSafe, будут Maybe.

К сожалению, я не нашел способа добиться этого, поскольку T | null | undefined допускает любой из этих типов, а не только комбинацию этих трех.

Есть ли способ добиться ошибки типа при передаче значения, отличного от Maybe, в функцию? Бонусные баллы были бы, если бы это также позволяло T | null и T | undefined, поскольку мы решили, что будем обрабатывать оба значения одинаково.

Зод: сила проверки и преобразования данных
Зод: сила проверки и преобразования данных
Сегодня я хочу познакомить вас с библиотекой Zod и раскрыть некоторые ее особенности, например, возможности валидации и трансформации данных, а также...
Как заставить Remix работать с Mantine и Cloudflare Pages/Workers
Как заставить Remix работать с Mantine и Cloudflare Pages/Workers
Мне нравится библиотека Mantine Component , но заставить ее работать без проблем с Remix бывает непросто.
Угловой продивер
Угловой продивер
Оригинал этой статьи на турецком языке. ChatGPT используется только для перевода на английский язык.
TypeScript против JavaScript
TypeScript против JavaScript
TypeScript vs JavaScript - в чем различия и какой из них выбрать?
Синхронизация localStorage в масштабах всего приложения с помощью пользовательского реактивного хука useLocalStorage
Синхронизация localStorage в масштабах всего приложения с помощью пользовательского реактивного хука useLocalStorage
Не все нужно хранить на стороне сервера. Иногда все, что вам нужно, это постоянное хранилище на стороне клиента для хранения уникальных для клиента...
Что такое ленивая загрузка в Angular и как ее применять
Что такое ленивая загрузка в Angular и как ее применять
Ленивая загрузка - это техника, используемая в Angular для повышения производительности приложения путем загрузки модулей только тогда, когда они...
1
0
464
1
Перейти к ответу Данный вопрос помечен как решенный

Ответы 1

Ответ принят как подходящий

Вот решение, которое немного уродливо, но соответствует вашим критериям:

type DefinitelyMaybe<T> = null extends T ? T : undefined extends T ? T : never

function isSafe<T>(val: DefinitelyMaybe<T>): val is NonNullable<typeof val> {
  return val !== null && val !== undefined;
}

// Argument of type 'string' is not assignable to parameter of type 'never'.
isSafe('test');

// OK
isSafe('test' as string | undefined);

По сути, DefinitelyMaybe<T> — это то же самое, что и T, если null, undefined или оба могут быть назначены T. В противном случае это never, что приводит к ошибке типа на сайте вызова, потому что аргумент не может быть назначен ему.

Ссылка на игровую площадку

Хорошо, если в одном месте некрасиво, а в других красивее :) Но действительно умное решение, спасибо

Marv 22.12.2020 09:44

Другие вопросы по теме