├── .github ├── pull_request_template.md └── workflows │ ├── ci.yml │ └── sync.yml ├── .gitignore ├── .npmrc ├── .prettierignore ├── .prettierrc ├── .vitepress ├── buildEnd.config.ts ├── config.ts ├── markdown-it-custom-anchor │ └── index.js ├── render-permalink │ └── index.js ├── theme │ ├── components │ │ ├── AsideSponsors.vue │ │ ├── BlogIndex.vue │ │ ├── SvgImage.vue │ │ ├── YouTubeVideo.vue │ │ └── landing │ │ │ ├── 1. hero-section │ │ │ ├── HeroDiagram.vue │ │ │ ├── HeroSection.vue │ │ │ └── svg-elements │ │ │ │ ├── SvgBlueIndicator.vue │ │ │ │ ├── SvgInputs.vue │ │ │ │ ├── SvgOutputs.vue │ │ │ │ └── SvgPinkIndicator.vue │ │ │ ├── 2. feature-section │ │ │ ├── FeatureCI.vue │ │ │ ├── FeatureFlexiblePlugins.vue │ │ │ ├── FeatureHMR.vue │ │ │ ├── FeatureInstantServerStart.vue │ │ │ ├── FeatureOptimizedBuild.vue │ │ │ ├── FeatureRichFeatures.vue │ │ │ ├── FeatureSSRSupport.vue │ │ │ ├── FeatureSection.vue │ │ │ ├── FeatureTypedAPI.vue │ │ │ └── images │ │ │ │ ├── css3.svg │ │ │ │ ├── js.svg │ │ │ │ ├── json.svg │ │ │ │ ├── postcss.svg │ │ │ │ ├── ts.svg │ │ │ │ └── wa.svg │ │ │ ├── 3. frameworks-section │ │ │ ├── FrameworkCard.vue │ │ │ ├── FrameworksSection.vue │ │ │ └── images │ │ │ │ ├── adonis.svg │ │ │ │ ├── analog.svg │ │ │ │ ├── angular.svg │ │ │ │ ├── astro.svg │ │ │ │ ├── ember.svg │ │ │ │ ├── hono.svg │ │ │ │ ├── laravel.svg │ │ │ │ ├── marko.svg │ │ │ │ ├── nuxt.svg │ │ │ │ ├── playwright.svg │ │ │ │ ├── preact.svg │ │ │ │ ├── qwik.svg │ │ │ │ ├── react.svg │ │ │ │ ├── redwood.svg │ │ │ │ ├── remix.svg │ │ │ │ ├── solid.svg │ │ │ │ ├── storybook.svg │ │ │ │ ├── svelte.svg │ │ │ │ ├── vitest.svg │ │ │ │ └── vue.svg │ │ │ ├── 4. community-section │ │ │ ├── CommunityCard.vue │ │ │ └── CommunitySection.vue │ │ │ ├── 5. sponsor-section │ │ │ └── SponsorSection.vue │ │ │ ├── 6. get-started-section │ │ │ └── GetStartedSection.vue │ │ │ └── common │ │ │ └── SvgNode.vue │ ├── composables │ │ ├── sponsor.ts │ │ ├── useCardAnimation.ts │ │ └── useSlideIn.ts │ ├── index.ts │ └── styles │ │ ├── landing.css │ │ └── vars.css └── tsconfig.json ├── .vscode └── settings.json ├── CONTRIBUTING.md ├── LICENSE ├── README.md ├── TERMINOLOGY.md ├── _data ├── blog.data.ts └── team.js ├── blog ├── announcing-vite2.md ├── announcing-vite3.md ├── announcing-vite4-3.md ├── announcing-vite4.md ├── announcing-vite5-1.md ├── announcing-vite5.md └── announcing-vite6.md ├── changes ├── hotupdate-hook.md ├── index.md ├── per-environment-apis.md ├── shared-plugins-during-build.md ├── ssr-using-modulerunner.md └── this-environment-in-hooks.md ├── config ├── build-options.md ├── dep-optimization-options.md ├── index.md ├── preview-options.md ├── server-options.md ├── shared-options.md ├── ssr-options.md └── worker-options.md ├── docs ├── logo-black.png ├── logo-transparent.png └── logo-white.png ├── guide ├── api-environment-frameworks.md ├── api-environment-instances.md ├── api-environment-plugins.md ├── api-environment-runtimes.md ├── api-environment.md ├── api-hmr.md ├── api-javascript.md ├── api-plugin.md ├── assets.md ├── backend-integration.md ├── build.md ├── cli.md ├── dep-pre-bundling.md ├── env-and-mode.md ├── features.md ├── index.md ├── migration-from-v1.md ├── migration-from-v2.md ├── migration-from-v3.md ├── migration-from-v4.md ├── migration.md ├── performance.md ├── philosophy.md ├── rolldown.md ├── ssr.md ├── static-deploy-github-pages.yaml ├── static-deploy.md ├── troubleshooting.md ├── using-plugins.md └── why.md ├── images ├── bundler.png ├── bundler.svg ├── diagrams.fig ├── esm.png ├── esm.svg ├── graph.png ├── graph.svg ├── lit.svg ├── placeholder.jpg ├── preact.svg ├── react.svg ├── svelte.svg ├── v3-docs.png ├── v3-new-open-issues-and-PRs.png ├── v3-open-issues-and-PRs.png ├── vercel-configuration.png ├── vite-3-cold-start.svg ├── vite-environments.svg ├── vite-plugin-inspect.png ├── vite.svg └── vue.svg ├── index.md ├── package.json ├── plugins └── index.md ├── pnpm-lock.yaml ├── public ├── _headers ├── _redirects ├── astro.svg ├── ecosystem-vite4.png ├── github.svg ├── googledb5f3175b0d5a81b.html ├── heart.svg ├── logo-home.svg ├── logo-uwu.png ├── logo-with-shadow.png ├── logo.svg ├── noise.png ├── nuxtlabs.svg ├── og-image-announcing-vite3.png ├── og-image-announcing-vite4-3.png ├── og-image-announcing-vite4.png ├── og-image-announcing-vite5-1.png ├── og-image-announcing-vite5.png ├── og-image-announcing-vite6.png ├── og-image.jpg ├── stackblitz.svg ├── vite.mp3 ├── vite4-3-hmr-time.png ├── vite4-3-startup-time.png ├── vite5-1-10K-modules-loading-time.png ├── vite6-npm-weekly-downloads.png ├── viteconf.svg ├── voice.svg └── voidzero.svg ├── releases.md ├── scripts └── rewrite-title │ ├── formatter.js │ └── index.js └── team.md /.github/pull_request_template.md: -------------------------------------------------------------------------------- 1 | ## 설명 2 | 3 | 4 | 5 | ## 연관 이슈 6 | 7 | 8 | 9 | resolved # 10 | 11 | ## 체크리스트 12 | 13 | - [ ] [번역 가이드](https://github.com/vitejs/docs-ko/blob/main/CONTRIBUTING.md)를 준수했습니다. 14 | - [ ] [맞춤법 검사기](http://speller.cs.pusan.ac.kr/)를 통해 문서를 검사했습니다. 15 | -------------------------------------------------------------------------------- /.github/workflows/ci.yml: -------------------------------------------------------------------------------- 1 | name: CI 2 | 3 | on: 4 | push: 5 | workflow_dispatch: 6 | 7 | permissions: 8 | contents: read 9 | pages: write 10 | id-token: write 11 | 12 | jobs: 13 | build: 14 | runs-on: ubuntu-latest 15 | steps: 16 | - name: Checkout 17 | uses: actions/checkout@v4 18 | 19 | - name: Setup pnpm 20 | uses: pnpm/action-setup@v4.1.0 21 | 22 | - name: Setup Node 23 | uses: actions/setup-node@v4 24 | with: 25 | node-version: lts/* 26 | cache: "pnpm" 27 | 28 | - name: Check dependency cache 29 | uses: actions/cache@v4 30 | id: dep-cache 31 | with: 32 | path: node_modules 33 | key: ${{ runner.os }}-pnpm-${{ hashFiles('pnpm-lock.yaml') }} 34 | restore-keys: | 35 | ${{ runner.os }}-pnpm- 36 | 37 | - name: Install dependencies if not installed 38 | if: steps.dep-cache.outputs.cache-hit != 'true' 39 | run: pnpm install 40 | 41 | - name: Build site 42 | run: pnpm run build 43 | -------------------------------------------------------------------------------- /.github/workflows/sync.yml: -------------------------------------------------------------------------------- 1 | name: yuki-no 2 | 3 | on: 4 | schedule: 5 | - cron: "0 * * * *" # Every hour 6 | workflow_dispatch: # Manual trigger (Optional) 7 | 8 | permissions: 9 | contents: read 10 | issues: write 11 | actions: read 12 | 13 | jobs: 14 | yuki-no: 15 | runs-on: ubuntu-latest 16 | steps: 17 | - uses: Gumball12/yuki-no@v1 18 | with: 19 | # GitHub access token. Required. 20 | access-token: ${{ secrets.GITHUB_TOKEN }} 21 | 22 | # The head repo to track. This is the repository you want to 23 | # take a diff. Required. 24 | head-repo: https://github.com/vitejs/vite.git 25 | 26 | # The git commit sha of head repo to start tracking. Yuki-no will 27 | # only track commit from this hash. Required. 28 | track-from: 14027b0f2a9b01c14815c38aab22baf5b29594bb 29 | 30 | # List of file patterns to track. Multiple patterns can be specified 31 | # with newlines. Files matching these glob patterns will be included 32 | # in tracking. 33 | # If empty, all files will be tracked. Optional. 34 | include: | 35 | docs/** 36 | 37 | # Whether to enable release tracking. 38 | # When enabled, Yuki-no will track releases for each issue 39 | # and add comments about release status. Optional. 40 | # Defaults to 'false' 41 | release-tracking: true 42 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | .DS_Store 2 | Thumbs.db 3 | db.json 4 | *.log 5 | node_modules/ 6 | .deploy*/ 7 | package-lock.json 8 | .vitepress/dist 9 | .vitepress/cache 10 | -------------------------------------------------------------------------------- /.npmrc: -------------------------------------------------------------------------------- 1 | auto-install-peers=true -------------------------------------------------------------------------------- /.prettierignore: -------------------------------------------------------------------------------- 1 | blog/* 2 | config/* 3 | docs/* 4 | guide/* 5 | changes/* 6 | team.md 7 | releases.md 8 | .vitepress/* 9 | !.vitepress/config.ts 10 | _data 11 | public 12 | plugins 13 | index.md 14 | -------------------------------------------------------------------------------- /.prettierrc: -------------------------------------------------------------------------------- 1 | { 2 | "semi": false, 3 | "singleQuote": true, 4 | "overrides": [ 5 | { 6 | "files": ["*.json5"], 7 | "options": { 8 | "singleQuote": false, 9 | "quoteProps": "preserve" 10 | } 11 | }, 12 | { 13 | "files": ["*.yml"], 14 | "options": { 15 | "singleQuote": false 16 | } 17 | } 18 | ] 19 | } 20 | -------------------------------------------------------------------------------- /.vitepress/buildEnd.config.ts: -------------------------------------------------------------------------------- 1 | import path from 'node:path' 2 | import { writeFileSync } from 'node:fs' 3 | import { Feed } from 'feed' 4 | import type { SiteConfig } from 'vitepress' 5 | import { createContentLoader } from 'vitepress' 6 | 7 | const siteUrl = 'https://vite.dev' 8 | const blogUrl = `${siteUrl}/blog` 9 | 10 | export const buildEnd = async (config: SiteConfig): Promise => { 11 | const feed = new Feed({ 12 | title: 'Vite', 13 | description: 'Next Generation Frontend Tooling', 14 | id: blogUrl, 15 | link: blogUrl, 16 | language: 'en', 17 | image: 'https://vite.dev/og-image.png', 18 | favicon: 'https://vite.dev/logo.svg', 19 | copyright: 'Copyright © 2019-present VoidZero Inc. & Vite Contributors', 20 | }) 21 | 22 | const posts = await createContentLoader('blog/*.md', { 23 | excerpt: true, 24 | render: true, 25 | }).load() 26 | 27 | posts.sort( 28 | (a, b) => 29 | +new Date(b.frontmatter.date as string) - 30 | +new Date(a.frontmatter.date as string), 31 | ) 32 | 33 | for (const { url, excerpt, frontmatter, html } of posts) { 34 | feed.addItem({ 35 | title: frontmatter.title, 36 | id: `${siteUrl}${url}`, 37 | link: `${siteUrl}${url}`, 38 | description: excerpt, 39 | content: html, 40 | author: [ 41 | { 42 | name: frontmatter.author.name, 43 | }, 44 | ], 45 | date: frontmatter.date, 46 | }) 47 | } 48 | 49 | writeFileSync(path.join(config.outDir, 'blog.rss'), feed.rss2()) 50 | } -------------------------------------------------------------------------------- /.vitepress/markdown-it-custom-anchor/index.js: -------------------------------------------------------------------------------- 1 | // https://github.com/vitejs/docs-cn/blob/96c6f1b1ab2c2a4231920a2ef6cda6151bf4752e/.vitepress/markdown-it-custom-anchor/index.js 2 | const anchorMatch = /^.+(\s*\{#([a-z0-9\-_]+?)\}\s*)$/ 3 | 4 | const removeAnchorFromTitle = (oldTitle) => { 5 | const match = anchorMatch.exec(oldTitle) 6 | return match ? oldTitle.replace(match[1], '').trim() : oldTitle 7 | } 8 | 9 | export default function (md) { 10 | const oldTitle = md.renderer.rules.text 11 | md.renderer.rules.text = (tokens, idx, options, env, slf) => { 12 | const titleAndId = oldTitle(tokens, idx, options, env, slf) 13 | return removeAnchorFromTitle(titleAndId) 14 | } 15 | } 16 | -------------------------------------------------------------------------------- /.vitepress/render-permalink/index.js: -------------------------------------------------------------------------------- 1 | const position = { 2 | false: 'push', 3 | true: 'unshift', 4 | } 5 | 6 | export default (slug, options, state, permalink) => { 7 | try { 8 | const tokens = state.tokens 9 | const token = tokens[permalink] 10 | const title = tokens[permalink + 1].children 11 | .filter((token) => token.type === 'text' || token.typoe === 'code_inline') 12 | .reduce((acc, token) => acc + token.content, '') 13 | const match = /^.+(\s*\{#([a-z0-9\-_]+?)\}\s*)$/.exec(title) 14 | 15 | slug = match ? match[2] : slug 16 | token.attrSet('id', slug) 17 | 18 | const space = () => 19 | Object.assign(new state.Token('text', '', 0), { content: '' }) 20 | 21 | const linkTokens = [ 22 | Object.assign(new state.Token('link_open', 'a', 1), { 23 | attrs: [ 24 | ...(options.permalinkClass 25 | ? [['class', options.permalinkClass]] 26 | : []), 27 | ['href', options.permalinkHref(slug, state)], 28 | ...Object.entries(options.permalinkAttrs(slug, state)), 29 | ], 30 | }), 31 | Object.assign(new state.Token('html_block', '', 0), { 32 | content: options.permalinkSymbol, 33 | }), 34 | new state.Token('link_close', 'a', -1), 35 | ] 36 | 37 | if (options.permalinkSpace) { 38 | linkTokens[position[!options.permalinkBefore]](space()) 39 | } 40 | 41 | state.tokens[permalink + 1].children[position[options.permalinkBefore]]( 42 | ...linkTokens, 43 | ) 44 | } catch (err) { 45 | console.log(err) 46 | } 47 | } 48 | -------------------------------------------------------------------------------- /.vitepress/theme/components/AsideSponsors.vue: -------------------------------------------------------------------------------- 1 | 20 | 21 | 36 | 37 | -------------------------------------------------------------------------------- /.vitepress/theme/components/BlogIndex.vue: -------------------------------------------------------------------------------- 1 | 8 | 9 | 23 | 24 | -------------------------------------------------------------------------------- /.vitepress/theme/components/SvgImage.vue: -------------------------------------------------------------------------------- 1 | 4 | 5 | 8 | 9 | 23 | -------------------------------------------------------------------------------- /.vitepress/theme/components/YouTubeVideo.vue: -------------------------------------------------------------------------------- 1 | 6 | 7 | 20 | 21 | -------------------------------------------------------------------------------- /.vitepress/theme/components/landing/1. hero-section/HeroSection.vue: -------------------------------------------------------------------------------- 1 | 4 | 5 | 43 | 44 | 137 | -------------------------------------------------------------------------------- /.vitepress/theme/components/landing/1. hero-section/svg-elements/SvgInputs.vue: -------------------------------------------------------------------------------- 1 | 12 | 13 | 52 | 53 | 66 | -------------------------------------------------------------------------------- /.vitepress/theme/components/landing/1. hero-section/svg-elements/SvgOutputs.vue: -------------------------------------------------------------------------------- 1 | 12 | 13 | 48 | 49 | 57 | -------------------------------------------------------------------------------- /.vitepress/theme/components/landing/2. feature-section/images/css3.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | -------------------------------------------------------------------------------- /.vitepress/theme/components/landing/2. feature-section/images/js.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | -------------------------------------------------------------------------------- /.vitepress/theme/components/landing/2. feature-section/images/json.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | -------------------------------------------------------------------------------- /.vitepress/theme/components/landing/2. feature-section/images/ts.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | -------------------------------------------------------------------------------- /.vitepress/theme/components/landing/2. feature-section/images/wa.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | -------------------------------------------------------------------------------- /.vitepress/theme/components/landing/3. frameworks-section/FrameworkCard.vue: -------------------------------------------------------------------------------- 1 | 44 | 45 | 62 | 63 | 128 | -------------------------------------------------------------------------------- /.vitepress/theme/components/landing/3. frameworks-section/images/adonis.svg: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /.vitepress/theme/components/landing/3. frameworks-section/images/angular.svg: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /.vitepress/theme/components/landing/3. frameworks-section/images/astro.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | -------------------------------------------------------------------------------- /.vitepress/theme/components/landing/3. frameworks-section/images/ember.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | -------------------------------------------------------------------------------- /.vitepress/theme/components/landing/3. frameworks-section/images/hono.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | -------------------------------------------------------------------------------- /.vitepress/theme/components/landing/3. frameworks-section/images/laravel.svg: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /.vitepress/theme/components/landing/3. frameworks-section/images/nuxt.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | -------------------------------------------------------------------------------- /.vitepress/theme/components/landing/3. frameworks-section/images/playwright.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | -------------------------------------------------------------------------------- /.vitepress/theme/components/landing/3. frameworks-section/images/preact.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | -------------------------------------------------------------------------------- /.vitepress/theme/components/landing/3. frameworks-section/images/qwik.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | -------------------------------------------------------------------------------- /.vitepress/theme/components/landing/3. frameworks-section/images/react.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | -------------------------------------------------------------------------------- /.vitepress/theme/components/landing/3. frameworks-section/images/redwood.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | -------------------------------------------------------------------------------- /.vitepress/theme/components/landing/3. frameworks-section/images/remix.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | -------------------------------------------------------------------------------- /.vitepress/theme/components/landing/3. frameworks-section/images/solid.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 35 | 36 | -------------------------------------------------------------------------------- /.vitepress/theme/components/landing/3. frameworks-section/images/storybook.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | -------------------------------------------------------------------------------- /.vitepress/theme/components/landing/3. frameworks-section/images/svelte.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | -------------------------------------------------------------------------------- /.vitepress/theme/components/landing/3. frameworks-section/images/vitest.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | -------------------------------------------------------------------------------- /.vitepress/theme/components/landing/3. frameworks-section/images/vue.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | -------------------------------------------------------------------------------- /.vitepress/theme/components/landing/4. community-section/CommunityCard.vue: -------------------------------------------------------------------------------- 1 | 31 | 32 | 54 | 55 | 123 | -------------------------------------------------------------------------------- /.vitepress/theme/components/landing/4. community-section/CommunitySection.vue: -------------------------------------------------------------------------------- 1 | 86 | 87 | 104 | 105 | 147 | -------------------------------------------------------------------------------- /.vitepress/theme/components/landing/common/SvgNode.vue: -------------------------------------------------------------------------------- 1 | 123 | 124 | 183 | 184 | 215 | -------------------------------------------------------------------------------- /.vitepress/theme/composables/sponsor.ts: -------------------------------------------------------------------------------- 1 | import { onMounted, onUnmounted, ref } from 'vue' 2 | 3 | interface Sponsors { 4 | special: Sponsor[] 5 | platinum: Sponsor[] 6 | platinum_china: Sponsor[] 7 | gold: Sponsor[] 8 | silver: Sponsor[] 9 | bronze: Sponsor[] 10 | } 11 | 12 | interface Sponsor { 13 | name: string 14 | img: string 15 | url: string 16 | /** 17 | * Expects to also have an **inversed** image with `-dark` postfix. 18 | */ 19 | hasDark?: true 20 | } 21 | 22 | // shared data across instances so we load only once. 23 | const data = ref() 24 | 25 | const dataHost = 'https://sponsors.vuejs.org' 26 | const dataUrl = `${dataHost}/vite.json` 27 | 28 | export const voidZero = { 29 | name: 'VoidZero', 30 | url: 'https://voidzero.dev', 31 | img: '/voidzero.svg', 32 | } satisfies Sponsor 33 | 34 | const viteSponsors: Pick = { 35 | special: [ 36 | // sponsors patak-dev 37 | { 38 | name: 'StackBlitz', 39 | url: 'https://stackblitz.com', 40 | img: '/stackblitz.svg', 41 | }, 42 | // sponsors antfu 43 | { 44 | name: 'NuxtLabs', 45 | url: 'https://nuxtlabs.com', 46 | img: '/nuxtlabs.svg', 47 | }, 48 | ], 49 | gold: [ 50 | // now automated via sponsors.vuejs.org too 51 | ], 52 | } 53 | 54 | function toggleDarkLogos() { 55 | if (data.value) { 56 | const isDark = document.documentElement.classList.contains('dark') 57 | data.value.forEach(({ items }) => { 58 | items.forEach((s: Sponsor) => { 59 | if (s.hasDark) { 60 | s.img = isDark 61 | ? s.img.replace(/(\.\w+)$/, '-dark$1') 62 | : s.img.replace(/-dark(\.\w+)$/, '$1') 63 | } 64 | }) 65 | }) 66 | } 67 | } 68 | 69 | export function useSponsor() { 70 | onMounted(async () => { 71 | const ob = new MutationObserver((list) => { 72 | for (const m of list) { 73 | if (m.attributeName === 'class') { 74 | toggleDarkLogos() 75 | } 76 | } 77 | }) 78 | ob.observe(document.documentElement, { attributes: true }) 79 | onUnmounted(() => { 80 | ob.disconnect() 81 | }) 82 | 83 | if (data.value) { 84 | return 85 | } 86 | 87 | const result = await fetch(dataUrl) 88 | const json = await result.json() 89 | 90 | data.value = mapSponsors(json) 91 | toggleDarkLogos() 92 | }) 93 | 94 | return { 95 | data, 96 | } 97 | } 98 | 99 | function mapSponsors(sponsors: Sponsors) { 100 | return [ 101 | { 102 | tier: 'in partnership with', 103 | size: 'big', 104 | items: viteSponsors['special'], 105 | }, 106 | { 107 | tier: 'Platinum Sponsors', 108 | size: 'big', 109 | items: mapImgPath(sponsors['platinum']), 110 | }, 111 | { 112 | tier: 'Gold Sponsors', 113 | size: 'medium', 114 | items: [...mapImgPath(sponsors['gold']), ...viteSponsors['gold']], 115 | }, 116 | ] 117 | } 118 | 119 | const viteSponsorNames = new Set( 120 | Object.values(viteSponsors).flatMap((sponsors) => 121 | sponsors.map((s) => s.name), 122 | ), 123 | ) 124 | 125 | /** 126 | * Map Vue/Vite sponsors data to objects and filter out Vite-specific sponsors 127 | */ 128 | function mapImgPath(sponsors: Sponsor[]) { 129 | return sponsors 130 | .filter((sponsor) => !viteSponsorNames.has(sponsor.name)) 131 | .map((sponsor) => ({ 132 | ...sponsor, 133 | img: `${dataHost}/images/${sponsor.img}`, 134 | })) 135 | } -------------------------------------------------------------------------------- /.vitepress/theme/composables/useCardAnimation.ts: -------------------------------------------------------------------------------- 1 | import { type Ref, onMounted, onUnmounted, ref } from 'vue' 2 | import { gsap } from 'gsap' 3 | import { ScrollTrigger } from 'gsap/dist/ScrollTrigger' 4 | 5 | gsap.registerPlugin(ScrollTrigger) 6 | 7 | /** 8 | * A custom hook for animating a card element. 9 | * 10 | * @param {HTMLElement | string} el - The element or selector for the element to be animated 11 | * @param {() => GSAPTimeline | null} animation - A function that returns a GSAP timeline for the animation 12 | * @param {object} options - Options for the animation 13 | */ 14 | export function useCardAnimation( 15 | el: HTMLElement | string, 16 | animation: (() => GSAPTimeline) | undefined = undefined, 17 | options?: { 18 | /** 19 | * A flag to indicate whether the animation should only run once, and not reset once complete. 20 | */ 21 | once?: boolean 22 | }, 23 | ) { 24 | /** 25 | * The GSAP timeline for this animation. 26 | */ 27 | let timeline: GSAPTimeline | null 28 | 29 | /** 30 | * A flag to indicate whether the card is currently active or not. 31 | * May be inactive while the animation is still finishing up, due to CSS transitions. 32 | */ 33 | const isCardActive: Ref = ref(false) 34 | 35 | /** 36 | * An internal flag to prevent multiple animations from running at the same time. 37 | */ 38 | const isAnimationRunning: Ref = ref(false) 39 | 40 | /** 41 | * Starts the card's animation, managing the lifecycle internally to prevent multiple animations from running at the same time. 42 | */ 43 | const startAnimation = () => { 44 | if (isAnimationRunning.value) { 45 | return 46 | } else { 47 | isAnimationRunning.value = true 48 | isCardActive.value = true 49 | } 50 | if (timeline) { 51 | timeline.kill() 52 | } 53 | if (!animation) { 54 | return 55 | } 56 | timeline = gsap.timeline({ 57 | onComplete: () => { 58 | if (!options?.once) { 59 | isCardActive.value = false 60 | setTimeout(() => { 61 | isAnimationRunning.value = false 62 | }, 3000) 63 | } 64 | }, 65 | }) 66 | timeline.add(animation()) 67 | } 68 | 69 | /** 70 | * The ScrollTrigger instance for this card. 71 | */ 72 | let scrollTriggerInstance: ScrollTrigger | null = null 73 | 74 | /** 75 | * Trigger's the card's animation automatically on mobile devices (no hover method) 76 | */ 77 | onMounted(() => { 78 | if (window.innerWidth < 768) { 79 | scrollTriggerInstance = ScrollTrigger.create({ 80 | trigger: el, 81 | start: 'top 60%', 82 | onEnter: () => { 83 | startAnimation() 84 | }, 85 | }) 86 | } 87 | }) 88 | 89 | /** 90 | * Remove the ScrollTrigger and GSAP timeline instances when the component is unmounted 91 | */ 92 | onUnmounted(() => { 93 | if (scrollTriggerInstance) { 94 | scrollTriggerInstance.kill() 95 | scrollTriggerInstance = null 96 | } 97 | if (timeline) { 98 | timeline.kill() 99 | timeline = null 100 | } 101 | }) 102 | 103 | return { 104 | startAnimation, 105 | isCardActive, 106 | } 107 | } -------------------------------------------------------------------------------- /.vitepress/theme/composables/useSlideIn.ts: -------------------------------------------------------------------------------- 1 | import { nextTick, onMounted } from 'vue' 2 | import { gsap } from 'gsap' 3 | 4 | export function useSlideIn(el: HTMLElement | string) { 5 | onMounted(async () => { 6 | await nextTick(() => { 7 | gsap.to(el, { 8 | x: 0, 9 | duration: 1, 10 | ease: 'power3.out', 11 | scrollTrigger: { 12 | trigger: el, 13 | start: 'top 100%', 14 | once: true, 15 | }, 16 | }) 17 | }) 18 | }) 19 | } -------------------------------------------------------------------------------- /.vitepress/theme/index.ts: -------------------------------------------------------------------------------- 1 | import { h } from 'vue' 2 | import type { Theme } from 'vitepress' 3 | import DefaultTheme from 'vitepress/theme' 4 | import TwoslashFloatingVue from '@shikijs/vitepress-twoslash/client' 5 | import '@shikijs/vitepress-twoslash/style.css' 6 | import './styles/vars.css' 7 | import './styles/landing.css' 8 | import AsideSponsors from './components/AsideSponsors.vue' 9 | import SvgImage from './components/SvgImage.vue' 10 | import YouTubeVideo from './components/YouTubeVideo.vue' 11 | import 'virtual:group-icons.css' 12 | 13 | export default { 14 | extends: DefaultTheme, 15 | Layout() { 16 | return h(DefaultTheme.Layout, null, { 17 | 'aside-ads-before': () => h(AsideSponsors), 18 | }) 19 | }, 20 | enhanceApp({ app }) { 21 | app.component('SvgImage', SvgImage) 22 | app.component('YouTubeVideo', YouTubeVideo) 23 | app.use(TwoslashFloatingVue) 24 | }, 25 | } satisfies Theme -------------------------------------------------------------------------------- /.vitepress/theme/styles/vars.css: -------------------------------------------------------------------------------- 1 | /** 2 | * Colors 3 | * -------------------------------------------------------------------------- */ 4 | 5 | :root { 6 | --vp-c-brand: #646cff; 7 | --vp-c-brand-light: #747bff; 8 | --vp-c-brand-lighter: #9499ff; 9 | --vp-c-brand-lightest: #bcc0ff; 10 | --vp-c-brand-dark: #535bf2; 11 | --vp-c-brand-darker: #454ce1; 12 | --vp-c-brand-dimm: rgba(100, 108, 255, 0.08); 13 | } 14 | 15 | /** 16 | * Component: Button 17 | * -------------------------------------------------------------------------- */ 18 | 19 | :root { 20 | --vp-button-brand-border: var(--vp-c-brand-light); 21 | --vp-button-brand-text: var(--vp-c-white); 22 | --vp-button-brand-bg: var(--vp-c-brand); 23 | --vp-button-brand-hover-border: var(--vp-c-brand-light); 24 | --vp-button-brand-hover-text: var(--vp-c-white); 25 | --vp-button-brand-hover-bg: var(--vp-c-brand-light); 26 | --vp-button-brand-active-border: var(--vp-c-brand-light); 27 | --vp-button-brand-active-text: var(--vp-c-white); 28 | --vp-button-brand-active-bg: var(--vp-button-brand-bg); 29 | } 30 | 31 | /** 32 | * Component: Custom Block 33 | * -------------------------------------------------------------------------- */ 34 | 35 | :root { 36 | --vp-custom-block-tip-border: var(--vp-c-brand); 37 | --vp-custom-block-tip-text: var(--vp-c-brand-darker); 38 | --vp-custom-block-tip-bg: var(--vp-c-brand-dimm); 39 | } 40 | 41 | .dark { 42 | --vp-custom-block-tip-border: var(--vp-c-brand); 43 | --vp-custom-block-tip-text: var(--vp-c-brand-lightest); 44 | --vp-custom-block-tip-bg: var(--vp-c-brand-dimm); 45 | } 46 | 47 | /** 48 | * Component: Algolia 49 | * -------------------------------------------------------------------------- */ 50 | 51 | .DocSearch { 52 | --docsearch-primary-color: var(--vp-c-brand) !important; 53 | --docsearch-container-background: rgba(0, 0, 0, 0.7); 54 | } 55 | 56 | /** 57 | * VitePress: Custom fix 58 | * -------------------------------------------------------------------------- */ 59 | 60 | /* 61 | Use lighter colors for links in dark mode for a11y. 62 | Also specify some classes twice to have higher specificity 63 | over scoped class data attribute. 64 | */ 65 | .dark .vp-doc a, 66 | .dark .vp-doc a > code, 67 | .dark .VPNavBarMenuLink.VPNavBarMenuLink:hover, 68 | .dark .VPNavBarMenuLink.VPNavBarMenuLink.active, 69 | .dark .link.link:hover, 70 | .dark .link.link.active, 71 | .dark .edit-link-button.edit-link-button, 72 | .dark .pager-link .title { 73 | color: var(--vp-c-brand-lighter); 74 | } 75 | 76 | .dark .vp-doc a:hover, 77 | .dark .vp-doc a > code:hover { 78 | color: var(--vp-c-brand-lightest); 79 | opacity: 1; 80 | } 81 | 82 | /* Transition by color instead of opacity */ 83 | .dark .vp-doc .custom-block a { 84 | transition: color 0.25s; 85 | } 86 | 87 | .vp-sponsor.aside .vp-sponsor-grid.mini .vp-sponsor-grid-image { 88 | max-width: 124px; 89 | } 90 | 91 | .vp-sponsor-grid.big .vp-sponsor-grid-image { 92 | max-height: 96px; 93 | } 94 | 95 | .vp-sponsor-grid.mini .vp-sponsor-grid-image[alt='Bit'] { 96 | max-height: 48px; 97 | } 98 | 99 | .vp-sponsor-grid.xmini .vp-sponsor-grid-image[alt='JetBrains'] { 100 | max-height: 54px; 101 | } 102 | 103 | .vp-sponsor-grid.medium .vp-sponsor-grid-image[alt='JetBrains'] { 104 | max-height: 100px; 105 | } -------------------------------------------------------------------------------- /.vitepress/tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "compilerOptions": { 3 | "target": "ES2022", 4 | "module": "ESNext", 5 | "moduleResolution": "bundler", 6 | "strict": true, 7 | "noImplicitOverride": true, 8 | "noUnusedLocals": true, 9 | "esModuleInterop": true, 10 | "noEmit": true 11 | }, 12 | "exclude": ["cache", "dist"] 13 | } -------------------------------------------------------------------------------- /.vscode/settings.json: -------------------------------------------------------------------------------- 1 | { 2 | "editor.suggest.showWords": false 3 | } -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | MIT License 2 | 3 | Copyright (c) 2019-present, VoidZero Inc. and Vite contributors 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | -------------------------------------------------------------------------------- /TERMINOLOGY.md: -------------------------------------------------------------------------------- 1 | ## 영어 번역 용어 비교표 2 | 3 | > 영어 번역 용어 비교표입니다. 번역 용어를 추가하거나 수정하고 싶으시다면 언제든지 PR 생성해주세요. 4 | 5 | | 영어 | 한국어 | 6 | | -------------- | -------------- | 7 | | Application | 애플리케이션 | 8 | | Branch | 브랜치 | 9 | | Bundle | 번들 | 10 | | Conditional | 조건부 | 11 | | Convention | 컨벤션 | 12 | | Dependency | 디펜던시 | 13 | | Frontend | 프런트엔드 | 14 | | Hook | 훅 | 15 | | Label | 레이블 | 16 | | Message | 메시지 | 17 | | Monorepo | 모노리포 | 18 | | On-demand | 온디맨드 | 19 | | Preview | 프리뷰 | 20 | | Production | 프로덕션 | 21 | | Property | 프로퍼티 | 22 | | Repository | 리포지토리 | 23 | | Rollup | | 24 | | Root | 루트 | 25 | | Security Notes | 보안 권고 사항 | 26 | | Shim | | 27 | | Source Map | 소스 맵 | 28 | | Tree-shaking | 트리 셰이킹 | 29 | | Virtual Module | 가상 모듈 | 30 | | Vite | | 31 | | Worker | 워커 | 32 | | Side effect | 사이드 이펙트 | 33 | | Proxy | 프록시 | 34 | | Minification | 축소화 | 35 | | Release | 릴리스 | 36 | | Asset | 에셋 | 37 | | Example Usage | 사용 예제 | 38 | | Type Signature | 타입 시그니처 | 39 | | Placeholder | 자리 표시자 | 40 | | Import | 임포트 | 41 | | Export | 익스포트 | 42 | | Load | 로드 | 43 | | Transform | 변환 | 44 | | Release | 릴리스 | 45 | | Ecosystem | 생태계 | 46 | | Performance | 성능 | 47 | -------------------------------------------------------------------------------- /_data/blog.data.ts: -------------------------------------------------------------------------------- 1 | import { createContentLoader } from 'vitepress' 2 | 3 | interface Post { 4 | title: string 5 | url: string 6 | date: { 7 | time: number 8 | string: string 9 | } 10 | } 11 | 12 | declare const data: Post[] 13 | export { data } 14 | 15 | export default createContentLoader('blog/*.md', { 16 | // excerpt: true, 17 | transform(raw): Post[] { 18 | return raw 19 | .map(({ url, frontmatter }) => ({ 20 | title: frontmatter.head.find((e) => e[1].property === 'og:title')[1] 21 | .content, 22 | url, 23 | date: formatDate(frontmatter.date), 24 | })) 25 | .sort((a, b) => b.date.time - a.date.time) 26 | }, 27 | }) 28 | 29 | function formatDate(raw: string): Post['date'] { 30 | const date = new Date(raw) 31 | date.setUTCHours(12) 32 | return { 33 | time: +date, 34 | string: date.toLocaleDateString('en-US', { 35 | year: 'numeric', 36 | month: 'long', 37 | day: 'numeric', 38 | }), 39 | } 40 | } -------------------------------------------------------------------------------- /blog/announcing-vite4-3.md: -------------------------------------------------------------------------------- 1 | --- 2 | title: Vite 4.3 is out! 3 | author: 4 | name: The Vite Team 5 | date: 2023-04-20 6 | sidebar: false 7 | head: 8 | - - meta 9 | - property: og:type 10 | content: website 11 | - - meta 12 | - property: og:title 13 | content: Announcing Vite 4.3 14 | - - meta 15 | - property: og:image 16 | content: https://vite.dev/og-image-announcing-vite4-3.png 17 | - - meta 18 | - property: og:url 19 | content: https://vite.dev/blog/announcing-vite4-3 20 | - - meta 21 | - property: og:description 22 | content: Vite 4.3 Release Announcement 23 | - - meta 24 | - name: twitter:card 25 | content: summary_large_image 26 | --- 27 | 28 | # Vite 4.3 is out! 29 | 30 | _April 20, 2023_ 31 | 32 | ![Vite 4.3 Announcement Cover Image](/og-image-announcing-vite4-3.png) 33 | 34 | Quick links: 35 | 36 | - Docs: [English](/), [简体中文](https://cn.vite.dev/), [日本語](https://ja.vite.dev/), [Español](https://es.vite.dev/), [Português](https://pt.vite.dev/) 37 | - [Vite 4.3 Changelog](https://github.com/vitejs/vite/blob/main/packages/vite/CHANGELOG.md#430-2023-04-20) 38 | 39 | ## Performance Improvements 40 | 41 | In this minor, we focused on improving the dev server performance. The resolve logic got streamlined, improving hot paths and implementing smarter caching for finding `package.json`, TS config files, and resolved URL in general. 42 | 43 | You can read a detailed walkthrough of the performance work done in this blog post by one of Vite Contributors: [How we made Vite 4.3 faaaaster 🚀](https://sun0day.github.io/blog/vite/why-vite4_3-is-faster.html). 44 | 45 | This sprint resulted in speed improvements across the board compared to Vite 4.2. 46 | 47 | These are the performance improvements as measured by [sapphi-red/performance-compare](https://github.com/sapphi-red/performance-compare), which tests an app with 1000 React Components cold and warm dev server startup time as well as HMR times for a root and a leaf component: 48 | 49 | | **Vite (babel)** | Vite 4.2 | Vite 4.3 | Improvement | 50 | | :----------------- | --------: | -------: | ----------: | 51 | | **dev cold start** | 17249.0ms | 5132.4ms | -70.2% | 52 | | **dev warm start** | 6027.8ms | 4536.1ms | -24.7% | 53 | | **Root HMR** | 46.8ms | 26.7ms | -42.9% | 54 | | **Leaf HMR** | 27.0ms | 12.9ms | -52.2% | 55 | 56 | | **Vite (swc)** | Vite 4.2 | Vite 4.3 | Improvement | 57 | | :----------------- | --------: | -------: | ----------: | 58 | | **dev cold start** | 13552.5ms | 3201.0ms | -76.4% | 59 | | **dev warm start** | 4625.5ms | 2834.4ms | -38.7% | 60 | | **Root HMR** | 30.5ms | 24.0ms | -21.3% | 61 | | **Leaf HMR** | 16.9ms | 10.0ms | -40.8% | 62 | 63 | ![Vite 4.3 vs 4.2 startup time comparison](/vite4-3-startup-time.png) 64 | 65 | ![Vite 4.3 vs 4.2 HMR time comparison](/vite4-3-hmr-time.png) 66 | 67 | You can read more information about the benchmark [here](https://gist.github.com/sapphi-red/25be97327ee64a3c1dce793444afdf6e). Specs and Versions for this performance run: 68 | 69 | - CPU: Ryzen 9 5900X, Memory: DDR4-3600 32GB, SSD: WD Blue SN550 NVME SSD 70 | - Windows 10 Pro 21H2 19044.2846 71 | - Node.js 18.16.0 72 | - Vite and React Plugin versions 73 | - Vite 4.2 (babel): Vite 4.2.1 + plugin-react 3.1.0 74 | - Vite 4.3 (babel): Vite 4.3.0 + plugin-react 4.0.0-beta.1 75 | - Vite 4.2 (swc): Vite 4.2.1 + plugin-react-swc 3.2.0 76 | - Vite 4.3 (swc): Vite 4.3.0 + plugin-react-swc 3.3.0 77 | 78 | Early adopters have also reported seeing 1.5x-2x dev startup time improvement on real apps while testing the Vite 4.3 beta. We'd love to know the results for your apps. 79 | 80 | ## Profiling 81 | 82 | We'll continue to work on Vite's performance. We're working on an official [Benchmark tool](https://github.com/vitejs/vite-benchmark) for Vite that let us get performance metrics for each Pull Request. 83 | 84 | And [vite-plugin-inspect](https://github.com/antfu/vite-plugin-inspect) now has more performance-related features to help you identify which plugins or middlewares are the bottleneck for your applications. 85 | 86 | Using `vite --profile` (and then pressing `p`) once the page loads will save a CPU profile of the dev server startup. You can open them in an app as [speedscope](https://www.speedscope.app/) to identify performance issues. And you can share your findings with the Vite Team in a [Discussion](https://github.com/vitejs/vite/discussions) or in [Vite's Discord](https://chat.vite.dev). 87 | 88 | ## Next Steps 89 | 90 | We decided to do a single Vite Major this year aligning with the [EOL of Node.js 16](https://endoflife.date/nodejs) in September, dropping support for both Node.js 14 and 16 in it. If you would like to get involved, we started a [Vite 5 Discussion](https://github.com/vitejs/vite/discussions/12466) to gather early feedback. -------------------------------------------------------------------------------- /changes/hotupdate-hook.md: -------------------------------------------------------------------------------- 1 | # HMR `hotUpdate` 플러그인 훅 {#hmr-hotupdate-plugin-hook} 2 | 3 | ::: tip 피드백 4 | [환경 API 피드백 논의](https://github.com/vitejs/vite/discussions/16358)에서 피드백을 남겨주세요. 5 | ::: 6 | 7 | [환경 API](/guide/api-environment.md)를 인식하고 `create`와 `delete` 이벤트를 추가로 처리할 수 있도록, `handleHotUpdate` 플러그인 훅을 [`hotUpdate` 훅](/guide/api-environment#the-hotupdate-hook)으로 대체할 예정입니다. 8 | 9 | 영향을 받는 범위: `Vite 플러그인 개발자` 10 | 11 | ::: warning 지원 중단 12 | `hotUpdate`는 `v6.0`에서 처음 도입되었습니다. `v7.0`에서 `handleHotUpdate` 지원이 중단될 예정입니다. 다만 아직은 `handleHotUpdate` 사용을 권장합니다. 실험해보고 피드백을 주고 싶다면, Vite 설정에서 `future.removePluginHookHandleHotUpdate`를 `"warn"`으로 설정할 수 있습니다. 13 | ::: 14 | 15 | ## 배경 {#motivation} 16 | 17 | [`handleHotUpdate` 훅](/guide/api-plugin.md#handlehotupdate)은 커스텀 HMR 업데이트 처리를 수행할 수 있게 해줍니다. 업데이트될 모듈 목록이 `HmrContext`로 전달됩니다: 18 | 19 | ```ts 20 | interface HmrContext { 21 | file: string 22 | timestamp: number 23 | modules: Array 24 | read: () => string | Promise 25 | server: ViteDevServer 26 | } 27 | ``` 28 | 29 | 그러나 이 훅은 모든 환경에서 한 번 호출되며, 전달된 모듈은 클라이언트와 SSR 환경에 대한 정보가 혼합되어 있습니다. 이제 프레임워크가 커스텀 환경으로 이동했기에, 각 환경에 대해 호출되는 새로운 훅이 필요해졌습니다. 30 | 31 | 새로운 `hotUpdate` 훅은 `handleHotUpdate`와 동일한 방식으로 작동하지만 각 환경에 대해 호출되며 새로운 `HotUpdateOptions` 인스턴스를 전달받습니다: 32 | 33 | ```ts 34 | interface HotUpdateOptions { 35 | type: 'create' | 'update' | 'delete' 36 | file: string 37 | timestamp: number 38 | modules: Array 39 | read: () => string | Promise 40 | server: ViteDevServer 41 | } 42 | ``` 43 | 44 | 이제 다른 플러그인 훅과 마찬가지로 `this.environment`를 통해 개발 환경에 접근할 수 있게 되었으며, `modules` 목록 역시 현재 환경에 대한 모듈 노드만을 포함합니다. 이를 통해 각 환경에 대한 업데이트는 서로 다른 전략을 취할 수 있습니다. 45 | 46 | 또한 이 훅은 `'update'`뿐만 아니라 추가적인 감시 이벤트에 대해서도 호출됩니다. `type`을 사용해 이들을 구분할 수 있습니다. 47 | 48 | ## 마이그레이션 가이드 {#migration-guide} 49 | 50 | 영향을 받는 모듈 목록을 필터링하고 좁혀서 HMR이 더 정확하게 동작하도록 합니다. 51 | 52 | ```js 53 | handleHotUpdate({ modules }) { 54 | return modules.filter(condition) 55 | } 56 | 57 | // 다음과 같이 마이그레이션: 58 | 59 | hotUpdate({ modules }) { 60 | return modules.filter(condition) 61 | } 62 | ``` 63 | 64 | 빈 배열을 반환해 전체 리로드를 수행: 65 | 66 | ```js 67 | handleHotUpdate({ server, modules, timestamp }) { 68 | // 수동으로 모듈 무효화 69 | const invalidatedModules = new Set() 70 | for (const mod of modules) { 71 | server.moduleGraph.invalidateModule( 72 | mod, 73 | invalidatedModules, 74 | timestamp, 75 | true 76 | ) 77 | } 78 | server.ws.send({ type: 'full-reload' }) 79 | return [] 80 | } 81 | 82 | // 다음과 같이 마이그레이션: 83 | 84 | hotUpdate({ modules, timestamp }) { 85 | // 수동으로 모듈 무효화 86 | const invalidatedModules = new Set() 87 | for (const mod of modules) { 88 | this.environment.moduleGraph.invalidateModule( 89 | mod, 90 | invalidatedModules, 91 | timestamp, 92 | true 93 | ) 94 | } 95 | this.environment.hot.send({ type: 'full-reload' }) 96 | return [] 97 | } 98 | ``` 99 | 100 | 빈 배열을 반환하고 클라이언트에 커스텀 이벤트를 전송해 완전히 커스텀한 HMR 처리를 수행: 101 | 102 | ```js 103 | handleHotUpdate({ server }) { 104 | server.ws.send({ 105 | type: 'custom', 106 | event: 'special-update', 107 | data: {} 108 | }) 109 | return [] 110 | } 111 | 112 | // 다음과 같이 마이그레이션: 113 | 114 | hotUpdate() { 115 | this.environment.hot.send({ 116 | type: 'custom', 117 | event: 'special-update', 118 | data: {} 119 | }) 120 | return [] 121 | } 122 | ``` -------------------------------------------------------------------------------- /changes/index.md: -------------------------------------------------------------------------------- 1 | # 주요 변경 사항 {#breaking-changes} 2 | 3 | API 지원 중단, 제거, 그리고 변경 사항을 포함한 Vite 주요 변경 사항 목록입니다. 아래 변경 사항 대부분은 Vite [`future` 옵션](/config/shared-options.html#future)을 통해 선택적으로 적용할 수 있습니다. 4 | 5 | ## 계획된 변경 사항 {#planned} 6 | 7 | 이러한 변경 사항들은 Vite의 다음 메이저 버전에서 적용될 예정입니다. 가능한 경우 지원 중단 또는 사용 관련 경고를 통해 안내할 예정이며, 프레임워크와 플러그인 개발자, 그리고 사용자들에게 이러한 변경 사항을 적용하도록 요청하고 있습니다. 8 | 9 | - _아직 계획된 변경 사항이 없습니다_ 10 | 11 | ## 검토 중인 변경 사항 {#considering} 12 | 13 | 아래 변경 사항들은 현재 검토 중이며, 대부분 사용 패턴을 개선하기 위한 실험적인 API입니다. 여기에 나열되지 않은 변경 사항도 있으므로, 전체 목록은 [Vite GitHub Discussions의 Experimental 레이블](https://github.com/vitejs/vite/discussions/categories/feedback?discussions_q=label%3Aexperimental+category%3AFeedback)을 확인해 주세요. 14 | 15 | 그리고 아직은 전환하는 것을 권장하지 않습니다. 이러한 API들은 피드백을 수집하기 위해 Vite에 포함되었습니다. 제안을 확인하고, 여러분의 사용 사례에서는 어떻게 동작하는지 GitHub Discussions에서 알려주시기 바랍니다. 16 | 17 | - [훅에서 `this.environment` 사용하기](/changes/this-environment-in-hooks) 18 | - [HMR `hotUpdate` 플러그인 훅](/changes/hotupdate-hook) 19 | - [환경별 API로 마이그레이션](/changes/per-environment-apis) 20 | - [`ModuleRunner` API를 사용하는 SSR](/changes/ssr-using-modulerunner) 21 | - [빌드 중 공유되는 플러그인](/changes/shared-plugins-during-build) 22 | 23 | ## 과거 변경 사항 {#past} 24 | 25 | 아래 변경 사항들은 이미 완료되었거나 철회되었습니다. 현재 메이저 버전에서는 더 이상 관련이 없습니다. 26 | 27 | - _아직 과거 변경 사항이 없습니다_ -------------------------------------------------------------------------------- /changes/per-environment-apis.md: -------------------------------------------------------------------------------- 1 | # 환경별 API로 마이그레이션 {#move-to-per-environment-apis} 2 | 3 | ::: tip 피드백 4 | [환경 API 피드백 논의](https://github.com/vitejs/vite/discussions/16358)에서 피드백을 남겨주세요. 5 | ::: 6 | 7 | 모듈 그래프 및 모듈 변환과 관련된 여러 `ViteDevServer` API가 `DevEnvironment` 인스턴스로 이동되었습니다. 8 | 9 | 영향을 받는 범위: `Vite 플러그인 개발자` 10 | 11 | ::: warning 지원 중단 12 | `Environment` 인스턴스는 `v6.0`에서 처음 도입되었습니다. `v7.0`에서 `server.moduleGraph` 및 현재 환경에 있는 다른 메서드들에 대한 지원이 중단될 예정입니다. 다만 아직은 서버 메서드 사용을 권장합니다. 이 변경 사항에 영향을 받는 코드를 미리 확인하고자 한다면, Vite 설정에서 다음과 같이 설정하세요. 13 | 14 | ```ts 15 | future: { 16 | removeServerModuleGraph: 'warn', 17 | removeServerTransformRequest: 'warn', 18 | } 19 | ``` 20 | 21 | ::: 22 | 23 | ## 배경 {#motivation} 24 | 25 | Vite v5 이전에는 하나의 Vite 개발 서버가 항상 두 개의 환경(`client`와 `ssr`)을 갖고 있었습니다. `server.moduleGraph`는 이 두 환경에 대한 모듈이 혼합되어 있었습니다. 노드들은 `clientImportedModules`와 `ssrImportedModules` 목록을 통해 연결되어 있었으며(각각에 대해 하나의 `importers` 목록이 유지됨), 변환된 모듈은 `id`와 `ssr` 불리언 값으로 표현되었습니다. 그리고 이 불리언 값은 `server.moduleGraph.getModuleByUrl(url, ssr)`과 `server.transformRequest(url, { ssr })`와 같은 API에 전달되어야 했습니다. 26 | 27 | Vite v6에서는 임의의 수의 커스텀 환경(`client`, `ssr`, `edge` 등)을 생성할 수 있습니다. 따라서 단일 `ssr` 불리언 값으로는 더 이상 충분하지 않습니다. `server.transformRequest(url, { environment })`와 같은 형태로 API를 변경하는 대신, 이러한 메서드들을 환경 인스턴스로 이동하여 Vite 개발 서버 없이도 호출할 수 있도록 했습니다. 28 | 29 | ## 마이그레이션 가이드 {#migration-guide} 30 | 31 | - `server.moduleGraph` -> [`environment.moduleGraph`](/guide/api-environment#separate-module-graphs) 32 | - `server.transformRequest(url, ssr)` -> `environment.transformRequest(url)` 33 | - `server.warmupRequest(url, ssr)` -> `environment.warmupRequest(url)` -------------------------------------------------------------------------------- /changes/shared-plugins-during-build.md: -------------------------------------------------------------------------------- 1 | # 빌드 중 공유되는 플러그인 {#shared-plugins-during-build} 2 | 3 | ::: tip 피드백 4 | [환경 API 피드백 논의](https://github.com/vitejs/vite/discussions/16358)에서 피드백을 남겨주세요. 5 | ::: 6 | 7 | [빌드 중 공유되는 플러그인](/guide/api-environment-plugins.md#shared-plugins-during-build)을 참고하세요. 8 | 9 | 영향을 받는 범위: `Vite 플러그인 개발자` 10 | 11 | ::: warning 기본값 변경 12 | `builder.sharedConfigBuild`는 `v6.0`에서 처음 도입되었습니다. 플러그인이 공유 설정에서 어떻게 동작하는지 확인하려면 이 값을 `true`로 설정해 주세요. 플러그인 생태계가 준비된다면 향후 메이저 버전에서 기본값을 변경하는 것에 대한 피드백을 받을 예정입니다. 13 | ::: 14 | 15 | ## 배경 {#motivation} 16 | 17 | 개발 환경과 빌드 플러그인 파이프라인을 일치시키고자 합니다. 18 | 19 | ## 마이그레이션 가이드 {#migration-guide} 20 | 21 | 환경 간 플러그인을 공유하려면, 플러그인의 상태가 현재 환경에 따라 구분되어야 합니다. 먼저 아래는 이를 구분하지 않고 모든 환경에 대해 변환된 모듈 수를 카운트하는 플러그인입니다. 22 | 23 | ```js 24 | function CountTransformedModulesPlugin() { 25 | let transformedModules 26 | return { 27 | name: 'count-transformed-modules', 28 | buildStart() { 29 | transformedModules = 0 30 | }, 31 | transform(id) { 32 | transformedModules++ 33 | }, 34 | buildEnd() { 35 | console.log(transformedModules) 36 | }, 37 | } 38 | } 39 | ``` 40 | 41 | 환경별 변환된 모듈 수를 카운트하려면 map 객체를 사용해야 합니다: 42 | 43 | ```js 44 | function PerEnvironmentCountTransformedModulesPlugin() { 45 | const state = new Map() 46 | return { 47 | name: 'count-transformed-modules', 48 | perEnvironmentStartEndDuringDev: true, 49 | buildStart() { 50 | state.set(this.environment, { count: 0 }) 51 | } 52 | transform(id) { 53 | state.get(this.environment).count++ 54 | }, 55 | buildEnd() { 56 | console.log(this.environment.name, state.get(this.environment).count) 57 | } 58 | } 59 | } 60 | ``` 61 | 62 | 이를 단순화하기 위해, Vite는 `perEnvironmentState` 헬퍼를 제공합니다: 63 | 64 | ```js 65 | function PerEnvironmentCountTransformedModulesPlugin() { 66 | const state = perEnvironmentState<{ count: number }>(() => ({ count: 0 })) 67 | return { 68 | name: 'count-transformed-modules', 69 | perEnvironmentStartEndDuringDev: true, 70 | buildStart() { 71 | state(this).count = 0 72 | } 73 | transform(id) { 74 | state(this).count++ 75 | }, 76 | buildEnd() { 77 | console.log(this.environment.name, state(this).count) 78 | } 79 | } 80 | } 81 | ``` -------------------------------------------------------------------------------- /changes/ssr-using-modulerunner.md: -------------------------------------------------------------------------------- 1 | # ModuleRunner API를 사용하는 SSR {#ssr-using-modulerunner-api} 2 | 3 | ::: tip 피드백 4 | [환경 API 피드백 논의](https://github.com/vitejs/vite/discussions/16358)에서 피드백을 남겨주세요. 5 | ::: 6 | 7 | `server.ssrLoadModule`이 [ModuleRunner](/guide/api-environment#modulerunner)를 통한 임포트로 대체되었습니다. 8 | 9 | 영향을 받는 범위: `Vite 플러그인 개발자` 10 | 11 | ::: warning 지원 중단 12 | `ModuleRunner`는 `v6.0`에서 처음 도입되었습니다. 향후 메이저 버전에서 `server.ssrLoadModule`이 지원 중단될 예정입니다. 이 변경 사항에 영향을 받는 코드를 미리 확인하고자 한다면, Vite 설정에서 `future.removeSsrLoadModule`을 `"warn"`으로 설정하세요. 13 | ::: 14 | 15 | ## 배경 {#motivation} 16 | 17 | `server.ssrLoadModule(url)`은 `ssr` 환경에서만 모듈을 임포트할 수 있었고, Vite 개발 서버와 동일한 프로세스에서만 모듈을 실행할 수 있었습니다. 커스텀 환경을 가진 앱의 경우, 각 환경은 별도의 스레드나 프로세스에서 실행될 수 있는 `ModuleRunner`와 연결됩니다. 이러한 환경에서는 `moduleRunner.import(url)`를 통해 모듈을 임포트할 수 있습니다. 18 | 19 | ## 마이그레이션 가이드 {#migration-guide} 20 | 21 | [프레임워크를 위한 환경 API 가이드](../guide/api-environment-frameworks.md)를 참고하세요. -------------------------------------------------------------------------------- /changes/this-environment-in-hooks.md: -------------------------------------------------------------------------------- 1 | # 훅에서 `this.environment` 사용하기 {#this-environment-in-hooks} 2 | 3 | ::: tip 피드백 4 | [환경 API 피드백 논의](https://github.com/vitejs/vite/discussions/16358)에서 피드백을 남겨주세요. 5 | ::: 6 | 7 | Vite 6 이전에는 `client`와 `ssr` 두 가지 환경만 사용할 수 있었습니다. 플러그인 개발자는 `options.ssr` 인자를 통해 모듈을 처리할 때 `resolveId`, `load`, `transform` 플러그인 훅에서 이 두 환경을 구분했습니다. Vite 6에서는 Vite 애플리케이션이 필요한만큼 환경을 정의할 수 있게 되었습니다. 따라서 플러그인 컨텍스트에 `this.environment`를 도입해, 훅에서 현재 모듈의 환경과 상호작용 할 수 있도록 했습니다. 8 | 9 | 영향을 받는 범위: `Vite 플러그인 개발자` 10 | 11 | ::: warning 지원 중단 12 | `this.environment`는 `v6.0`에서 도입되었습니다. `v7.0`에서 `options.ssr` 지원이 중단될 예정입니다. 그 시점에 새로운 API를 사용하도록 플러그인 마이그레이션을 권장하고자 합니다. 이 변경 사항에 영향을 받는 코드를 미리 확인하고자 한다면, Vite 설정에서 `future.removePluginHookSsrArgument`를 `"warn"`으로 설정하세요. 13 | ::: 14 | 15 | ## 배경 {#motivation} 16 | 17 | `this.environment`는 플러그인 훅 구현 시 현재 환경 이름을 알 수 있게 할 뿐만 아니라, 환경 설정 옵션, 모듈 그래프 정보, 변환 파이프라인(`environment.config`, `environment.moduleGraph`, `environment.transformRequest()`)에도 접근할 수 있게 해줍니다. 컨텍스트에서 환경 인스턴스를 사용할 수 있게 함으로써, 플러그인 개발자가 전체 개발 서버에 대한 의존성을 피할 수 있게 됩니다(일반적으로 `configureServer` 훅을 통해 시작 시 캐시됨). 18 | 19 | ## 마이그레이션 가이드 {#migration-guide} 20 | 21 | 기존 플러그인을 빠르게 마이그레이션하려면 `resolveId`, `load`, `transform` 훅에서 `options.ssr` 인자를 `this.environment.name !== 'client'`로 대체하세요: 22 | 23 | ```ts 24 | import { Plugin } from 'vite' 25 | 26 | export function myPlugin(): Plugin { 27 | return { 28 | name: 'my-plugin', 29 | resolveId(id, importer, options) { 30 | const isSSR = options.ssr // [!code --] 31 | const isSSR = this.environment.name !== 'client' // [!code ++] 32 | 33 | if (isSSR) { 34 | // SSR 관련 로직 35 | } else { 36 | // 클라이언트 관련 로직 37 | } 38 | }, 39 | } 40 | } 41 | ``` 42 | 43 | 더 견고하고 장기적인 구현을 위해서는, 환경 이름에 의존하는 대신 [여러 환경](/guide/api-environment.html#accessing-the-current-environment-in-hooks)을 위한 세분화된 환경 옵션을 사용해 플러그인 훅을 처리해야 합니다. -------------------------------------------------------------------------------- /config/dep-optimization-options.md: -------------------------------------------------------------------------------- 1 | # 디펜던시 최적화 옵션 {#dep-optimization-options} 2 | 3 | - **관련 항목:** [사전 번들링된 디펜던시](/guide/dep-pre-bundling) 4 | 5 | 별도로 명시되지 않은 한, 이 섹션의 옵션들은 개발 환경에서만 사용되는 디펜던시 최적화 도구에만 적용됩니다. 6 | 7 | ## optimizeDeps.entries {#optimizedeps-entries} 8 | 9 | - **타입:** `string | string[]` 10 | 11 | 기본적으로 Vite는 모든 `.html` 파일을 크롤링해 사전 번들링이 필요한 디펜던시를 탐지합니다(`node_modules`, `build.outDir`, `__tests__` 및 `coverage` 디렉터리는 무시). 만약 `build.rollupOptions.input`이 지정된 경우 Vite가 대신 해당 진입점을 탐색합니다. 12 | 13 | 둘 다 필요에 맞지 않는다면 이 옵션을 사용해 진입점을 지정할 수 있습니다. 이 값은 [`tinyglobby` 패턴](https://github.com/SuperchupuDev/tinyglobby) 또는 Vite 프로젝트 루트를 기준으로 상대 경로 패턴의 배열 값이 될 수 있습니다. 이렇게 되면 기존에 사용하던 진입점 추론 방식을 덮어쓰게 됩니다. `optimizeDeps.entries`가 명시적으로 정의된 경우에는 기본적으로 `node_modules` 및 `build.outDir` 디렉터리만 무시됩니다. 다른 폴더를 추가로 무시하고자 하는 경우에는 진입점 리스트 요소에 `!` 로 시작하는 무시 패턴을 사용할 수 있습니다. `node_modules` 및 `build.outDir` 디렉터리를 무시하고 싶지 않다면, `tinyglobby` 패턴 없이 리터럴 문자열 경로를 사용해 주세요. 14 | 15 | ## optimizeDeps.exclude {#optimizedeps-exclude} 16 | 17 | - **타입:** `string[]` 18 | 19 | 사전 번들링에서 제외할 디펜던시 목록입니다. 20 | 21 | :::warning CommonJS 22 | CommonJS 디펜던시는 최적화에서 제외돼서는 안 됩니다. ESM 디펜던시가 최적화에서 제외되었지만 이와 중첩된(Nested) CommonJS 디펜던시가 있는 경우, CommonJS 디펜던시를 `optimizeDeps.include`에 추가해줘야 합니다: 23 | 24 | ```js twoslash 25 | import { defineConfig } from 'vite' 26 | // ---cut--- 27 | export default defineConfig({ 28 | optimizeDeps: { 29 | include: ['esm-dep > cjs-dep'], 30 | }, 31 | }) 32 | ``` 33 | 34 | ::: 35 | 36 | ## optimizeDeps.include {#optimizedeps-include} 37 | 38 | - **타입:** `string[]` 39 | 40 | 기본적으로 `node_modules` 내부에 없는 연결된 패키지들은 미리 번들로 제공되지 않습니다. 이 옵션을 사용하여 연결된 패키지를 미리 번들로 묶을 수 있습니다. 41 | 42 | 많은 수의 라이브러리를 디렉터리 깊은 곳에서까지 가져와야 하는 경우, 끝에 Glob 패턴을 지정해 모든 라이브러리를 한 번에 사전 번들로 묶을 수 있습니다. 이렇게 하면 유사한 라이브러리를 가져올 때마다 반복적으로 사전 번들링을 수행하는 것을 피할 수 있습니다. [이에 대한 피드백은 여기에 남겨주세요](https://github.com/vitejs/vite/discussions/15833). 예를 들어 다음과 같이 사용할 수 있습니다: 43 | 44 | ```js twoslash 45 | import { defineConfig } from 'vite' 46 | // ---cut--- 47 | export default defineConfig({ 48 | optimizeDeps: { 49 | include: ['my-lib/components/**/*.vue'], 50 | }, 51 | }) 52 | ``` 53 | 54 | ## optimizeDeps.esbuildOptions {#optimizedeps-esbuildoptions} 55 | 56 | - **타입:** [`Omit`](https://www.typescriptlang.org/docs/handbook/utility-types.html#omittype-keys)`<`[`EsbuildBuildOptions`](https://esbuild.github.io/api/#general-options)`, 57 | | 'bundle' 58 | | 'entryPoints' 59 | | 'external' 60 | | 'write' 61 | | 'watch' 62 | | 'outdir' 63 | | 'outfile' 64 | | 'outbase' 65 | | 'outExtension' 66 | | 'metafile'>` 67 | 68 | 디펜던시 스캐닝 및 최적화 중 Esbuild에 전달할 옵션입니다. 69 | 70 | 특정 옵션은 Vite의 디펜던시 최적화와 호환되지 않기에 생략되었습니다. 71 | 72 | - `external`은 생략됩니다. 이 대신 Vite의 `optimizeDeps.exclude` 옵션을 사용합니다. 73 | - `plugins`는 Vite의 디펜던시 플러그인과 병합됩니다. 74 | 75 | ## optimizeDeps.force {#optimizedeps-force} 76 | 77 | - **타입:** `boolean` 78 | 79 | `true`로 설정하면 최적화되어 캐시된 디펜던시들을 무시하고, 디펜던시 사전 번들링을 강제로 실행합니다. 80 | 81 | ## optimizeDeps.holdUntilCrawlEnd {#optimizedeps-holduntilcrawlend} 82 | 83 | - **실험적 기능**: [이 곳에 피드백을 남겨주세요](https://github.com/vitejs/vite/discussions/15834) 84 | - **타입:** `boolean` 85 | - **기본값:** `true` 86 | 87 | 이 옵션이 활성화되어 있으면 콜드 스타트 시 모든 정적 에셋이 크롤링될 때까지 디펜던시 최적화가 완료되지 않습니다. 이는 크롤링 도중 새로운 디펜던시가 발견되어 공통 청크를 다시 만들어야 하는 경우 전체 페이지를 다시 로드해야 하는 상황을 피할 수 있습니다(자세한 설명은 [이 코멘트](https://github.com/vitejs/vite/pull/8869#issuecomment-1172902125)를 참고해 주세요. - 옮긴이). 만약 디펜던시 스캐너로 `include`에 정의된 목록을 포함해 모든 디펜던시를 찾을 수 있다면, 브라우저가 병렬로 더 많은 요청을 처리할 수 있도록 이 옵션을 비활성화하는 것이 좋습니다. 88 | 89 | ## optimizeDeps.disabled {#optimizedeps-disabled} 90 | 91 | - **지원 중단 예정** 92 | - **실험적 기능:** [이 곳에 피드백을 남겨주세요](https://github.com/vitejs/vite/discussions/13839) 93 | - **타입:** `boolean | 'build' | 'dev'` 94 | - **기본값:** `'build'` 95 | 96 | 이 옵션은 더 이상 사용되지 않습니다. Vite 5.1부터 빌드 중 수행되는 디펜던시 사전 번들링이 제거되었습니다. `optimizeDeps.disabled`를 `true` 또는 `'dev'`로 설정하면 최적화가 비활성화되고, `false` 또는 `'build'`로 설정하면 개발 모드에서 최적화가 활성화됩니다. 97 | 98 | 최적화를 완전히 비활성화하려면, `optimizeDeps.noDiscovery: true`를 사용해 디펜던시 자동 탐색을 허용하지 않고, `optimizeDeps.include`를 정의하지 않거나 비워두세요. 99 | 100 | :::warning 101 | 빌드 중 디펜던시를 최적화하는 것은 **실험적** 기능이었습니다. 이 전략을 시도하는 프로젝트는 `build.commonjsOptions: { include: [] }`를 사용해 `@rollup/plugin-commonjs`를 제거해야 합니다. 이렇게 했다면 번들링 중 CJS 패키지를 지원하기 위해 다시 활성화하도록 안내하는 경고가 표시됩니다. 102 | ::: 103 | 104 | ## optimizeDeps.needsInterop {#optimizedeps-needsinterop} 105 | 106 | - **실험적 기능** 107 | - **타입:** `string[]` 108 | 109 | 명시된 디펜던시를 가져올 때 ESM 상호 운용을 강제합니다. Vite는 디펜던시가 상호 운용 필요한지를 정확하게 감지할 수 있기 때문에 이 옵션은 일반적으로 필요하지 않습니다. 그러나 디펜던시들의 다양한 조합에 따라 이들 중 일부는 사전 번들링이 다르게 적용될 수 있습니다. 이 패키지들을 `needsInterop`에 추가하면 전체 페이지에 대한 리로드를 피하고 콜드 스타트를 가속할 수 있습니다. 만약 사용하는 디펜던시가 이 상황에 해당한다면, 설정 파일에 이 패키지 이름을 추가하라는 경고가 표시됩니다. -------------------------------------------------------------------------------- /config/index.md: -------------------------------------------------------------------------------- 1 | --- 2 | title: Vite 설정하기 3 | --- 4 | 5 | # Vite 설정하기 {#configuring-vite} 6 | 7 | 명령 줄에서 `vite`를 실행시킬 때, Vite는 자동으로 [프로젝트 루트](/guide/#index-html-and-project-root)의 `vite.config.js` 파일 확인을 시도합니다. (다른 JS 및 TS 확장도 지원) 8 | 9 | 가장 기본적인 설정 파일의 내용은 다음과 같습니다: 10 | 11 | ```js [vite.config.js] 12 | export default { 13 | // 설정 옵션들 14 | } 15 | ``` 16 | 17 | 참고로 Vite는 프로젝트가 네이티브 Node ESM을 사용하지 않는 경우에도 설정 파일에서 ES 모듈 구문을 사용할 수 있도록 지원하고 있습니다(예: `package.json`의 `type: "module"`). 이 때 설정 파일은 사용되기 전에 자동으로 미리 처리됩니다. 18 | 19 | 또한 `--config` CLI 옵션을 사용하여 명시적으로 특정 설정 파일을 지정할 수도 있습니다. (경로는 `cwd`를 기준으로 하여 상대적으로 처리됩니다.) 20 | 21 | ```bash 22 | vite --config my-config.js 23 | ``` 24 | 25 | ::: tip 설정 파일 로딩 26 | 기본적으로 Vite는 `esbuild`를 사용해 설정 파일을 임시 파일로 번들링한 뒤 로드합니다. 다만 이는 모노리포에서 TypeScript 파일을 불러올 때 문제가 발생할 수 있습니다. 이러한 문제가 발생한다면 `--configLoader runner`를 지정해 [모듈 러너](/guide/api-environment-runtimes.html#modulerunner)를 대신 사용할 수 있습니다. 모듈 러너는 임시 설정 파일을 생성하지 않고 파일을 즉시 변환합니다. 참고로 모듈 러너는 설정 파일에서 CJS를 지원하지 않으나, 그럼에도 외부 CJS 패키지는 정상적으로 동작합니다. 27 | 28 | 또는 TypeScript를 지원하는 환경(예: `node --experimental-strip-types`)을 사용하거나 순수 JavaScript만 작성하는 경우, `--configLoader native`를 지정하여 현재 환경의 네이티브 런타임으로 설정 파일을 로드할 수 있습니다. 단, 설정 파일에서 불러온 모듈의 업데이트는 감지되지 않으므로 Vite 서버가 자동으로 재시작되지 않습니다. 29 | ::: 30 | 31 | ## 인텔리센스 설정 {#config-intellisense} 32 | 33 | Vite는 TypeScript 타입을 포함하고 있기 때문에, jsdoc 힌트를 통해 IDE 인텔리센스를 활용할 수 있습니다: 34 | 35 | ```js 36 | /** @type {import('vite').UserConfig} */ 37 | export default { 38 | // ... 39 | } 40 | ``` 41 | 42 | 또는, jsdoc 대신 `defineConfig` 도우미 함수를 통해 인텔리센스를 활용할 수 있습니다: 43 | 44 | ```js 45 | import { defineConfig } from 'vite' 46 | 47 | export default defineConfig({ 48 | // ... 49 | }) 50 | ``` 51 | 52 | TypeScript 설정 파일 또한 지원합니다. 위 `defineConfig` 도우미 함수 또는 `satisfies` 연산자를 사용해 `vite.config.ts` 파일을 사용할 수 있습니다: 53 | 54 | ```ts 55 | import type { UserConfig } from 'vite' 56 | 57 | export default { 58 | // ... 59 | } satisfies UserConfig 60 | ``` 61 | 62 | ## 조건부 설정 {#conditional-config} 63 | 64 | 만약 설정에서 명령(`serve` 또는 `build`), 사용 중인 [모드](/guide/env-and-mode#modes), SSR 빌드 여부(`isSsrBuild`), 또는 빌드 프리뷰(`isPreview`) 여부에 따라 조건부로 옵션을 결정해야 하는 경우, 아래와 같이 함수를 내보낼 수 있습니다: 65 | 66 | ```js twoslash 67 | import { defineConfig } from 'vite' 68 | // ---cut--- 69 | export default defineConfig(({ command, mode, isSsrBuild, isPreview }) => { 70 | if (command === 'serve') { 71 | return { 72 | // 개발 서버 설정 73 | } 74 | } else { 75 | // command === 'build' 76 | return { 77 | // 빌드 설정 78 | } 79 | } 80 | }) 81 | ``` 82 | 83 | Vite의 API에서 `command` 값은 개발 서버(CLI [`vite`](/guide/cli#vite)는 `vite dev` 및 `vite serve`의 별칭)에서 `serve`이며, 프로덕션으로 빌드 시([`vite build`](/guide/cli#vite-build))에는 `build`가 들어가게 됩니다. 84 | 85 | `isSsrBuild`와 `isPreview`는 각각 `build`와 `serve` 명령을 구분하기 위한 추가적인 선택적 플래그입니다. Vite 설정을 불러오는 일부 툴은 이러한 플래그를 지원하지 않을 수 있으며, 이 경우에는 `undefined`를 전달합니다. 따라서 `true`와 `false`에 대한 명시적인 비교를 사용하는 것이 좋습니다. 86 | 87 | ## 비동기 설정 {#async-config} 88 | 89 | 만약 설정에서 비동기 함수를 호출해야 하는 경우, 이 대신 비동기 함수를 내보낼 수 있습니다. 또한 이 비동기 함수는 인텔리센스 지원을 위해 `defineConfig`를 통해 전달할 수도 있습니다: 90 | 91 | ```js twoslash 92 | import { defineConfig } from 'vite' 93 | // ---cut--- 94 | export default defineConfig(async ({ command, mode }) => { 95 | const data = await asyncFunction() 96 | return { 97 | // Vite 설정 값 전달 98 | } 99 | }) 100 | ``` 101 | 102 | ## 설정에서 환경 변수 사용하기 {#using-environment-variables-in-config} 103 | 104 | 환경 변수 역시 `process.env` 객체를 통해 가져올 수 있습니다. 105 | 106 | 참고로 Vite는 Vite의 설정을 끝마친 뒤 어떻게 파일을 불러올 것인지 알 수 있기 때문에, 기본적으로 `.env` 파일을 로드하지 않습니다. 가령 `root` 또는 `envDir` 설정 값에 따라 어떻게 파일을 불러올 것인지 달라집니다. 다만 필요하다면 `loadEnv` 헬퍼를 사용해 `.env` 파일을 불러올 수도 있습니다. 107 | 108 | ```js twoslash 109 | import { defineConfig, loadEnv } from 'vite' 110 | 111 | export default defineConfig(({ mode }) => { 112 | // 현재 작업 디렉터리의 `mode`를 기반으로 env 파일을 불러옴 113 | // 세 번째 매개변수를 ''로 설정하면 `VITE_` 접두사에 관계없이 114 | // 모든 환경 변수를 불러옴 115 | const env = loadEnv(mode, process.cwd(), '') 116 | return { 117 | // Vite 설정 118 | define: { 119 | __APP_ENV__: JSON.stringify(env.APP_ENV), 120 | } 121 | } 122 | }) 123 | ``` 124 | 125 | ## VS Code에서 설정 파일 디버깅하기 {#debugging-the-config-file-on-vs-code} 126 | 127 | 기본 설정인 `--configLoader bundle` 모드에서, Vite는 `node_modules/.vite-temp` 폴더에 임시 설정 파일을 작성합니다. 이 경우 중단점을 이용해 Vite 설정 파일을 디버깅하면 파일을 찾을 수 없다는 오류가 발생합니다. 이 문제는 다음과 같이 `.vscode/settings.json` 설정을 추가해 해결할 수 있습니다: 128 | 129 | ```json 130 | { 131 | "debug.javascript.terminalOptions": { 132 | "resolveSourceMapLocations": [ 133 | "${workspaceFolder}/**", 134 | "!**/node_modules/**", 135 | "**/node_modules/.vite-temp/**" 136 | ] 137 | } 138 | } 139 | ``` -------------------------------------------------------------------------------- /config/preview-options.md: -------------------------------------------------------------------------------- 1 | # 프리뷰 옵션 {#preview-options} 2 | 3 | 별도로 명시되지 않은 한, 이 섹션의 옵션들은 프리뷰에만 적용됩니다. 4 | 5 | ## preview.host {#preview-host} 6 | 7 | - **타입:** `string | boolean` 8 | - **기본값:** [`server.host`](./server-options#server-host) 9 | 10 | 어떤 IP 주소를 대상으로 서버가 수신 대기(Listen)하는지 지정합니다. 11 | `0.0.0.0` 또는 `true`로 설정된 경우 LAN 및 공용 주소를 포함한 모든 주소를 대상으로 합니다. 12 | 13 | CLI의 경우 `--host 0.0.0.0` 또는 `--host`로 지정이 가능합니다. 14 | 15 | ::: tip 참고 16 | 17 | Vite 대신 다른 서버가 응답하는 경우가 있습니다. 18 | 이에 대해서는 [`server.host`](./server-options#server-host)를 참고해주세요. 19 | 20 | ::: 21 | 22 | ## preview.allowedHosts {#preview-allowedhosts} 23 | 24 | - **타입:** `string | true` 25 | - **기본값:** [`server.allowedHosts`](./server-options#server-allowedhosts) 26 | 27 | Vite가 응답할 수 있는 호스트 이름 목록입니다. 28 | 29 | 자세한 내용은 [`server.allowedHosts`](./server-options#server-allowedhosts)를 참고해 주세요. 30 | 31 | ## preview.port {#preview-port} 32 | 33 | - **타입:** `number` 34 | - **기본값:** `4173` 35 | 36 | 서버의 포트를 지정합니다. 포트가 이미 사용 중이면 Vite가 자동으로 사용 가능한 다음 포트로 설정되기에 실제 서버 포트가 아닐 수 있습니다. 37 | 38 | **예제:** 39 | 40 | ```js 41 | export default defineConfig({ 42 | server: { 43 | port: 3030 44 | }, 45 | preview: { 46 | port: 8080 47 | } 48 | }) 49 | ``` 50 | 51 | ## preview.strictPort {#preview-strictport} 52 | 53 | - **타입:** `boolean` 54 | - **기본값:** [`server.strictPort`](./server-options#server-strictport) 55 | 56 | `true`로 설정한 경우, 포트가 이미 사용 중일 때 자동으로 다른 포트로 설정을 시도하지 않고 종료되도록 합니다. 57 | 58 | ## preview.https {#preview-https} 59 | 60 | - **타입:** `https.ServerOptions` 61 | - **기본값:** [`server.https`](./server-options#server-https) 62 | 63 | TLS + HTTP/2를 활성화합니다. 64 | 65 | 자세한 내용은 [`server.https`](./server-options#server-https)를 참고해 주세요. 66 | 67 | ## preview.open {#preview-open} 68 | 69 | - **타입:** `boolean | string` 70 | - **기본값:** [`server.open`](./server-options#server-open) 71 | 72 | 서버 시작 시 자동으로 브라우저를 열도록 설정할 수 있습니다. 값이 문자열인 경우 URL 경로를 의미하며, 원하는 특정 브라우저를 열고자 하는 경우에는 `process.env.BROWSER` 환경 변수를 `firefox`와 같은 값으로 설정하면 됩니다. `process.env.BROWSER_ARGS` 환경 변수를 통해 추가적인 인자를 전달할 수도 있습니다(예: `--incognito`). 73 | 74 | `BROWSER`와 `BROWSER_ARGS`는 `.env` 파일에서 설정할 수 있는 특별한 환경 변수입니다. 자세한 내용은 [`open` 패키지](https://github.com/sindresorhus/open#app)를 참고해주세요. 75 | 76 | ## preview.proxy {#preview-proxy} 77 | 78 | - **타입:** `Record` 79 | - **기본값:** [`server.proxy`](./server-options#server-proxy) 80 | 81 | 프리뷰 서버에 대한 커스텀 프록시 규칙을 설정할 수 있습니다. `{ key: options }` 형태로 구성되며, 키값이 `^`로 시작하는 경우 `RegExp`로 해석됩니다. `configure` 옵션을 사용하여 프록시 인스턴스에 접근할 수 있습니다. 82 | 83 | 이는 [`http-proxy`](https://github.com/http-party/node-http-proxy)를 사용하며, 더 많은 옵션은 [이 링크](https://github.com/http-party/node-http-proxy#options)를 참고해주세요. 84 | 85 | ## preview.cors {#preview-cors} 86 | 87 | - **타입:** `boolean | CorsOptions` 88 | - **기본값:** [`server.cors`](./server-options#server-cors) 89 | 90 | 프리뷰 서버에 대한 CORS를 구성합니다. 91 | 92 | 자세한 내용은 [`server.cors`](./server-options#server-cors)를 참고해 주세요. 93 | 94 | ## preview.headers {#preview-headers} 95 | 96 | - **타입:** `OutgoingHttpHeaders` 97 | 98 | 서버 응답 헤더를 지정합니다. -------------------------------------------------------------------------------- /config/ssr-options.md: -------------------------------------------------------------------------------- 1 | # SSR 옵션 {#ssr-options} 2 | 3 | 별도로 명시되지 않은 한, 이 섹션의 옵션들은 개발과 빌드 모두에게 적용됩니다. 4 | 5 | ## ssr.external {#ssr-external} 6 | 7 | - **타입:** `string[] | true` 8 | - **관련 항목:** [SSR Externals](/guide/ssr#ssr-externals) 9 | 10 | SSR을 위한 디펜던시와 이들의 전이 디펜던시(설치한 디펜던시가 갖고 있는 디펜던시 - 옮긴이)를 외부화합니다. 기본적으로 (HMR을 위해)링크된 디펜던시를 제외한 모든 디펜던시가 외부화됩니다. 만약 링크된 디펜던시를 외부화하길 원한다면, 이 옵션에 디펜던시 이름을 전달해 주세요. 11 | 12 | `true`인 경우, 링크된 디펜던시를 포함한 모든 디펜던시가 외부화됩니다. 13 | 14 | `string[]` 타입을 사용한 경우, `ssr.noExternal`에 해당 디펜던시가 어떤 타입으로 존재하더라도 항상 우선권을 갖습니다. 15 | 16 | ## ssr.noExternal {#ssr-noexternal} 17 | 18 | - **타입:** `string | RegExp | (string | RegExp)[] | true` 19 | - **관련 항목:** [SSR Externals](/guide/ssr#ssr-externals) 20 | 21 | 이 옵션으로 전달된 디펜던시는 SSR을 위해 외부화되지 않고 빌드 시 번들로 제공됩니다. 기본적으로 (HMR을 위해)링크된 디펜던시만 외부화되지 않습니다. 만약 링크된 디펜던시를 외부화하길 원한다면, `ssr.external` 옵션에 디펜던시 이름을 전달해 주세요. 22 | 23 | `true`인 경우, 모든 디펜던시가 외부화되지 않습니다. 다만 `ssr.external`에 `string[]` 타입으로 나열된 디펜던시는 우선권을 갖고 외부화됩니다. `ssr.target: 'node'`로 설정되어 있으면, 기본적으로 Node.js 내장 기능도 외부화됩니다. 24 | 25 | 만약 `ssr.noExternal: true`와 `ssr.external: true`가 모두 설정되어 있다면, `ssr.noExternal`이 우선권을 갖고 모든 디펜던시가 외부화되지 않습니다. 26 | 27 | ## ssr.target {#ssr-target} 28 | 29 | - **타입:** `'node' | 'webworker'` 30 | - **기본값:** `node` 31 | 32 | SSR 서버를 위한 빌드 타깃입니다. 33 | 34 | ## ssr.resolve.conditions {#ssr-resolve-conditions} 35 | 36 | - **타입:** `string[]` 37 | - **기본값:** `['module', 'node', 'development|production']` (`defaultClientConditions`) (`ssr.target === 'webworker'` 이면 `['module', 'browser', 'development|production']` (`defaultClientConditions`)) 38 | - **관련 항목:** [Resolve Conditions](./shared-options.md#resolve-conditions) 39 | 40 | 이 조건은 플러그인 파이프라인에서 사용되며, SSR 빌드 중에 외부화되지 않은 디펜던시에만 영향을 미칩니다. 외부화된 임포트에 영향을 미치려면 `ssr.resolve.externalConditions`를 사용하세요. 41 | 42 | ## ssr.resolve.externalConditions {#ssr-resolve-externalconditions} 43 | 44 | - **타입:** `string[]` 45 | - **기본값:** `['node']` 46 | 47 | 외부화된 직접 디펜던시(Vite에 의해 임포트된 외부 디펜던시)의 SSR 임포트(`ssrLoadModule` 포함) 중에 사용되는 조건입니다. 48 | 49 | :::tip 50 | 51 | 이 옵션을 사용할 때는 개발과 빌드 모두 동일한 값을 전달하고 Node를 [`--conditions` 플래그](https://nodejs.org/docs/latest/api/cli.html#-c-condition---conditionscondition)와 함께 실행해야 일관된 동작을 수행합니다. 52 | 53 | 예를 들어, `['node', 'custom']`을 설정할 때는 개발 시에는 `NODE_OPTIONS='--conditions custom' vite`를, 빌드 후에는 `NODE_OPTIONS="--conditions custom" node ./dist/server.js`를 실행해야 합니다. 54 | 55 | ::: 56 | 57 | ### ssr.resolve.mainFields {#ssr-resolve-mainfields} 58 | 59 | - **타입:** `string[]` 60 | - **기본값:** `['module', 'jsnext:main', 'jsnext']` 61 | 62 | 패키지 진입점을 해석할 때 시도할 `package.json` 필드 목록입니다. 이는 `exports` 필드에서 해석된 조건부 내보내기보다 우선순위가 낮습니다: `exports`에서 진입점이 성공적으로 해석되면 모든 main 필드는 무시됩니다. 이 설정은 외부화되지 않은 디펜던시에만 영향을 미칩니다. -------------------------------------------------------------------------------- /config/worker-options.md: -------------------------------------------------------------------------------- 1 | # 워커 옵션 {#worker-options} 2 | 3 | 별도로 명시되지 않은 한, 이 섹션의 옵션들은 개발, 빌드, 그리고 프리뷰 모두에게 적용됩니다. 4 | 5 | ## worker.format {#worker-format} 6 | 7 | - **타입:** `'es' | 'iife'` 8 | - **기본값:** `'iife'` 9 | 10 | 워커 번들에 대한 포맷입니다. 11 | 12 | ## worker.plugins {#worker-plugins} 13 | 14 | - **타입:** [`() => (Plugin | Plugin[])[]`](./shared-options#plugins) 15 | 16 | 워커 번들에 적용되는 Vite 플러그인입니다. [config.plugins](./shared-options#plugins)은 개발 모드에서만 워커에 적용되며, 빌드 시에는 여기에 설정해야 합니다. 17 | 함수는 병렬 Rollup 워커 빌드에서 사용되는 새로운 플러그인 인스턴스를 반환해야 합니다. 따라서 `config` 훅에서 `config.worker` 옵션을 수정하는 것은 무시됩니다. 18 | 19 | ## worker.rollupOptions {#worker-rollupoptions} 20 | 21 | - **타입:** [`RollupOptions`](https://rollupjs.org/configuration-options/) 22 | 23 | 워커 번들 빌드 시 Rollup 옵션입니다. -------------------------------------------------------------------------------- /docs/logo-black.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vitejs/docs-ko/fc14d974a6885dbe5da00fcd51c053c57144deb4/docs/logo-black.png -------------------------------------------------------------------------------- /docs/logo-transparent.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vitejs/docs-ko/fc14d974a6885dbe5da00fcd51c053c57144deb4/docs/logo-transparent.png -------------------------------------------------------------------------------- /docs/logo-white.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vitejs/docs-ko/fc14d974a6885dbe5da00fcd51c053c57144deb4/docs/logo-white.png -------------------------------------------------------------------------------- /guide/assets.md: -------------------------------------------------------------------------------- 1 | # 에셋 가져오기 {#static-asset-handling} 2 | 3 | - 관련 항목: [Public Base Path](./build#public-base-path) 4 | - 관련 항목: [`assetsInclude` 설정 옵션](/config/shared-options.md#assetsinclude) 5 | 6 | ## URL을 통해 에셋 가져오기 {#importing-asset-as-url} 7 | 8 | 정적 에셋을 가져오게 되면 에셋에 접근할 수 있는 URL이 반환됩니다. 9 | 10 | ```js twoslash 11 | import 'vite/client' 12 | // ---cut--- 13 | import imgUrl from './img.png' 14 | document.getElementById('hero-img').src = imgUrl 15 | ``` 16 | 17 | 예를 들어 `imgUrl` 객체는 개발 시 `/src/img.png` 값으로 할당되지만, 프로덕션에서는 `/assets/img.2d8efhg.png`와 같은 값이 할당됩니다. 18 | 19 | Webpack의 `file-loader`와 비슷한데, 하나 차이점이 있다면 Vite는 절대 경로와 상대 경로 둘 다 사용할 수 있습니다. 20 | 21 | - `url()`로 참조되는 CSS의 경우 동일한 방식으로 동작합니다. 22 | 23 | - 만약 Vue 플러그인을 사용한다면, [Vue SFC](https://v3.vuejs.org/guide/single-file-component.html) 에셋의 경우 자동으로 변환되어 가져와집니다. 24 | 25 | - 일반적인 이미지, 미디어, 폰트 파일 타입은 자동으로 에셋 목록에 포함됩니다. 물론 [`assetsInclude` 옵션](/config/shared-options.md#assetsinclude)을 이용해 더 많은 파일 타입을 포함하도록 할 수 있습니다. 26 | 27 | - 참조된 에셋은 빌드 에셋 그래프의 일부 요소로 포함되며, 파일 이름이 해싱되거나 최적화를 위해 플러그인으로 처리될 수 있습니다. 28 | 29 | - [`assetsInlineLimit` 옵션](/config/shared-options.md#assetsinlinelimit)의 값보다 작은 에셋 파일의 경우, Base64 포맷의 데이터 URL 문자열로 가져옵니다. 30 | 31 | - Git LFS 자리 표시자는 파일 내용을 포함하지 않기에 인라인에서 자동으로 제외됩니다. 만약 이 역시 인라인에 포함하고자 한다면 빌드하기 전 Git LFS를 통해 파일을 다운로드해주세요. 32 | 33 | - TypeScript의 경우, 기본적으로 정적 에셋 가져오기를 유효한 모듈로 인식하지 않습니다. 이를 해결하려면 [`vite/client`](./features#client-types)를 포함해주세요. 34 | 35 | ::: tip `url()`을 통해 SVG 인라이닝하기 36 | JS를 통해 직접 `url()`로 SVG URL을 전달하는 경우, 변수는 반드시 큰따옴표로 감싸져야 합니다. 37 | 38 | ```js twoslash 39 | import 'vite/client' 40 | // ---cut--- 41 | import imgUrl from './img.svg' 42 | document.getElementById('hero-img').style.background = `url("${imgUrl}")` 43 | ``` 44 | 45 | ::: 46 | 47 | ### 접미사를 이용해 URL로 에셋 가져오기 {#explicit-url-imports} 48 | 49 | Vite 내부적으로 설정된 목록이나 `assetsInclude`에 포함되지 않은 에셋도 `?url` 접미사를 사용해 명시적으로 URL로서 가져올 수 있습니다. 이는 [Houdini Paint Worklets](https://developer.mozilla.org/en-US/docs/Web/API/CSS/paintWorklet_static)를 가져올 때와 같은 상황에서 유용합니다. 50 | 51 | ```js twoslash 52 | import 'vite/client' 53 | // ---cut--- 54 | import workletURL from 'extra-scalloped-border/worklet.js?url' 55 | CSS.paintWorklet.addModule(workletURL) 56 | ``` 57 | 58 | ### 명시적인 인라인 처리 {#explicit-inline-handling} 59 | 60 | 에셋은 `?inline` 또는 `?no-inline` 접미사를 사용해 인라인 처리 여부를 명시적으로 지정하여 가져올 수 있습니다. 61 | 62 | ```js twoslash 63 | import 'vite/client' 64 | // ---cut--- 65 | import imgUrl1 from './img.svg?no-inline' 66 | import imgUrl2 from './img.png?inline' 67 | ``` 68 | 69 | ### 문자열 형태로 에셋 가져오기 {#importing-asset-as-string} 70 | 71 | `?raw` 접미사를 붙여 가져오는 에셋은 문자열 형태로 가져와지게 됩니다. 72 | 73 | ```js twoslash 74 | import 'vite/client' 75 | // ---cut--- 76 | import shaderString from './shader.glsl?raw' 77 | ``` 78 | 79 | ### 스크립트를 Worker로 가져오기 {#importing-script-as-a-worker} 80 | 81 | 스크립트는 웹 워커로 가져올 수 있는데, 이 때는 `?worker` 접미사를 이용합니다. 82 | 83 | ```js twoslash 84 | import 'vite/client' 85 | // ---cut--- 86 | // 프로덕션 빌드 시에는 청크로 분리됩니다. 87 | import Worker from './shader.js?worker' 88 | const worker = new Worker() 89 | ``` 90 | 91 | ```js twoslash 92 | import 'vite/client' 93 | // ---cut--- 94 | // sharedworker 95 | import SharedWorker from './shader.js?sharedworker' 96 | const sharedWorker = new SharedWorker() 97 | ``` 98 | 99 | ```js twoslash 100 | import 'vite/client' 101 | // ---cut--- 102 | // `inline` 접미사는 Base64 포맷의 문자열로 에셋을 가져옵니다. 103 | import InlineWorker from './shader.js?worker&inline' 104 | ``` 105 | 106 | 좀 더 자세한 사항은 [웹 워커 섹션](./features#web-workers)을 참고해주세요. 107 | 108 | ## `public` 디렉터리 {#the-public-directory} 109 | 110 | 아래와 같은 에셋은: 111 | 112 | - `robots.txt`와 같이 소스 코드에서 참조되지 않는 에셋 113 | - 해싱을 거치지 않고 항상 같은 이름을 가져야 하는 에셋 114 | - ...또는 URL을 얻기 위해 `import` 할 필요 없는 에셋 115 | 116 | `public` 디렉터리 아래에 에셋을 위치시키세요. 이 곳에 위치한 에셋은 개발 시 `/` 경로에, 배포 시 `dist` 디렉터리에 위치하게 됩니다. 117 | 118 | 만약 `/public` 이 아닌 다른 디렉터리를 사용하고자 하는 경우, [`publicDir` 옵션](/config/shared-options.md#publicdir)을 이용할 수 있습니다. 119 | 120 | 참고로 `public` 디렉터리에 위치해 있는 에셋을 가져오고자 하는 경우, 항상 루트를 기준으로 하는 절대 경로로 가져와야 합니다. (예: `public/icon.png` 에셋은 소스 코드에서 `/icon.png`으로 접근이 가능) 121 | 122 | ## new URL(url, import.meta.url) {#new-url-url-import-meta-url} 123 | 124 | 네이티브 ESM의 API 중 하나인 [import.meta.url](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Statements/import.meta)은 현재 모듈의 URL을 보여주는 기능입니다. [URL 생성자](https://developer.mozilla.org/en-US/docs/Web/API/URL)와 함께 사용하면, 정적 에셋의 전제 URL을 확인할 수 있게 됩니다. 125 | 126 | ```js 127 | const imgUrl = new URL('./img.png', import.meta.url).href 128 | 129 | document.getElementById('hero-img').src = imgUrl 130 | ``` 131 | 132 | 위 코드는 네이티브 ESM을 지원하는 모던 브라우저에서 동작합니다. 물론, Vite는 위 동작을 자동으로 수행해주기에 따로 처리할 필요는 없습니다. 133 | 134 | 참고로 위 코드는 템플릿 리터럴을 이용해 동적으로 생성되는 URL에서도 동작합니다. 135 | 136 | ```js 137 | function getImageUrl(name) { 138 | // note that this does not include files in subdirectories 139 | return new URL(`./dir/${name}.png`, import.meta.url).href 140 | } 141 | ``` 142 | 143 | 프로덕션 빌드 시, Vite는 번들링 및 에셋 해싱 후에도 해당 에셋에 대한 URL을 올바르게 가리키기 위해 필요한 변환 작업을 수행합니다. 144 | 145 | ```js 146 | // Vite는 아래 코드를 변환하지 않음 147 | const imgUrl = new URL(imagePath, import.meta.url).href 148 | ``` 149 | 150 | ::: details 동작 방식 151 | 152 | Vite는 `getImageUrl` 함수를 다음과 같이 변환합니다: 153 | 154 | ```js 155 | import __img0png from './dir/img0.png' 156 | import __img1png from './dir/img1.png' 157 | 158 | function getImageUrl(name) { 159 | const modules = { 160 | './dir/img0.png': __img0png, 161 | './dir/img1.png': __img1png, 162 | } 163 | return new URL(modules[`./dir/${name}.png`], import.meta.url).href 164 | } 165 | ``` 166 | 167 | ::: 168 | 169 | ::: warning SSR과 함께 사용하지 마세요! 170 | `import.meta.url`은 브라우저와 Node.js 간 서로 다른 의미를 갖기 때문에, 이 패턴은 서버-사이드 렌더링(SSR)에 Vite를 사용하는 경우 동작하지 않습니다. 또한 서버 번들은 클라이언트 호스트의 URL을 미리 결정할 수 없습니다. 171 | ::: -------------------------------------------------------------------------------- /guide/dep-pre-bundling.md: -------------------------------------------------------------------------------- 1 | # 사전 번들링 된 디펜던시 {#dependency-pre-bundling} 2 | 3 | 처음 `vite`를 실행할 때, Vite는 로컬에 사이트를 불러오기 전에 프로젝트의 디펜던시를 사전 번들링합니다. 이는 기본적으로 자동으로 투명하게 진행됩니다. 4 | 5 | ## 왜 이런 메시지가 나타나나요? {#the-why} 6 | 7 | 이러한 메시지가 나타나는 이유는 Vite의 "사전 번들링(Pre-bundling)" 기능으로 인한 것인데, 이를 사용하는 목적은 다음과 같습니다. 8 | 9 | 1. **CommonJS 그리고 UMD 모듈을 ESM으로 가져오기:** 개발 시, Vite의 개발 서버는 모든 코드를 네이티브 ESM으로 가져오게 됩니다. 따라서, vite는 반드시 모든 CommonJS 및 UMD 파일을 ESM으로 불러올 수 있도록 변환 작업을 진행해줘야 합니다. 10 | 11 | vite는 조금 영리하게 ESM 파일로 변환을 진행하는데, 가령 CommonJS 디펜던시를 변환해주는 경우 아래와 같이 이름을 지정해 CommonJS 형태의 모듈을 가져올 수도 있습니다. 12 | 13 | ```js 14 | // 아래 코드는 정상적으로 동작합니다. 15 | import React, { useState } from 'react' 16 | ``` 17 | 18 | 2. **성능:** vite는 여러 디펜던시가 존재하는 ESM 모듈을 하나의 모듈로 변환하여 페이지 로드에 대한 성능을 향상시킵니다. 19 | 20 | 600개의 모듈을 갖고 있는 [`lodash-es`](https://unpkg.com/browse/lodash-es/)와 같이 매우 많은 모듈을 필요로 하는 경우, 그 수만큼 HTTP 요청을 전송하게 됩니다(`import { debounce } from 'lodash-es'`를 한다고 해도 말이죠). 서버가 이 요청들을 모두 정상적으로 처리한다고 해도, 브라우저 자체에서 이러한 네트워크 요청에 대한 오버헤드가 존재하기에 페이지 로드 성능은 떨어질 수 밖에 없습니다. 가령 `lodash-es` 모듈을 가져오게 된다면 600개의 HTTP 요청을 전송하게 되는 것이죠. 21 | 22 | 만약 `lodash-es` 모듈을 하나의 모듈로 번들링하게 된다면 어떻게 될까요? 브라우저는 단지 하나의 HTTP 요청만을 전송하게 됩니다. 23 | 24 | ::: tip 참고 25 | 디펜던시 사전 번들링 기능은 개발 모드에서만 적용되며, `esbuild`를 이용해 디펜던시를 ESM으로 변환합니다. 프로덕션 빌드의 경우, 이 대신 `@rollup/plugin-commonjs`가 대신 사용됩니다. 26 | ::: 27 | 28 | ## 자동으로 디펜던시 탐색하기 {#automatic-dependency-discovery} 29 | 30 | 만약 디펜던시가 캐시되지 않았다면 어떻게 될까요? vite는 프로젝트 내 모든 소스 코드를 탐색하여 디펜던시를 찾아낸 뒤, 사전 번들링을 이용해 Import 합니다(`node_modules`에서 디펜던시를 가져오듯이 말이죠). 물론, 이 사전 번들링 과정은 `esbuild`를 이용하기에 보통 매우 빠른 속도로 진행됩니다. 31 | 32 | 서버가 이미 시작된 이후에 캐시되지 않은 새로운 디펜던시가 추가되는 경우라면, vite는 디펜던시 번들링 과정을 재시작하고 이후 필요하다면 해당 페이지를 다시 불러오게 됩니다. 33 | 34 | ## 모노리포 디펜던시 {#monorepos-and-linked-dependencies} 35 | 36 | 모노리포 프로젝트의 경우 디펜던시는 동일한 하나의 리포지토리에 연결된 패키지일 수 있습니다. Vite는 사용하는 디펜던시가 `node_modules`에 존재하지 않더라도 스스로 탐색하여 이를 소스 코드로 가져올 수 있지만, 이를 번들로 묶지는 않습니다. 그저 연결된 디펜던시 목록을 분석할 뿐이죠. 37 | 38 | 이를 위해서는 연결된 디펜던시가 ESM 형태로 내보내져야 합니다. 만약 그렇지 않다면, 해당되는 디펜던시들을 [`optimizeDeps.include`](/config/dep-optimization-options.md#optimizedeps-include)와 [`build.commonjsOptions.include`](/config/build-options.md#build-commonjsoptions) 설정에 추가해주세요. 39 | 40 | ```js twoslash [vite.config.js] 41 | import { defineConfig } from 'vite' 42 | // ---cut--- 43 | export default defineConfig({ 44 | optimizeDeps: { 45 | include: ['linked-dep'] 46 | }, 47 | build: { 48 | commonjsOptions: { 49 | include: [/linked-dep/, /node_modules/] 50 | } 51 | } 52 | }) 53 | ``` 54 | 55 | 설정 값 변경 이후 `--force` 플래그를 이용해 개발 서버를 다시 시작하게 되면 해당 내용이 적용됩니다. 56 | 57 | ## 디펜던시 탐색 과정 커스터마이즈하기 {#customizing-the-behavior} 58 | 59 | Vite의 디펜던시 탐색 휴리스틱이 항상 바람직한 것은 아닙니다. 만약 특정 디펜던시를 명시적으로 포함시키거나 포함시키지 않도록 설정하고자 한다면 [`optimizeDeps` 옵션](/config/dep-optimization-options.md)을 이용해주세요. 60 | 61 | `optimizeDeps.include` 또는 `optimizeDeps.exclude`의 일반적인 사용 사례는 소스 코드에서 직접 탐색할 수 없는 Import가 있는 경우입니다. 플러그인 변환의 결과물에 Import가 사용된 경우를 예로 들 수 있습니다. 이는 Vite가 초기 스캔 시 해당 Import를 발견할 수 없음을 의미합니다. 브라우저에서 파일을 요청하고 변환된 이후에만 해당 Import를 발견할 수 있습니다. 이는 서버가 시작된 이후에 서버를 다시 번들링하게 만듭니다. 62 | 63 | 이를 해결하기 위해 `include`와 `exclude` 옵션 둘 다 사용될 수 있습니다. 만약 디펜던시가 크거나(내부 모듈이 많은 경우) CommonJS 포맷이라면 `include` 옵션에 명시해야 합니다. 만약 디펜던시가 작고 이미 ESM 스타일로 작성되어 있다면 `exclude` 옵션에 명시해 브라우저에서 바로 불러올 수 있도록 설정할 수 있습니다. 64 | 65 | 또한 [`optimizeDeps.esbuildOptions` 옵션](/config/dep-optimization-options.md#optimizedeps-esbuildoptions)을 통해 esbuild를 더욱 세밀하게 커스터마이즈할 수 있습니다. 예를 들어, 특정 파일을 디펜던시에서 처리하기 위한 esbuild 플러그인을 추가하거나, [빌드 `target`](https://esbuild.github.io/api/#target)을 변경할 수 있습니다. 66 | 67 | ## 캐싱 {#caching} 68 | 69 | ### 파일 시스템 캐시 {#file-system-cache} 70 | 71 | Vite는 사전 번들링 된 디펜던시를 `node_modules/.vite` 디렉터리 내에 캐시하고 있습니다. 다만 이를 다시 번들링하는 경우가 있는데, 다음과 같습니다. 72 | 73 | - 패키지 매니저의 락파일 내용, 예를 들어 `package-lock.json`, `yarn.lock`, `pnpm-lock.yaml` 또는 `bun.lockb` 74 | - 폴더의 수정 시간을 패치 75 | - `vite.config.js`와 관련되어 있는 필드가 변경되었을 때 76 | - `NODE_ENV` 값 77 | 78 | 위의 변경 사항이 발생된 경우 사전 번들링 과정을 다시 시작하게 됩니다. 79 | 80 | 만약 강제로 디펜던시를 다시 번들링해야 하는 경우, 개발 서버를 `--force` 옵션과 함께 시작해주세요. 또는 그냥 `node_modules/.vite` 디렉터리를 삭제해줘도 됩니다. 81 | 82 | ### 브라우저 캐시 {#browser-cache} 83 | 84 | HTTP 헤더를 `max-age=31536000,immutable`(사전 번들링 된 디펜던시는 이 헤더가 추가됩니다. - 옮긴이)과 같이 디펜던시가 반드시 캐시되도록 설정한 경우, 개발 시 페이지를 다시 불러오는 상황에 대한 성능을 향상시킬 수 있습니다. 한 번 캐시된 디펜던시는 다시 서버에 요청하지 않기 때문이죠. 물론 캐시된 디펜던시와 다른 버전이 설치된 경우 기존 버전은 자동으로 무효화됩니다. 물론 아래의 과정을 통해 버전 변경 없이 직접 디펜던시를 수정(디버그)할 수도 있습니다. 85 | 86 | 1. 브라우저의 개발자 도구를 이용해 캐시를 사용하지 않도록 설정합니다. 87 | 2. 디펜던시를 다시 번들링하는 `--force` 옵션과 함께 Vite의 개발 서버를 재시작합니다. 88 | 3. 페이지를 다시 로드합니다. -------------------------------------------------------------------------------- /guide/migration-from-v1.md: -------------------------------------------------------------------------------- 1 | # v1에서 마이그레션하기 {#migrating-from-v1} 2 | 3 | ## 설정 바꾸기 {#config-options-change} 4 | 5 | - 아래의 옵션들은 제거되었으며, [플러그인](./api-plugin)을 통해 구현해야 합니다. 6 | 7 | - `resolvers` 8 | - `transforms` 9 | - `indexHtmlTransforms` 10 | 11 | - `jsx`와 `enableEsbuild`는 제거되었습니다. 이 대신 새로운 [`esbuild`](/config/shared-options.md#esbuild) 옵션을 사용해주세요. 12 | 13 | - [CSS 관련 옵션](/config/shared-options.md#css-modules)은 이제 `css` 아래에 위치합니다. 14 | 15 | - 모든 [빌드별 옵션](/config/build-options.md)는 이제 `build` 아래에 위치합니다. 16 | 17 | - `rollupInputOptions`와 `rollupOutputOptions`는 [`build.rollupOptions`](/config/build-options.md#build-rollupoptions)로 대체되었습니다. 18 | - `esbuildTarget`은 이제 [`build.target`](/config/build-options.md#build-target) 입니다. 19 | - `emitManifest`는 이제 [`build.manifest`](/config/build-options.md#build-manifest) 입니다. 20 | - 아래의 빌드 옵션은 제거되었으나, 플러그인 훅(Hook) 또는 기타 옵션을 통해 가져올 수 있습니다. 21 | - `entry` 22 | - `rollupDedupe` 23 | - `emitAssets` 24 | - `emitIndex` 25 | - `shouldPreload` 26 | - `configureBuild` 27 | 28 | - 모든 [서버 옵션](/config/server-options.md)은 이제 `server` 아래에 위치합니다. 29 | 30 | - `hostname`은 이제 [`server.host`](/config/server-options.md#server-host) 입니다. 31 | - `httpsOptions`는 제거되었습니다. 대신, [`server.https`](/config/server-options.md#server-https)가 직접 옵션 객체를 받을 수 있도록 구성되어 있습니다. 32 | - `chokidarWatchOptions`는 이제 [`server.watch`](/config/server-options.md#server-watch) 입니다. 33 | 34 | - [`assetsInclude`](/config/shared-options.md#assetsinclude)는 이제 함수 대신 `string | RegExp | (string | RegExp)[]` 타입으로 설정됩니다. 35 | 36 | - 모든 Vue 옵션은 제거되었으며, Vue 플러그인에 옵션을 전달하도록 구성해야 합니다. 37 | 38 | ## 별칭 동작 변경 {#alias-behavior-change} 39 | 40 | [`alias`](/config/shared-options.md#resolve-alias)는 이제 `@rollup/plugin-alias`로 전달되고, 더 이상 경로의 시작과 끝에 슬래시가 필요하지 않습니다. 따라서, 1.0 스타일의 디렉터리 별칭 키 끝에 있는 슬래시는 제거해주세요: 41 | 42 | ```diff 43 | - alias: { '/@foo/': path.resolve(__dirname, 'some-special-dir') } 44 | + alias: { '/@foo': path.resolve(__dirname, 'some-special-dir') } 45 | ``` 46 | 47 | 조금 더 세부적으로 구성하고자 한다면, `[{ find: RegExp, replacement: string }]` 형태로 이용할 수도 있습니다. 48 | 49 | ## Vue 지원 {#vue-support} 50 | 51 | Vite 2.0 코어는 이제 특정 프레임워크에 종속적이지 않습니다. Vue는 이제 [`@vitejs/plugin-vue`](https://github.com/vitejs/vite/tree/main/packages/plugin-vue)를 통해 제공되며, 간단하게 설치하고 아래와 같이 Vite 설정에 추가하기만 하면 됩니다. 52 | 53 | ```js 54 | import vue from '@vitejs/plugin-vue' 55 | import { defineConfig } from 'vite' 56 | 57 | export default defineConfig({ 58 | plugins: [vue()] 59 | }) 60 | ``` 61 | 62 | ### 커스텀 블록 변환 {#custom-blocks-transforms} 63 | 64 | 커스텀 플러그인을 사용해 아래와 같이 Vue 커스텀 블록을 변환(Transform)할 수 있습니다: 65 | 66 | ```ts 67 | // vite.config.js 68 | import vue from '@vitejs/plugin-vue' 69 | import { defineConfig } from 'vite' 70 | 71 | const vueI18nPlugin = { 72 | name: 'vue-i18n', 73 | transform(code, id) { 74 | if (!/vue&type=i18n/.test(id)) { 75 | return 76 | } 77 | if (/\.ya?ml$/.test(id)) { 78 | code = JSON.stringify(require('js-yaml').load(code.trim())) 79 | } 80 | return `export default Comp => { 81 | Comp.i18n = ${code} 82 | }` 83 | } 84 | } 85 | 86 | export default defineConfig({ 87 | plugins: [vue(), vueI18nPlugin] 88 | }) 89 | ``` 90 | 91 | ## React 지원 {#react-support} 92 | 93 | React의 Fast Refresh는 이제 [`@vitejs/plugin-react`](https://github.com/vitejs/vite/tree/main/packages/plugin-react) 플러그인을 통해 지원됩니다. 94 | 95 | ## HMR API 변경 {#hmr-api-change} 96 | 97 | `import.meta.hot.acceptDeps()`는 더 이상 사용되지 않습니다. 또한 [`import.meta.hot.accept()`](./api-hmr#hot-accept-deps-cb)는 이제 하나 이상의 디펜던시를 받을 수 있도록 구성되었습니다. 98 | 99 | ## 매니페스트 포맷 변경 {#manifest-format-change} 100 | 101 | 이제 빌드 매니페스트는 아래와 같은 포맷을 사용합니다: 102 | 103 | ```json 104 | { 105 | "index.js": { 106 | "file": "assets/index.acaf2b48.js", 107 | "imports": [...] 108 | }, 109 | "index.css": { 110 | "file": "assets/index.7b7dbd85.css" 111 | } 112 | "asset.png": { 113 | "file": "assets/asset.0ab0f9cd.png" 114 | } 115 | } 116 | ``` 117 | 118 | JS 청크 파일의 경우, 사전 로드 지시문(Preload Directives)을 렌더링하는 데 사용할 수 있도록 가져와진(Import) 청크도 나열됩니다. 119 | 120 | ## 플러그인 개발자를 위해 {#for-plugin-authors} 121 | 122 | Vite 2는 Rollup 플러그인을 확장하는 완전히 재설계된 플러그인 인터페이스를 사용합니다. 이와 관련된 내용은 새로운 [플러그인 개발 가이드](./api-plugin)를 참고해주세요. 123 | 124 | 아래는 v1 플러그인을 v2로 마이그레이션하는 방법에 대한 몇 가지 지침 사항입니다: 125 | 126 | - `resolvers` -> [`resolveId`](https://rollupjs.org/guide/en/#resolveid) 훅을 이용 127 | - `transforms` -> [`transform`](https://rollupjs.org/guide/en/#transform) 훅을 이용 128 | - `indexHtmlTransforms` -> [`transformIndexHtml`](./api-plugin#transformindexhtml) 훅을 이용 129 | - 가상(Virtual) 파일 제공 -> [`resolveId`](https://rollupjs.org/guide/en/#resolveid) + [`load`](https://rollupjs.org/guide/en/#load) 훅을 이용 130 | - `alias`, `define` 또는 기타 설정 옵션 추가 -> [`config`](./api-plugin#config) 훅을 이용 131 | 132 | 대부분의 로직은 미들웨어가 아닌 플러그인 훅을 통해 이루어져야 하기 때문에, 미들웨어의 필요성은 크게 줄어들게 됩니다. 또한 Vite의 내부 서버는 이제 Koa가 아닌 [connect](https://github.com/senchalabs/connect)의 인스턴스입니다. 133 | -------------------------------------------------------------------------------- /guide/migration-from-v3.md: -------------------------------------------------------------------------------- 1 | # v3에서 마이그레이션하기 {#migration-from-v3} 2 | 3 | ## Rollup 3 {#rollup-3} 4 | 5 | Vite는 이제 [Rollup 3](https://github.com/vitejs/vite/issues/9870)을 사용하며, Vite의 내부 에셋 처리를 단순화하고 많은 개선이 있습니다. 자세한 것은 [Rollup 3 릴리스 노트](https://github.com/rollup/rollup/releases/tag/v3.0.0)를 참고해주세요. 6 | 7 | Rollup 3는 많은 부분에서 Rollup 2와 호환됩니다. 만약 커스텀 [`rollupOptions`](../config/build-options.md#build-rollupoptions)를 사용하는 프로젝트에서 문제가 발생된다면, [Rollup 마이그레이션 가이드](https://rollupjs.org/migration/)를 참고하여 설정을 업그레이드하세요. 8 | 9 | ## 모던 브라우저 표준 변경 {#modern-browser-baseline-change} 10 | 11 | 모던 브라우저 빌드는 이제 ES2020 호환성을 넓히기 위해 기본적으로 `safari14`를 대상으로 합니다. 이는 모던 빌드가 이제 [`BigInt`](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/BigInt)를 사용할 수 있고 [nullish coalescing operator](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Operators/Nullish_coalescing)가 더 이상 트랜스파일되지 않는다는 것을 의미합니다. 만약 이전 브라우저를 지원해야 한다면, [`@vitejs/plugin-legacy`](https://github.com/vitejs/vite/tree/main/packages/plugin-legacy)를 사용해주세요. 12 | 13 | ## 일반적인 변경사항 {#general-changes} 14 | 15 | ### 인코딩 {#encoding} 16 | 17 | 빌드 시 이제 기본적으로 utf8을 사용합니다. 자세한 것은 [#10753](https://github.com/vitejs/vite/issues/10753)를 참고해주세요. 18 | 19 | ### 문자열로 CSS 가져오기 {#importing-css-as-a-string} 20 | 21 | Vite 3에서, `.css` 파일의 `default export`를 가져오는 것은 CSS를 두 번 로드할 수 있습니다. 22 | 23 | ```ts 24 | import cssString from './global.css' 25 | ``` 26 | 27 | 이 중복 로딩은 가져온 `.css`에 대한 스타일이 생성됨과 동시에 CSS 문자열이 애플리케이션 코드에서도 사용될 수 있기 때문에 발생할 수 있습니다(예를 들어, 프레임워크 런타임에 의해 주입될 수 있습니다). Vite 4부터 `.css`의 `default export`는 [사용이 중단되었으며](https://github.com/vitejs/vite/issues/11094), 이 대신 `?inline` 쿼리 접미사 수정자를 사용해야 합니다. 이 경우에는 가져온 `.css`에 대해 스타일을 생성하지 않습니다. 28 | 29 | ```ts 30 | import stuff from './global.css?inline' 31 | ``` 32 | 33 | ### 기본적으로 Production 빌드를 수행 {#production-builds-by-default} 34 | 35 | `vite build`는 이제 전달된 `--mode`에 관계없이 항상 프로덕션 빌드를 수행합니다. 이전에는 `mode`를 `production` 이외의 다른 값으로 변경하면 개발 모드로 빌드가 수행되었습니다. 이제 개발 모드 빌드를 수행하려면 `.env.{mode}` 파일에서 `NODE_ENV=development`를 설정하면 됩니다. 36 | 37 | 이 변경 사항의 일부로, `vite dev`와 `vite build`는 이미 정의된 경우 `process.env.NODE_ENV`를 더 이상 덮어쓰지 않습니다. 따라서 `process.env.NODE_ENV = 'development'`를 빌드하기 전에 설정했다면 개발 모드로 빌드할 수 있습니다. 이렇게 하면 여러 빌드 또는 병렬로 실행되는 개발 서버를 실행할 때 더 많은 제어를 할 수 있습니다. 38 | 39 | 더 자세한 정보는 [모드](./env-and-mode.md#modes) 문서를 참조하세요. 40 | 41 | ### 환경 변수 {#environment-variables} 42 | 43 | Vite는 이제 `dotenv` 16과 `dotenv-expand` 9를 사용합니다(이전에는 `dotenv` 14와 `dotenv-expand` 5를 사용했습니다). `#` 또는 `` ` ``를 포함하는 값이 있다면, 이 값을 따옴표로 감싸주세요. 44 | 45 | ```diff 46 | -VITE_APP=ab#cd`ef 47 | +VITE_APP="ab#cd`ef" 48 | ``` 49 | 50 | 자세한 내용은 [`dotenv`](https://github.com/motdotla/dotenv/blob/master/CHANGELOG.md)과 [`dotenv-expand` CHANGELOG](https://github.com/motdotla/dotenv-expand/blob/master/CHANGELOG.md)를 참고해주세요. 51 | 52 | ## 고급 {#advanced} 53 | 54 | 플러그인/툴 개발자에게만 영향을 미치는 변경사항이 있습니다. 55 | 56 | - [[#11036] feat(client)!: remove never implemented hot.decline](https://github.com/vitejs/vite/issues/11036) 57 | - `hot.invalidate`를 대신 사용 58 | - [[#9669] feat: align object interface for `transformIndexHtml` hook](https://github.com/vitejs/vite/issues/9669) 59 | - `order`를 `enforce` 대신 사용 60 | 61 | 다음은 많은 사용자에게 영향을 미치지 않는 변경사항입니다. 62 | 63 | - [[#11101] feat(ssr)!: remove dedupe and mode support for CJS](https://github.com/vitejs/vite/pull/11101) 64 | - CJS의 SSR 지원은 다음 Vite 메이저 업데이트에서 제거될 수 있으므로, SSR을 위해 기본적으로 ESM을 사용하도록 마이그레이션해야 합니다. 65 | - [[#10475] feat: handle static assets in case-sensitive manner](https://github.com/vitejs/vite/pull/10475) 66 | - 프로젝트는 파일 이름의 대소문자를 무시하는 OS에 의존하지 않아야 합니다. 67 | - [[#10996] fix!: make `NODE_ENV` more predictable](https://github.com/vitejs/vite/pull/10996) 68 | - 이 변경사항에 대한 설명은 PR을 참고하세요. 69 | - [[#10903] refactor(types)!: remove facade type files](https://github.com/vitejs/vite/pull/10903) 70 | 71 | ## v2에서 마이그레이션하기 {#migration-from-v2} 72 | 73 | [v2에서 마이그레이션하기 가이드](./migration-from-v2.md)를 먼저 확인하여 앱을 Vite v3로 포팅하기 위해 필요한 변경사항을 확인한 다음 이 페이지의 변경사항을 진행하세요. -------------------------------------------------------------------------------- /guide/philosophy.md: -------------------------------------------------------------------------------- 1 | # 프로젝트 철학 {#project-philosophy} 2 | 3 | ## 간결하고 확장가능한 코어 {#lean-extendable-core} 4 | 5 | Vite는 모든 사용 사례를 다루지 않습니다. 대부분의 상황에서 보편적으로 사용할 수 있는 웹 앱 빌드 패턴을 지원하는 것이 Vite의 목표이지만, 프로젝트를 장기적으로 유지하고 관리할 수 있도록 [Vite 코어](https://github.com/vitejs/vite)는 간결한 상태를 유지하고자 합니다. 사용자가 필요로 하는 기능은 충분히 [Vite의 Rollup 기반 플러그인 시스템](./api-plugin.md)을 이용해 가능하기에, 이로 구현할 수 있는 기능은 일반적으로 Vite 코어에 추가되지 않습니다. [vite-plugin-pwa](https://vite-pwa-org.netlify.app/)와 같은 플러그인은 Vite 코어로 무엇을 구현할 수 있는지를 보여주는 좋은 예시이며, 이처럼 [잘 관리되는 플러그인](https://github.com/vitejs/awesome-vite#plugins)을 이용해 개발 요구 사항을 충족할 수 있을 것입니다. 또한 Vite는 Rollup 프로젝트와 긴밀하게 협력하여 플러그인을 일반적인 Rollup 그리고 Vite 프로젝트 모두에서 사용할 수 있게끔 구성했으며, 필요한 확장 기능을 플러그인 API에 가능한 한 많이 도입하고자 노력하고 있습니다. 6 | 7 | ## 모던 웹으로 나아가기 {#pushing-the-modern-web} 8 | 9 | Vite는 모던 코드를 작성할 수 있도록 유도하고 있습니다. 예를 들어 다음과 같습니다: 10 | 11 | - 소스 코드는 ESM으로만 작성할 수 있으며, ESM이 아닌 디펜던시는 정상적으로 동작할 수 있도록 [ESM으로 사전 번들링](./dep-pre-bundling)해야 합니다. 12 | - 웹 워커는 최신 표준을 따르기 위해 [`new Worker` 구문](./features#web-workers)으로 작성하는 것이 권장됩니다. 13 | - Node.js 모듈은 브라우저에서 사용할 수 없습니다. 14 | 15 | 이러한 패턴은 새로운 기능을 추가할 때 미래 지향적인 API를 만들 수 있도록 도와주지만, 다른 빌드 툴과는 호환되지 않을 수 있습니다. 16 | 17 | ## 성능에 대한 실용적인 접근 {#a-pragmatic-approach-to-performance} 18 | 19 | Vite는 [개발 초기부터](./why.md) 성능에 초점을 맞추어 왔습니다. 개발 서버 아키텍처는 프로젝트가 확장되어도 빠른 HMR을 유지할 수 있도록 도와줍니다. 성능 집약적인 작업은 [esbuild](https://esbuild.github.io/)와 [SWC](https://github.com/vitejs/vite-plugin-react-swc) 같은 네이티브 툴을 사용해 구현하지만, 그 외의 코드는 JS로 유지해 속도와 유연성의 균형을 맞추었습니다. 다만 필요한 경우, 프레임워크 플러그인은 사용자 코드를 컴파일하기 위해 [Babel](https://babeljs.io/)을 사용할 수도 있습니다. 빌드 타임에는 현재 [Rollup](https://rollupjs.org/)을 사용하는데, 이는 네이티브 툴을 사용해 얻을 수 있는 성능보다 더 효율적인 번들 크기와 광범위한 플러그인 생태계가 존재한다는 것을 더 중요하게 생각하기 때문입니다. 이처럼 Vite는 최대한 API를 안정적으로 유지하되, DX를 개선할 수 있는 새로운 라이브러리가 등장하면 이를 사용해 내부적으로 계속 발전할 것입니다. 20 | 21 | ## Vite를 기반으로 프레임워크 구축하기 {#building-frameworks-on-top-of-vite} 22 | 23 | Vite는 직접 사용할 수도 있지만, 프레임워크를 만드는 도구로서도 빛을 발합니다. Vite의 코어가 프레임워크에 구애받는 것이 아님에도 불구하고, 각 UI 프레임워크에 대한 완성도 높은 플러그인이 존재합니다. 애플리케이션 프레임워크 개발자는 [JS API](./api-javascript.md)를 통해 Vite의 기능들을 활용하여 사용자에게 맞춤화된 경험을 제공할 수 있으며, 최신 웹 프레임워크 구축에 필수적이지만 일반적으로 높은 수준의 도구에서만 지원하는 [기본적인 SSR 기능들](./ssr.md) 역시 지원하고 있습니다. 또한 Vite 플러그인은 프레임워크 간에 공유할 수 있는 방법을 제공함으로써 이러한 모든 것을 완성합니다. Vite는 [Ruby](https://vite-ruby.netlify.app/)와 [Laravel](https://laravel.com/docs/10.x/vite)과 같은 [백엔드 프레임워크](./backend-integration.md)와 함께 사용할 때도 매우 좋은 선택입니다. 24 | 25 | ## 활발한 생태계 {#an-active-ecosystem} 26 | 27 | Vite의 진화는 프레임워크와 플러그인의 관리자, 사용자, 그리고 Vite 팀 간의 협력으로 이루어집니다. 만약 진행 중인 프로젝트가 Vite를 채택한다면, Vite의 코어 개발에 적극적으로 참여해 볼 것을 권장합니다. 우리는 각 릴리스에서 이전 버전으로의 회귀를 최소화하기 위해 생태계의 주요 프로젝트와 긴밀하게 협력하고 있으며, [vite-ecosystem-ci](https://github.com/vitejs/vite-ecosystem-ci)와 같은 도구도 활용하고 있습니다. 특히 이 도구를 통해 PR에서 Vite를 사용해 주요 프로젝트의 CI를 실행할 수 있는데, 이는 해당 릴리스의 여파를 명확하게 파악할 수 있도록 도와줍니다. 우리는 사용자에게 영향을 미치기 전에 버그를 수정하고, 프로젝트가 릴리스와 함께 다음 버전으로 업데이트할 수 있도록 최선을 다하고 있습니다. 만약 여러분이 Vite를 사용하고 있다면, [Vite의 Discord](https://chat.vite.dev)에서 우리와 함께 프로젝트에 참여해 보세요. -------------------------------------------------------------------------------- /guide/static-deploy-github-pages.yaml: -------------------------------------------------------------------------------- 1 | # static-deploy.md 에서 임포트 2 | # renovate가 액션 버전 업데이트를 수행할 수 있도록 이 파일로 분리 3 | # 4 | #region content 5 | # GitHub Pages를 통해 정적 콘텐츠를 배포하는 간단한 워크플로우 6 | name: Deploy static content to Pages 7 | 8 | on: 9 | # 기본 브랜치에 대한 푸시 이벤트 발생 시 실행 10 | push: 11 | branches: ['main'] 12 | 13 | # Actions 탭에서 수동으로 워크플로우를 실행할 수 있도록 구성 14 | workflow_dispatch: 15 | 16 | # GITHUB_TOKEN의 권한을 설정하여 GitHub Pages에 배포할 수 있도록 함 17 | permissions: 18 | contents: read 19 | pages: write 20 | id-token: write 21 | 22 | # 동시에 하나의 배포만 허용하도록 구성 23 | concurrency: 24 | group: 'pages' 25 | cancel-in-progress: true 26 | 27 | jobs: 28 | # 단순히 배포만 수행하기에 하나의 잡으로만 구성 29 | deploy: 30 | environment: 31 | name: github-pages 32 | url: ${{ steps.deployment.outputs.page_url }} 33 | runs-on: ubuntu-latest 34 | steps: 35 | - name: Checkout 36 | uses: actions/checkout@v4 37 | - name: Set up Node 38 | uses: actions/setup-node@v4 39 | with: 40 | node-version: lts/* 41 | cache: 'npm' 42 | - name: Install dependencies 43 | run: npm ci 44 | - name: Build 45 | run: npm run build 46 | - name: Setup Pages 47 | uses: actions/configure-pages@v5 48 | - name: Upload artifact 49 | uses: actions/upload-pages-artifact@v3 50 | with: 51 | # dist 폴더 업로드 52 | path: './dist' 53 | - name: Deploy to GitHub Pages 54 | id: deployment 55 | uses: actions/deploy-pages@v4 56 | #endregion content -------------------------------------------------------------------------------- /guide/using-plugins.md: -------------------------------------------------------------------------------- 1 | # 플러그인 사용하기 {#using-plugins} 2 | 3 | Vite는 몇 가지 추가적인 Vite 전용 옵션과 함께 잘 설계된 Rollup의 플러그인 인터페이스를 기반으로 하는 플러그인들을 사용하여 확장할 수 있습니다. 이는 Vite 사용자가 필요에 따라 개발 서버나 SSR과 같은 기능들을 확장할 수 있는 것과 동시에, 검증된 Rollup 플러그인 생태계에도 의존할 수 있음을 의미합니다. 4 | 5 | ## 플러그인 추가하기 {#adding-a-plugin} 6 | 7 | 플러그인을 사용하려면 프로젝트의 `devDependencies`에 플러그인을 추가하고, `vite.config.js` 설정 파일의 `plugins` 배열에 해당 플러그인을 포함시켜야 합니다. 예를 들어, 레거시 브라우저에 대한 지원을 제공하기 위해 공식 플러그인 중 하나인 [@vitejs/plugin-legacy](https://github.com/vitejs/vite/tree/main/packages/plugin-legacy)를 사용하고자 한다면 다음과 같이 할 수 있습니다: 8 | 9 | ``` 10 | $ npm add -D @vitejs/plugin-legacy 11 | ``` 12 | 13 | ```js twoslash [vite.config.js] 14 | import legacy from '@vitejs/plugin-legacy' 15 | import { defineConfig } from 'vite' 16 | 17 | export default defineConfig({ 18 | plugins: [ 19 | legacy({ 20 | targets: ['defaults', 'not IE 11'] 21 | }) 22 | ] 23 | }) 24 | ``` 25 | 26 | `plugins`에는 여러 플러그인을 하나의 요소로 묶는 사전 설정도 포함시킬 수 있습니다. 이는 프레임워크 통합과 같은 여러 플러그인을 사용하여 구현되는 복잡한 기능을 구현할 때 유용하게 사용될 수 있습니다. 이 때 전달되는 배열은 내부적으로 Flatten 연산을 거치게 됩니다. 27 | 28 | 참고로 다른 플러그인을 쉽게 활성화하거나 비활성화 시킬 수 있는 잘못된 플러그인은 무시됩니다. 29 | 30 | ## 플러그인을 찾는 방법 {#finding-plugins} 31 | 32 | :::tip 참고 33 | Vite는 웹 개발 시 일반적으로 필요한 대부분의 기능들을 제공하고 있습니다. 따라서 Vite 또는 호환되는 Rollup 플러그인을 검색하기 전, [지원하는 기능들](../guide/features.md) 섹션을 먼저 확인해주세요. Rollup으로 프로젝트를 구성할 때 필요했던 플러그인 대부분은 이미 Vite에서 자체적으로 제공하고 있습니다. 34 | ::: 35 | 36 | 공식 플러그인에 대한 정보는 [플러그인 섹션](../plugins/)을 참고해주세요. Vite 커뮤니티 플러그인은 [awesome-vite](https://github.com/vitejs/awesome-vite#plugins)에서 볼 수 있습니다. 37 | 38 | 플러그인이 [권장 규칙](./api-plugin.md#conventions)을 따르는 경우에는, Vite 플러그인의 경우 [npm에서 vite-plugin을](https://www.npmjs.com/search?q=vite-plugin&ranking=popularity), Rollup 플러그인의 경우 [npm에서 rollup-plugin을 검색](https://www.npmjs.com/search?q=rollup-plugin&ranking=popularity)해 찾을 수 있습니다. 39 | 40 | ## 플러그인 순서 정하기 {#enforcing-plugin-ordering} 41 | 42 | 일부 Rollup 플러그인과의 호환을 위해 플러그인 순서를 정하거나 빌드 시에만 플러그인이 동작하도록 구성할 수 있습니다. 이는 Vite 플러그인만을 위한 기능이며, 가령 플러그인 순서를 정하고자 하는 경우 `enforce` 프로퍼티를 이용할 수 있습니다: 43 | 44 | - `pre`: Vite의 코어 플러그인보다 먼저 실행하고자 하는 플러그인 45 | - default: Vite의 코어 플러그인 이후에 실행하고자 하는 플러그인 46 | - `post`: Vite의 빌드 플러그인 이후에 실행하고자 하는 플러그인 47 | 48 | ```js twoslash [vite.config.js] 49 | import image from '@rollup/plugin-image' 50 | import { defineConfig } from 'vite' 51 | 52 | export default defineConfig({ 53 | plugins: [ 54 | { 55 | ...image(), 56 | enforce: 'pre' 57 | } 58 | ] 59 | }) 60 | ``` 61 | 62 | 이에 대해 좀 더 자세한 내용은 [플러그인 API 가이드](./api-plugin.md#plugin-ordering)를 확인해주세요. 63 | 64 | ## 조건부 플러그인 {#conditional-application} 65 | 66 | 기본적으로 플러그인은 개발 서버(`'serve'`)와 빌드(`'build'`) 시 모두 동작합니다. 만약 조건부로 동작하기를 원한다면, `apply` 프로퍼티를 이용해 `'build'` 또는 `'serve'` 중에만 플러그인이 동작하도록 할 수 있습니다: 67 | 68 | ```js twoslash [vite.config.js] 69 | import typescript2 from 'rollup-plugin-typescript2' 70 | import { defineConfig } from 'vite' 71 | 72 | export default defineConfig({ 73 | plugins: [ 74 | { 75 | ...typescript2(), 76 | apply: 'build' 77 | } 78 | ] 79 | }) 80 | ``` 81 | 82 | ## 플러그인 작성 {#building-plugins} 83 | 84 | 플러그인 작성에 대한 문서는 [플러그인 API 가이드](./api-plugin.md)를 참고해주세요. -------------------------------------------------------------------------------- /guide/why.md: -------------------------------------------------------------------------------- 1 | # Vite를 사용해야 하는 이유 {#why-vite} 2 | 3 | ## 이런 문제점이 있었어요 {#the-problems} 4 | 5 | 브라우저에서 ESM(ES Modules)을 지원하기 전까지, JavaScript 모듈화를 네이티브 레벨에서 진행할 수 없었습니다. 그래서 소스 모듈을 브라우저에서 실행할 수 있는 파일로 크롤링, 처리 및 연결하는 "번들링(Bundling)"이라는 해결 방법을 사용해야 했습니다. 6 | 7 | [Webpack](https://webpack.js.org/), [Rollup](https://rollupjs.org) 그리고 [Parcel](https://parceljs.org/)과 같은 도구는 이런 번들링 작업을 진행해줌으로써 프런트엔드 개발자의 생산성을 크게 향상시켰습니다. 8 | 9 | 하지만 애플리케이션이 점점 더 발전함에 따라 처리해야 하는 JavaScript 모듈의 개수도 극적으로 증가하고 있습니다. 심지어 수천 개의 모듈이 존재하는 것도 대규모 프로젝트에서는 그리 드문 일이 아닙니다. 이러한 상황에서 JavaScript 기반의 도구는 성능 병목 현상이 발생되었고, 종종 개발 서버를 가동하는 데 비합리적으로 오랜 시간을 기다려야 한다거나 HMR을 사용하더라도 변경된 파일이 적용될 때 까지 수 초 이상 소요되곤 했습니다. 이와 같은 느린 피드백 루프는 개발자의 생산성과 행복에 적지 않은 영향을 줄 수 있습니다. 10 | 11 | Vite는 이러한 것에 초점을 맞춰, 브라우저에서 지원하는 ES Modules(ESM) 및 네이티브 언어로 작성된 JavaScript 도구 등을 활용해 문제를 해결하고자 합니다. 12 | 13 | ### 지루할 정도로 길었던 서버 구동 {#slow-server-start} 14 | 15 | 콜드 스타트 방식으로 개발 서버를 구동할 때, 번들러 기반의 도구의 경우 애플리케이션 내 모든 소스 코드에 대해 크롤링 및 빌드 작업을 마쳐야지만이 실제 페이지를 제공할 수 있습니다. 16 | 17 | vite는 애플리케이션의 모듈을 **디펜던시**와 **소스 코드** 두 가지 카테고리로 나누어 개발 서버의 시작 시간을 개선합니다. 18 | 19 | - **디펜던시**: 개발 시 그 내용이 바뀌지 않을 일반적인 JavaScript 소스 코드입니다. 기존 번들러로는 컴포넌트 라이브러리와 같이 몇 백 개의 JavaScript 모듈을 갖고 있는 매우 큰 디펜던시에 대한 번들링 과정이 매우 비효율적이었고 많은 시간을 필요로 했습니다. 20 | 21 | Vite [사전 번들링](./dep-pre-bundling.md) 기능은 [Esbuild](https://esbuild.github.io/)를 사용하고 있습니다. Go로 작성된 Esbuild는 Webpack, Parcel과 같은 기존의 번들러 대비 10-100배 빠른 속도를 제공합니다. 22 | 23 | - **소스 코드**: JSX, CSS 또는 Vue/Svelte 컴포넌트와 같이 컴파일링이 필요하고, 수정 또한 매우 잦은 Non-plain JavaScript 소스 코드는 어떻게 할까요? (물론 이들 역시 특정 시점에서 모두 불러올 필요는 없습니다.) 24 | 25 | vite는 [Native ESM](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Guide/Modules)을 이용해 소스 코드를 제공합니다. 이것은 본질적으로 브라우저가 번들러의 작업의 일부를 차지할 수 있도록 합니다. vite는 브라우저가 요청하는 대로 소스 코드를 변환하고 제공하기만 하면 됩니다. 조건부 동적 import 이후의 코드는 현재 화면에서 실제로 사용되는 경우에만 처리됩니다. 26 | 27 | 31 | 32 | 33 | 34 | ### 느렸던 소스 코드 갱신 {#slow-updates} 35 | 36 | 기존의 번들러 기반으로 개발을 진행할 때, 소스 코드를 업데이트 하게 되면 번들링 과정을 다시 거쳐야 했었습니다. 따라서 서비스가 커질수록 소스 코드 갱신 시간 또한 선형적으로 증가하게 됩니다. 37 | 38 | 일부 번들러는 메모리에서 작업을 수행하여 실제로 갱신에 영향을 받는 파일들만을 새롭게 번들링하도록 했지만, 결국 처음에는 모든 파일에 대한 번들링을 수행해야 했습니다. "모든 파일"을 번들링 하고, 이를 다시 웹 페이지에서 불러오는 것이 얼마나 비효율적인 것인지 느껴지시나요? 이러한 이슈를 우회하고자 HMR(Hot Module Replacement) 이라는 대안이 나왔으나, 이 역시 명확한 해답은 아니었습니다. 39 | 40 | 물론, vite는 HMR을 지원합니다. 이는 번들러가 아닌 ESM을 이용하는 것입니다. 어떤 모듈이 수정되면 vite는 그저 수정된 모듈과 관련된 부분만을 교체할 뿐이고, 브라우저에서 해당 모듈을 요청하면 교체된 모듈을 전달할 뿐입니다. 전 과정에서 완벽하게 ESM을 이용하기에, 앱 사이즈가 커져도 HMR을 포함한 갱신 시간에는 영향을 끼치지 않습니다. 41 | 42 | 또한 vite는 HTTP 헤더를 활용하여 전체 페이지의 로드 속도를 높입니다. 필요에 따라 소스 코드는 `304 Not Modified`로, 디펜던시는 `Cache-Control: max-age=31536000,immutable`을 이용해 캐시됩니다. 이렇게 함으로써 요청 횟수를 최소화하여 페이지 로딩을 빠르게 만들어 줍니다. 43 | 44 | 이렇게나 빠른 Vite를 사용하지 않을 이유가 있나요? 45 | 46 | ## 배포 시 번들링 과정이 필요한 이유 {#why-bundle-for-production} 47 | 48 | 이제 기본적으로 ESM이 대부분의 환경에서 지원되지만, 프로덕션에서 번들 되지 않은 ESM을 가져오는 것은 중첩된 import로 인한 추가 네트워크 통신으로 인해 여전히 비효율적입니다(HTTP/2를 사용하더라도). 프로덕션 환경에서 최적의 로딩 성능을 얻으려면 트리 셰이킹, 지연 로딩 및 청크 파일 분할(더 나은 캐싱을 위해)을 이용하여 번들링 하는 것이 더 좋습니다. 49 | 50 | 개발 서버와 프로덕션 빌드 간에 최적의 출력과 동작 일관성을 보장하는 것은 쉽지 않습니다. 이것이 바로 Vite가 미리 설정된 [빌드 커맨드](./build.md)를 이용하고, [빌드 최적화](./features.md#build-optimizations)를 진행하는 이유입니다. 51 | 52 | ## 왜 번들링 시에는 Esbuild를 사용하지 않나요? {#why-not-bundle-with-esbuild} 53 | 54 | Vite는 [개발 환경에서 일부 디펜던시를 사전 번들링](./dep-pre-bundling.md)하기 위해 esbuild를 사용하지만, 프로덕션 빌드를 위한 번들러로는 사용하지 않습니다. 55 | 56 | Vite의 현재 플러그인 API는 `esbuild`를 번들러로 사용하는 것과 호환되지 않습니다. `esbuild`가 더 빠르지만, Vite가 Rollup의 유연한 플러그인 API 및 인프라를 적극적으로 채택한 것은 생태계에서의 성공에 큰 기여를 했습니다. 현재로서는 Rollup이 성능 대 유연성 트레이드오프에서 더 나은 선택이라고 믿습니다. 57 | 58 | Rollup은 [v4에서 파서를 SWC로 전환](https://github.com/rollup/rollup/pull/5073)하는 등 성능 개선을 위해 노력해 왔습니다. 또한 Rollup의 Rust 포팅인 Rolldown을 만드는 작업이 진행 중입니다. Rolldown이 준비되면 Rollup과 esbuild를 모두 대체하여 빌드 성능을 크게 향상시키고 개발과 빌드 사이의 불일치를 제거할 수 있습니다. [Evan You의 ViteConf 2023 키노트](https://youtu.be/hrdwQHoAp0M)에서 자세한 내용을 확인할 수 있습니다. 59 | 60 | ## Vite는 다른 번들링하지 않는 빌드 툴과 어떤 관계가 있나요? {#how-vite-relates-to-other-unbundled-build-tools} 61 | 62 | Preact 팀이 제공하는 [WMR](https://github.com/preactjs/wmr)은 비슷한 기능을 제공하고자 했습니다. Vite 개발 및 빌드를 위한 범용 Rollup 플러그인 API는 여기에서 영감을 받았습니다. 다만 WMR은 더 이상 관리되지 않습니다. Preact 팀은 Vite와 함께 [@preactjs/preset-vite](https://github.com/preactjs/preset-vite) 플러그인 사용을 권장하고 있습니다. 63 | 64 | [Snowpack](https://www.snowpack.dev/)도 번들링을 하지 않는 네이티브 ESM 개발 서버로, Vite와 매우 유사한 영역에 있었습니다. Vite에서 제공하는 디펜던시 사전 번들링 기능 역시 Snowpack v1(현재는 [`esinstall`](https://github.com/snowpackjs/snowpack/tree/main/esinstall))에서 영감을 받았습니다. 마찬가지로 Snowpack은 더 이상 관리되지 않고 있습니다. Snowpack 팀은 현재 Vite를 기반으로 한 정적 사이트 빌더인 [Astro](https://astro.build/)를 개발하고 있습니다. 65 | 66 | [@web/dev-server](https://modern-web.dev/docs/dev-server/overview/)(이전에는 `es-dev-server`)는 훌륭한 프로젝트로, 이로부터 Vite 1.0 Koa 기반 서버 설정에 대한 영감을 받았었습니다. `@web`라는 우산 아래에 있는 프로젝트는 활발하게 유지보수되고 있으며, Vite 사용자에게도 도움이 될 수 있는 많은 우수한 도구들을 포함하고 있습니다. -------------------------------------------------------------------------------- /images/bundler.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vitejs/docs-ko/fc14d974a6885dbe5da00fcd51c053c57144deb4/images/bundler.png -------------------------------------------------------------------------------- /images/bundler.svg: -------------------------------------------------------------------------------- 1 | 2 | Bundle based dev server 3 | 4 | 5 | entry 6 | 7 | ··· 8 | 9 | route 10 | 11 | route 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | module 23 | 24 | module 25 | 26 | module 27 | 28 | module 29 | 30 | ··· 31 | 32 | 33 | 34 | Bundle 35 | 36 | Server ready 37 | 38 | -------------------------------------------------------------------------------- /images/diagrams.fig: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vitejs/docs-ko/fc14d974a6885dbe5da00fcd51c053c57144deb4/images/diagrams.fig -------------------------------------------------------------------------------- /images/esm.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vitejs/docs-ko/fc14d974a6885dbe5da00fcd51c053c57144deb4/images/esm.png -------------------------------------------------------------------------------- /images/esm.svg: -------------------------------------------------------------------------------- 1 | 2 | Native ESM based dev server 3 | 4 | entry 5 | 6 | 7 | ··· 8 | 9 | 10 | route 11 | 12 | route 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | module 25 | 26 | module 27 | 28 | module 29 | 30 | module 31 | 32 | ··· 33 | 34 | Server ready 35 | 36 | 37 | Dynamic import (code split point) 38 | HTTP request 39 | 40 | 41 | 42 | 43 | 44 | 45 | 46 | 47 | 48 | 49 | 50 | 51 | 52 | -------------------------------------------------------------------------------- /images/graph.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vitejs/docs-ko/fc14d974a6885dbe5da00fcd51c053c57144deb4/images/graph.png -------------------------------------------------------------------------------- /images/lit.svg: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /images/placeholder.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vitejs/docs-ko/fc14d974a6885dbe5da00fcd51c053c57144deb4/images/placeholder.jpg -------------------------------------------------------------------------------- /images/preact.svg: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /images/react.svg: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /images/svelte.svg: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /images/v3-docs.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vitejs/docs-ko/fc14d974a6885dbe5da00fcd51c053c57144deb4/images/v3-docs.png -------------------------------------------------------------------------------- /images/v3-new-open-issues-and-PRs.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vitejs/docs-ko/fc14d974a6885dbe5da00fcd51c053c57144deb4/images/v3-new-open-issues-and-PRs.png -------------------------------------------------------------------------------- /images/v3-open-issues-and-PRs.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vitejs/docs-ko/fc14d974a6885dbe5da00fcd51c053c57144deb4/images/v3-open-issues-and-PRs.png -------------------------------------------------------------------------------- /images/vercel-configuration.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vitejs/docs-ko/fc14d974a6885dbe5da00fcd51c053c57144deb4/images/vercel-configuration.png -------------------------------------------------------------------------------- /images/vite-plugin-inspect.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vitejs/docs-ko/fc14d974a6885dbe5da00fcd51c053c57144deb4/images/vite-plugin-inspect.png -------------------------------------------------------------------------------- /images/vite.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | -------------------------------------------------------------------------------- /images/vue.svg: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /index.md: -------------------------------------------------------------------------------- 1 | --- 2 | title: Vite 3 | titleTemplate: 프런트엔드 개발의 새로운 기준 4 | pageClass: landing dark 5 | 6 | layout: home 7 | aside: false 8 | editLink: false 9 | markdownStyles: false 10 | --- 11 | 12 | 28 | 29 |
30 | 31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | 41 | 42 | 43 | 44 | 45 | 46 | 47 |
-------------------------------------------------------------------------------- /package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "docs-ko", 3 | "version": "1.0.0", 4 | "description": "Vite.js documentation Korean translation", 5 | "repository": "https://github.com/vitejs/docs-ko", 6 | "author": "Evan You", 7 | "license": "MIT", 8 | "type": "module", 9 | "private": true, 10 | "packageManager": "pnpm@10.8.1", 11 | "engines": { 12 | "node": ">=22.0.0" 13 | }, 14 | "devDependencies": { 15 | "@shikijs/types": "^3.2.2", 16 | "@shikijs/vitepress-twoslash": "^2.5.0", 17 | "@type-challenges/utils": "^0.1.1", 18 | "@types/markdown-it-footnote": "^3.0.4", 19 | "@types/node": "^22.13.4", 20 | "feed": "^4.2.2", 21 | "gray-matter": "^4.0.3", 22 | "gsap": "^3.12.7", 23 | "markdown-it-footnote": "^4.0.0", 24 | "prettier": "3.5.1", 25 | "vite": "^6.3.1", 26 | "vitepress": "^1.6.3", 27 | "vitepress-plugin-group-icons": "^1.5.2", 28 | "vue": "^3.5.13" 29 | }, 30 | "scripts": { 31 | "dev": "vitepress dev", 32 | "build": "vitepress build", 33 | "serve": "vitepress serve", 34 | "rewrite-title": "node scripts/rewrite-title" 35 | }, 36 | "pnpm": { 37 | "overrides": { 38 | "vite": "^6.3.1", 39 | "rollup": "^4.40.0" 40 | } 41 | } 42 | } 43 | -------------------------------------------------------------------------------- /plugins/index.md: -------------------------------------------------------------------------------- 1 | # 플러그인 {#plugins} 2 | 3 | :::tip 참고 4 | `Vite`는 일반적인 웹 개발 패턴들에 대한 기본적인 지원을 제공하는 것을 목표로 합니다. `Vite` 또는 `Rollup` 호환 플러그인을 검색하기 전에, [지원하는 기능들](../guide/features.md) 페이지를 확인해 보세요. `Rollup` 프로젝트에 플러그인이 필요한 많은 경우가 이미 `Vite`에 구현되어 있습니다. 5 | ::: 6 | 7 | 플러그인 사용법은 [플러그인 사용하기](../guide/using-plugins) 문서를 참고해주세요. 8 | 9 | ## 공식 플러그인 {#official-plugins} 10 | 11 | ### [@vitejs/plugin-vue](https://github.com/vitejs/vite-plugin-vue/tree/main/packages/plugin-vue) {#vitejs-plugin-vue} 12 | 13 | - Vue 3 단일 파일 컴포넌트(SFC)의 지원을 제공합니다. 14 | 15 | ### [@vitejs/plugin-vue-jsx](https://github.com/vitejs/vite-plugin-vue/tree/main/packages/plugin-vue-jsx) {#vitejs-plugin-vue-jsx} 16 | 17 | - Vue 3 JSX 지원을 제공합니다. ([전용 `Babel` 변형](https://github.com/vuejs/jsx-next)을 통해) 18 | 19 | ### [@vitejs/plugin-vue2](https://github.com/vitejs/vite-plugin-vue2) {#vitejs-plugin-vue2} 20 | 21 | - Vue 2.7 단일 파일 컴포넌트(SFC)를 지원합니다. 22 | 23 | ### [@vitejs/plugin-vue2-jsx](https://github.com/vitejs/vite-plugin-vue2-jsx) {#vitejs-plugin-vue2-jsx} 24 | 25 | - [전용 바벨 프리셋](https://github.com/vuejs/jsx-vue2/)을 통해 Vue 2.7 JSX를 지원합니다 26 | 27 | ### [@vitejs/plugin-react](https://github.com/vitejs/vite-plugin-react/tree/main/packages/plugin-react) {#vitejs-plugin-react} 28 | 29 | - esbuild와 Babel을 사용하여 작은 패키지 크기와 Babel 변형 파이프라인의 유연성을 통해 빠른 HMR을 달성합니다. 추가 Babel 플러그인이 없으면 빌드 중 esbuild만 사용됩니다. 30 | 31 | ### [@vitejs/plugin-react-swc](https://github.com/vitejs/vite-plugin-react-swc) {#vitejs-plugin-react-swc} 32 | 33 | - 개발 중에는 Babel 대신 SWC를 사용합니다. 프로덕션 빌드 중 플러그인을 사용하게 된다면 SWC+esbuild를 사용하고, 그렇지 않다면 esbuild만을 사용합니다. 비표준 React 확장이 필요하지 않은 대규모 프로젝트의 경우, 콜드 스타트와 Hot Module Replacement(HMR)이 훨씬 빠르게 작동할 수 있습니다. 34 | 35 | ### [@vitejs/plugin-legacy](https://github.com/vitejs/vite/tree/main/packages/plugin-legacy) {#vitejs-plugin-legacy} 36 | 37 | - 프로덕션 빌드를 위한 이전 브라우저 지원을 제공합니다. 38 | 39 | ## 커뮤니티 플러그인 {#community-plugins} 40 | 41 | [awesome-vite](https://github.com/vitejs/awesome-vite)를 확인해 보세요. 또한 그곳에서 PR을 제출하여 여러분의 플러그인을 목록에 올릴 수 있습니다. 42 | 43 | ## `Rollup` 플러그인 {#rollup-plugins} 44 | 45 | [Vite 플러그인](../guide/api-plugin)은 `Rollup` 플러그인 인터페이스의 확장입니다. 더 많은 정보를 알려면 [Rollup 플러그인 호환 섹션](../guide/api-plugin#rollup-plugin-compatibility)을 참고하세요. -------------------------------------------------------------------------------- /public/_headers: -------------------------------------------------------------------------------- 1 | /assets/* 2 | cache-control: max-age=31536000 3 | cache-control: immutable 4 | 5 | /*.svg 6 | cache-control: max-age=604800 7 | cache-control: immutable 8 | 9 | /*.png 10 | cache-control: max-age=604800 11 | cache-control: immutable -------------------------------------------------------------------------------- /public/_redirects: -------------------------------------------------------------------------------- 1 | # temporary, we'll flip this around some day 2 | https://ko.vitejs.dev/* https://ko.vite.dev/:splat 301! 3 | 4 | /guide/api-vite-runtime /guide/api-environment 301 5 | /guide/api-vite-runtime.html /guide/api-environment 301 6 | /guide/api-vite-environment /guide/api-environment 301 7 | /guide/api-vite-environment.html /guide/api-environment 301 8 | /guide/comparisons /guide/why#how-vite-relates-to-other-unbundled-build-tools 301 9 | /guide/comparisons.html /guide/why#how-vite-relates-to-other-unbundled-build-tools 301 10 | 11 | # llms.txt 12 | /*.txt /:splat.md 301 13 | /llms.md /llms.txt 301 14 | /llms.txt /llms.txt 200! 15 | /llms-full.txt /llms-full.txt 200! 16 | 17 | # short links 18 | /rolldown /guide/rolldown 301 -------------------------------------------------------------------------------- /public/astro.svg: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /public/ecosystem-vite4.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vitejs/docs-ko/fc14d974a6885dbe5da00fcd51c053c57144deb4/public/ecosystem-vite4.png -------------------------------------------------------------------------------- /public/github.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | -------------------------------------------------------------------------------- /public/googledb5f3175b0d5a81b.html: -------------------------------------------------------------------------------- 1 | google-site-verification: googledb5f3175b0d5a81b.html -------------------------------------------------------------------------------- /public/logo-home.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | 41 | 42 | 43 | 44 | 45 | 46 | 47 | -------------------------------------------------------------------------------- /public/logo-uwu.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vitejs/docs-ko/fc14d974a6885dbe5da00fcd51c053c57144deb4/public/logo-uwu.png -------------------------------------------------------------------------------- /public/logo-with-shadow.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vitejs/docs-ko/fc14d974a6885dbe5da00fcd51c053c57144deb4/public/logo-with-shadow.png -------------------------------------------------------------------------------- /public/logo.svg: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | -------------------------------------------------------------------------------- /public/noise.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vitejs/docs-ko/fc14d974a6885dbe5da00fcd51c053c57144deb4/public/noise.png -------------------------------------------------------------------------------- /public/nuxtlabs.svg: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /public/og-image-announcing-vite3.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vitejs/docs-ko/fc14d974a6885dbe5da00fcd51c053c57144deb4/public/og-image-announcing-vite3.png -------------------------------------------------------------------------------- /public/og-image-announcing-vite4-3.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vitejs/docs-ko/fc14d974a6885dbe5da00fcd51c053c57144deb4/public/og-image-announcing-vite4-3.png -------------------------------------------------------------------------------- /public/og-image-announcing-vite4.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vitejs/docs-ko/fc14d974a6885dbe5da00fcd51c053c57144deb4/public/og-image-announcing-vite4.png -------------------------------------------------------------------------------- /public/og-image-announcing-vite5-1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vitejs/docs-ko/fc14d974a6885dbe5da00fcd51c053c57144deb4/public/og-image-announcing-vite5-1.png -------------------------------------------------------------------------------- /public/og-image-announcing-vite5.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vitejs/docs-ko/fc14d974a6885dbe5da00fcd51c053c57144deb4/public/og-image-announcing-vite5.png -------------------------------------------------------------------------------- /public/og-image-announcing-vite6.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vitejs/docs-ko/fc14d974a6885dbe5da00fcd51c053c57144deb4/public/og-image-announcing-vite6.png -------------------------------------------------------------------------------- /public/og-image.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vitejs/docs-ko/fc14d974a6885dbe5da00fcd51c053c57144deb4/public/og-image.jpg -------------------------------------------------------------------------------- /public/stackblitz.svg: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /public/vite.mp3: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vitejs/docs-ko/fc14d974a6885dbe5da00fcd51c053c57144deb4/public/vite.mp3 -------------------------------------------------------------------------------- /public/vite4-3-hmr-time.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vitejs/docs-ko/fc14d974a6885dbe5da00fcd51c053c57144deb4/public/vite4-3-hmr-time.png -------------------------------------------------------------------------------- /public/vite4-3-startup-time.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vitejs/docs-ko/fc14d974a6885dbe5da00fcd51c053c57144deb4/public/vite4-3-startup-time.png -------------------------------------------------------------------------------- /public/vite5-1-10K-modules-loading-time.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vitejs/docs-ko/fc14d974a6885dbe5da00fcd51c053c57144deb4/public/vite5-1-10K-modules-loading-time.png -------------------------------------------------------------------------------- /public/vite6-npm-weekly-downloads.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/vitejs/docs-ko/fc14d974a6885dbe5da00fcd51c053c57144deb4/public/vite6-npm-weekly-downloads.png -------------------------------------------------------------------------------- /public/voice.svg: -------------------------------------------------------------------------------- 1 | 7 | -------------------------------------------------------------------------------- /releases.md: -------------------------------------------------------------------------------- 1 | # 릴리스 {#releases} 2 | 3 | Vite 릴리스는 [시멘틱 버저닝](https://semver.org/)을 따릅니다. 최신 안정 버전은 [Vite npm 패키지 페이지](https://www.npmjs.com/package/vite)에서 확인할 수 있습니다. 4 | 5 | 이전 릴리스의 전체 변경 사항은 [GitHub](https://github.com/vitejs/vite/blob/main/packages/vite/CHANGELOG.md)에서 확인할 수 있습니다. 6 | 7 | ## 릴리스 주기 {#release-cycle} 8 | 9 | Vite는 정해진 릴리스 주기가 없습니다. 10 | 11 | - **패치** 릴리스는 필요할 때(보통 매주)마다 배포됩니다. 12 | - **마이너** 릴리스는 새로운 기능을 포함하며, 필요할 때(보통 2개월 단위)마다 배포됩니다. 베타 프리 릴리스 단계를 거칩니다. 13 | - **메이저** 릴리스는 일반적으로 [Node.js EOL 일정](https://endoflife.date/nodejs)에 맞춰 진행되며, 미리 공지됩니다. 이러한 릴리스는 생태계와 장기적인 논의와 함께, 알파 및 베타 프리 릴리스 단계(보통 매년)를 모두 거칩니다. 14 | 15 | Vite 팀이 지원하는 Vite 버전 범위는 아래 규칙에 따라 자동으로 결정됩니다: 16 | 17 | - **최신 마이너 버전** 은 정기적으로 수정 사항이 반영됩니다. 18 | - **직전 메이저 버전** (최신 마이너 버전만 해당) 및 **직전 마이너 버전** 은 중요한 수정 및 보안 패치를 지원받습니다. 19 | - **이전 두 메이저 버전** (최신 마이너 버전만 해당) 및 **이전 두 마이너 버전** 은 보안 패치를 지원받습니다. 20 | - 그 외 이전 모든 버전은 지원되지 않습니다. 21 | 22 | 예를 들어, Vite 최신 버전이 5.3.10인 경우: 23 | 24 | - `vite@5.3`은 5.3.10에 존재하는 정기 수정 사항이 포함되어 있습니다. 25 | - 중요한 수정 및 보안 패치는 `vite@4` 및 `vite@5.2`로 백포트됩니다. 26 | - 보안 패치도 `vite@3` 및 `vite@5.1`로 백포트됩니다. 27 | - `vite@2` 및 `vite@5.0`은 더 이상 지원하지 않습니다. 필요하다면 더 높은 버전을 사용해야 합니다. 28 | 29 | 따라서 정기적인 Vite 업데이트를 권장합니다. 메이저 버전 업데이트 시에는 [마이그레이션 가이드](https://ko.vite.dev/guide/migration.html)를 참고해 주세요. Vite 팀은 새 버전에 대한 품질을 보장하기 위해 생태계 내 주요 프로젝트와 긴밀하게 협력하고 있습니다. 새로운 Vite 버전은 출시 전 [vite-ecosystem-ci 프로젝트](https://github.com/vitejs/vite-ecosystem-ci)를 통해 테스트하기에, Vite를 사용하는 생태계 내 프로젝트 대부분은 출시 직후 이를 신속하게 지원하거나 마이그레이션을 제공할 수 있습니다. 30 | 31 | ## 시멘틱 버저닝 예외 사항 {#semantic-versioning-edge-cases} 32 | 33 | ### TypeScript 정의 {#typescript-definitions} 34 | 35 | Vite 마이너 버전 간 TypeScript 정의에 대한 호환되지 않는 변경 사항이 포함될 수 있습니다. 이유는 다음과 같습니다: 36 | 37 | - TypeScript 자체에서 마이너 버전 간 호환되지 않는 변경 사항이 존재하는 경우가 있으며, 이 경우 최신 버전의 TypeScript 지원을 위해 타입을 수정해야 할 수 있습니다. 38 | - 최신 버전의 TypeScript에서만 사용할 수 있는 기능을 채택해야 하는 경우가 있으며, 이 경우 TypeScript의 최소 요구 버전을 올려야 할 수 있습니다. 39 | - TypeScript를 사용하는 경우, 현재 마이너 버전을 고정하도록 semver 범위를 정의하고 새로운 Vite 마이너 버전이 릴리스되면 이를 수동으로 업그레이드할 수 있습니다. 40 | 41 | ### esbuild {#esbuild} 42 | 43 | [esbuild](https://esbuild.github.io/)는 1.0.0 이전 버전이기에, 때때로 새로운 기능과 성능 개선을 위해 포함해야 하는 중요한 변경 사항이 있을 수 있습니다. Vite 마이너 버전에서는 esbuild 버전이 변경될 수 있습니다. 44 | 45 | ### Node.js 비 LTS 버전 {#nodejs-non-lts-versions} 46 | 47 | LTS가 아닌 Node.js 버전(홀수)은 Vite CI의 대상으로 테스트되지 않지만, [EOL](https://endoflife.date/nodejs) 이전까지는 여전히 작동합니다. 48 | 49 | ## 프리 릴리스​ {#pre-releases} 50 | 51 | 마이너 릴리스는 일반적으로 정해지지 않은 횟수의 베타 릴리스를 거칩니다. 메이저 릴리스는 알파 단계와 베타 단계를 거칩니다. 52 | 53 | 프리 릴리스는 초기 사용자와 생태계 유지 관리자가 통합 및 안정성 테스트를 수행하고 피드백을 제공할 수 있도록 합니다. 따라서 프리 릴리스는 프로덕션 환경에서 사용하지 않아야 합니다. 모든 프리 릴리스는 불안정하며, 릴리스 사이에 중요한 변경 사항이 적용될 수도 있습니다. 또한 프리 릴리스는 항상 정확한 버전을 지정해 사용해주세요. 54 | 55 | ## 사용 중단 {#deprecations} 56 | 57 | 더 나은 대안으로 대체된 기능은 마이너 릴리스에서 주기적으로 사용이 중단됩니다. 사용이 중단된 기능은 타입이나 경고 로그와 함께 계속 작동은 하지만, 다음 메이저 릴리스에서 제거됩니다. 사용이 중단된 기능에 대한 목록과 마이그레이션 가이드는 각 메이저 버전의 [마이그레이션 가이드](https://ko.vite.dev/guide/migration.html)에서 확인할 수 있습니다. 58 | 59 | ## 실험적 기능 {#experimental-features} 60 | 61 | 일부 기능은 Vite의 안정 버전이 출시될 때 실험적 기능으로 표시됩니다. 실험적 기능의 목표는 사용자가 프로덕션 환경에서 테스트하여 피드백을 제공받을 수 있도록 하는 것이며, 이렇게 수집된 피드백은 최종 설계에 영향을 미칠 수 있습니다. 다만 실험적 기능 자체는 불안정한 것으로 간주되며, 통제된 방식으로만 사용해야 합니다. 또한 이러한 기능은 마이너 버전 간에 변경될 수 있으므로 사용자는 이를 사용할 때 Vite 버전을 고정해야 합니다. 이러한 실험적 기능에 대해서는 [GitHub Discussion](https://github.com/vitejs/vite/discussions/categories/feedback?discussions_q=is%3Aopen+label%3Aexperimental+category%3AFeedbac)을 만들 예정입니다. -------------------------------------------------------------------------------- /scripts/rewrite-title/formatter.js: -------------------------------------------------------------------------------- 1 | const fs = require('fs') 2 | const matter = require('gray-matter') 3 | 4 | module.exports = { 5 | open(filePath) { 6 | this.filePath = filePath 7 | this.file = fs.readFileSync(filePath) 8 | this.matter = matter(this.file.toString()) 9 | 10 | return this 11 | }, 12 | 13 | set(key, value) { 14 | this.matter.data[key] = value 15 | return this 16 | }, 17 | 18 | save() { 19 | const matterStringifyData = this.matter.stringify() 20 | 21 | fs.writeFile(this.filePath, matterStringifyData, (err) => { 22 | if (err) { 23 | console.warn(`${this.filePath} - Saving file with matter failed`) 24 | } 25 | }) 26 | }, 27 | } 28 | -------------------------------------------------------------------------------- /scripts/rewrite-title/index.js: -------------------------------------------------------------------------------- 1 | const path = require('path') 2 | const fs = require('fs') 3 | const formatter = require('./formatter') 4 | const workspacePath = path.resolve(__dirname, '..', '..') 5 | 6 | const h1MdRE = /^#\s+(.+)\s+(\{#([\w-]+)\})$/ 7 | const articleDirs = ['blog', 'config', 'guide', 'plugins'] 8 | 9 | const rewriteMdTitle = (filePath) => { 10 | const matter = formatter.open(filePath) 11 | const lines = matter.file.toString().split(/\r?\n/) 12 | const h1Line = lines.find((line) => h1MdRE.test(line)) 13 | 14 | if (h1Line === undefined) { 15 | return 16 | } 17 | 18 | const title = h1MdRE.exec(h1Line)[1] 19 | matter.set('title', title).save() 20 | } 21 | 22 | const ergodicDirectory = (dirPath) => 23 | fs.readdir(dirPath, (err, files) => { 24 | if (err) { 25 | console.warn(`${dirPath} - Directory reading failed`) 26 | return 27 | } 28 | 29 | files.forEach((file) => { 30 | const filePath = path.join(dirPath, file) 31 | 32 | fs.stat(filePath, (err, stats) => { 33 | if (err) { 34 | console.log(`${filePath} - File status reading failed`) 35 | return 36 | } 37 | 38 | if ( 39 | // rewrite files 40 | stats.isFile() && 41 | filePath.split('.').pop().toLowerCase() === 'md' 42 | ) { 43 | rewriteMdTitle(filePath) 44 | } else if ( 45 | // recursive find target file 46 | stats.isDirectory() && 47 | articleDirs.includes(file) 48 | ) { 49 | ergodicDirectory(filePath) 50 | } 51 | }) 52 | }) 53 | }) 54 | 55 | ergodicDirectory(workspacePath) 56 | -------------------------------------------------------------------------------- /team.md: -------------------------------------------------------------------------------- 1 | --- 2 | layout: page 3 | title: Meet the Team 4 | description: The development of Vite is guided by an international team. 5 | --- 6 | 7 | 16 | 17 | 18 | 19 | 20 | 23 | 24 | 25 | 26 | 27 | 30 | 33 | 34 | --------------------------------------------------------------------------------