空のフォルダーからCMake+MSVC+vcpkgをCopilot CLIで構築する手順

空のフォルダーからでも、GitHub Copilot CLIのPlan Modeで構成を設計し、リポジトリ内のvcpkg、vcpkg.jsonCMakeLists.txtCMakePresets.jsonを生成させれば、MSVCによるビルドと実行確認まで一気に進められます

重要なのは、Copilotに絶対パスのinclude先や.libファイルを直接指定させないことです。依存関係はvcpkg manifest modeで宣言し、CMakeではfind_package()とインポート済みターゲットを使います。これにより、PCごとのインストール先を意識せず、別の開発環境やCIでも復元しやすいC++プロジェクトになります。

Microsoft C++ Team Blogでも、空のフォルダーからGitHub Copilot CLI、vcpkg、CMake、MSVCを組み合わせてコンソールアプリを構築する流れが紹介されています。(Microsoft for Developers)

目次

Copilot CLI+vcpkg+CMake+MSVCの役割

まず、4つのツールが何を担当するのかを整理しておきましょう。

要素主な役割この構成で作るもの
GitHub Copilot CLI要件整理、ライブラリ選定、ファイル生成、コマンド実行実装計画、ソースコード、設定ファイル
vcpkgC++ライブラリの取得、ビルド、依存関係管理vcpkg.jsonvcpkg_installed
CMakeソース、ライブラリ、コンパイラ設定の統合CMakeLists.txt、ビルドシステム
MSVC Build ToolsC++のコンパイルとリンク.exe、オブジェクトファイル

ここでいう「手作業のinclude/link設定なし」とは、第三者ライブラリのヘッダーディレクトリやライブラリファイルを、次のように直接記述しないという意味です。

# 避けたい例
include_directories("C:/libraries/fmt/include")
link_directories("C:/libraries/fmt/lib")
target_link_libraries(myapp PRIVATE "C:/libraries/fmt/lib/fmt.lib")

代わりに、次のようなターゲットベースの書き方へ統一します。

find_package(fmt CONFIG REQUIRED)
target_link_libraries(myapp PRIVATE fmt::fmt)

vcpkgのCMake toolchainを読み込むと、find_package()がvcpkgで復元されたライブラリを検索できるようになります。manifest modeでは、CMakeの構成時にvcpkg.jsonが検出され、必要なパッケージのインストールも自動的に実行されます。(Microsoft Learn)

完成後のプロジェクト構成

この記事では、JSONファイルからランダムにメッセージを選び、整形して表示するquotecliを例にします。

完成後の構成は次のとおりです。

quotecli/
├─ .git/
├─ .gitignore
├─ .gitmodules
├─ CMakeLists.txt
├─ CMakePresets.json
├─ README.md
├─ vcpkg.json
├─ data/
│  └─ quotes.json
├─ src/
│  └─ main.cpp
└─ vcpkg/
   ├─ bootstrap-vcpkg.bat
   └─ scripts/
      └─ buildsystems/
         └─ vcpkg.cmake

buildフォルダーやvcpkg_installedは、構成・ビルド時に生成されるため、Gitには登録しません。

また、vcpkgを単なるコピーとして置くのではなく、Git submoduleとして登録する構成にすると、チーム内で使用するvcpkg自体のコミットも固定できます。試作だけなら通常のgit cloneでも動きますが、継続的に管理するリポジトリではsubmoduleのほうが意図を明確にしやすくなります。

事前に準備するもの

MSVC Build Toolsをインストールする

Visual Studio IDE全体は必須ではありません。Microsoft C++ Build Toolsだけでも、C++コンパイラ、リンカー、Windows SDKなどを利用できます。

Visual Studio Installerでは、少なくとも次のワークロードを選択します。

  • C++によるデスクトップ開発
  • MSVC C++ビルドツール
  • Windows SDK
  • CMake関連ツール

MSVCのコマンドラインツールは複数の環境変数に依存します。通常のPowerShellで環境変数を手動設定するのではなく、スタートメニューから「Developer PowerShell」または「x64 Native Tools Command Prompt」を開く方法が推奨されています。(Microsoft Learn)

開いたターミナルで、cl.exeが認識されることを確認します。

where.exe cl
cl

