TypeScript / Advanced

    TypeScript zaawansowany

    Generics, conditional types, mapped types, template literal types, Stage 3 decorators i nowości TypeScript 5.x.

    Generics
    Reusable types
    Conditional
    Logika typów
    Decorators
    Metadane klas
    Type Guards
    Zawężanie typów

    6 zaawansowanych funkcji TypeScript

    Generics, conditional types, mapped types, template literals, decorators i type guards — każda funkcja otwiera nowe możliwości type-safe kodu.

    Generics

    Parametryzacja typów

    function identity(arg: T): T

    Reusable, type-safe collections i utilities

    Conditional Types

    Logika typów

    T extends U ? X : Y

    Utility types, type transformations

    Mapped Types

    Transformacja typów

    {[K in keyof T]: T[K]}

    Partial, Required, Readonly, custom transforms

    Template Literal Types

    String types

    type EventName = 'on${Capitalize}'

    API routes, event names, CSS properties

    Decorators (Stage 3)

    Metadata / AOP

    @Controller('users')

    NestJS, Angular, TypeORM, class-validator

    Type Guards + infer

    Narrowing / Inference

    value is string, infer R

    Runtime safety, conditional type inference

    Często zadawane pytania

    Generics w TypeScript — co to jest i jak używać?

    Generics: parametryzowane typy — jak szablony (templates) w C++ lub Java. Pozwalają pisać kod wielokrotnego użytku z zachowaniem type safety. Podstawowy generic: function identity(arg: T): T {return arg}. identity('hello') — TypeScript infers T = string. identity(42) — T = number. Generic z constraints: function getLength(arg: T): number. T extends {length: number} — T musi mieć property length. String, Array, itd. spełniają. Generic interface: interface Repository {findById(id: string): Promise. findAll(): Promise. create(entity: T): Promise}. Generic class: class Stack {private items: T[] = []. push(item: T): void. pop(): T | undefined}. Multiple generics: function merge(a: T, b: U): T & U. Conditional types z generics: type NonNullable = T extends null | undefined ? never : T. Mapped types: type Partial = {[P in keyof T]?: T[P]}. Required, Readonly, Pick, Omit. Utility types wbudowane: Partial, Required, Readonly, Record, Pick, Omit, Exclude, Extract, NonNullable, ReturnType, Parameters, InstanceType, Awaited. infer keyword: type ReturnType = T extends (...args: any) => infer R ? R : never. Variadic tuple types: type Concat = [...A, ...B]. Template literal types: type EventName = 'on${Capitalize}'. Distributive conditional types: T extends U — działa per union member.

    Conditional types, mapped types i advanced utility types?

    Conditional types: T extends U ? X : Y. Podstawowe: type IsString = T extends string ? true : false. Nested: type DeepReadonly = T extends object ? {readonly [K in keyof T]: DeepReadonly} : T. Distributive: type ToArray = T extends any ? T[] : never. ToArray = string[] | number[] (nie (string|number)[]). infer w conditional types: type UnwrapPromise = T extends Promise ? U : T. type FirstParam = T extends (first: infer F, ...rest: any[]) => any ? F : never. Mapped types: {[K in keyof T]: ...} — iteruj po kluczach. Optional: {[K in keyof T]?: T[K]}. Readonly: {readonly [K in keyof T]: T[K]}. Remapping z as: {[K in keyof T as K extends string ? Capitalize : K]: T[K]}. Filtered mapped: {[K in keyof T as T[K] extends string ? K : never]: T[K]}. Template literal types: type EventName = 'on${Capitalize}'. type CSSProperty = 'padding-${string}'. type i18nKeys = 'en' | 'pl'. type Translation = {[K in i18nKeys]: string}. Discriminated unions: type Shape = {kind: 'circle', radius: number} | {kind: 'rect', w: number, h: number}. Exhaustive check: default: const _: never = shape. TypeScript strict mode opcje: strictNullChecks (najważniejszy). noImplicitAny. strictFunctionTypes. strictPropertyInitialization. noImplicitReturns. exactOptionalPropertyTypes (v4.4). useUnknownInCatchVariables.

    Decorators w TypeScript — co to jest i kiedy używać?

    Decorators: metadata annotations dla klas, metod, właściwości i parametrów. Stage 3 TC39 (native JS decorators — TypeScript 5.0+). Legacy decorators: experimentalDecorators: true (Reflect.metadata). Używane przez: NestJS (wszystkie dekoratory). TypeORM / MikroORM (@Entity, @Column). class-transformer (@Type, @Expose). class-validator (@IsEmail, @MinLength). Angular (cały framework). Class decorator: @sealed function sealed(constructor: Function) {Object.seal(constructor). Object.seal(constructor.prototype)}. Method decorator: @deprecated (loguje deprecation warning). Property decorator: @observable — integrates z MobX. Parameter decorator: @Inject(TOKEN) — dependency injection. NestJS przykład: @Controller('users') — route prefix. @Get(':id') — HTTP method + path. @Injectable() — DI provider. @Module({imports, providers, controllers}) — module definition. class-validator + class-transformer: @IsEmail() email: string. @MinLength(8) password: string. validate(dto) — walidacja. plainToClass(CreateUserDto, body) — transform + validate. TypeScript 5.x nowe dekoratory (TC39 Stage 3): bez Reflect.metadata. context zamiast descriptor. Kompatybilne ze standardem JS. NestJS 10+ wspiera nowe dekoratory. Kiedy unikaj dekoratorów: prostsze projekty (overhead konfiguracji). Bun + Elysia (własny system). Bez NestJS/Angular — useReducer może być prostszy.

    Type guards, assertion functions i narrowing?

    Type narrowing: TypeScript zawęża typ na podstawie kontroli. typeof: if (typeof value === 'string') — TypeScript wie że value: string w bloku. instanceof: if (error instanceof CustomError) — value: CustomError. in operator: if ('email' in user) — user ma property email. Type guards (user-defined): function isString(value: unknown): value is string {return typeof value === 'string'}. isString(x) — po true, x jest typed jako string. Discriminated union narrowing: switch (shape.kind) {case 'circle': ...} — TypeScript wie jaki typ. Assertion functions: function assertIsString(value: unknown): asserts value is string {if (typeof value !== 'string') throw new Error(...)}. assertIsString(x) — po wywołaniu x jest string. never type: wyczerpujące sprawdzenie. default: const _: never = value — błąd jeśli nie wszystkie przypadki obsłużone. unknown vs any: unknown — bezpieczniejszy any. Musisz sprawdzić typ przed użyciem. any — wyłącza type checking. Unikaj any, używaj unknown. Satisfies operator (TS 4.9): const config = {...} satisfies Config. Walidacja bez zmiany inferowanego typu. as const: const colors = ['red', 'blue'] as const. Typ: readonly ['red', 'blue']. Literalne typy zamiast string[]. Template literal zamiast string enum. noUncheckedIndexedAccess: array[index] jest T | undefined (nie T). Bezpieczniejsze array access.

    TypeScript 5.x — co nowego i jak migrować z starszych wersji?

    TypeScript 5.0 (2023): Decorators Stage 3 (TC39). const type parameters. All enums jako union enums. --moduleResolution bundler. speedup (15-20%). TypeScript 5.1: Unrelated types for getters/setters. Undefined-returning functions. JSX transform. TypeScript 5.2: using declarations (Stage 3 Explicit Resource Management). Symbol.dispose, Symbol.asyncDispose. Automatyczne cleanup zasobów (connection, file, etc). TypeScript 5.3: Import attributes (JSON modules). Resolution customization flags. TypeScript 5.4: NoInfer utility type. Preserved narrowing in closures. TypeScript 5.5: Inferred type predicates (automatyczne type guards!). Regular Expression type checking. TypeScript 5.6: Iterator methods (filter, map, take na lazy sequences). Disallowed nullish and truthy checks. TypeScript 5.7: Path rewriting (node16 moduleResolution). Checks for never-initialized variables. Migracja: strict mode włącz stopniowo. tsconfig.json: 'strict': true. Napraw błędy jeden po drugim. ts-migrate — automatyczna migracja. allowJs: true + checkJs: false dla mixed projektu. skipLibCheck: true — pomiń sprawdzanie d.ts. Narzędzia TypeScript: ts-morph (TypeScript Compiler API). tsc --noEmit (tylko type check). ts-prune (nieużywane exports). knip (dead code). type-coverage (procent pokrycia typami).

    Czytaj dalej

    Powiązane artykuły

    Kontakt

    Skontaktuj się z nami

    Porozmawiajmy o Twoim projekcie. Bezpłatna wycena w ciągu 24 godzin.

    Wyślij zapytanie

    Bezpłatna wycena w 24h
    Bez zobowiązań
    Indywidualne podejście
    Ekspresowa realizacja

    Telefon

    +48 790 814 814

    Pon-Pt: 9:00 - 18:00

    Email

    adam@fotz.pl

    Odpowiadamy w ciągu 24h

    Adres

    Plac Wolności 16

    61-739 Poznań

    Godziny pracy

    Pon - Pt9:00 - 18:00
    Sob - NdzZamknięte

    Wolisz porozmawiać?

    Zadzwoń teraz i porozmawiaj z naszym specjalistą o Twoim projekcie.

    Zadzwoń teraz