完整指南:cpack --preset 配置字段全解析)
构建工具开发工具CLI【免费下载链接】CMakeMirror of CMake upstream repository项目地址https://gitcode.com/gh_mirrors/cm/CMake点击查看免费下载导读Package Preset包预设是 CMake 预设体系中专门面向打包阶段CPack的配置单元它把 CPack 的生成器、构建配置、变量、输出目录等参数收敛到CMakePresets.json中使“配置 → 构建 → 测试 → 打包”整条流水线都能以预设驱动。本文以仓库中 Help/manual/presets/packagePresets-properties.rst 为骨架结合 CPack 源码实现与预设 schema逐字段讲解packagePresets的语义、继承规则与 CLI 对应关系并给出可直接落地的完整示例读完即可在项目中用cpack --preset实现一键打包。背景Package Preset 在 CMake 预设体系中的位置CMake 预设Presets自 3.19 引入目标是解决“常见构建配置难以与他人共享”的问题见 Help/manual/cmake-presets.7.rst。预设文件为CMakePresets.json可入库共享与CMakeUserPresets.json个人本地配置不应入库二者格式完全相同。包预设于预设格式版本 6CMake 3.25正式加入见 Help/manual/cmake-presets.7.rst用于为cpack指定打包参数。根据 Help/manual/presets/schema.yaml 中的定义根对象上的packagePresets是一个可选的包预设对象数组每个对象对应一次打包的参数集合。在同一目录下packagePresets数组内部每一项的字段依次解析如下对应 Help/manual/presets/packagePresets-properties.rst。在预设体系中包预设与 configure/build/test/workflow 预设并列但存在依赖关系它通过configurePreset字段关联一个配置预设从而复用其binaryDir与构建产物目录。通用元数据字段name、hidden、inherits、condition、vendor、displayName、description这七个字段是所有预设共有的“骨架”字段包预设同样适用。name必填机器可读的预设名称也是cpack --preset命令行使用的标识符。约束如下在同一目录下CMakePresets.json与CMakeUserPresets.json的并集中不允许出现两个同名包预设但包预设可以与 configure、build、test、workflow 预设同名互不冲突。例如取自 Help/manual/presets/example.json 的示例片段packagePresets: [ { name: default, configurePreset: default, generators: [TGZ] } ]hidden可选布尔hidden为true时该预设不能通过cpack --preset直接使用不需要拥有有效的configurePreset即使通过继承也无法获得也不要求有效典型用途是作为基类预设供其他预设通过inherits继承。inherits可选字符串或字符串数组指定继承来源。单个字符串等价于只含一个元素的数组。继承规则默认继承inherits预设的全部字段但name、hidden、inherits、description、displayName不参与继承可在子预设中自由覆盖若多个被继承预设对同一字段给出冲突值inherits数组中靠前的预设优先只能继承同一文件中定义、或该文件直接/间接include的文件中的预设CMakePresets.json中的预设不能继承CMakeUserPresets.json中的预设后者隐含包含前者反之不成立见 Help/manual/cmake-presets.7.rst。condition可选一个Condition对象用于判断预设是否可用例如仅在特定操作系统上启用。条件支持const、equals、notEquals、inList、notInList、matches、notMatches、anyOf、allOf、not等类型其中lhs/rhs/string/regex/list字段支持宏展开详见 Help/manual/cmake-presets.7.rst。vendor可选映射存放厂商私有信息的映射。CMake 本身不解释其内容只校验“若存在则必须是 map”。建议遵循根级vendor字段的约定厂商实现继承时也应采取合理策略。displayName 与 description可选字符串displayName为人类可读名称description为人类可读描述二者仅用于展示不影响行为。environment打包环境变量的声明与合并规则environment为可选的环境变量映射key 为变量名不能是空字符串value 为null或字符串每个变量都会被设置无论进程环境是否已给它赋值即显式覆盖外部环境。该字段支持宏展开且映射内部的变量可以互相引用、顺序任意但不能成环例如ENV_1是$env{ENV_2}则ENV_2就不能是$env{ENV_1}。$penv{NAME}只读取父进程环境用于向已有环境变量前插/后插值典型如PATH拼接。合并规则见 Help/manual/presets/packagePresets-properties.rst环境变量通过inherits继承预设的最终环境 自身environment∪ 所有父预设的environment多个预设定义同一变量时按标准inherits规则处理靠前优先将某变量设为null会使其不被设置即使从其他预设继承了值也会被清除。从源码看依赖型预设build/test/package在解析时通过InheritOptionalValue逐字段继承父预设值Source/cmCMakePresetsGraph.cxx而null语义对应 “清除继承值”。configurePreset关联配置预设推断打包目录configurePreset为可选字符串指定与该包预设关联的 configure preset 名称若未指定则必须从inherits预设继承除非该预设是hidden打包目录由该 configure preset 推断打包将在与配置、构建相同的binaryDir中运行。这一点在 CPack 入口源码中有直接印证Source/CPack/cpack.cxx 通过--preset解析出的包预设查找对应 configure preset取其展开后的BinaryDir作为打包工作目录若 configure preset 不存在会报错并打印可用列表。inheritConfigureEnvironment是否继承配置预设的环境可选布尔值默认true为true时关联 configure preset 的环境变量会在所有继承来的包预设环境之后、本预设显式声明的环境变量之前注入为false时则不继承 configure preset 的环境。源码实现见 Source/cmCMakePresetsGraph.cxx当InheritConfigureEnvironment.value_or(true)为真时将 configure preset 的Environment插入到包预设自身的Environment之前随后再进行宏展开。同时注意关联的 configure preset 必须是可达的ReachableFiles校验见同文件 L1329-L1334否则报错CONFIGURE_PRESET_UNREACHABLE_FROM_FILE。打包行为字段generators、configurations、variables、configFile这四个字段直接把包预设映射到 cpack 命令行选项。generators可选字符串数组指定 CPack 使用的生成器列表如TGZ、ZIP、DEB、RPM、NSIS等。configurations可选字符串数组指定 CPack 要打包的构建配置如Debug、Release。variables可选映射要传给 CPack 的变量映射等价于-D命令行参数key 为变量名value 为赋值字符串。例如{CPACK_PACKAGE_CONTACT: devexample.com}等价于cpack -D CPACK_PACKAGE_CONTACTdevexample.com。configFile可选字符串指定 CPack 使用的配置文件即 CPack 的.cmake配置脚本对应 CLI 的-C/--config。以上四个字段的 CLI 对应关系在 Source/CPack/cpack.cxx 中体现仅当对应命令行参数尚未给出时才会用预设值填充——即显式命令行参数优先于预设值if (!expandedPreset-ConfigFile.empty() cpackConfigFile.empty()) { cpackConfigFile expandedPreset-ConfigFile; } if (!expandedPreset-Generators.empty() generator.empty()) { generator cmList::to_string(expandedPreset-Generators); } if (!expandedPreset-Configurations.empty() cpackBuildConfig.empty()) { cpackBuildConfig cmList::to_string(expandedPreset-Configurations); } definitions.insert(expandedPreset-Variables.begin(), expandedPreset-Variables.end());JSON 解析侧这些字段在 Source/cmCMakePresetsGraphReadJSONPackagePresets.cxx 中被逐一绑定generators、configurations使用PresetVectorStringHelper字符串数组variables使用Mapstd::stringconfigFile使用PresetStringHelper。output调试与详细输出开关output为可选对象目前合法键只有两个定义于 Help/manual/presets/packageOutput-properties.rst键类型说明debug布尔为true时打印调试信息等价于命令行cpack --debugverbose布尔为true时详细输出等价于命令行cpack --verbose源码侧由OutputHelper解析两个字段均用PresetOptionalBoolHelperSource/cmCMakePresetsGraphReadJSONPackagePresets.cxxCPack 入口在展开预设后据此调用调试/详细日志Source/CPack/cpack.cxx。包信息字段packageName、packageVersion、packageDirectory、vendorName这四者分别对应 CPack 的包名、版本、输出目录与厂商名对应关系如下字段类型对应 CLI / 变量packageName字符串cpack --package-name覆盖CPACK_PACKAGE_NAMEpackageVersion字符串cpack --package-version覆盖CPACK_PACKAGE_VERSIONpackageDirectory字符串cpack -B覆盖CPACK_PACKAGE_DIRECTORYvendorName字符串cpack --vendor覆盖CPACK_PACKAGE_VENDOR其赋值逻辑在 Source/CPack/cpack.cxx仅在对应命令行值尚未指定时填充即显式命令行参数优先。⚠️ packageName 与 packageVersion 的已知问题原文档对packageName与packageVersion各附有一条重要警告Help/manual/presets/packagePresets-properties.rst 与 L158-L164由于实现问题这两个字段不会影响最终生成的包文件名但包的其他方面可能使用该值从而造成不一致。未来的 CMake 版本可能修复此问题在此之前建议不要使用这两个字段。也就是说设置packageName不会让产出物改名最终文件名仍由 CPack 配置文件中的CPACK_PACKAGE_FILE_NAME等决定但包内元数据等其他环节可能引用该值因此可能出现“文件名与内容不一致”的中间状态。在仓库当前状态下这是需要特别注意的坑。完整实操示例从预设到一键打包综合 Help/manual/presets/example.json 的结构下面给出一个覆盖包预设主要字段的完整示例{ version: 10, cmakeMinimumRequired: { major: 3, minor: 23, patch: 0 }, configurePresets: [ { name: default, displayName: Default Config, generator: Ninja, binaryDir: ${sourceDir}/build/default, cacheVariables: { CMAKE_BUILD_TYPE: Release }, environment: { PATH: /path/to/ninja/bin:$penv{PATH} } } ], packagePresets: [ { name: base-pack, hidden: true, generators: [TGZ, ZIP], configurations: [Release], variables: { CPACK_PACKAGE_CONTACT: devexample.com, CPACK_PACKAGE_VENDOR: Example Corp }, output: { verbose: true } }, { name: default, inherits: base-pack, configurePreset: default, packageDirectory: ${sourceDir}/dist, vendor: { example.com/ExampleIDE/1.0: { sign: true } } } ] }使用方式# 列出可用包预设 cpack --list-presets # 一键打包读取 CMakePresets.json 中名为 default 的包预设 cpack --preset default执行cpack --preset default时CPack 会解析default包预设展开继承自base-pack的字段通过configurePreset找到default配置预设推断二进制目录为${sourceDir}/build/default应用generatorsTGZ、ZIP与configurationsRelease注入variables中的 CPack 变量设置输出目录${sourceDir}/dist以 verbose 模式执行打包。若CMakePresets.json与CMakeUserPresets.json都不存在也可以使用cpack --presets-file file指定预设文件CMake 4.4 起支持见 Help/manual/cpack.1.rst。与 CLI 参数的优先级约定包预设与命令行参数的优先级遵循“显式命令行优先预设兜底”原则Source/CPack/cpack.cxx 中每个字段都先检查 CLI 值是否为空。可用性判定方面cpack --list-presets会对每个包预设做双重校验Source/cmCMakePresetsGraph.cxx关联的 configure preset 是否可用预设声明的 generators 在当前构建的 CPack 生成器列表中是否存在否则给出 “one or more package generators are not available” 的不可用原因。关键源码与文档索引字段权威定义Help/manual/presets/packagePresets-properties.rstoutput子对象定义Help/manual/presets/packageOutput-properties.rst预设总览与宏展开、版本历史Help/manual/cmake-presets.7.rst机器可读 schema含packagePresets的 JSON Schema 描述Help/manual/presets/schema.yaml 与 Help/manual/presets/schema.json完整示例文件Help/manual/presets/example.json包预设 JSON 解析实现Source/cmCMakePresetsGraphReadJSONPackagePresets.cxx预设图解析 / 继承 / 列表打印实现Source/cmCMakePresetsGraph.cxxcpack 对预设的消费逻辑与 CLI 选项Source/CPack/cpack.cxx 与 Help/manual/cpack.1.rst赞分享构建工具开发工具CLI【免费下载链接】CMakeMirror of CMake upstream repository项目地址https://gitcode.com/gh_mirrors/cm/CMake点击查看免费下载相关推荐CMake Configure Preset 字段完全指南configurePresets-properties 深度解析CMake Configure Preset 字段完全指南configurePresets properties 深度解析 本文以 CMake 官方手册 He构建工具开发工具CLICodex Dream Skin 预设主题Preset Packs完整指南内置 preset 包结构、theme.json 字段规范与投稿流程Codex Dream Skin 预设主题Preset Packs完整指南内置 preset 包结构、theme.json 字段规范与投稿流程 Codex桌面应用Starship Tokyo Night 预设Preset完整指南安装、配置与源码级解析Starship Tokyo Night 预设Preset完整指南安装、配置与源码级解析 Starship 的 Tokyo Night 预设是一套以 VSCLI开发工具上一篇GoSearch扩展功能如何集成BreachDirectory的180亿条记录下一篇让老旧Mac焕发新生macOS Catalina Patcher完全使用指南创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考