clが認識されない場合は、C++ワークロードが不足しているか、通常のPowerShellを開いている可能性があります。

GitHub Copilot CLIをインストールする

Windowsでは、WinGetからインストールできます。

winget install GitHub.Copilot

Node.js 22以降が導入済みなら、npmを利用する方法もあります。

npm install -g @github/copilot

インストール後に確認します。

copilot --version

GitHub Copilot CLIはCopilotの各プランで利用できますが、組織からライセンスが割り当てられている場合は、組織側のCopilot CLIポリシーが有効になっている必要があります。(GitHub Docs)

GitとCMakeを確認する

この記事のCMakePresets.jsonは、CMake 3.21以降で利用できるプリセット形式のバージョン3を使用します。

git --version
cmake --version
cmake --help

cmake --helpの「Generators」欄には、そのPCで使用できるVisual StudioジェネレーターやNinjaが表示されます。

CMake Presetsのバージョン3では、generatorを省略して通常のジェネレーター検出に任せることができます。また、同じバージョンからtoolchainFileフィールドも利用できます。(CMake)

空のフォルダーでCopilot CLIを起動する

Developer PowerShellで作業用フォルダーを作成します。

New-Item -ItemType Directory -Path quotecli
Set-Location quotecli
copilot

初回起動時は、Copilot CLI内で次のコマンドを実行してGitHubへサインインします。

/login

現在のフォルダーをAIツールで扱ってよいか確認されたら、フォルダーの内容を確認したうえで信頼を許可します。GitHubの公式ドキュメントでは、Copilot CLIは明示的な承認なしにファイル変更を行わないと説明されています。(GitHub Docs)

Plan Modeで実装前に構成を固める

今回のように、vcpkgの導入、複数ファイルの生成、CMake設定、ビルド検証まで含む作業では、いきなり実装させずPlan Modeから始めます。

Copilot CLIでShiftTabを押すとPlan Modeへ切り替えられます。通常モードから/planコマンドを使う方法もあります。

Plan Modeでは、Copilotが要件を分析し、必要に応じて確認事項を提示したあと、構造化された計画を作ります。計画を承認するまで実装は開始されません。(GitHub Docs)

そのまま使えるPlan Mode用プロンプト

次のプロンプトを入力します。

Windows上の空のフォルダーから、CMake、MSVC Build Tools、vcpkg manifest modeを使う
C++20コンソールアプリを構築してください。

最初はPlan Modeで計画だけを作成し、承認するまでファイル変更や
インストールコマンドの実行はしないでください。

アプリの要件:
- プロジェクト名は quotecli
- data/quotes.json を読み込む
- JSON配列から1件をランダムに選ぶ
- 本文と作成者名をコンソールへ表示する
- ファイル未検出、JSON構文エラー、空配列を適切に処理する
- C++20を使用する
- MSVCでは /W4、/permissive-、/utf-8 を有効にする

依存ライブラリ:
- JSON処理には nlohmann-json を候補にする
- 文字列整形には fmt を候補にする
- 端末の色表示には rang を候補にする
- 各ライブラリが本当に必要かを説明し、不要な依存関係は追加しない
- vcpkgのポート名とCMakeのインポート済みターゲット名を確認する

vcpkgの要件:
- プロジェクトルートで git init を実行する
- vcpkgは ./vcpkg にGit submoduleとして配置する
- bootstrap-vcpkg.batでブートストラップする
- classic modeではなくmanifest modeを使用する
- 依存関係はvcpkg.jsonへ記録する
- builtin-baselineにはローカルvcpkgの実在するGitコミットを設定する
- 架空のバージョン番号やコミットSHAを作らない
- vcpkg integrate installは実行しない

CMakeの要件:
- CMakeLists.txtを生成する
- ライブラリはfind_package(... CONFIG REQUIRED)で検出する
- target_link_librariesには名前付きのインポート済みターゲットを使用する
- include_directoriesやlink_directoriesに第三者ライブラリの絶対パスを書かない
- CMakePresets.jsonにDebugとReleaseの構成、ビルド、テストプリセットを作る
- vcpkg/scripts/buildsystems/vcpkg.cmakeをtoolchainFileに設定する
- cmake --helpと現在のMSVC環境を確認し、利用可能なジェネレーターを選ぶ
- Visual Studioジェネレーターを明示する場合は、実際にインストールされている名前を使う
- x64ビルドにする
- ビルド後、dataフォルダーを実行ファイルと同じ場所へコピーする
- CTestで実行確認できるスモークテストを追加する

