In FVM, how do fvm use and fvm global differ, and which SDK does fvm flutter pick when both are set?
answer
- project pin versus machine default
- nearest .fvmrc wins
- global is a default link
- put default/bin on PATH
- fallback to PATH's flutter
basics
~20 sfvm use pins a version for one project in .fvmrc; fvm global sets a machine-wide default link. fvm flutter uses the nearest project pin first, then the global version, then whatever flutter is on PATH.
solid answer
~40 s`fvm use <version>` is **per project**: it writes `.fvmrc`, links `.fvm/flutter_sdk` and updates project tooling. `fvm global <version>` is **per machine**: it points the link `~/fvm/default` at a cached SDK, and you put `~/fvm/default/bin` on `PATH` so plain `flutter` uses it; FVM warns if your `PATH` resolves `flutter` elsewhere, and `fvm global --unlink` removes it. When you run `fvm flutter` or `fvm dart`, FVM searches from the current directory upward for the nearest `.fvmrc`; if it finds a pin it runs that version, otherwise it uses the global version, and without either it falls back to `flutter` on `PATH`. `fvm list` shows cached versions with Global and Local columns, and `fvm releases` lists installable releases, stable by default.
code
bash · 9 linesfvm global 3.47.5 # machine default -> ~/fvm/default
export PATH="$HOME/fvm/default/bin:$PATH" # once, in your shell profile
cd ~/work/client_a && fvm use 3.41.4 # project pin
fvm flutter --version # 3.41.4 (project pin wins)
cd ~ && fvm flutter --version # 3.47.5 (no .fvmrc above, global used)
fvm list # Global and Local columns show both
fvm use stable --pin # pin stable's latest release as an exact versiongo deeper
Know that fvm use is for one project and fvm global is the machine default, and that fvm list shows both.
Explain the lookup order, nearest .fvmrc then global then PATH, why global needs default/bin on PATH, and channel pins versus exact versions.
Diagnose the wrong SDK running with fvm doctor and fvm list, use --pin or exact versions for reproducibility, and structure pins in nested folders.
Set a policy for global defaults versus mandatory project pins so developer machines cannot drift from what CI builds.
## Two scopes FVM manages SDKs at two scopes, and confusing them is the most common FVM mistake. | | `fvm use <version>` | `fvm global <version>` | |---|---|---| | Scope | one project (and its subfolders) | the whole machine | | Stored in | `.fvmrc` in the project root | the link `<fvm dir>/default` | | Links created | `.fvm/flutter_sdk`, `.fvm/versions/<version>` | `default` pointing at the cached SDK | | Side effects | SDK setup, `.gitignore`, `pub get`, VS Code settings | a warning if `PATH` resolves `flutter` elsewhere | | Undo | `fvm use` another version | `fvm global --unlink` | The FVM directory is `~/fvm` by default (`FVM_CACHE_PATH` or `fvm config --cache-path` changes it); cached SDKs live in its `versions/` folder. ## How fvm flutter chooses an SDK `fvm flutter`, `fvm dart` and `fvm exec` all run the same selection: 1. **Project pin.** Starting at the current directory, walk up the directory tree to the nearest folder containing `.fvmrc`. If it pins a version, make sure it is cached and use it. 2. **Global version.** Otherwise, if `fvm global` has set one, use it. 3. **`PATH`.** Otherwise, run whatever `flutter` or `dart` the shell finds. The chosen SDK's `bin` directories are **prepended to `PATH`** for the child process, so tools that the command spawns also see the right SDK. Because the lookup walks upward, a package in `packages/shared` without its own `.fvmrc` uses the pin at the repository root, while an app with its own `.fvmrc` overrides it. ## Making plain flutter use the global version `fvm global` changes a link; it cannot change your shell. For plain `flutter` to use it, `<fvm dir>/default/bin` must be on `PATH`, typically ahead of any other Flutter install. After setting the global version, FVM compares `which flutter` with the expected paths and prints the current and the suggested path when they disagree. In VS Code's integrated terminal the editor may override `PATH`, and FVM says so. ## Seeing what is where - **`fvm list`** — cached SDKs with their channel, Flutter and Dart versions, release date, and markers in the **Global** and **Local** columns; a **Projects** column counts known projects pinning each SDK and labels unpinned ones `Unused`. - **`fvm releases`** — releases available to install; `-c` filters by channel and defaults to `stable`. - **`fvm doctor`** — the project, the pin and the environment FVM sees, useful when the wrong SDK runs. - **`fvm remove <version>`** or **`fvm cleanup`** — free disk space from versions nothing uses. ## Channels versus exact versions Both commands accept a channel name (`stable`, `beta`) or an exact version. A channel pin follows whatever that cached channel checkout is, so two machines can differ. For reproducibility: - pin exact versions, or - use `fvm use stable --pin`, which resolves the channel's latest release and writes that exact version. `fvm flutter upgrade` is refused when the selected version is a release rather than a channel, because upgrading a pinned release would silently change it.
- In a repository with .fvmrc at the root and none in packages/shared, which SDK does fvm flutter test use inside packages/shared?The root's. FVM walks up from the current directory to the nearest `.fvmrc`, so a subfolder without its own file inherits the root pin. A nested project that runs `fvm use` gets its own `.fvmrc`, which then takes precedence for that subtree.
- Why does FVM refuse fvm flutter upgrade on a project pinned to 3.47.5?A release pin means exactly that version. Running `flutter upgrade` inside the cached SDK would move it to a newer build while the pin still says 3.47.5, and every project sharing the cache would change too. FVM allows upgrade only on channel installs; to move a project, run `fvm use` with the new version.
saying these in an interview costs you the question
- Uses fvm global to pin a single project's version
- Expects fvm global to change PATH by itself
- Thinks fvm flutter ignores .fvmrc files in parent directories
- Pins a channel name and calls the build reproducible
- Runs fvm flutter upgrade to move a release-pinned project