Open-Source Wikis

/

Vue.js

/

How to contribute

/

Development workflow

vuejs/core

Development workflow

This page describes the day-to-day cycle of writing a change against vuejs/core: branching, committing, opening a PR, and getting it merged. It complements Getting started, which covers the one-time setup.

Pick a branch

The repo has two upstream branches:

  • main — receives bug fixes (3.5.x line). Patch releases are cut from here.
  • minor — receives feature work and performance changes for the next minor (3.6 at the time of writing).

Decide by the change you are making:

Change Target branch
Fix a bug, fix a regression, restore old behavior main
Add a new public API, deprecate one, or change semantics minor
Performance improvement that touches many files minor
Docs, types, comments, build config, CI, lint whichever the related code lives on (usually main)

The diagram in .github/git-branch-workflow.png shows how main is periodically merged into minor so feature branches stay current.

Fork the repo, then branch off the right base:

git checkout main           # or `minor`
git pull
git checkout -b fix-keep-alive-leak

Commit

Vue enforces the Angular commit convention. The validator regex from scripts/verify-commit.js is:

/^(revert: )?(feat|fix|docs|dx|style|refactor|perf|test|workflow|build|ci|chore|types|wip)(\(.+\))?: .{1,50}/

Examples (taken from the existing git log):

  • fix(reactivity): correctly handle Symbol(...)keys inarrayInstrumentations (close #12345)
  • feat(compiler-sfc): support importing types from .d.ts modules
  • perf(runtime-core): avoid an extra closure when scheduling jobs
  • chore(deps): bump rollup to 4.60.2
  • docs(contributing): clarify branch model

Subject lines are imperative ("add", not "added"), capped at 50 characters, and don't end in a period. Scopes are free-form; common ones are core, compiler, compiler-sfc, ssr, runtime-dom, v-model, transition, keep-alive, hydration, types, deps.

Only feat, fix, and perf show up in the auto-generated changelog. If the commit changes behavior in a backwards-incompatible way, add a BREAKING CHANGE: footer.

The pre-commit hook (simple-git-hooks) will:

  1. Run pnpm lint-staged (Prettier + ESLint on staged .js/.ts/.json).
  2. Run pnpm check (full-monorepo tsc --noEmit). On a fresh checkout this can take a minute. Use the --incremental cache (tsconfig.json already enables it).

The commit-msg hook validates the message against the regex above.

Open the PR

The PR template requires:

  • Description: what the change does and why. For bugs, link the issue (fix #1234) so the changelog entry has a backlink.
  • Repro: a CodeSandbox / SFC Playground link or a minimal repo for non-trivial bugs. See .github/bug-repro-guidelines.md.
  • Test coverage: a Vitest test under the relevant __tests__/ directory. The contributing guide says "make sure tests pass!" — and CI will reject anything that fails.
  • Allow edits from maintainers: leave the checkbox enabled. Evan and other reviewers often push small fixes directly to keep the queue moving.

CI runs on every push:

  • .github/workflows/ci.ymlpnpm check, pnpm lint, pnpm format-check.
  • .github/workflows/test.yml — Vitest unit tests, e2e tests, dts tests.
  • .github/workflows/size-report.yml — runs the size report and posts a delta comment on the PR.
  • .github/workflows/ecosystem-ci-trigger.yml — opt-in cross-repo testing against Nuxt, Quasar, Vuetify, etc.
  • .github/workflows/autofix.yml — auto-applies Prettier formatting changes when needed.

Address review

The .github/maintenance.md doc lays out the maintainers' expectations:

  • PR scope should match the title. If you find a related bug, open a separate PR.
  • Performance-sensitive code (renderer, scheduler, dep.ts, prop normalization) should be benchmarked. Run pnpm bench-compare against pnpm bench baseline.
  • Bundle size is a recurring concern. The size-report bot will comment with the delta; if your change adds runtime code, justify the cost in the PR description. Dev-only paths must be inside __DEV__ branches so they tree-shake out of prod builds.

Squash and merge

The maintainers usually squash-merge so the squashed commit message becomes the changelog entry. That means your final commit subject — not your individual WIP commits — needs to follow the convention.

If your PR closes an issue, include fix #N (or close #N) in either the subject or body so GitHub auto-closes it.

Releases

Releases are cut by scripts/release.js, run by maintainers (not contributors). The script bumps versions in every package, regenerates the changelog with conventional-changelog, tags the commit, and publishes through .github/workflows/release.yml. End users see the result in CHANGELOG.md and on npm.

Built by Factory AutoWiki from public repository content. It is a generated preview for codebase exploration, not source-maintained documentation.

Development workflow – Vue.js wiki | Factory