検証:
- cmake --preset msvc-debug
- cmake --build --preset build-debug
- ctest --preset test-debug
- 上記がすべて成功するまで原因を調査して修正する
- エラーを無視したり、テストを削除して成功扱いにしたりしない
- 実行したコマンド、変更ファイル、検証結果を最後に整理する

そのほか:
- build、vcpkg_installed、CMakeUserPresets.jsonを除外する.gitignoreを作る
- セットアップとビルド手順をREADME.mdへ記載する
- 削除や上書きを伴う破壊的なコマンドは事前に確認する

Copilotが作った計画で確認するポイント

計画が表示されたら、すぐに承認せず次の項目を確認します。

確認項目合格と判断できる内容
vcpkgの配置./vcpkgに配置され、Git submoduleとして固定される
依存関係vcpkg.jsonにポート名が記録される
バージョン管理実在するbuiltin-baselineが設定される
CMake連携vcpkgのtoolchain fileが構成時に読み込まれる
ライブラリ検出find_package(... CONFIG REQUIRED)を使う
リンク方法fmt::fmtなどの名前付きターゲットを使う
ジェネレーター実際にインストール済みのものを使用する
アーキテクチャx64として構成される
検証configure、build、CTestまで実行する
グローバル変更vcpkg integrate installやシステムPATH変更を行わない

次のような記述が計画に含まれていたら、修正を依頼します。

C:\Users\ユーザー名\vcpkg\installed\x64-windows\include
C:\Program Files\...\lib
include_directories(...)
link_directories(...)

自分のプロジェクト内ヘッダーに対するtarget_include_directories()は問題ありません。避けるべきなのは、第三者ライブラリの環境依存パスを直接埋め込むことです。

C++ライブラリをどう選ぶか

今回の例では、次の3ライブラリが候補になります。

用途vcpkgポート名CMakeターゲット判断
JSONの解析nlohmann-jsonnlohmann_json::nlohmann_jsonJSONを扱うため採用
書式付き出力fmtfmt::fmtエラー表示や出力整形に採用
端末の色付けrangrang::rang色表示が必要な場合だけ採用

fmtfmt::fmt、nlohmann/jsonはnlohmann_json::nlohmann_jsonというCMakeターゲットを公式に提供しています。rangもrang::名前空間付きでCMakeターゲットをエクスポートしています。(GitHub)

対象をリンクする部分は次の形になります。

find_package(fmt CONFIG REQUIRED)
find_package(nlohmann_json CONFIG REQUIRED)
find_package(rang CONFIG REQUIRED)

target_link_libraries(quotecli
    PRIVATE
        fmt::fmt
        nlohmann_json::nlohmann_json
        rang::rang
)

端末の色表示が要件に含まれないなら、rangを外す選択も合理的です。AIにライブラリを選ばせる場合でも、「使えそうだから追加する」のではなく、標準ライブラリだけで実装した場合の複雑さと比較して判断します。

計画を承認して実装させる

計画に問題がなければ、次のように指示します。

計画を承認します。実装を開始してください。

configure、build、CTestが成功するまで検証してください。
コマンドが失敗した場合は、設定を迂回せず根本原因を調べて修正してください。
プロジェクト外のファイル削除、グローバル設定変更、管理者権限が必要な操作は
実行前に確認してください。

Copilot CLIがコマンド実行やファイル変更の承認を求めたら、対象のパスとコマンドを確認します。

特に次のコマンドは、プロジェクトのルートで実行されることを確認してください。

git init
git submodule add https://github.com/microsoft/vcpkg.git vcpkg
.\vcpkg\bootstrap-vcpkg.bat

vcpkgの公式手順でも、リポジトリを取得したあと、Windowsではbootstrap-vcpkg.batを実行してvcpkg.exeを準備します。(Microsoft Learn)

生成される設定ファイルの実例

Copilotの出力は環境やプロンプトによって変わります。ここでは、正しく生成されたかを判断する基準として、実用的な構成例を示します。

vcpkg.json

初期状態は次のようになります。

