バージョン管理の概要

マニフェストでのバージョンの使用

まず、依存fmtzlibする単純な CMake プロジェクトを作成してみましょう。

次のファイルを含むフォルダーを作成します。

vcpkg.json

{
    "name": "versions-test",
    "version": "1.0.0",
    "dependencies": [
        {
            "name": "fmt",
            "version>=": "7.1.3#1"
        }, 
        "zlib"
    ],
    "builtin-baseline": "3426db05b996481ca31e95fff3734cf23e0f51bc"
}

main.cpp

#include <fmt/core.h>
#include <zlib.h>

int main()
{
    fmt::print("fmt version is {}\n"
               "zlib version is {}\n", 
               FMT_VERSION, ZLIB_VERSION);
    return 0;
}

CMakeLists.txt

cmake_minimum_required(VERSION 3.18)

project(versionstest CXX)

add_executable(main main.cpp)

find_package(ZLIB REQUIRED)
find_package(fmt CONFIG REQUIRED)
target_link_libraries(main PRIVATE ZLIB::ZLIB fmt::fmt)

次に、CMake を使用してプロジェクトをビルドして実行します。

  1. プロジェクトのビルド ディレクトリを作成します。

    PS D:\versions-test> mkdir build
    PS D:\versions-test> cd build
    
  2. CMake を構成します。

    PS D:\versions-test\build> cmake -G Ninja -DCMAKE_TOOLCHAIN_FILE=D:/vcpkg/scripts/buildsystems/vcpkg.cmake ..
    -- Running vcpkg install
    Detecting compiler hash for triplet x86-windows...
    The following packages will be built and installed:
        fmt[core]:x64-windows -> 7.1.3#1 -- D:\Work\viromer\vcpkg\buildtrees\versioning\versions\fmt\4f8427eb0bd40da1856d4e67bde39a4fda689d72
        vcpkg-cmake[core]:x64-windows -> 2021-02-26 -- D:\Work\viromer\vcpkg\buildtrees\versioning\versions\vcpkg-cmake\51896aa8073adb5c8450daa423d03eedf0dfc61f
        vcpkg-cmake-config[core]:x64-windows -> 2021-02-26 -- D:\Work\viromer\vcpkg\buildtrees\versioning\versions\vcpkg-cmake-config\d255b3d566a8861dcc99a958240463e678528066
        zlib[core]:x64-windows -> 1.2.11#9 -- D:\Work\viromer\vcpkg\buildtrees\versioning\versions\zlib\827111046e37c98153d9d82bb6fa4183b6d728e4
    ...
    
  3. プロジェクトをビルドします。

    PS D:\versions-test\build> cmake --build .
    [2/2] Linking CXX executable main.exe
    
  4. 実行する

    PS D:\versions-test\build> ./main.exe
    fmt version is 70103
    zlib version is 1.2.11
    

出力を見てみましょう。

fmt[core]:x86-windows -> 7.1.3#1 -- D:\vcpkg\buildtrees\versioning\versions\fmt\4f8427eb0bd40da1856d4e67bde39a4fda689d72
...
zlib[core]:x86-windows -> 1.2.11#9 -- D:\vcpkg\buildtrees\versioning\versions\zlib\827111046e37c98153d9d82bb6fa4183b6d728e4

でポートファイルports/を使用する代わりに、vcpkg チェック buildtrees/versioning/versions/は . ファイルは、クラシック モードで ports/ vcpkg を実行するときに引き続き使用されます。

Note

CMake の構成中の vcpkg からの出力は、CMake バージョン 3.18 以降を使用している場合にのみ使用できます。 古い CMake を使用している場合は、代わりにビルド ディレクトリにファイルをチェックvcpkg-manifest-install.logできます。

MSBuild でマニフェストを使用する方法については、マニフェストのお知らせに関するブログ記事を参照してください。

マニフェストの変更

マニフェストを使用したことがある場合は、新しい JSON プロパティがいくつか存在することがわかります。 次の変更を確認しましょう。

version

{
    "name": "versions-test",
    "version": "1.0.0"
}

これはプロジェクトのバージョン宣言です。 以前は、プロパティを使用して version-string プロジェクトのバージョンのみを宣言できました。 バージョン管理が行われるようになったので、vcpkg はいくつかの新しいバージョン管理スキームを認識しています。

バージョン スキーム 説明
version ドット区切りの数値: 1.0.0.5.
version-semver 準拠 セマンティック バージョン: 1.2.0 および 1.2.0-rc.
version-date 日付の YYYY-MM-DD 形式: 2021-01-01
version-string 任意の文字列: vista, candy.

version>=

{
    "dependencies": [
        { "name": "fmt", "version>=": "7.1.3" },
        "zlib"
    ]
}

このプロパティは、最小バージョンの制約を表すために使用され、宣言の "dependencies" 一部としてのみ許可されます。 この例では、バージョン7.1.3#1fmtに明示的な制約を設定します。

推移的な依存関係に新しいバージョンが必要な場合、vcpkg はこの制約をアップグレードできます。 たとえば、バージョンへの依存関係を宣言する場合zlib、代わりに vcpkg がインストール7.1.4されます。fmt7.1.4

vcpkg は最小バージョンのアプローチを使用します。この例では、バージョン8.0.0がリリースされる場合fmtでも、vcpkg は制約を満たす最小バージョンであるため、バージョン7.1.3#1をインストールします。 この方法の利点は、vcpkg を更新するときに予期しない依存関係のアップグレードが行われず、同じマニフェストを使用している限り、再現可能なビルド (使用されているバージョンの観点から) が得られない点です。

