Skip to content
This repository has been archived by the owner on Jan 6, 2025. It is now read-only.

Commit

Permalink
add never handling to struct API, closes #242 (#245)
Browse files Browse the repository at this point in the history
  • Loading branch information
gcanti authored Apr 18, 2023
1 parent 0ce16a9 commit 6a7d7be
Show file tree
Hide file tree
Showing 5 changed files with 57 additions and 7 deletions.
5 changes: 5 additions & 0 deletions .changeset/nasty-vans-tan.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
---
"@effect/schema": patch
---

add `never` handling to struct API
34 changes: 30 additions & 4 deletions docs/modules/Schema.ts.md
Original file line number Diff line number Diff line change
Expand Up @@ -40,6 +40,8 @@ Added in v1.0.0
- [nonNegativeBigint](#nonnegativebigint)
- [nonPositiveBigint](#nonpositivebigint)
- [positiveBigint](#positivebigint)
- [boolean](#boolean)
- [not](#not)
- [combinators](#combinators)
- [annotations](#annotations-1)
- [array](#array-1)
Expand Down Expand Up @@ -139,7 +141,7 @@ Added in v1.0.0
- [primitives](#primitives)
- [any](#any)
- [bigint](#bigint-1)
- [boolean](#boolean)
- [boolean](#boolean-1)
- [never](#never)
- [null](#null)
- [number](#number-1)
Expand Down Expand Up @@ -519,6 +521,20 @@ export declare const positiveBigint: <A extends bigint>(
Added in v1.0.0
# boolean
## not
Negates a boolean value
**Signature**
```ts
export declare const not: <I>(self: Schema<I, boolean>) => Schema<I, boolean>
```
Added in v1.0.0
# combinators
## annotations
Expand Down Expand Up @@ -930,7 +946,13 @@ Added in v1.0.0

```ts
export declare const struct: <
Fields extends Record<string | number | symbol, Schema<any, any> | PropertySignature<any, any, boolean>>
Fields extends Record<
string | number | symbol,
| Schema<any, any>
| Schema<never, never>
| PropertySignature<any, any, boolean>
| PropertySignature<never, never, boolean>
>
>(
fields: Fields
) => Schema<
Expand Down Expand Up @@ -2299,7 +2321,11 @@ Added in v1.0.0

```ts
export type OptionalKeys<Fields, ToIsOptional extends boolean> = {
[K in keyof Fields]: Fields[K] extends PropertySignature<any, any, ToIsOptional> ? K : never
[K in keyof Fields]: Fields[K] extends
| PropertySignature<any, any, ToIsOptional>
| PropertySignature<never, never, ToIsOptional>
? K
: never
}[keyof Fields]
```

Expand All @@ -2310,7 +2336,7 @@ Added in v1.0.0
**Signature**

```ts
export interface PropertySignature<From, To = From, ToIsOptional extends boolean = true> {
export interface PropertySignature<From, To = From, ToIsOptional extends boolean = boolean> {
readonly From: (_: From) => From
readonly To: (_: To) => To
readonly ToIsOptional: ToIsOptional
Expand Down
6 changes: 6 additions & 0 deletions dtslint/ts4.9/Schema.ts
Original file line number Diff line number Diff line change
Expand Up @@ -234,6 +234,9 @@ export type MyModelFrom = S.From<typeof MyModel>
// $ExpectType { readonly a: string; readonly b: number; }
export type MyModelTo = S.To<typeof MyModel>

// $ExpectType Schema<{ readonly a: never; }, { readonly a: never; }>
S.struct({ a: S.never })

// ---------------------------------------------
// optional
// ---------------------------------------------
Expand All @@ -248,6 +251,9 @@ S.struct({ a: S.string, b: S.number, c: S.optional(NumberFromString) });
// $ExpectType Schema<{ readonly a?: string; }, { readonly a?: string; }>
S.struct({ a: pipe(S.string, S.optional) })

// $ExpectType Schema<{ readonly a?: never; }, { readonly a?: never; }>
S.struct({ a: S.optional(S.never) })

// ---------------------------------------------
// optional.withDefault
// ---------------------------------------------
Expand Down
13 changes: 10 additions & 3 deletions src/Schema.ts
Original file line number Diff line number Diff line change
Expand Up @@ -461,7 +461,7 @@ export type PropertySignatureId = typeof PropertySignatureId
/**
* @since 1.0.0
*/
export interface PropertySignature<From, To = From, ToIsOptional extends boolean = true> {
export interface PropertySignature<From, To = From, ToIsOptional extends boolean = boolean> {
readonly From: (_: From) => From
readonly To: (_: To) => To
readonly ToIsOptional: ToIsOptional
Expand Down Expand Up @@ -504,7 +504,8 @@ optional.withDefault = dual(2, (schema, value) => _optional(schema, { to: "defau
* @since 1.0.0
*/
export type OptionalKeys<Fields, ToIsOptional extends boolean> = {
[K in keyof Fields]: Fields[K] extends PropertySignature<any, any, ToIsOptional> ? K
[K in keyof Fields]: Fields[K] extends
PropertySignature<any, any, ToIsOptional> | PropertySignature<never, never, ToIsOptional> ? K
: never
}[keyof Fields]

Expand All @@ -513,7 +514,13 @@ export type OptionalKeys<Fields, ToIsOptional extends boolean> = {
* @since 1.0.0
*/
export const struct = <
Fields extends Record<PropertyKey, Schema<any> | PropertySignature<any, any, boolean>>
Fields extends Record<
PropertyKey,
| Schema<any>
| Schema<never>
| PropertySignature<any>
| PropertySignature<never>
>
>(
fields: Fields
): Schema<
Expand Down
6 changes: 6 additions & 0 deletions test/optional.ts
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,12 @@ describe.concurrent("optional", () => {
await Util.expectEncodeSuccess(schema, { a: O.none() }, {})
})

it("never", async () => {
const schema = S.struct({ a: S.optional(S.never), b: S.number })
await Util.expectParseSuccess(schema, { b: 1 })
await Util.expectParseFailure(schema, { a: "a", b: 1 }, `/a Expected never, actual "a"`)
})

it("all", async () => {
const schema = S.struct({
a: S.boolean,
Expand Down

0 comments on commit 6a7d7be

Please sign in to comment.