{
  "name": "quotecli",
  "version-string": "0.1.0",
  "dependencies": [
    "fmt",
    "nlohmann-json",
    "rang"
  ]
}

その後、ローカルのvcpkgリポジトリに対応するbuiltin-baselineを追加します。

.\vcpkg\vcpkg.exe x-update-baseline --add-initial-baseline

このコマンドは、現在のvcpkgインスタンスのGitコミットを使って、manifestへbuiltin-baselineを追加します。Web記事や別プロジェクトから適当なSHAをコピーするのではなく、自分のリポジトリ内にあるvcpkgと対応させることが重要です。(Microsoft Learn)

実行後は、次のように実在するコミットSHAが追加されます。

{
  "name": "quotecli",
  "version-string": "0.1.0",
  "dependencies": [
    "fmt",
    "nlohmann-json",
    "rang"
  ],
  "builtin-baseline": "実際のvcpkgコミットSHA"
}

記事中では意図的にSHAを記載していません。利用者のvcpkgコミットと一致しない値を固定すると、再現性を高めるどころか、構成エラーの原因になるためです。

CMakeLists.txt

cmake_minimum_required(VERSION 3.21)

project(
    quotecli
    VERSION 0.1.0
    LANGUAGES CXX
)

find_package(fmt CONFIG REQUIRED)
find_package(nlohmann_json CONFIG REQUIRED)
find_package(rang CONFIG REQUIRED)

add_executable(
    quotecli
    src/main.cpp
)

target_compile_features(
    quotecli
    PRIVATE
        cxx_std_20
)

target_link_libraries(
    quotecli
    PRIVATE
        fmt::fmt
        nlohmann_json::nlohmann_json
        rang::rang
)

if(MSVC)
    target_compile_options(
        quotecli
        PRIVATE
            /W4
            /permissive-
            /utf-8
    )
else()
    target_compile_options(
        quotecli
        PRIVATE
            -Wall
            -Wextra
            -Wpedantic
    )
endif()

add_custom_command(
    TARGET quotecli
    POST_BUILD
    COMMAND
        ${CMAKE_COMMAND} -E copy_directory
        "${CMAKE_SOURCE_DIR}/data"
        "$<TARGET_FILE_DIR:quotecli>/data"
    VERBATIM
)

include(CTest)

if(BUILD_TESTING)
    add_test(
        NAME quotecli-runs
        COMMAND $<TARGET_FILE:quotecli>
    )

    set_tests_properties(
        quotecli-runs
        PROPERTIES
            WORKING_DIRECTORY "$<TARGET_FILE_DIR:quotecli>"
    )
endif()

add_custom_command()dataフォルダーを実行ファイルの隣へコピーしているため、Visual StudioジェネレーターとNinjaで出力場所が異なっても、実行時に同じ相対パスを使用できます。

また、CTestでは実行ファイルの絶対位置をCMakeのジェネレーター式から取得しています。build/Debug/quotecli.exeのような環境依存パスをテスト側に直接書く必要がありません。

CMakePresets.json

次の例では、ジェネレーターをあえて固定していません。CMake 3.21以降では、ジェネレーターを省略すると通常の検出処理が使われます。

{
  "version": 3,
  "cmakeMinimumRequired": {
    "major": 3,
    "minor": 21,
    "patch": 0
  },
  "configurePresets": [
    {
      "name": "msvc-debug",
      "displayName": "MSVC Debug",
      "binaryDir": "${sourceDir}/build/msvc-debug",
      "toolchainFile": "${sourceDir}/vcpkg/scripts/buildsystems/vcpkg.cmake",
      "cacheVariables": {
        "CMAKE_BUILD_TYPE": "Debug",
        "CMAKE_CXX_STANDARD": "20",
        "CMAKE_CXX_STANDARD_REQUIRED": "ON"
      }
    },
    {
      "name": "msvc-release",
      "displayName": "MSVC Release",
      "binaryDir": "${sourceDir}/build/msvc-release",
      "toolchainFile": "${sourceDir}/vcpkg/scripts/buildsystems/vcpkg.cmake",
      "cacheVariables": {
        "CMAKE_BUILD_TYPE": "Release",
        "CMAKE_CXX_STANDARD": "20",
        "CMAKE_CXX_STANDARD_REQUIRED": "ON"
      }
    }
  ],
  "buildPresets": [
    {
      "name": "build-debug",
      "configurePreset": "msvc-debug",
      "configuration": "Debug"
    },
    {
      "name": "build-release",
      "configurePreset": "msvc-release",
      "configuration": "Release"
    }
  ],
  "testPresets": [
    {
      "name": "test-debug",
      "configurePreset": "msvc-debug",
      "configuration": "Debug",
      "output": {
        "outputOnFailure": true
      }
    },
    {
      "name": "test-release",
      "configurePreset": "msvc-release",
      "configuration": "Release",
      "output": {
        "outputOnFailure": true
      }
    }
  ]
}

