Frontend/TypeScript

Typescript 간단정리

findmypiece 2021. 9. 24. 15:44
728x90

1. Typescript는 코드 작성시 변수, 함수, 클래스 등에 타입을 지정할 수 있고 전용 컴파일러가 일반 javascript 문법으로 컴파일하는 과정에서 타입을 체크한다. 만약 지정된 타입 외의 값을 대입하려 한다면 컴파일러가 경고메시지를 출력하는데 이로 인해 타입안정성이 보장되고 자연스레 생산성도 향상된다.

 

2. 변수 선언시 타입을 지정할 수 있다.

let var_number: number;
let var_string: string;
let var_boolean: boolean;
let var_enum: 1 | 2 | 3 = 1; //타입 외에 값을 제한할 수도 있다.

let var_union: number | string; // 여러개의 타입을 지정할 수도 있다. 이를 union 타입이라고 부른다.
var_union = 'string';
var_union = 1;

let var_any: any; // 모든 타입을 소화할 수 있는 any를 지정할수도 있다.
var_any = "string";
var_any = 1;
var_any = true;

let numbers: number[] = [1, 2, 3];
let messages: string[] = ['hello', 'world'];

여기에서 특이한 것은 union 타입이라는 명칭이다. 위와 같이 정의하면 var_union 변수에는 number  또는 string 타입을 허용하갰다는 것이고 이는 타입을 우리가 흔히 알고 있는 or 조건으로 정의한 것이다.

 

여러개의 타입을 합쳐서 정의했다는 점에서 union(결합) 이라는 표현을 썼다고 이해하면 되는데 Intersection 타입을 마주하면 뭔가 이상하다는 점을 느낄 수 있을 것이다.

 

Intersection 은 밑에서 설명할 커스텀 타입을 합쳐주는 것으로 A타입의 변수와 B타입의 변수가 모두 결합된 새로운 타입을 생성할 때 사용한다. 오히려 Intersection 타입 union 이라는 명칭을 썼어야 하는게 아닌가 하는 생각이 든다.

 

3. 함수 선언시에도 파라미터나 리턴타입의 타입을 지정할 수 있다.

//함수선언문
function sum(x: number, y: number): number {
  return x + y;
}

//함수표현식
const sum = function sum(a: number, b: number): number {
  return a + b;
};

//화살표 함수
const sum = (x: number, y: number): number => {
  return x + y;
}

 

4. 선언하는 타입은 기본타입 외에 직접 생성한 커스텀 타입을 사용할 수도 있는데 이러한 타입은 type, interface 키워드로 생성할 수 있다.

interface

interface Person {
  name: string;
  age?: number; // key 값에 ?를 추가하면 타입 생성시 해당 값을 선택적으로 할당할 수 있다.
}

interface Developer extends Person { //extends 키워드를 통해 상속을 사용할 수 있다.
  skills: string[];
}

const person_nonAge: Person = {
  name: '김사람'
};

const person: Person = {
  name: '김사람',
  age: 20
};

const expert: Developer = {
  name: '김개발',
  skills: ['javascript', 'react']
};

const people: Person[] = [person_nonAge, person, expert];

type

type Person {
  name: string;
  age?: number; // key 값에 ?를 추가하면 타입 생성시 해당 값을 선택적으로 할당할 수 있다.
}

// 참고: https://www.typescriptlang.org/docs/handbook/advanced-types.html#intersection-types
type Developer = Person & { //interface 의 extends와 다르게 합성을 지원한다.
  skills: string[];
};

const person_nonAge: Person = {
  name: '김사람'
};


const person: Person = {
  name: '김사람',
  age: 20
};

const expert: Developer = {
  name: '김개발',
  skills: ['javascript', 'react']
};

const people: Person[] = [person_nonAge, person, expert];

type People = Person[];
const people: People = [person, expert];

interface, type 키워드의 사용법이 비슷해보이는데 커스텀 타입을 선언할 때 대체 무엇을 사용해야 할까?

 

일단 interface 는 java에서 사용되는 그것과 비슷한데 extends, implements 키워드를 통해서 타입을 확장할 수 있고 선언병합(declaration merging) 이라는 기능 덕분에 여러번 선언하면 이후 선언된 것으로 재정의 되는 것이 아니라 컴파일 시점에 자동으로  병합된다.

 

type 은 엄밀히 따지고 보면 타입을 선언하는 것이 아니라 별칭을 선언하는 것이다. 이에 타입과 관련된 에러가 발생했을 시 컴파일러는 type으로 선언된 명칭을 보여주지 않고 실제 타입을 보여준다. interface는 실제로 타입이 생성되는 것이기 때문에 타입 에러 발생시 interface 명칭으로 알려준다.

 

 

