import subprocess
from typing import List

from debputy import elf_util
from debputy.elf_util import ELF_LINKING_TYPE_DYNAMIC
from debputy.plugin.api import (
    VirtualPath,
    BinaryCtrlAccessor,
    MetadataDetectorPackageContext,
)

SKIPPED_DEBUG_DIRS = [
    "lib",
    "lib64",
    "usr",
    "bin",
    "sbin",
    "opt",
    "dev",
    "emul",
    ".build-id",
]

SKIP_DIRS = {f"./usr/lib/debug/{subdir}" for subdir in SKIPPED_DEBUG_DIRS}


def _walk_filter(fs_path: VirtualPath, children: List[VirtualPath]) -> bool:
    if fs_path.path in SKIP_DIRS:
        children.clear()
        return False
    return True


def detect_shlibdeps(
    fs_root: VirtualPath,
    ctrl: BinaryCtrlAccessor,
    context: MetadataDetectorPackageContext,
) -> None:
    elf_files_to_process = elf_util.find_all_elf_files(
        fs_root,
        walk_filter=_walk_filter,
        with_linking_type=ELF_LINKING_TYPE_DYNAMIC,
    )

    if not elf_files_to_process:
        return

    binary_package = context.binary_package

    with ctrl.substvars.flush() as substvars_file:
        dpkg_cmd = ["dpkg-shlibdeps", f"-T{substvars_file}"]
        if binary_package.is_udeb:
            dpkg_cmd.append("-tudeb")
        dpkg_cmd.extend(p.fs_path for p in elf_files_to_process)
        print(f"Executing for {binary_package.name}: {dpkg_cmd}")
        subprocess.check_call(dpkg_cmd)
