aboutsummaryrefslogtreecommitdiffstats
path: root/packaging-tools/installer_utils.py
blob: 91c4ec48a47f9938c5cd53043b623b0b777e9954 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
#!/usr/bin/env python3
# -*- coding: utf-8 -*-

#############################################################################
#
# Copyright (C) 2023 The Qt Company Ltd.
# Contact: https://www.qt.io/licensing/
#
# This file is part of the release tools of the Qt Toolkit.
#
# $QT_BEGIN_LICENSE:GPL-EXCEPT$
# Commercial License Usage
# Licensees holding valid commercial Qt licenses may use this file in
# accordance with the commercial license agreement provided with the
# Software or, alternatively, in accordance with the terms contained in
# a written agreement between you and The Qt Company. For licensing terms
# and conditions see https://www.qt.io/terms-conditions. For further
# information use the contact form at https://www.qt.io/contact-us.
#
# GNU General Public License Usage
# Alternatively, this file may be used under the terms of the GNU
# General Public License version 3 as published by the Free Software
# Foundation with exceptions as appearing in the file LICENSE.GPL3-EXCEPT
# included in the packaging of this file. Please review the following
# information to ensure the GNU General Public License requirements will
# be met: https://www.gnu.org/licenses/gpl-3.0.html.
#
# $QT_END_LICENSE$
#
#############################################################################

import os
from contextlib import contextmanager
from fnmatch import fnmatch
from pathlib import Path
from typing import Any, Generator, List
from urllib.parse import urlparse

import wget  # type: ignore

from logging_util import init_logger
from runner import run_cmd

log = init_logger(__name__, debug_mode=False)


class PackagingError(Exception):
    pass


@contextmanager
def ch_dir(path: str) -> Generator[Any, Any, Any]:
    oldwd = Path.cwd()
    os.chdir(path)
    try:
        yield
    finally:
        os.chdir(oldwd)


def is_valid_url_path(url: str) -> bool:
    try:
        result = urlparse(url)
        return all([result.scheme, result.netloc, result.path])
    except Exception:
        return False


def download_archive(url: str, dest_dir: str) -> str:
    parts = urlparse(url)
    file_name = Path(parts.path).name
    dest_file = os.path.join(dest_dir, file_name)
    if os.path.isfile(dest_file):
        log.info("Using existing downloaded file: %s", dest_file)
    else:
        wget.download(url, dest_file)
    return dest_file


def get_extract_cmd(artifact: str) -> List[str]:
    if artifact.endswith(".7z") or artifact.endswith(".zip"):
        return ['7z', 'x', artifact]
    if any(fnmatch(artifact, p) for p in ["*.tar*", "*.tgz"]):
        return ['tar', '-xf', artifact]
    raise PackagingError(f"Could not find suitable extractor for: {artifact}")


async def extract_archive(artifact: str, destination_dir: str) -> None:
    log.info("Extracting file: %s into: %s", artifact, destination_dir)
    extract_cmd = get_extract_cmd(artifact)
    try:
        Path(destination_dir).mkdir(parents=True, exist_ok=True)
        with ch_dir(destination_dir):
            run_cmd(cmd=extract_cmd)
    except Exception:
        log.exception("Could not extact a file %s to %s", artifact, destination_dir)
        raise