git » core-pkgbuilds.git » main » tree

[main] / bsbot.py

#!/usr/bin/env python3

# BootStrapBot (lol)
# BuildSystemBot
# BullShitBot :P


import os
import sys
from time import strftime
import subprocess
from subprocess import DEVNULL, PIPE, STDOUT

class Return:
    def __init__(self, rv, out=None):
        self.rv = rv
        self.out = out
    def __bool__(self):
        return self.rv == 0
    def __int__(self):
        return self.rv
    def __str__(self):
        if self.out:
            return self.out
        return str(self.rv)

def sub(*args, **kwargs):
    c = subprocess.run(*args, **kwargs)
    return Return(c.returncode, c.stdout)

def subc(*args, **kwargs):
    c = subprocess.run(*args, **kwargs)
    if c.returncode != 0:
        print("subprocess failed: ", args)
        print("code:", c.returncode)
        sys.exit(1)
    return Return(c.returncode, c.stdout)


def subtea(cmds, log):
    if not isinstance(cmds[0], list):
        cmds = [cmds]
    teecmd = ["tee", log ]
    for cmd in cmds:
        proc = subprocess.Popen(cmd, stdin=DEVNULL, stderr=STDOUT, stdout=PIPE)
        tee = subprocess.Popen(teecmd, stdin=proc.stdout)
        r1 = proc.wait()
        tee.wait()
        if r1:
            print("subprocess failed: ", cmd)
            print("code:", r1)
            sys.exit(1)
        teecmd = ["tee", "-a", log ]

if len(sys.argv) != 2:
    print(f"Usage: {sys.argv[0]} <list|directory>")
    sys.exit(0)

try:
    with open(sys.argv[1], 'r') as pkgf:
        pkgs = pkgf.readlines()
except IsADirectoryError:
    pkgs = [ sys.argv[1] ]

basedir = os.getcwd()

with open("pre-rm-pkg", 'r') as f:
    pre_rm_list = [ x.strip() for x in f.readlines() ]

print(pre_rm_list)

def pre_rm(pkg):
    if pkg not in pre_rm_list:
        return
    print("Performing pre-remove")
    cmd = [ "pacman", "-Rdd", "--noconfirm", pkg ]
    x = sub(cmd, stdin=DEVNULL, stderr=STDOUT, stdout=DEVNULL)
    print(f"Result: {str(x)}")

is_64bits = sys.maxsize > 2**32

chost = "aarch64" if is_64bits else "armv7h"

bspkg = f"/sources/pkg/{chost}/bootstrap"
try:
	os.stat(bspkg)
except FileNotFoundError:
	bspkg = f"/sources/pkg/{chost}/core"


def pkgbuild_check_sums():
    with open('PKGBUILD', 'r') as f:
        for line in f:
            if 'sums=' in line:
                return True

    sumcmd = [ "su", "builder", "-c", "makepkg -g >> PKGBUILD" ]
    subc(sumcmd)

logdir = strftime("logs-%y%m%d-%H%M%S")
os.mkdir(logdir)


for pkgline in pkgs:
    p_l = pkgline.rstrip().split(' ',maxsplit=1)
    pkg = p_l[0]

    if len(p_l) > 1:
        line = " " + p_l[1] + "=1"
        ll = "-" + p_l[1]
    else:
        line = ""
        ll = ""

    os.chdir(basedir)
    subc(["chown", "-R", "builder:builder", pkg])
    print(f"{strftime('%H:%M:%S')} Build {pkg}{line}")
    pre_rm(pkg)

    logfn = logdir + '/' + pkg + ll + ".log"
    with open(logfn, "w") as lf:
        os.chdir(pkg)
        pkgbuild_check_sums()
        makepkg = "makepkg -C --holdver" + line
        bcmd = [ "su", "builder", "-c", makepkg ]
        print(f"Building (log: '{logfn}')..")
        bres = sub(bcmd, stdin=DEVNULL, stderr=STDOUT, stdout=lf)

    if not bres:
        os.chdir(basedir)
        print(f"Build {pkg} failed. Tail:")
        sub(["tail", "-n", "100", logfn])
        print(f"Tail over. Build {pkg} failed.")
        sys.exit(1)

    print("Done. Packaging..")
    repo_pkgs = []
    pacu_pkgs = []
    with os.scandir() as it:
        for e in it:
            if e.name.endswith('.pkg.tar.xz') and e.is_file():
                if "-debug-" not in e.name and "-dbginfo-" not in e.name:
                    pacu_pkgs.append(e.name)
                repo_pkgs.append(e.name)
    # Do a single pacman-U call so that inter-pkg dependencies are resolved
    if len(pacu_pkgs):
        #subc(["pacman", "-Udd", "--noconfirm", '--overwrite', '*'] + pacu_pkgs)
        subc(["pacman", "-U", "--noconfirm"] + pacu_pkgs)
    for rp in repo_pkgs:
        subc(["mv", rp, bspkg + '/'])
    os.chdir(bspkg)
    for rp in repo_pkgs:
        subc(["repo-add", "-R", "core.db.tar.gz", rp])
    print("Done.")