Refactor license retrieval to use Conan's Git helper

Replaced the external `gitpython` library with Conan's built-in `Git` helper for repository operations. Simplified and improved the license retrieval logic while maintaining existing functionality, ensuring better integration and reduced dependency overhead.
This commit is contained in:
Jelle Spijker 2025-03-26 11:50:52 +01:00
parent fa1ead3064
commit adf8f5bdd8
No known key found for this signature in database
GPG Key ID: DE9D445A0C3D8AA1

View File

@ -5,8 +5,6 @@ import tempfile
import tarfile
from io import StringIO
from pathlib import Path
from git import Repo
from git.exc import GitCommandError
from jinja2 import Template
@ -14,7 +12,7 @@ from conan import ConanFile
from conan.tools.files import copy, rmdir, save, mkdir, rm, update_conandata
from conan.tools.microsoft import unix_path
from conan.tools.env import VirtualRunEnv, Environment, VirtualBuildEnv
from conan.tools.scm import Version
from conan.tools.scm import Version, Git
from conan.errors import ConanInvalidConfiguration, ConanException
required_conan_version = ">=2.7.0" # When changing the version, also change the one in conandata.yml/extra_dependencies
@ -218,45 +216,47 @@ class CuraConan(ConanFile):
dependencies[data["info"]["name"]] = dependency_description
@staticmethod
def _get_license_from_repository(sources_url, version, license_file_name = None):
if sources_url.startswith("https://github.com/Ultimaker/") and "private" in sources_url:
return None
git_url = sources_url
if git_url.endswith('/'):
git_url = git_url[:-1]
def _format_git_url(url):
"""Return a properly formatted git repository URL."""
git_url = url.rstrip("/")
if not git_url.endswith(".git"):
git_url = f"{git_url}.git"
git_url = git_url.replace("/cgit/", "/")
return git_url.replace("/cgit/", "/")
tags = [f"v{version}", version]
files = ["LICENSE", "LICENSE.txt", "LICENSE.md", "COPYRIGHT", "COPYING", "COPYING.LIB"] if license_file_name is None else [license_file_name]
def _get_license_from_repository(self, repository_url, version, license_file_name=None):
# Do not retrieve license if repository is flagged as private.
if repository_url.startswith("https://github.com/Ultimaker/") and "private" in repository_url:
return None
with tempfile.TemporaryDirectory() as clone_dir:
repo = Repo.clone_from(git_url, clone_dir, depth=1, no_checkout=True)
# Prepare the Git URL and candidate lists.
git_url = self._format_git_url(repository_url)
candidate_tags = [f"v{version}", version]
candidate_license_files = (
[license_file_name] if license_file_name
else ["LICENSE", "LICENSE.txt", "LICENSE.md", "COPYRIGHT", "COPYING", "COPYING.LIB"]
)
for tag in tags:
# Clone the repository into a temporary directory.
with tempfile.TemporaryDirectory() as clone_directory:
git = Git(self, clone_directory)
git.clone(url=git_url, target=".", args=["--depth", "1"])
# Iterate over candidate tags.
for tag in candidate_tags:
try:
repo.git.fetch('--depth', '1', 'origin', 'tag', tag)
except GitCommandError:
continue
repo.git.sparse_checkout('init', '--cone')
for file_name in files:
repo.git.sparse_checkout('add', file_name)
try:
repo.git.checkout(tag)
except GitCommandError:
pass
for file_name in files:
license_file = os.path.join(clone_dir, file_name)
if os.path.exists(license_file):
with open(license_file, 'r', encoding='utf8') as file:
return file.read()
git.checkout(commit=tag)
except Exception:
continue # Try next tag if checkout fails.
# Search for any existing license file in the repository.
for file_name in candidate_license_files:
license_path = os.path.join(clone_directory, file_name)
if os.path.exists(license_path):
with open(license_path, "r", encoding="utf8") as license_file:
return license_file.read()
# Exit if no license file was found for the checked out tag.
break
return None
def _make_conan_dependency_description(self, dependency, dependencies):
dependency_description = {