toolchainFileは、通常のCMAKE_TOOLCHAIN_FILEより優先されます。プロジェクトルートのCMakePresets.jsonに記録することで、開発者ごとに長い-D CMAKE_TOOLCHAIN_FILE=...を入力する必要がなくなります。(CMake)

チームやCIでジェネレーターも固定したい場合は、Copilotにcmake --helpの結果を確認させたうえで、実在する名前を追加します。

Visual Studioジェネレーターの例は次の形です。

{
  "generator": "実際にcmake --helpへ表示されたVisual Studioジェネレーター名",
  "architecture": "x64"
}

Ninjaを使用する場合は、x64用のDeveloper PowerShellを開き、cl.exeninja.exeの両方が認識されることを確認します。

src/main.cpp

#include <fmt/core.h>
#include <nlohmann/json.hpp>
#include <rang.hpp>

#include <cstddef>
#include <fstream>
#include <iostream>
#include <random>
#include <stdexcept>
#include <string>

int main()
{
    try
    {
        std::ifstream input{"data/quotes.json"};

        if (!input)
        {
            throw std::runtime_error{"Could not open data/quotes.json"};
        }

        nlohmann::json quotes;
        input >> quotes;

        if (!quotes.is_array())
        {
            throw std::runtime_error{"The JSON root must be an array"};
        }

        if (quotes.empty())
        {
            throw std::runtime_error{"The quote list is empty"};
        }

        std::mt19937 engine{std::random_device{}()};

        std::uniform_int_distribution<std::size_t> distribution{
            0,
            quotes.size() - 1
        };

        const auto& selected = quotes.at(distribution(engine));

        const auto text =
            selected.at("text").get<std::string>();

        const auto author =
            selected.value("author", std::string{"Unknown"});

        std::cout
            << rang::fg::cyan
            << '"'
            << text
            << '"'
            << rang::style::reset
            << '\n';

        fmt::print("  -- {}\n", author);

        return 0;
    }
    catch (const nlohmann::json::exception& error)
    {
        fmt::print(
            stderr,
            "JSON error: {}\n",
            error.what()
        );

        return 1;
    }
    catch (const std::exception& error)
    {
        fmt::print(
            stderr,
            "Error: {}\n",
            error.what()
        );

        return 1;
    }
}

rangはiostreamへ色やスタイルを適用するライブラリです。rang::fg::cyanrang::style::resetを使って、端末ごとの差異をライブラリ側で処理できます。(GitHub)

data/quotes.json

[
  {
    "text": "Make the smallest change that proves the design.",
    "author": "Project note"
  },
  {
    "text": "A reproducible build is part of the product.",
    "author": "Build note"
  },
  {
    "text": "Prefer declared dependencies over hidden machine state.",
    "author": "Dependency note"
  }
]

.gitignore

/build/
/vcpkg_installed/
CMakeUserPresets.json

CMakePresets.jsonはチームで共有する設定なのでGitへ登録します。一方、個人のローカル設定を記録するCMakeUserPresets.jsonは、通常はGitへ登録しません。CMakeの公式ドキュメントでも、この使い分けが示されています。(CMake)

CMakeの構成・ビルド・テストを実行する

まず、利用可能なプリセットを確認します。

cmake --list-presets=all

Debug構成を作成します。

cmake --preset msvc-debug

初回構成時は、vcpkgがvcpkg.jsonを検出し、fmtnlohmann-jsonrangと、その依存パッケージを取得・ビルドします。そのため、初回だけ時間がかかることがあります。

続けてビルドします。

