turborepo로 모노레포 패키지 관리하기

jh·2025년 1월 20일

디자인 시스템

목록 보기
13/14

기존에는 pnpm workspace만 사용하고, turborepo의 필요성을 못 느껴서 사용하지 않았는데 이제는 turborepo 없이는 모노레포 개발할 수가 없다..

현재 상황

  • 그냥 나름 복잡?한 상황이 있다는 정도만 이해하시면 됩니다

현재 총 4개의 내부 패키지가 있는데
cli, ui, docs, animation

이중에서 docs

  • 외부(aws)에 업로드되어야 함
  • 다른 내부 패키지에 의존성을 가지고 있음, 다른 패키지들이 빌드된 이후에 빌드되어야 함

나머지 패키지들은

  • npm에 배포되어야 하는 것과(cli,animation), 단순 내부 사용 패키지로 나뉨

  • cli 패키지에서는 ui의 컴포넌트들을 파싱해서, docs의 public 폴더에 컴포넌트들의 메타데이터를 json으로 저장해야 하고, 이 역할을 하는 함수가 있음 -> 이를 docs가 빌드되기 전에 실행해야 함
    (특수한 실행순서가 지켜져야 한다는 의미)

  • npm에 배포되어야 하는것들 중에서도 다른 내부 패키지에 의존성을 가지고 있는 것들이 있음

  • npm 배포의 경우 changeset을 통해 버전 관리 및 npm 배포

결론적으로, 해결해야 하는 점은

  • 빌드 순서가 지켜져야 한다
    예를 들어 a(npm 배포)에서 b 패키지를 의존(사용)하고 있는데, a가 먼저 빌드되어 버리면 b의 변경사항이 제대로 반영되지 않기 때문에 이를 다운로드 받아 사용하는 입장에서는 정상적인 작동이 되지 않는다

나의 경우 총 4개밖에 되지 않기 때문에 package.json scripts 필드를 통해서 어떻게든 순서를 관리할 수 있지만, 관리해야 할 패키지가 늘어남에 따라 따로 스크립트 파일 등을 작성해서 빌드 순서를 관리해줘야 한다

  • 경우에 따라 빌드가 필요없는 패키지도 존재한다
    예를 들어 위에 나왔던 a 패키지만 변경되어서, npm에 배포하려고 한다면 a와 그 의존성 패키지들만 빌드해서 배포하면 된다
    (물론 모든 패키지를 다 빌드해도 상관은 없다)
    이를 위해서는 어떤 패키지가 변경이 되었는지 찾고, 이 의존성을 또 파악해서 순서를 정하고..등등의 과정을 거쳐야 한다

turborepo로 해결하기

  1. turborepo running task in the right order
//turbo.json
{
    "build": {
      "outputs": ["dist/**", ".next/**", "out/**"],
      "dependsOn": ["^build"]
    },
    "docs#build": {
      "dependsOn": ["cli#build"]
    },
}

turborepo를 통해서, 간단한 옵션만 제공하여 이러한 task의 순서를 제어할 수 있다

  • build 과정만 예시로 들었습니다

여기서 dependsOn 이라는 건 말그대로 ~에 의존하고 있다는 뜻이다
첫번째 설정인 "dependsOn": ["^build"] 를 통해서 각 패키지들의 의존성을 분석해서 순서를 알맞게 설정해준다
예를 들어 a 패키지의 dependencies에 b가 있으면, b -> a 순서로 진행된다

두번째는 특수한 설정으로 docsbuild 스크립트는 clibuild 스크립트 이후에 진행하라는 뜻이다.

    "build": "tsup && node ./src/build-script.ts",

cli의 빌드 스크립트를 이런식으로 조정하여 docs의 빌드 전에 필요한 작업들을 모두 처리할 수 있다

결론

  • 설정을 통해 전반적인 task 순서 관리, 특수한 상황의 task 순서 관리가 가능하다
  1. remote caching 사용하기
    문서

변경된 패키지만 찾아서 빌드하는 건 매우 복잡하기 때문에, 그런걸 따지지 말고 전체를 다 빌드하지만 캐싱을 통해 변경점이 없는 부분은 건너뛰는 것이다

github actions에서는 remote caching을 사용하면 가능하다

  • hobby버전(무료버전)도 사용 가능하다

  • 사용법이 매우 간단하다

  • 물론 완벽한 해결책은 아니다. 일단 캐시를 비교하는 것도 비용이 소모되는 일이고, 가끔 캐시를 remote에서 못 불러온다거나 분명 변경사항이 없는데도 cache miss가 나는 등의 일이 있어서 잘 체크하면서 사용해야 할것 같다

이 밖에 잘 사용하고 있는 기능

  • Just-In-Time package
    ts를 사용하는 다른 패키지를 참조할 경우 빌드 후에 참조해야 하는데, 이게 굉장히 생산성을 떨어뜨린다.
    하지만 turborepo가 제공하는 JIT package를 통해 바로 참조할 수 있다
    관련 포스트
  • @turbo/gen
    plop같이 코드 generator 기능이다(내부적으로 plop을 사용하는 걸로 알고있다)
    간단한 파일 generate부터 특정 패키지 템플릿을 만들어놓고 복사하는 것도 가능하다

0개의 댓글