pnpm Workspace๋กœ Monorepo ๋งŒ๋“ค๊ธฐ

14644 ๋‹จ์–ด lernaturborepomonorepopnpm

์ถ”์ƒ์ ์ธ



ํ˜„์žฌ ๋‹ค์–‘ํ•œ ๋„๊ตฌ๋“ค์ด monorepo ๊ฐœ๋…์„ ์ง€์›ํ•˜๊ณ  ์žˆ์Šต๋‹ˆ๋‹ค. ๊ธฐ๋ณธ ํŒจํ‚ค์ง€ ๋ ˆ๋ฒจ์—์„œ ์ง€์›yarn berry , pnpm workspace ์ด๋‚˜ ๊ด€๋ จ ๋„๊ตฌ๋“คNx , ์ตœ๊ทผ์— Nx ์— ์ธ์ˆ˜๋˜์–ด ์ƒˆ๋กœ์šด ๋ถ„๋Ÿ‰์„ ํ•ด์ œํ•œ lerna , Vercel ์˜ turborepo ๋“ฑ์˜ ๋„๊ตฌ๋“ค์ด ๊ทธ ์˜ˆ์ด๋‹ค.
์ด๋ฒˆ ์ถœํŒ์—์„œ ๊ต๋ฆฌ ๋‚ด์šฉ์€ ์ด์ค‘์—์„œ ๊ฐ€์žฅ ์‰ฝ๊ณ  ๊ฐ„๋‹จํ•˜๊ฒŒ monorepo ๊ฐœ๋…์„ ๋‹ฌ์„ฑํ•  ์ˆ˜ ์žˆ๋Š”pnpm workspace ์„ ์‚ฌ์šฉํ•˜๋Š” ๋ฐฉ๋ฒ•์ด๋‹ค.

์ฐธ๊ณ  ๋งํฌ: https://monorepo.tools/

์ „์ œ ์กฐ๊ฑด



pnpm ์„ค์น˜๊ฐ€ ํ•„์š”ํ•˜๋‹ค.


๋‹จ๋ง๊ธฐ


npm i -g pnpm


์‹œ์ž‘ํ•˜๊ธฐ



ํ”„๋กœ์ ํŠธ ํด๋”๋ฅผ ๊ตฌ์„ฑํ•˜๋Š” monorepo ํ”„๋กœ์ ํŠธ๋ฅผ ์ƒ์„ฑํ•ฉ๋‹ˆ๋‹ค.


๋‹จ๋ง๊ธฐ


pnpm init


pnpm-workspace.yaml ํŒŒ์ผ์„ ์ƒ์„ฑํ•˜๊ณ  ๊ทผ์ ‘ํ•˜๊ฒŒ ์ž…๋ ฅ


pnpm-workspace.yaml


packages:
  - 'packages/*'


package.json ์— ๋‹ค์Œ๊ณผ ํ•จ๊ป˜ ์ž…๋ ฅํ•˜์„ธ์š”.
pnpm์˜ ๋ฒ„์ „์€ ์ตœ์‹  ๋ฒ„์ „์œผ๋กœ ์š”์ฒญํ•˜๋ฉด ๋ฉ๋‹ˆ๋‹ค.
(2022/08/08 ๊ธฐ์ค€ 7.9.0)


ํŒจํ‚ค์ง€.json


{
  "name": "@soom/root", 
  "private": true,
  "scripts": {
    "preinstall": "pnpm dlx only-allow pnpm"
  },
  "workspaces": ["packages/*"],
  "engines": {
    "node": ">=16.14.2", 
    "pnpm": ">=7.9.0" 
  },
  "packageManager": "pnpm@7.9.0", 
  "devDependencies": {
    "pnpm": "^7.9.0"
  }
}


package.json ๊ธฐ๋ฐ˜์œผ๋กœ ์„ค์น˜


๋‹จ๋ง๊ธฐ


pnpm install


packages ํด๋”๋ฅผ ๋งŒ๋“ค๊ธฐ common , app ํด๋”๋ฅผ ์ƒ์„ฑ
๊ตฌ์กฐ๋Š” ๋‹ค์Œ๊ณผ ๊ฐ™๋‹ค.

.
โ”œโ”€โ”€ packages/
โ”‚   โ”œโ”€โ”€ app
โ”‚   โ””โ”€โ”€ common
โ”œโ”€โ”€ package.json
โ”œโ”€โ”€ pnpm-lock.yaml
โ””โ”€โ”€ pnpm-workspace.yaml


common , app ๊ฐ๊ฐ์˜ ํด๋”์—์„œ ํ”„๋กœ์ ํŠธ๋ฅผ ์ƒ์„ฑํ•ฉ๋‹ˆ๋‹ค.
์„œ๋Š” vite๋ฅผ ์‚ฌ์šฉํ•˜์—ฌ ํ”„๋กœ์ ํŠธ ์ƒ์„ฑ
react-ts ํ˜•์‹์„ ์ด์šฉํ•˜์˜€๋‹ค.


๋‹จ๋ง๊ธฐ


pnpm create vite

โœ” Select a framework: โ€บ react
โœ” Select a variant: โ€บ react-ts

