添加 McuVersionGen.py

This commit is contained in:
2025-05-06 21:36:49 +08:00
commit 8dc4632f33

154
McuVersionGen.py Normal file
View File

@@ -0,0 +1,154 @@
import re
import subprocess
import os
import sys
import datetime
import io
import locale
system_encoding = locale.getpreferredencoding(False)
sys.stdout = io.TextIOWrapper(sys.stdout.buffer, encoding=system_encoding)
# 语义化版本 https://semver.org/lang/zh-CN/spec/v2.0.0.html
default_major_version = 0 # 主版本号
defalut_minor_version = 1 # 次版本号
defalut_revision_version = 0 # 修订版本号
defalut_pre_release_version = "" # 预发行版本号
def get_version_from_file(path):
"""从项目根目录的version.txt文件中读取版本信息"""
version_file = os.path.join(path, "version.txt")
# 默认版本号
versions = {
"major_version": default_major_version,
"minor_version": defalut_minor_version,
"revision_version": defalut_revision_version,
"pre_release_version": defalut_pre_release_version
}
# 检查文件是否存在
if not os.path.exists(version_file):
# 创建默认version.txt文件
try:
with open(version_file, 'w', encoding='utf-8') as f:
f.write(f"major_version={versions['major_version']}\n")
f.write(f"minor_version={versions['minor_version']}\n")
f.write(f"revision_version={versions['revision_version']}\n")
f.write(
f"pre_release_version={versions['pre_release_version']}\n")
print(f"已在项目根目录创建默认的version.txt文件")
except Exception as e:
print(f"创建version.txt文件失败: {str(e)}")
return versions
# 读取version.txt文件
try:
with open(version_file, 'r', encoding='utf-8') as f:
for line in f:
line = line.strip()
if '=' in line:
key, value = line.split('=', 1)
key = key.strip()
value = value.strip()
if key in versions:
# 处理整数类型的版本号
if key != "pre_release_version":
try:
versions[key] = int(value)
except ValueError:
raise ValueError(
f"版本号解析错误: {key}必须是整数,当前值为'{value}'")
else:
versions[key] = value
except Exception as e:
raise Exception(f"解析version.txt文件失败: {str(e)}")
return versions
def generate_version_file(name, path, file_version, file_build_time):
if not os.path.exists(f"{path}/Core/App/AutoGen/"):
os.makedirs(f"{path}/Core/App/AutoGen/", exist_ok=True)
with open(f"{path}/Core/App/AutoGen/autogen_version.c", "w", encoding="utf-8") as f:
f.write("// 这个文件是自动生成的\n")
f.write("// 对它作任何修改都将在编译前由程序自动覆盖\n")
f.write("// 不需要修改这个文件的内容\n")
f.write("\n")
f.write(f'const char *g_name = "{name}";\n')
f.write(f'const char *g_version = "{file_version}";\n')
f.write(f'const char *g_buildTime = "{file_build_time}";\n')
def generate_version(path):
# 从version.txt获取版本信息
try:
versions = get_version_from_file(path)
major_version = versions["major_version"]
minor_version = versions["minor_version"]
revision_version = versions["revision_version"]
pre_release_version = versions["pre_release_version"]
except Exception as e:
print(f"错误: {str(e)}")
sys.exit(-1)
generated_version = f"{major_version}.{minor_version}.{revision_version}"
git_commit_id = ""
# 检查是否在Git仓库中
git_process = subprocess.run(
["git", "rev-parse"], capture_output=True, text=True, cwd=path)
if git_process.returncode == 0:
# 检查是否有未提交的更改
commit_process = subprocess.run(
["git", "status", "-s"], capture_output=True, text=True, cwd=path)
if commit_process.stdout != "":
# 有未提交的更改获取当前commit id并加*
process = subprocess.run(
["git", "rev-parse", "--short", "HEAD"], capture_output=True, text=True, cwd=path)
git_commit_id = process.stdout.strip() + "*"
else:
# 没有未提交的更改直接获取当前commit id
process = subprocess.run(["git", "rev-parse", "--short=8", "HEAD"], capture_output=True, text=True,
cwd=path)
git_commit_id = process.stdout.strip()
# 根据 pre_release_version 和 git_commit_id 更新版本号
if pre_release_version and git_commit_id:
generated_version += f"-{pre_release_version}+{git_commit_id}"
elif pre_release_version:
generated_version += f"-{pre_release_version}"
elif git_commit_id:
generated_version += f"+{git_commit_id}"
# https://regex101.com/r/Ly7O1x/3/
semver_regex = (
r"^(?P<major>0|[1-9]\d*)\.(?P<minor>0|[1-9]\d*)\.(?P<patch>0|[1-9]\d*)(?:-(?P<prerelease>(?:0|[1-9]\d*|\d*["
r"a-zA-Z-][0-9a-zA-Z-]*)(?:\.(?:0|[1-9]\d*|\d*[a-zA-Z-][0-9a-zA-Z-]*))*))?(?:\+(?P<buildmetadata>["
r"0-9a-zA-Z-]+(?:\.[0-9a-zA-Z-]+)*|\*|.*\*))?$")
if not re.match(semver_regex, generated_version):
print(f"生成的版本号 {generated_version} 不符合语义化版本规范")
return generated_version
if __name__ == "__main__":
try:
name = sys.argv[1] if len(sys.argv) > 1 else 'McuProgram'
project_directory = sys.argv[2] if len(sys.argv) > 2 else '.'
if not os.path.isdir(project_directory):
raise Exception("Invalid project directory")
version = generate_version(project_directory)
build_time = datetime.datetime.now().strftime("%Y-%m-%d %H:%M:%S")
generate_version_file(
name, project_directory, version, build_time)
print(f"Program name: {name}")
print(f"Version: {version}")
print(f"Build time: {build_time}")
sys.exit(0)
except Exception as e:
print(e)
sys.exit(-1)