Skip to content
C++
Package Manager
Updated 2025-01-01T00:00:00.000Z

vcpkg

Microsoft's C++ package manager — manifest mode, classic mode, CMake integration, triplets, overlays, and binary caching.

TL;DR

vcpkg is a cross-platform C++ package manager from Microsoft. Manifest mode (recommended) keeps your dependencies in a vcpkg.json next to your CMakeLists.txt. CMake integration is seamless — packages just work after find_package().

bash
git clone https://github.com/microsoft/vcpkg
./vcpkg/bootstrap-vcpkg.sh  # Linux/macOS
# or: .\vcpkg\bootstrap-vcpkg.bat  (Windows)

Create vcpkg.json in your project root:

json
{
  "name": "my-project",
  "version": "1.0.0",
  "dependencies": [
    "fmt",
    "nlohmann-json",
    "boost-algorithm",
    {
      "name": "openssl",
      "version>=": "3.0.0"
    }
  ]
}

Tell CMake where vcpkg is:

cmake
# CMakeLists.txt — before project()
set(CMAKE_TOOLCHAIN_FILE "${VCPKG_ROOT}/scripts/buildsystems/vcpkg.cmake"
    CACHE STRING "vcpkg toolchain")

cmake_minimum_required(VERSION 3.25)
project(my-project)

find_package(fmt CONFIG REQUIRED)
find_package(nlohmann_json CONFIG REQUIRED)
find_package(OpenSSL REQUIRED)

add_executable(myapp main.cpp)
target_link_libraries(myapp PRIVATE
    fmt::fmt
    nlohmann_json::nlohmann_json
    OpenSSL::SSL
)
bash
# vcpkg installs dependencies automatically during cmake configure
cmake -B build -DVCPKG_ROOT=/path/to/vcpkg
cmake --build build

Set VCPKG_ROOT environment variable permanently to avoid repeating it:

bash
export VCPKG_ROOT=/home/user/vcpkg   # ~/.bashrc or ~/.zshrc

Classic mode

Install packages globally into the vcpkg installation:

bash
vcpkg install fmt nlohmann-json boost-algorithm
vcpkg install openssl:x64-linux     # explicit triplet
vcpkg list                          # show installed packages
vcpkg remove fmt                    # uninstall
vcpkg upgrade                       # update all

Classic mode is useful for quick experiments but manifest mode is preferred for reproducible builds.


Triplets — platform/compiler targets

Triplets specify the target architecture, OS, and linkage:

bash
# Common triplets
x64-linux            # x86-64, Linux, dynamic
x64-linux-release    # x86-64, Linux, release static
x64-windows          # x86-64, Windows, dynamic (MSVC)
x64-windows-static   # x86-64, Windows, static (MSVC)
x64-mingw-dynamic    # x86-64, Windows, MinGW
arm64-osx            # Apple Silicon macOS
arm-neon-android     # Android ARM

# In vcpkg.json — set default triplet
{
  "name": "my-project",
  "dependencies": ["fmt"],
  "vcpkg-configuration": {
    "default-registry": {
      "kind": "git",
      "repository": "https://github.com/microsoft/vcpkg",
      "baseline": "abc123..."
    }
  }
}
cmake
# Force static linking
set(VCPKG_TARGET_TRIPLET "x64-linux-release" CACHE STRING "")

Binary caching

vcpkg can cache compiled packages to avoid recompiling on every CI run:

bash
# Local filesystem cache (default location on Linux)
~/.cache/vcpkg/archives/

# Custom cache location
export VCPKG_DEFAULT_BINARY_CACHE=/mnt/cache/vcpkg

# GitHub Actions cache
- uses: actions/cache@v4
  with:
    path: ~/.cache/vcpkg
    key: vcpkg-${{ hashFiles('vcpkg.json') }}

Versioning and baselines

Manifest mode supports exact version pinning:

json
{
  "name": "my-project",
  "dependencies": [
    { "name": "fmt", "version>=": "10.1.0" },
    { "name": "boost-filesystem", "version>=": "1.83.0" }
  ],
  "overrides": [
    { "name": "fmt", "version": "10.1.1" }
  ],
  "builtin-baseline": "a42af01b72c28a8e1d7b48107b33e4f286a55ef6"
}

The builtin-baseline pins the entire registry to a specific git commit, ensuring reproducible builds.

bash
# Update baseline to latest
vcpkg x-update-baseline

Custom overlays

Add packages not in the vcpkg registry:

cpp
project/
├── CMakeLists.txt
├── vcpkg.json
└── overlays/
    └── ports/
        └── my-private-lib/
            ├── portfile.cmake
            └── vcpkg.json
json
// vcpkg.json — reference the overlay
{
  "name": "my-project",
  "dependencies": ["my-private-lib"],
  "vcpkg-configuration": {
    "overlay-ports": ["./overlays/ports"]
  }
}

Common packages and their CMake target names

vcpkg packagefind_package()Target
fmtfmtfmt::fmt
nlohmann-jsonnlohmann_jsonnlohmann_json::nlohmann_json
boost-filesystemBoost COMPONENTS filesystemBoost::filesystem
opensslOpenSSLOpenSSL::SSL OpenSSL::Crypto
sqlite3unofficial-sqlite3unofficial::sqlite3::sqlite3
catch2Catch2Catch2::Catch2WithMain
gtestGTestGTest::gtest_main
spdlogspdlogspdlog::spdlog
protobufProtobufprotobuf::libprotobuf
zlibZLIBZLIB::ZLIB

CI integration (GitHub Actions)

yaml
- name: Setup vcpkg
  uses: lukka/run-vcpkg@v11
  with:
    vcpkgDirectory: ${{ github.workspace }}/vcpkg
    vcpkgGitCommitId: 'a42af01b72c28a8e1d7b48107b33e4f286a55ef6'

- name: Configure CMake
  run: cmake -B build -DCMAKE_TOOLCHAIN_FILE=$VCPKG_ROOT/scripts/buildsystems/vcpkg.cmake

- name: Build
  run: cmake --build build

Or using the built-in GitHub-hosted vcpkg:

yaml
- name: Install vcpkg deps
  run: vcpkg install --triplet x64-linux
  env:
    VCPKG_ROOT: /usr/local/share/vcpkg
Edit on GitHubUpdated 2025-01-01T00:00:00.000Z