mirror of
https://git.mirrors.martin98.com/https://github.com/Ultimaker/Cura
synced 2025-04-19 12:19:37 +08:00
126 lines
5.1 KiB
Python
126 lines
5.1 KiB
Python
# Copyright (c) 2022 UltiMaker
|
|
# Cura is released under the terms of the LGPLv3 or higher.
|
|
|
|
|
|
import argparse # Command line arguments parsing and help.
|
|
import os
|
|
import shutil
|
|
import subprocess
|
|
import uuid
|
|
import semver
|
|
from datetime import datetime
|
|
from pathlib import Path
|
|
|
|
from jinja2 import Template
|
|
|
|
|
|
def work_path(filename: Path) -> Path:
|
|
if not filename.is_absolute():
|
|
return Path(os.getcwd(), filename.parent)
|
|
else:
|
|
return filename.parent
|
|
|
|
|
|
def generate_wxs(source_path: Path, dist_path: Path, filename: Path, app_name: str, version: str):
|
|
source_loc = Path(os.getcwd(), source_path)
|
|
dist_loc = Path(os.getcwd(), dist_path)
|
|
work_loc = work_path(filename)
|
|
work_loc.mkdir(parents=True, exist_ok=True)
|
|
parsed_version = semver.Version.parse(version)
|
|
|
|
jinja_template_path = Path(source_loc.joinpath("packaging", "msi", "UltiMaker-Cura.wxs.jinja"))
|
|
with open(jinja_template_path, "r") as f:
|
|
template = Template(f.read())
|
|
|
|
wxs_content = template.render(
|
|
app_name=f"{app_name}",
|
|
main_app="UltiMaker-Cura.exe",
|
|
version=version,
|
|
version_major=str(parsed_version.major),
|
|
version_minor=str(parsed_version.minor),
|
|
version_patch=str(parsed_version.patch),
|
|
company="UltiMaker",
|
|
web_site="https://ultimaker.com",
|
|
year=datetime.now().year,
|
|
upgrade_code=str(uuid.uuid5(uuid.NAMESPACE_DNS, app_name)),
|
|
cura_license_file=str(source_loc.joinpath("packaging", "msi", "cura_license.rtf")),
|
|
cura_banner_top=str(source_loc.joinpath("packaging", "msi", "banner_top.bmp")),
|
|
cura_banner_side=str(source_loc.joinpath("packaging", "msi", "banner_side.bmp")),
|
|
cura_icon=str(source_loc.joinpath("packaging", "icons", "Cura.ico")),
|
|
)
|
|
|
|
with open(work_loc.joinpath("UltiMaker-Cura.wxs"), "w") as f:
|
|
f.write(wxs_content)
|
|
|
|
try:
|
|
shutil.copy(source_loc.joinpath("packaging", "msi", "ExcludeComponents.xslt"),
|
|
work_loc.joinpath("ExcludeComponents.xslt"))
|
|
except shutil.SameFileError:
|
|
pass
|
|
|
|
|
|
def cleanup_artifacts(dist_path: Path):
|
|
dist_loc = Path(os.getcwd(), dist_path)
|
|
dirt = [d for d in dist_loc.rglob("__pycache__") if d.is_dir()]
|
|
dirt += [d for d in dist_loc.rglob("*.dist-info") if d.is_dir()]
|
|
for d in dirt:
|
|
if d.exists():
|
|
shutil.rmtree(d, ignore_errors=True)
|
|
|
|
|
|
def build(dist_path: Path, filename: Path):
|
|
dist_loc = Path(os.getcwd(), dist_path)
|
|
work_loc = work_path(filename)
|
|
wxs_loc = work_loc.joinpath("UltiMaker-Cura.wxs")
|
|
heat_loc = work_loc.joinpath("HeatFile.wxs")
|
|
exclude_components_loc = work_loc.joinpath("ExcludeComponents.xslt")
|
|
build_loc = work_loc.joinpath("build_msi")
|
|
|
|
heat_command = ["heat",
|
|
"dir", f"{dist_loc.as_posix()}\\",
|
|
"-dr", "APPLICATIONFOLDER",
|
|
"-cg", "NewFilesGroup",
|
|
"-sw5150", # Don't pollute logs with warnings from auto generated content
|
|
"-gg",
|
|
"-g1",
|
|
"-sf",
|
|
"-srd",
|
|
"-var", "var.CuraDir",
|
|
"-t", f"{exclude_components_loc.as_posix()}",
|
|
"-out", f"{heat_loc.as_posix()}"]
|
|
subprocess.call(heat_command)
|
|
|
|
build_command = ["candle",
|
|
"-arch", "x64",
|
|
f"-dCuraDir={dist_loc}\\",
|
|
"-ext", "WixFirewallExtension",
|
|
"-out", f"{build_loc.as_posix()}\\",
|
|
f"{wxs_loc.as_posix()}",
|
|
f"{heat_loc.as_posix()}"]
|
|
subprocess.call(build_command)
|
|
|
|
link_command = ["light",
|
|
f"{build_loc.joinpath(wxs_loc.name).with_suffix('.wixobj')}",
|
|
f"{build_loc.joinpath(heat_loc.name).with_suffix('.wixobj')}",
|
|
"-sw1076", # Don't pollute logs with warnings from auto generated content
|
|
"-dcl:high", # Use high compression ratio
|
|
"-sval", # Disable ICE validation otherwise the CI complains
|
|
"-ext", "WixUIExtension",
|
|
"-ext", "WixFirewallExtension",
|
|
"-out", f"{work_loc.joinpath(filename.name)}"]
|
|
subprocess.call(link_command)
|
|
|
|
|
|
if __name__ == "__main__":
|
|
parser = argparse.ArgumentParser(description="Create Windows msi installer of Cura.")
|
|
parser.add_argument("--source_path", type=Path, help="Path to Conan install Cura folder.")
|
|
parser.add_argument("--dist_path", type=Path, help="Path to Pyinstaller dist folder")
|
|
parser.add_argument("--filename", type=Path,
|
|
help="Filename of the exe (e.g. 'UltiMaker-Cura-5.1.0-beta-Windows-X64.msi')")
|
|
parser.add_argument("--name", type=str, help="App name (e.g. 'UltiMaker Cura')")
|
|
parser.add_argument("--version", type=str, help="The full cura version, e.g. 5.9.0-beta.1+24132")
|
|
args = parser.parse_args()
|
|
generate_wxs(args.source_path.resolve(), args.dist_path.resolve(), args.filename.resolve(), args.name, args.version)
|
|
cleanup_artifacts(args.dist_path.resolve())
|
|
build(args.dist_path.resolve(), args.filename)
|