카테고리 없음

라이브러리는 어떻게 구성되어 있을까

Ahyeon, Jung 2024. 6. 9. 17:43

일단 무슨 이유든 라이브러리를 열게 되면, 어떻게 구성되는건지 이해가 안가서 보통 특정 메서드를 잡고 타고 들어가면서 해당 메서드를 이해했다. 하지만 그건 라이브러리의 극히 일부이기 때문에, 연결고리를 파악하기 어려운 지점도 있고 패키지 모듈로 들어가버리면 쉽게 길을 잃어버린다. 처음에야 라이브러리를 열어본다는 만족감으로 한 두개 메서드 이해하고 나가면 그만이지만, 점점 극히 일부만 알고 있다는 느낌이 생기거나 라이브러리를 만들고 싶은데 어떻게 해야할지 방법을 못찾게 된다.


 

일단은 pakcage 폴더안으로 진입해야한다. 또한 라이브러리 packag.json에서 바벨을 이용해 여러가지 의존성을 가지고 있음을 알 수 있다.

 

하나의 npm 패키지 안에 여러 구성 요소가 들어있다. 이 구성 요소들이 모듈 시스템을 통해 필요한 부분만 가져와서 사용하는 방식으로 보인다.

모듈화된 하나의 패키지

JavaScript의 모듈 시스템 덕분에 패키지가 여러 개 있는 것처럼 보인다. 큰 소프트웨어 시스템을 작은, 독립적인 모듈로 나누어 개발하는 모듈화를 활용하여, 각 모듈이 특정 기능을 수행하며, 다른 모듈들과 결합하여 전체 시스템을 구성한다. 모듈별로 코드가 분리되어 있어 특정 기능에 문제가 생기면 해당 모듈만 수정하면 되기 때문에 유지보수성이 좋아지고, 새로운 기능 추가를 할 때 기존 모듈을 수정하는 것이 아니라 새로운 모듈을 추가하면 되기 때문에 확장성이 좋아진다. 또한 이를 통해 개발 속도가 향상되며 코드를 재사용할 수 있는 이점이 있다.

모듈화의 주요 원칙

  • 단일 책임의 원칙: 각 모듈은 하나의 기능 또는 책임만 가진다. 이를 통해 모듈의 복잡성을 줄이고, 변경이 필요한 경우 해당 모듈만 수정할 수 있다.
  • 정보 은닉: 모듈 내부의 구현 세부사항은 숨기고, 필요한 인터페이스만 외부에 공개한다. 이를 통해 모듈 간의 결합도를 낮추고, 독립적으로 개발할 수 있다.
  • 명확한 인터페이스: 모듈 간의 상호작용은 명확한 인터페이스를 통해 이루어져야 한다. 이를 통해 모듈 간의 의존성을 줄이고, 모듈 교체가 용이해진다.
  • 재사용성: 모듈은 재사용 가능하도록 설계 되어야 한다. 이를 통해 코드 중복을 줄이고, 개발 시간을 단축할 수 있다.

왜 react-router-dom은 react 패키지의 구성 요소가 아닐까

이렇게 많은 구성 요소로 한 패키지가 구성되어 있는데, 왜 react-router-dom은 react 패키지 안에 들어가 있지 않은걸까 하는 궁금증이 들었다. 결론적으로 말하자면 라우팅을 하지 않는 페이지를 만들 수도 있기 때문에, 패키지를 분리함으로써 책임을 분리하기 위함이다. react 패키지는 사용자 인터페이스 구축에 중점을 두고 있으며, React-router-dom 패키지는 라우팅 기능에 중점을 두고 있다. 이 두 개의 책임을 분리함으로써 개발자는 필요한 기능만 선택하여 사용할 수 있으며, 독립적인 업데이트와 유연성을 유지할 수 있다. 즉, 모듈화된 소프트웨어 개발을 위함이다.

  • 책임의 분리: React는 사용자 인터페이스를 구축하는 데 중점을 둔 라이브러리임으로, 라우팅과 상태 관리 등의 기능을 포함하지는 않는다.
  • 유연성: 라우팅 기능을 별도로 독립시켜 필요한 애플리케이션에만 추가할 수 있다.
  • 독립적인 업데이트: 각각의 라이브러리가 자신의 릴리스 사이클을 가지고 빠르고 독립적인 개선이 가능하다. 

packages/react

import React from 'react;

 

index.js 파일을 보면 package/react/src/ReactClient.js에서 여러 React API를 가져오는 방식의 베럴 파일이다. 

 

