vcpkg/docs/users/manifests.md
Billy O'Neal b12e71232e
[vcpkg docs] Delete old schema file (#28187)
* Delete old schema file that has been replaced with https://raw.githubusercontent.com/microsoft/vcpkg-tool/main/docs/vcpkg.schema.json

This caused confusion for @Nekko in Discord here: https://discordapp.com/channels/400588936151433218/687365466422902841/1048988171393835099

* Also fix the one docs use pointed out by @autoantwort.
2022-12-12 14:38:01 -08:00

13 KiB

Manifest Mode

The latest version of this documentation is available on GitHub.

vcpkg has two modes of consuming dependencies - classic mode and manifest mode.

In classic mode, vcpkg produces an "installed" tree, whose contents are changed by explicit calls to vcpkg install or vcpkg remove. The installed tree is intended for consumption by any number of projects: for example, installing a bunch of libraries and then using those libraries from Visual Studio, without additional configuration. Because the installed tree is not associated with an individual project, it's similar to tools like brew or apt, except that the installed tree is vcpkg-installation-local, rather than global to a system or user.

In manifest mode, an installed tree is associated with a particular project rather than the vcpkg installation. The set of installed ports is controlled by editing the project's "manifest file", and the installed tree is placed in the project directory or build directory. This mode acts more similarly to language package managers like Cargo, or npm. We recommend using this manifest mode whenever possible, because it allows one to encode a project's dependencies explicitly in a project file, rather than in the documentation, making your project much easier to consume.

Check out the manifest cmake example for an example project using CMake and manifest mode.

Table of Contents

Simple Example Manifest

{
  "$schema": "https://raw.githubusercontent.com/microsoft/vcpkg-tool/main/docs/vcpkg.schema.json",
  "name": "my-application",
  "version": "0.15.2",
  "dependencies": [
    "boost-system",
    {
      "name": "cpprestsdk",
      "default-features": false
    },
    "libxml2",
    "yajl"
  ]
}

Manifest Syntax Reference

A manifest is a JSON-formatted file named vcpkg.json which lies at the root of your project. It contains all the information a person needs to know to get dependencies for your project, as well as all the metadata about your project that a person who depends on you might be interested in.

Manifests follow strict JSON: they can't contain C++-style comments (//) nor trailing commas. However you can use field names that start with $ to write your comments in any object that has a well-defined set of keys. These comment fields are not allowed in any objects which permit user-defined keys (such as "features").

The latest JSON Schema is available at https://raw.githubusercontent.com/microsoft/vcpkg-tool/main/docs/vcpkg.schema.json. IDEs with JSON Schema support such as Visual Studio and Visual Studio Code can use this file to provide IntelliSense and syntax checking. For most IDEs, you should set "$schema" in your vcpkg.json to this URL (like the above example).

Each manifest contains a top level object with the following fields:

"name"

This is the name of your project! It must be formatted in a way that vcpkg understands - in other words, it must be lowercase alphabetic characters, digits, and hyphens, and it must not start nor end with a hyphen. For example, Boost.Asio might be given the name boost-asio.

Version Fields

There are four version field options, depending on how the port orders its releases.

  • "version" - Generic, dot-separated numeric sequence.
  • "version-semver" - Semantic Version 2.0.0
  • "version-date" - Used for packages which do not have numeric releases (for example, Live-at-HEAD). Matches YYYY-MM-DD with optional trailing dot-separated numeric sequence.
  • "version-string" - Used for packages that don't have orderable versions. This should be rarely used, however all ports created before the other version fields were introduced use this scheme.

Additionally, the optional "port-version" field is used to indicate revisions to the port with the same upstream source version. For pure consumers, this field should not be used.

See versioning for more details.

"description"

This is where you describe your project. Give it a good description to help in searching for it! This can be a single string, or it can be an array of strings; in the latter case, the first string is treated as a summary, while the remaining strings are treated as the full description.

"builtin-baseline"

This field indicates the commit of vcpkg which provides global minimum version information for your manifest.

It is required for top-level manifest files using versioning without a specified "default-registry". It has the same semantic as defining your default registry to be:

{
  "default-registry": {
    "kind": "builtin",
    "baseline": "<value>"
  }
}

See versioning for more semantic details.

"dependencies"

This field lists all the dependencies you'll need to build your library (as well as any your dependents might need, if they were to use you). It's an array of strings and objects:

  • A string dependency (e.g., "dependencies": [ "zlib" ]) is the simplest way one can depend on a library; it means you don't depend on a single version, and don't need to write down any more information.
  • On the other hand, an object dependency (e.g., "dependencies": [ { "name": "zlib" } ]) allows you to add that extra information.

Example:

"dependencies": [
  {
    "name": "arrow",
    "default-features": false,
    "features": [ "json" ]
  },
  "boost-asio",
  "openssl",
  {
    "name": "picosha2",
    "platform": "!windows"
  }
]

"name" Field

The name of the dependency. This follows the same restrictions as the "name" property for a project.

"features" and "default-features" Fields

"features" is an array of feature names which tell you the set of features that the dependencies need to have at a minimum, while "default-features" is a boolean that tells vcpkg whether or not to install the features the package author thinks should be "most common for most people to use".

For example, ffmpeg is a library which supports many, many audio and video codecs; however, for your specific project, you may only need mp3 encoding. Then, you might just ask for:

{
  "name": "ffmpeg",
  "default-features": false,
  "features": [ "mp3lame" ]
}

"host" Field

A boolean indicating that the dependency must be built for the host triplet instead of the current port's triplet. Defaults to false.

Any dependency that provides tools or scripts which should be "executed" during a build (such as buildsystems, code generators, or helpers) should be marked as "host": true. This enables correct cross-compilation in cases that the target is not executable -- such as when compiling for arm64-android.

See Host Dependencies for more information.

"platform" Field

The "platform" field defines the platforms where the dependency should be installed - for example, you might need to use sha256, and so you use platform primitives on Windows, but picosha2 on non-Windows platforms.

{
  "name": "picosha2",
  "platform": "!windows"
}

This is a string field which takes boolean expressions of the form <identifier>, !expression, expression { & expression & expression...}, and expression { | expression | expression...}, along with parentheses to denote precedence. For example, a dependency that's only installed on the Windows OS, for the ARM64 architecture, and on Linux on x64, would be written (windows & arm64) | (linux & x64).

The common identifiers are:

  • The operating system: windows, uwp, linux, osx (includes macOS), android, emscripten
  • The architecture: x86, x64, wasm32, arm64, arm (includes both arm32 and arm64 due to backwards compatibility)

although one can define their own.

"version>=" Field

A minimum version constraint on the dependency.

This field specifies the minimum version of the dependency, optionally using a #N suffix to denote port-version if non-zero.

See also versioning for more semantic details.

"overrides"

This field pins exact versions for individual dependencies.

"overrides" from transitive manifests (i.e. from dependencies) are ignored.

See also versioning for more semantic details.

Example:

  "overrides": [
    {
      "name": "arrow", "version": "1.2.3", "port-version": 7
    }
  ]

"supports"

If your project doesn't support common platforms, you can tell your users this with the "supports" field. It uses the same platform expressions as "platform", from dependencies, as well as the "supports" field of features. For example, if your library doesn't support linux, you might write { "supports": "!linux" }.

"features" and "default-features"

The "features" field defines your project's optional features, that others may either depend on or not. It's an object, where the keys are the names of the features, and the values are objects describing the feature. "description" is required, and acts exactly like the "description" field on the global package, and "dependencies" are optional, and again act exactly like the "dependencies" field on the global package. There's also the "supports" field, which again acts exactly like the "supports" field on the global package.

You also have control over which features are default, if a person doesn't ask for anything specific, and that's the "default-features" field, which is an array of feature names.

Example:

{
  "name": "libdb",
  "version": "1.0.0",
  "description": [
    "An example database library.",
    "Optionally can build with CBOR, JSON, or CSV as backends."
  ],
  "$default-features-explanation": "Users using this library transitively will get all backends automatically",
  "default-features": [ "cbor", "csv", "json" ],
  "features": {
    "cbor": {
      "description": "The CBOR backend",
      "dependencies": [
        {
          "$explanation": [
            "This is how you tell vcpkg that the cbor feature depends on the json feature of this package"
          ],
          "name": "libdb",
          "default-features": false,
          "features": [ "json" ]
        }
      ]
    },
    "csv": {
      "description": "The CSV backend",
      "dependencies": [
        "fast-cpp-csv-parser"
      ]
    },
    "json": {
      "description": "The JSON backend",
      "dependencies": [
        "jsoncons"
      ]
    }
  }
}

"vcpkg-configuration"

Allows to embed vcpkg configuration properties inside the vcpkg.json file. Everything inside the vcpkg-configuration property is treated as if it were defined in a vcpkg-configuration.json file. See the vcpkg-configuration.json documentation for details.

Having a vcpkg-configuration defined in vcpkg.json while also having a vcpkg-configuration.json file is not allowed and will result in the vcpkg command terminating with an error message.

Example:

  "name": "test",
  "version": "1.0.0",
  "dependencies": [ "beison", "zlib" ],
  "vcpkg-configuration": {
    "registries": [
      {
        "kind": "git",
        "baseline": "dacf4de488094a384ca2c202b923ccc097956e0c",
        "repository": "https://github.com/northwindtraders/vcpkg-registry",
        "packages": [ "beicode", "beison" ]
      }
    ],
    "overlay-ports": [ "./my-ports/fmt", 
                       "./team-ports"
    ]
  }