별칭 선언 역할을 하기 때문에 interface와 달리 여러번 선언할 경우 이후에 선언된 것으로 재정의 된다. 이를 이용해서 기본타입을 다른 명칭으로 사용되게 할 수도 있다.(예: type Name = string)

 

type 은 & 키워드를 통해 interface 의 선언병합과 비슷한 기능을 제공하고 | 키워드를 통해 type만의 union 기능을 제공하기도 하지만 어디까지나 별칭을 선언하는 것이지 타입 선언이라고 보기엔 조금 어색하다.

 

이런 이유로 공식문서에서도 기본적으로 interface 사용을 권장하고 기본타입에 새로운 이름을 붙이거나 union 으로 동적타입 선언이 필요한 경우에만 type을 사용하라고 하고 있다.

 

5. 타입선언시 제네릭을 지원한다. 이는 Java의 제네릭과 비슷하다. 제네릭을 사용하면 제네릭은 동적으로 타입을 확정할 수 있으며 이렇게 확정된 타입이 일관되게 사용될 수 있다.

function merge<A, B>(a: A, b: B): A & B {
  return {
    ...a,
    ...b
  };
}

const merged = merge({ foo: 1 }, { bar: 1 });

만약 merge 함수에서 제네릭을 사용하지 않는다면 파라미터의 타입을 any로 지정해야 하고 리턴되는 타입 역시 any 로 지정할 수 밖에 없다. 파라미터로 받은 값을 그대로 리턴하는데 그 타입이 유지되지 않기 때문에 결과값에 대한 타입도 유추할 수 없게 된다.

 

5. node.js?

자바스크립트로 html 을 조작할 수 있다. 이를 위해서는 자바스크립트를 해석할 수 있어야 하고 브라우저에는 자바스크립트를 해석할 수 있는 엔진이 포함되어 있다.

그러다가 구글의 크롬브라우저 개발자들이 자바스크립트 해석엔진인 V8 을 만들었는데 성능이 너무 뛰어나 해당 엔진만 분리해서 node.js 라는 별도 프로그램을 출시하게 된다.

 

node.js 는 쉽게 말해 자바스크립트 런타임이다. 이를 통해 브라우저가 아닌 환경에서도 자바스크립트가 활용될 수 있게 되었다. 특정서버에서 java 를 사용하기 위해 jdk 설치가 필요하듯 자바스크립트를 사용하기 위해 node를 설치한다고 이해하면 편할거 같다.

가장 중요한 것은 내장 http 서버 라이브러리를 포함하고 있어 별도 데몬(Apache, Nginx 등) 없이도 웹서버로서의 역할을 수행할 수 있다는 것이다. 때문에 웹서버 개발에 많이 사용된다.

sveltekit 을 사용하기 위해서는 기본적으로 로컬에 node가 설치되어 있어야 하는데 이를 통해 로컬이 웹서버 역할을 수행할 수 있는 상태가 되고 npm run dev 명령어를 통해 웹서버를 띄울수 있게 된다.

 

6. typescript?

typescript 는 javascript 의 확장언어이다. 하지만 node 를 포함한 자바스크립트 해석엔진은 javascript 만 해석할 수 있기 때문에  typescript 는 결국 javascript로 컴파일 되어야 한다. typescript 패키지를 설치하면 해당 컴파일러가 기본적으로 내장되어 있다. 개발은 typescript 로 하지만 실제로 운영서버에 배포될 때는 javascript 로 컴파일된 내용이 배포된다.

하지만 개발환경에서는 일일히 컴파일해서 보기에는 번거로우니 이 과정없이 typescript 코드를 직접 실행시킬 수 있는 ts-node 라는 node.js 에 대한 REPL(Read-Eval-Print-Loop) 역할을 한다. typescript  코드에 대해 수동으로 컴파일할 필요없이 그 결과물을 바로 확인할 수 있다.

 

 

https://react.vlpt.us/using-typescript/01-practice.html
https://joonsungum.github.io/post/2019-02-25-typescript-interface-and-type-alias/
https://ui.toast.com/weekly-pick/ko_20210521
https://velog.io/@zeros0623/TypeScript-%EA%B3%A0%EA%B8%89-%ED%83%80%EC%9E%85
https://joshua1988.github.io/ts/usage/declaration.html
https://hanamon.kr/nodejs-개념-이해하기/

 

728x90

'Frontend > TypeScript' 카테고리의 다른 글

타입스크립트에서 비구조화 할당문법 사용하기  (0) 2021.10.21
typescript .d.ts 파일  (0) 2021.10.08