๊ฐ ํด๋”์—์„œ ํ”„๋กœ์ ํŠธ๊ฐ€ ์ž‘๋™ํ•˜๋Š”์ง€ ํ™•์ธ


์‹œ์‚ฌ


common ํ”„๋กœ์ ํŠธ์— ๊ฐ„๋‹จํ•œ ๋ฒ„ํŠผ์„ ์ƒ์„ฑ


ํŒจํ‚ค์ง€/common/src/components/Button.tsx


import type { FC, PropsWithChildren } from 'react';

interface Props extends PropsWithChildren {
    textColor: string;
}

const Button: FC<Props> = (props) => {
    return <button style={{ color: props.textColor }}>{props.children}</button>;
};

export default Button;


main.tsx , package.json ์„ ๋‹ค์Œ๊ณผ ํ•จ๊ป˜ ์ˆ˜์ •


ํŒจํ‚ค์ง€/common/src/main.tsx


import Button from './components/Button';

export { Button };


ํŒจํ‚ค์ง€/๊ณตํ†ต/package.json


{
    "name": "@soom/common",
    "private": true,
    "version": "0.0.0",
    "type": "module",
    "main": "./src/main.tsx",
...
}


app ํด๋”๋กœ ์ด๋™ package.json ์— ๋‹ค์Œ๊ณผ ๊ฐ™์ด ์ˆ˜์ •ํ•˜๊ณ  pnpm install ์„ ํ†ตํ•ด ์„ค์น˜ํ•œ๋‹ค.
์—ฌ๊ธฐ@soom/common ํŒจํ‚ค์ง€๋Š”common ํด๋”์˜ ํ”„๋กœ์ ํŠธ ์ด๋ฆ„์ด๋‹ค.


ํŒจํ‚ค์ง€/์•ฑ/package.json


{
    "name": "@soom/app",
...
    "dependencies": {
        "@soom/common": "^0.0.0",
        "react": "^18.2.0",
        "react-dom": "^18.2.0"
    },
...
}


๋‹จ๋ง๊ธฐ


pnpm install

dependencies:
+ @soom/common 0.0.0 <- ../common


App.tsx์—์„œ ์„ค์น˜ํ•œ @soom/common ํŒจํ‚ค์ง€์—์„œ ๋ฒ„ํŠผ์„ ๋ถˆ๋Ÿฌ์˜ต๋‹ˆ๋‹ค.props ๋„ ์ž˜ ์š”์ƒˆ๋Š” ๊ฑธ ํ™•์ธํ•  ์ˆ˜ ์žˆ๋‹ค.


ํŒจํ‚ค์ง€/์•ฑ/src/App.tsx


import './App.css';
import { Button } from '@soom/common';

function App() {
    return (
        <div className='App'>
            <h1>Monorepo Button?</h1>

            <Button textColor='red'>Hello Common Package Button</Button>
        </div>
    );
}

export default App;


์‹œ์‚ฌ



โž• ์ถ”์‹ 

๋งˆ์ง€๋ง‰์œผ๋กœ monorepo๋ฅผ ํด๋”์—์„œ ์ง์ ‘ app ํด๋”์— ์ ‘๊ทผํ•˜์ง€ ๋ชปํ•˜๊ฒŒ ํ•˜๊ธฐ ์œ„ํ•ด package.json ์— ๋‹ค์Œ๊ณผ ๊ฐ™์ด ํŽผ์ณ์งˆ ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.


ํŒจํ‚ค์ง€.json


{
    "name": "@soom/root",
...
    "scripts": {
        "preinstall": "pnpm dlx only-allow pnpm",
        "dev:app": "pnpm --filter @soom/app dev"
    },
...
}


๋‹จ๋ง๊ธฐ


pnpm dev:app



โž•โž• Stackblitz ์ƒ˜ํ”Œ




๊ฒฐ๋ก 


pnpm workspace ๋ฅผ ์ด์šฉํ•˜์—ฌ monorepo๋ฅผ ๊ตฌ์„ฑํ•ด์™”์Šต๋‹ˆ๋‹ค.
์ด ํ”„๋กœ์ ํŠธ์— turborepo , lerna ๋“ฑ์„ ์—ฌ๋Ÿฌ ๊ฐ€์ง€๋กœ ๊ด€๋ฆฌํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.
monorepo๋ฅผ ๊ตฌ์„ฑํ•˜๋Š” ๋ฐฉ๋ฒ•์€ ๋ถˆ์ด ๋ฒˆ์ฉ ๋ฒˆ์ฉํ•˜์—ฌ pnpm workspace ๋ฅผ ์‚ฌ์šฉํ•˜๋Š” ๋ฐฉ๋ฒ•์ด ๊ฐ€์žฅ ์ทจ์†Œ๋œ ๊ฒƒ์ž…๋‹ˆ๋‹ค.

pnpm์˜ ์ž์„ธํ•œ ๋‚ด์šฉ์€ ๋งํฌ๋ฅผ ์ฐธ์กฐํ•˜์‹ญ์‹œ์˜ค.

https://pnpm.io/ko/

์ข‹์€ ์›นํŽ˜์ด์ง€ ์ฆ๊ฒจ์ฐพ๊ธฐ