create-react-app

보통 npx create-react-app을 통해 리엑트 프로젝트를 쉽게 세팅할 수 있기 때문에 react의 package.json의 scrips에 있을 줄 알았다. 하지만 막상 찾아보니 없었다. package 안으로 들어가서 찾아보다가 생각해보니, 사용자 인터페이스를 구축하는 역할도 아니고, 생각해보면 npx create-react-app 이라는게 패키지를 처음에 한번 설치한다는 뜻이니 다른 패키지로 독립되어 있음을 이해할 수 있었다.

 

GitHub - facebook/create-react-app: Set up a modern web app by running one command.

Set up a modern web app by running one command. Contribute to facebook/create-react-app development by creating an account on GitHub.

github.com

이외에도 facebook에서는 react-native, react-strict-dom, react-native-website, prop-types, react-router, react-devtools 등을 따로 npm package로 배포하고 있었다.

패키지 배포하기

npm 패키지를 방학 때 한번 만들어볼 생각이라 찾아봤는데, 찾아볼수록 그냥 웹 페이지조차도 npm 패키지로 배포할 수 있었다. 일반적으로 버전 관리, 문서화, 테스트를 거쳐서 그냥 npm 패키지로 올려놓을 수 있는 것이다. 즉, 모든 npm package가 라이브러리인 것은 아니었다. npm에 배포되는 패키지에는 다양한 유형이 존재한다.

  • 라이브러리: 재사용 가능한 코드 모음. 다른 프로젝트에서 쉽게 가져다 사용할 수 있도록 작성. ex. react
  • CLI 도구: 명령 줄에서 실행되는 프로그램을 제공 ex. create-react-app, eslint, webpack, babel-cli등
  • 애플리케이션: 완전히 동작하는 애플리케이션
  • 설정 및 구성 파일 ex. Babel 프리셋, ESLint 구성 파일
  • 템플릿 및 보일러플레이트

라이브러리와 프레임워크

라이브러리는 특정 기능이나 작업을 수행하기 위해 사용되는 코드의 집합이다. 라이브러리를 사용할 때, 개발자가 선택하여 기능을 호출하는 도구적 특성을 가진다. 프레임워크는 애플리케이션 개발의 뼈대를 제공하며, 전체적인 구조와 흐름을 제어한다. 즉 프레임워크가 규칙과 패턴을 정의하고 개발자는 이를 따르는 방식이다.

리액트의 경우, 최소한의 UI 라이브러리로, 필요한 기능을 독립적인 라이브러리(react-router-dom, recoil 등)를 통해 확장하는 방식이다. vue의 경우 애플리케이션 개발에 필요한 대부분의 기능을 자체적으로 포함하거나 공식 플러그인을 통해 제공하는 프레임워크이다.

모노레포

다시 패키지 분석으로 돌아와서, react 내부를 들여다보면 여러가지 패키지로 구성되는 것을 확인할 수 있다. 이러한 방식으로 여러 패키지(프로젝트)를 하나의 레포지토리에서 관리하는 방식을 모노레포라고 칭한다. 모노레포의 경우 단일 버전 관리를 통해 코드와 개발 환경의 일관성을 유지하기 쉽고, 코드 공유와 재사용, 의존성 관리가 쉬워진다. 또한 모든 프로젝트를 함께 빌드하고 테스트할 수 있어 전체적인 통합 테스트와 빌드 자동화를 쉽게 설정할 수 있다. 또한 단일 저장소에서 여러 프로젝트를 관리하고, 공통된 의존성이나 도구를 공유하는 것이기 때문에, 하나의 웹 사이트에서 일부 페이지는 React로, 다른 일부 페이지는 Vue로 구성된 웹 프로젝트도 모노레포로 구성할 수 있다.

마이크로 프론트엔드

마이크로 프론트엔드는 프론트엔드 애플리케이션을 여러 개의 독립된 작은 애플리케이션으로 나누어 개발하고 배포하는 아키텍처 스타일이다. 이를 통해 대규모 프론트엔드 애플리케이션을 유연하게 관리할 수 있다. 즉 각각의 마이크로 프론트엔드를 하나의 저장소에서 모노레포로 관리할 수 있다. 즉 각각의 페이지를 하나의 프로젝트로 만들어서 하나의 도메인 아래서 합치면 마이크로 프론트엔드이고, 그걸 하나의 저장소에서 관리하면 모노레포식으로 관리하는 것이다.


결론: 그렇군!