cmake --build --preset build-debug

CTestで実行確認します。

ctest --preset test-debug

成功時は、概ね次のような結果になります。

100% tests passed, 0 tests failed out of 1

Release構成も同じ流れです。

cmake --preset msvc-release
cmake --build --preset build-release
ctest --preset test-release

生成された実行ファイルを直接起動する

Visual Studioジェネレーターでは構成名のサブフォルダーが作られる一方、Ninjaなどでは別の配置になることがあります。

出力パスを決め打ちせず、PowerShellで実行ファイルを検索すると確実です。

$exe = Get-ChildItem .\build\msvc-debug -Recurse -Filter quotecli.exe | Select-Object -First 1

if (-not $exe) {
    throw "quotecli.exe was not found"
}

Push-Location $exe.DirectoryName
& $exe.FullName
Pop-Location

実行例は次のとおりです。

"A reproducible build is part of the product."
  -- Build note

なぜ手作業のinclude/link設定が不要になるのか

この構成では、次の3段階で依存関係が接続されます。

  1. vcpkg.jsonが必要なライブラリ名を宣言する
  2. vcpkg toolchainが構成時にライブラリを復元する
  3. find_package()がCMakeターゲットを読み込み、target_link_libraries()が必要な使用条件を引き継ぐ

CMakeターゲットには、単なるライブラリファイル名だけでなく、必要なインクルードパス、コンパイル定義、推移的な依存関係などを持たせられます。

例えば、nlohmann_json::nlohmann_jsonターゲットには、必要なインクルードディレクトリやコンパイル要件が含まれます。利用側はnlohmann/json.hppの実際の配置場所を調べる必要がありません。(Nlohmann JSON)

また、CMake向けのプロジェクトではvcpkg toolchainを使用するため、ユーザー単位のvcpkg integrate installは必要ありません。グローバル統合を避けることで、そのPCだけで偶然ビルドできる状態を減らせます。

vcpkg本体とライブラリのバージョンを固定する

再現性を高めるには、次の2つを分けて考えます。

  • vcpkg本体とポート定義の位置:Git submoduleのコミットで固定
  • 採用する依存ライブラリの基準バージョンbuiltin-baselineで固定

builtin-baselineには、vcpkgリポジトリのコミットSHAを指定します。これにより、そのコミット時点のパッケージバージョン集合を基準として解決できます。(Microsoft Learn)

確認コマンドは次のとおりです。

git submodule status
git -C .\vcpkg rev-parse HEAD
Get-Content .\vcpkg.json

git -C .\vcpkg rev-parse HEADの結果と、vcpkg.jsonbuiltin-baselineが意図したコミットになっているか確認します。

依存関係を更新するときは、vcpkgのsubmoduleだけを更新して終わらせず、次の作業を同じ変更単位で行います。

  • 新しいvcpkgコミットを選ぶ
  • bootstrap-vcpkg.batを再実行する
  • x-update-baselineでmanifestを更新する
  • クリーンなビルドフォルダーで再構成する
  • DebugとReleaseのテストを通す
  • submoduleのコミットとvcpkg.jsonを同じコミットまたはプルリクエストに含める

最も確実な検証は新しいクローンで行う

ローカルで一度ビルドできただけでは、過去に設定したPATHやグローバルライブラリを参照している可能性を完全には排除できません。

別フォルダーへsubmodule込みでクローンし、最初からビルドする方法が確実です。

git clone --recurse-submodules <リポジトリのURL> quotecli-verification
Set-Location quotecli-verification

.\vcpkg\bootstrap-vcpkg.bat

cmake --preset msvc-debug
cmake --build --preset build-debug
ctest --preset test-debug

この確認で成功すれば、少なくとも元の作業フォルダーに残っていた生成物へ依存していないことを確認できます。

よくあるエラーと対処法