依存関係をアップグレードする場合は、最小バージョンの制約を満たすか、新しいベースラインを使用できます。

builtin-baseline

{ "builtin-baseline": "3426db05b996481ca31e95fff3734cf23e0f51bc" }

このフィールドは、すべてのポートのバージョン管理ベースラインを宣言します。 バージョン管理を有効にするにはベースラインの設定が必要です。それ以外の場合は、ディレクトリ上の現在のバージョンを ports/ 取得します。 'git rev-parse HEAD' を実行して vcpkg の現在のコミットを取得し、それを組み込みベースラインとして設定できます。 詳細については、 "builtin-baseline" ドキュメント を参照してください。

この例では、バージョン制約を zlib宣言しません。代わりに、バージョンはベースラインから取得されます。 内部的には、vcpkg はコミット 3426db05b996481ca31e95fff3734cf23e0f51bc を調び、その時点で最新の zlib バージョン (この場合は最新のバージョン) 1.2.11#9を確認します。

バージョン解決中、ベースライン バージョンは最小バージョン制約として扱われます。 ベースライン バージョンより低い明示的制約を宣言すると、明示的な制約はベースライン バージョンにアップグレードされます。

たとえば、次のように依存関係を変更した場合は、次のようになります。

{ "dependencies": [
    {
        "name": "fmt",
        "version>=": "7.1.3#1"
    },
    {
        "name": "zlib",
        "version>=": "1.2.11#7"
    }
] }

Note

1.2.11#7はバージョン、ポート 7バージョン1.2.11を表します。

ベースラインでは at に対してzlib1.2.11#9最小バージョン制約が導入され、上位のバージョンでは最小バージョンの制約1.2.11#7を満たしているため、vcpkg はアップグレードを許可されます。

ベースラインは、一度に複数のバージョンをアップグレードする便利なメカニズムでもあります。たとえば、複数 boost のライブラリに依存する場合は、各パッケージでバージョン制約を宣言するよりも、1 回を設定 baseline する方が便利です。

ただし、ベースラインより古いバージョンをピン留めする場合はどうでしょうか。

overrides

ベースラインは、すべてのパッケージのバージョン フロアを確立し、明示的な制約がベースラインより低い場合にアップグレードされるため、ベースラインを超えてバージョンをダウングレードする別のメカニズムが必要です。

vcpkg がそのシナリオに対して提供するメカニズムは overrides. パッケージでオーバーライドが宣言されている場合、vcpkg は、マニフェストで直接宣言された、または推移的な依存関係から他のすべてのバージョン制約を無視します。 要するに、 overrides vcpkg は宣言された正確なバージョンである period を使用するように強制します。

この例をもう一度変更して、今度は vcpkg にバージョン 6.0.0fmt強制的に使用してみましょう。

{
    "name": "versions-test",
    "version": "1.0.0",
    "dependencies": [
        {
            "name": "fmt",
            "version>=": "7.1.3#1"
        },
        {
            "name": "zlib",
            "version>=": "1.2.11#7"
        }
    ],
    "builtin-baseline": "3426db05b996481ca31e95fff3734cf23e0f51bc",
    "overrides": [
        {
            "name": "fmt",
            "version": "6.0.0"
        }
    ]
}

プロジェクトをリビルドします。

PS D:\versions-test\build> rm ./CMakeCache.txt
PS D:\versions-test\build> rm -r ./vcpkg_installed
PS D:\versions-test\build> cmake -G Ninja -DCMAKE_TOOLCHAIN_FILE=D:/vcpkg/scripts/buildsystems/vcpkg.cmake ..
-- Running vcpkg install
Detecting compiler hash for triplet x86-windows...
The following packages will be built and installed:
    fmt[core]:x86-windows -> 6.0.0 -- D:\vcpkg\buildtrees\versioning\versions\fmt\d99b6a35e1406ba6b6e09d719bebd086f83ed5f3
    zlib[core]:x86-windows -> 1.2.11#9 -- D:\vcpkg\buildtrees\versioning\versions\zlib\827111046e37c98153d9d82bb6fa4183b6d728e4
...
PS D:\versions-test\build> cmake --build .
[2/2] Linking CXX executable main.exe

そして、それを実行します!

PS D:\versions-test\build> .\main.exe
fmt version is 60000
zlib version is 1.2.11

必要な fmt バージョンと同じように、バージョン 6.0.0 がどのようになっているかに注目してください。

バージョンとカスタム ポート

最後に、オーバーレイ ポートとバージョン管理の解決の相互作用について説明します。 答えは:彼らはしません。

さらに詳しく説明すると、ポートのオーバーレイを指定すると、vcpkg は常にオーバーレイ ポートを使用し、それに含まれているバージョンを気にしません。 その理由は 2 つあります。(1) 既存のポートを完全にマスクするオーバーレイ ポートの既存の動作と一致し、(2) オーバーレイ ポートは vcpkg のバージョン管理機能に電力を供給するのに十分な情報を提供しません (また、想定されていません)。

バージョン管理と共に柔軟なポートカスタマイズを行う場合は、独自のカスタム レジストリを作成することを検討する必要があります。

参考資料

バージョン管理のしくみの詳細については、バージョン管理のリファレンスバージョン管理の概念を参照することをお勧めします。