-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
1 parent
61da576
commit 94e33b3
Showing
2 changed files
with
87 additions
and
0 deletions.
There are no files selected for viewing
38 changes: 38 additions & 0 deletions
38
contents/_draft/2023-09-15-type-safe-builder-pattern-on-typescript.md
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,38 @@ | ||
--- | ||
title: Type-Safe Builder Pattern on TypeScript | ||
--- | ||
|
||
Listen from TypeScript Meetup | ||
|
||
```typescript | ||
class Inventory<Items extends Record<string, unknown> = {}> { | ||
|
||
items: Items = {} as Items; | ||
|
||
add<NewItem extends Record<string, unknown>>(value: NewItem) { | ||
this.items = { | ||
...value as unknown as Items | ||
} | ||
return this as Inventory<Items & NewItem>; | ||
} | ||
} | ||
|
||
const inventory = new Inventory() | ||
.add({ | ||
hello: 'world', | ||
}).add({ | ||
typescript: 5.1, | ||
numbers: [23, '123'] | ||
}); | ||
|
||
console.log(inventory.items.typescript) | ||
|
||
|
||
type A = typeof inventory.items; | ||
// ^? type A = { | ||
// hello: string; | ||
// } & { | ||
// typescript: number; | ||
// numbers: (string | number)[]; | ||
// } | ||
``` |
49 changes: 49 additions & 0 deletions
49
contents/posts/2023-09-15-typecheck-schemas-on-existing-types.md
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,49 @@ | ||
--- | ||
title: วิธีตรวจสอบให้ Zod schemas ตรงกับ Type ที่ประกาศไว้อยู่แล้ว | ||
uuid: e6btvc1 | ||
tags: | ||
- TypeScript | ||
- Data Validation | ||
- Zod | ||
--- | ||
|
||
วันนี้เราจะมาพูดถึงวิธีการในการตรวจสอบความเข้ากันได้ระหว่าง [Zod](https://github.com/colinhacks/zod) Schema และ TypeScript อย่างสะดวกและรวดเร็ว ไอเดียดีๆ นี้มาจาก [@colinhacks](https://github.com/colinhacks) ซึ่งเป็นคนสร้าง Zod โดยการใช้ Zod และอยากแบ่งปันให้ทุกคน | ||
|
||
โดยปกติแล้ว เราบ่งบอกประเภทของข้อมูลด้วย TypeScript เพื่อให้รู้ว่าข้อมูลที่เราใช้เป็นแบบไหน แต่ถ้าเราใช้ Zod Schema เพื่อทำการตรวจสอบข้อมูล มีวิธีหนึ่งที่จะทำให้เราสามารถตรวจสอบความเข้ากันได้ระหว่าง Zod Schema และ TypeScript ได้อย่างมีประสิทธิภาพ และเรียบง่าย นั่นคือการใช้ฟังก์ชัน `schemaForType` ตามตัวอย่างด้านล่าง: | ||
|
||
```typescript | ||
import { z } from 'zod'; | ||
|
||
type Dog = { | ||
name: string | ||
neutered: boolean | ||
} | ||
|
||
|
||
function schemaForType<TSchema>() { | ||
return <TZodSchema extends z.ZodType<TSchema, any, any>>(arg: TZodSchema) => arg; | ||
} | ||
|
||
// ใช้งานได้ประมาณนี้: | ||
const dog = schemaForType<Dog>()( | ||
z.object({ | ||
// name: z.string(), | ||
neutered: z.boolean(), | ||
}) | ||
// ❌ Property 'name' is missing in type | ||
// '{ neutered: boolean; }' but required in type 'Dog' | ||
); | ||
``` | ||
|
||
การทำงานของฟังก์ชันซ้อนกันนี้อาจดูแปลก ๆ แต่มันเป็นจำเป็น เพราะมีระดับการใช้ Generic สองระดับ | ||
|
||
1. TypeScript ที่ต้องการ `TSchema` | ||
2. Schema ที่สร้างขึ้นอย่างอัตโนมัติ `TZodSchema` ซึ่งถูก จำกัดโดย `extends z.ZodType<TSchema, any, any>` | ||
|
||
อย่างไรก็ตาม คุณไม่ต้องกังวลเกี่ยวกับ `any` ที่เหลือสองตัวนั้น เนื่องจากเรากำลังใช้ `TSchema` เป็น Type hint โดยตรง นั่นหมายความว่าเราต้องใช้ฟังก์ชันเพิ่มเติมที่ให้เราสามารถตรวจสอบประเภทของ `TZodSchema` ได้ ซึ่งนี้เป็นเพราะ TypeScript จำเป็นต้องระบุพารามิเตอร์ Generic ทั้งหมดโดยชัดเจนหรือให้มันถูก Infer ทั้งหมด ไม่สามารถเลือกหรือผสมผสานได้ แม้ว่ามีข้อเสนอรองเรื่องนี้อยู่ [microsoft/TypeScript#26242](https://github.com/microsoft/TypeScript/issues/26242) ในเดียวนี้ | ||
|
||
ดังนั้น เราสามารตรวจสอบให้ Zod schemas ตรงกับ Type ที่ประกาศไว้อยู่แล้ว คุณสามารถใช้ฟังก์ชัน `schemaForType` เพื่อรักษาความ Consistency ในโปรเจคของคุณอีกด้วย! ขอบคุณที่ติดตามบทความนี้ครับและขอให้สนุกกับการเขียนโปรแกรมนะจ๊ะ | ||
|
||
## Ref | ||
- [colinhacks/zod Issuse#372](https://github.com/colinhacks/zod/issues/372#issuecomment-826380330) | ||
- ใช้ ChatGPT ช่วยเรียบเรียงด้วย |