症状主な原因対処
clが見つからない通常のPowerShellを使用しているx64 Developer PowerShellで開き直す
CMakeがコンパイラを検出できないMSVCワークロード不足Visual Studio InstallerでC++によるデスクトップ開発を追加する
Could not find fmtと表示されるvcpkg toolchainが読み込まれていないCMakePresets.jsontoolchainFileを確認する
vcpkg.jsonが無視されるmanifestの場所が異なるvcpkg.jsonをプロジェクトルートへ置く
ジェネレーターが一致しない同じbuildフォルダーを別ジェネレーターで再利用した該当するbuildフォルダーを削除して再構成する
quotes.jsonが見つからないデータコピー処理がない、または作業ディレクトリが異なるPOST_BUILDのコピーとCTestのWORKING_DIRECTORYを確認する
baseline関連のエラーが出る架空または別リポジトリのSHAを指定しているローカルvcpkgでx-update-baselineを実行する
クローン後にvcpkgが空submoduleを取得していないgit submodule update --init --recursiveを実行する

toolchainを追加したのにパッケージが見つからない場合

CMakeのtoolchain fileは、最初のproject()呼び出し中に評価されます。一度toolchainなしで構成したbuildフォルダーへ後から設定を追加した場合、キャッシュが残っていると正しく反映されないことがあります。(Microsoft Learn)

Debug用のbuildフォルダーを削除し、再構成します。

Remove-Item -Recurse -Force .\build\msvc-debug

cmake --preset msvc-debug
cmake --build --preset build-debug
ctest --preset test-debug

削除前に、パスがプロジェクト内のbuild/msvc-debugであることを必ず確認してください。

Copilotが存在しないターゲット名を生成した場合

vcpkgのポート名とCMakeターゲット名は、必ずしも同じではありません。

例えば、nlohmann/jsonでは次のように異なります。

vcpkgポート名:
nlohmann-json

find_package名:
nlohmann_json

CMakeターゲット名:
nlohmann_json::nlohmann_json

構成時にvcpkgが表示する使用方法や、上流ライブラリのCMakeドキュメントを確認し、推測だけで修正しないことが大切です。

Copilot CLIに任せてよい範囲と人が確認する範囲

Copilot CLIは、空のフォルダーから複数の設定ファイルを作り、実際のビルドエラーを読みながら修正する用途に向いています。一方、次の判断まで無条件に任せるべきではありません。

  • ライブラリを追加する必要性
  • ライセンスが用途に適合するか
  • メンテナンス状況やセキュリティ上の懸念
  • グローバル設定を変更してよいか
  • 自動生成されたバージョンやSHAが実在するか
  • 削除コマンドの対象パスが正しいか
  • 警告やテスト失敗を無効化していないか

実務では、次の順番を守ると失敗を減らせます。

要件を渡す
↓
Plan Modeで構成を確認する
↓
依存関係と変更範囲を修正する
↓
実装を承認する
↓
configure・build・CTestを実行する
↓
差分を確認する
↓
新しいクローンで再検証する
↓
コミットする

GitHubの公式ベストプラクティスでも、複雑な変更では「調査、計画、レビュー、実装、検証、コミット」という段階的な進め方が示されています。(GitHub Docs)

最後に確認するチェックリスト

公開またはチーム共有の前に、次の点を確認します。

  • vcpkg.jsonに必要な依存関係だけが記載されている
  • builtin-baselineが実在するvcpkgコミットになっている
  • vcpkgのsubmoduleコミットがGitに記録されている
  • CMakePresets.jsonからvcpkg toolchainを読み込んでいる
  • 第三者ライブラリの絶対パスをCMakeへ書いていない
  • DebugとReleaseの両方をビルドできる
  • CTestが成功する
  • data/quotes.jsonが実行ファイルの隣へコピーされる
  • 新しいクローンでも同じ手順でビルドできる
  • READMEだけで別の開発者が環境を再構築できる

最初に行うべき作業は、x64用のDeveloper PowerShellを開き、空の作業フォルダーでCopilot CLIを起動して、提示したプロンプトをPlan Modeへ入力することです。計画内のvcpkg配置、manifest、toolchain、CMakeターゲット、検証コマンドを確認してから実装を承認すれば、環境依存のinclude/link設定を持たないC++プロジェクトへ仕上げられます。

この記事を書いた人

実務の現場で詰まりがちなポイントを地図にするITブログ「IT trip」を運営。Windows/Office(Teams・Excel)からSQL、サーバ運用、ガジェットまで、再現性のある手順と“なぜそうなるか”を丁寧に解説します。読んだらすぐ試せること、そして迷った人の次の一歩が見えることを大切にしています。

コメント

コメントする

目次