정말 감사합니다.
여기서 사용된 모든 코드는 https://github.com/bluejoyq/package-test 에서 확인하실 수 있습니다.
mkdir package-test
cd package-test
# yarn 2 선택(yarn version 3, yarn2, yarn berry는 다 같은 표현)
yarn set version berry
# 워크 스페이스 초기화
yarn init -w
yarnPath: .yarn/releases/yarn-3.5.0.cjs
nodeLinker: node-modules #추가
/package.json
packageManager
버젼이 3.5private
private이 true인 패키지만 워크스페이스가 가능, publish를 막기 위해workspaces
기본적으로 packages
폴더 아래의 모든 폴더를 워크스페이스로 본다.{
"name": "package-test",
"packageManager": "yarn@3.5.0",
"private": true,
"workspaces": [
"packages/*"
]
}
yarn add -D typescript @typescript-eslint/parser
# tsconfig.json 생성
touch tsconfig.base.json
tsconfig.base.json
내용 채우기{
"compilerOptions": {
"allowSyntheticDefaultImports": true,
"moduleResolution": "Node",
"resolveJsonModule": true,
"esModuleInterop": true,
"strict": true,
"target": "es6",
"lib": [
"ES5",
"ES6",
"ESNext",
"DOM"
],
"skipLibCheck": true,
"baseUrl": ".",
"forceConsistentCasingInFileNames": true,
"module": "esnext",
"isolatedModules": true
},
"references": [ // 미래에 추가할 패키지들
{
"path": "packages/core"
},
{
"path": "packages/example"
},
],
"exclude": [
"packages/**/dist/**"
],
"include": []
}
format on save
를 원하면 https://velog.io/@bluejoyq/Next-JSTypescript-Eslint-Prettier-Init 의 세팅 방법 참조yarn add -D eslint prettier eslint-config-prettier eslint-plugin-prettier @typescript-eslint/eslint-plugin
.eslintrc.cjs
생성 및 수정 하기module.exports = {
env: { browser: true, es2020: true },
extends: [
"eslint:recommended",
"plugin:@typescript-eslint/recommended",
"plugin:prettier/recommended",
],
parser: "@typescript-eslint/parser",
parserOptions: {
ecmaVersion: "latest",
sourceType: "module",
project: ["./tsconfig.base.json", "./packages/**/tsconfig.json"],
}
};
yarn create vite packages/core --template react-ts
├── .eslintrc.cjs # 삭제할 것
├── .gitignore
├── index.html
├── package.json
├── public
│ └── vite.svg
├── src
│ ├── App.css
│ ├── App.tsx
│ ├── assets
│ │ └── react.svg
│ ├── index.css
│ ├── main.tsx
│ └── vite-env.d.ts
├── tsconfig.json
├── tsconfig.node.json
└── vite.config.ts
packages/core/.eslintrc.cjs
를 삭제한다.{
"extends": "../../tsconfig.base.json", // 추가
"compilerOptions": {
"target": "ESNext",
"lib": [
"DOM",
"DOM.Iterable",
"ESNext"
],
"module": "ESNext",
"skipLibCheck": true,
/* Bundler mode */
"moduleResolution": "bundler",
"allowImportingTsExtensions": true,
"resolveJsonModule": true,
"isolatedModules": true,
"noEmit": true,
"jsx": "react-jsx",
/* Linting */
"strict": true,
"noUnusedLocals": true,
"noUnusedParameters": true,
"noFallthroughCasesInSwitch": true
},
"include": [
"src"
],
"references": [
{
"path": "./tsconfig.node.json"
}
]
}
yarn add -D eslint-plugin-react-hooks eslint-plugin-react-refresh
module.exports = {
env: { browser: true, es2020: true },
extends: [
"eslint:recommended",
"plugin:@typescript-eslint/recommended",
"plugin:prettier/recommended",
],
parser: "@typescript-eslint/parser",
parserOptions: {
ecmaVersion: "latest",
sourceType: "module",
project: ["./tsconfig.base.json", "./packages/**/tsconfig.json"],
},
overrides: [
{
extends: ["plugin:react-hooks/recommended"],
files: ["packages/core/**/*.ts?(x)", "packages/core/**/*.js?(x)"],
plugins: ["react-refresh"],
rules: {
"react-refresh/only-export-components": "warn",
},
},
],
};
yarn create vite packages/example --template react-ts
packages/example/tsconfig.json
에 extend 추가packages/example/eslintrc.cjs
삭제.eslintrc.cjs
에 구성 추가(이번에는 둘다 vite 기반의 react-ts이기에 걍 files만 추가해줬음)├── .gitignore
├── package.json
├── src
│ ├── components
│ │ └── Button.tsx
│ ├── index.ts
│ └── vite-env.d.ts
├── tsconfig.json
├── tsconfig.node.json
└── vite.config.ts
packages/core/index.ts
export { Button } from "./components/Button";
packages/core/components/Button.tsx
import { ReactElement } from "react";
export function Button(): ReactElement {
return <button>Click Me</button>;
}
packages/core
yarn add -D vite-plugin-dts
packages/core/package.json
{
"name": "@package-test/core", // 이것도 생각난 김에 수정!
"private": true,
"version": "0.0.0",
"type": "module",
"scripts": {
"dev": "vite",
"build": "tsc && vite build",
"lint": "eslint src --ext ts,tsx --report-unused-disable-directives --max-warnings 0",
"preview": "vite preview"
},
"dependencies": {
"react": "^18.2.0",
"react-dom": "^18.2.0"
},
"devDependencies": {
"@types/react": "^18.0.28",
"@types/react-dom": "^18.0.11",
"@typescript-eslint/eslint-plugin": "^5.57.1",
"@typescript-eslint/parser": "^5.57.1",
"@vitejs/plugin-react": "^4.0.0",
"eslint": "^8.39.0",
"eslint-plugin-react-hooks": "^4.6.0",
"eslint-plugin-react-refresh": "^0.3.4",
"typescript": "^5.0.2",
"vite": "^4.3.2"
},
"main": "dist/core.js", // 추가
"types": "dist/index.d.ts" // 추가
}
import { defineConfig } from 'vite'
import react from '@vitejs/plugin-react'
import dts from 'vite-plugin-dts'
// https://vitejs.dev/config/
export default defineConfig({
plugins: [react(),dts()],
build: {
lib: {
entry: 'src/index.ts',
name: '@package-test/core',
formats: ['es']
},
rollupOptions: {
external: ['react'],
output: {
globals: {
react: 'React'
}
}
}
}
})
packages/example/package.json
{
"name": "@package-test/example",
"private": true,
"version": "0.0.0",
"type": "module",
"scripts": {
"dev": "vite",
"build": "tsc && vite build",
"lint": "eslint src --ext ts,tsx --report-unused-disable-directives --max-warnings 0",
"preview": "vite preview"
},
"dependencies": {
"@package-test/core": "0.0.0",
"react": "^18.2.0",
"react-dom": "^18.2.0"
},
"devDependencies": {
"@types/react": "^18.0.28",
"@types/react-dom": "^18.0.11",
"@typescript-eslint/eslint-plugin": "^5.57.1",
"@typescript-eslint/parser": "^5.57.1",
"@vitejs/plugin-react": "^4.0.0",
"eslint": "^8.38.0",
"eslint-plugin-react-hooks": "^4.6.0",
"eslint-plugin-react-refresh": "^0.3.4",
"typescript": "^5.0.2",
"vite": "^4.3.2"
}
}
packages/example/src/App.tsx
import { useState } from "react";
import reactLogo from "./assets/react.svg";
import viteLogo from "/vite.svg";
import "./App.css";
import { Button } from "@package-test/core";
function App() {
const [count, setCount] = useState(0);
return (
<>
<div>
<Button />
<a href="https://vitejs.dev" target="_blank">
<img src={viteLogo} className="logo" alt="Vite logo" />
</a>
<a href="https://react.dev" target="_blank">
<img src={reactLogo} className="logo react" alt="React logo" />
</a>
</div>
<h1>Vite + React</h1>
<div className="card">
<button onClick={() => setCount((count) => count + 1)}>
count is {count}
</button>
<p>
Edit <code>src/App.tsx</code> and save to test HMR
</p>
</div>
<p className="read-the-docs">
Click on the Vite and React logos to learn more
</p>
</>
);
}
export default App;
나도 이제 모노 레포 구성할 수 있따!!!
안녕하세요 잘 읽었습니다.!
읽다보니 궁금한 점이 있는데요.
혹시 core폴더에서의 컴포넌트 생성할 때 화면에서와 확인이나 디버깅은 어떻게 진행하셨는지 궁금합니다..!
감사합니다 :)