conan入门(三十六):在set_version方法中从pom.xml中读取版本号实现动态版本定义

一般情况下,我们通过self.version字段定义conan 包的版本号如下:

class PkgConan(ConanFile):
	name = "pkg"
	version = "1.7.3"

因为版本号是写死的,所以这种方式有局限性:
比如我的java项目中版本号是在pom.xml中定义的,c++项目是java项目的子项目,如果java项目版本号升级了,我每次发布java版本的时候都需要手工修改conanfile.py中的self.version才能让c++子项目的版本号与java项目的版本号同步更新,虽然不复杂,但增加了维护工作量,容易忘记。
所以如果conanfile.py中定义的版本号能自动与pom.xml中的版本号同步是最好的解决办法,
conanfile.py中的 set_version方法用就是用于实现动态版本号定义。
这个方法在官方文档中有说明和示例,只不过官方示例只是从读取一个简单的包含了版本号的文本文件,赋值给self.version。(参见《set_version()》)

但对于pom.xml,就复杂些,需要引入xml相关的包,解析xml,然后读取version节点,pom.xml文件内容示例如下:


<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
	<modelVersion>4.0.0modelVersion>
	<parent>
		<groupId>com.gitee.l0kmgroupId>
		<artifactId>facedbartifactId>
		<version>3.1.1-SNAPSHOTversion>
		<relativePath>..relativePath>
	parent>
	<artifactId>facedb-rpc-cppartifactId>
	<name>facedb C++ clientname>
project>

如下在conanfile.py中实现 set_version方法,方法中解析pom.xml,从中读取parent/version节点获取版本号。

from conan import ConanFile
import xml.etree.ElementTree as ET
import os

class Pkg(ConanFile):
    # 将包含版本号的pom.xml与conanfile.py放在一起
    exports = "pom.xml"
    exports_sources = "CMakeLists.txt","src/CMakeLists.txt", "src/facedbclient/*","src/facedbclient/CMakeLists.txt","src/gfaux_tools/*","src/gfaux_tools/CMakeLists.txt","src/test/*","src/test/CMakeLists.txt", "cmake/*.cmake.in"

    def set_version(self):
        # 从pom.xml中解析 parent/version 节点获取pom.xml中定义的版本
        root = ET.parse(os.path.join(self.recipe_folder,"pom.xml")).getroot()
        # 将版本号转为小写如果1.0.0-snapshot,因为conan不允许版本号中有大写字母
        # pom.xml中有namespace定义,所以要加{*}指定任意namespace
        self.version = root.find("{*}parent/{*}version").text.lower()
        self.output.info(f"version:{self.version}")

完整的conanfile.py代码示例参见
https://gitee.com/l0km/facedb/blob/master/facedb-rpc-cpp/conanfile.py

参考资料

《set_version()》
《xml.etree.ElementTree》
《Reading Maven Pom xml in Python》

conan系列文章

《conan入门(一):conan 及 JFrog Artifactory 安装》
《conan入门(二):conan 服务配置-密码管理及策略》
《conan入门(三):上传预编译的库(artifact)》
《conan入门(四):conan 引用第三方库示例》
《conan入门(五):conan 交叉编译引用第三方库示例》
《conan入门(六):conanfile.txt conanfile.py的区别》
《conan入门(七):将自己的项目生成conan包》
《conan入门(八):交叉编译自己的conan包项目》
《conan入门(九):NDK交叉编译自己的conan包项目塈profile的定义》
《conan入门(十):Windows下Android NDK交叉编译Boost》
《conan入门(十一):Linux下Android NDK交叉编译Boost》
《conan入门(十二):Windows NDK 编译 boost报错:CMake was unable to find a build program … MinGW Makefile》
《conan入门(十三):conan info 命令的基本用法》
《conan入门(十四):conan new 命令的新特性–模板功能(–template)》
《conan入门(十五):AttributeError: ‘CMake‘ object has no attribute ‘definitions‘》
《conan入门(十六):profile template功能实现不同平台下profile的统一》
《conan入门(十七):支持android NDK (armv7,armv8,x86,x86_64)交叉编译的统一profile jinja2模板》
《conan入门(十八):Cannot recognize the Windows subsystem, install MSYS2/cygwin or specify a build_require》
《conan入门(十九):封装第三方开源库cpp_redis示例》
《conan入门(二十):封装只包含头文件(header_only)的库示例》
《conan入门(二十一):解决MinGW编译Openssl的编译错误:crypto/dso/dso_win32.c》
《conan入门(二十二):编译 openssl要求python 3.7以上版本》
《conan入门(二十三):Windows下MinGW编译libcurl》
《conan入门(二十四):通过CONAN_DISABLE_CHECK_COMPILER禁用编译器检查》
《conan入门(二十五):imports将包安装到本地项目或其他指定位置》
《conan入门(二十七):因profile [env]字段废弃导致的boost/1.81.0 在aarch64-linux-gnu下交叉编译失败》
《conan入门(二十八):解决conan 1.60.0下 arch64-linux-gnu交叉编译openssl/3.1.2报错问题》
《conan入门(二十九):对阿里mnn进行Conan封装塈conans.CMake和conan.tools.cmake.CMake的区别》
《conan入门(三十):对腾讯ncnn进行Conan封装》
《conan入门(三十一):在命令行(shell)中从profile中读取配置参数》
《conan 入门(三十二):package_info中配置禁用CMakeDeps生成使用项目自己生成的config.cmake》
《conan 入门(三十三):requirements()指定header的可见性(transitive_headers)》
《conan 入门(三十四):conan 2.x实现对只有Makefile的项目(erpcgen)的封装示例》
《conan 入门(三十五):在conanfile.py中获取C++编译器完整路径的方法》
《conan入门(三十六):在set_version方法中从pom.xml中读取版本号实现动态版本定义》

你可能感兴趣的:(conan,conan,python,version,pom.xml)