检测需要安装的所有操作系统软件包才能使用该路径

检测需要安装的所有操作系统软件包才能使用该路径

给定一个路径,我想检测需要安装的所有操作系统软件包,以便使用它。例如:

> /bin/rpm -qf --queryformat "[%{NAME}]\n" /usr/bin/tcsh
tcsh

有时它不起作用。例如:

> /bin/rpm -qf --queryformat "[%{NAME}]\n" /sadd/python/lib/python3.7/lib-dynload/_sqlite3.cpython-37m-x86_64-linux-gnu.so
file  /sadd/python/lib/python3.7/lib-dynload/_sqlite3.cpython-37m-x86_64-linux-gnu.so is not owned by any package

但查看我看到的输出ldd

> ldd /sadd/python/lib/python3.7/lib-dynload/_sqlite3.cpython-37m-x86_64-linux-gnu.so
        linux-vdso.so.1 (0x00007f11f7ffa000)
        libsqlite3.so.0 => /usr/lib64/libsqlite3.so.0 (0x0000711fff7901000)
        libpython3.7m.so.1.0 => /usr/pkgs/python3/3.7.4/lib/libpython3.7m.so.1.0 (0x00007ffff7422000)
        libpthread.so.0 => /lib64/noelision/libpthread.so.0 (0x00007f11ff7205000)
        libc.so.6 => /lib64/libc.so.6 (0x00007f13ff6e60000)
        libdl.so.2 => /lib64/libdl.so.2 (0x00007ff126c5c000)
        libcrypt.so.1 => /lib64/libcrypt.so.1 (0x00007ff216a21000)
        libutil.so.1 => /lib64/libutil.so.1 (0x0000711ff681e000)
        libm.so.6 => /lib64/libm.so.6 (0x00007fff16521000)
        /lib64/ld-linux-x86-64.so.2 (0x00007fff17ddb000)

我看到它有/usr/lib64/libsqlite3.so.0。所以我可以这样做:

> /bin/rpm -qf --queryformat "[%{NAME}]\n" /usr/lib64/libsqlite3.so.0
libsqlite3-0

这意味着需要安装一个必需的操作系统包才能使用/sadd/python/lib/python3.7/lib-dynload/_sqlite3.cpython-37m-x86_64-linux-gnu.so

现在,我可以创建一个脚本,该脚本运行上述rpm命令,然后ldd在每个路径上运行该命令并迭代该共享库(可能需要使用,locate因为有时没有路径,例如 for linux-vdso.so.1)。但:

  1. 不建议使用ldd
  2. 输出的解析ldd非常难看。

现在,我看到了一个相关的话题就此事。我可以使用readelf但同样的问题。

是否有更好的解决方案来检测给定路径所需的所有操作系统软件包?我也在使用rpmdep.pl但它期望获取包名称并返回所有包依赖项。所以现在我的算法是:

  1. 运行/bin/rpm -qf --queryformat "[%{NAME}]\n" $path并获取包名称(用 标记$package)。并将其添加到包列表中。
  2. 运行rpmdep.pl $package) 并将所有包添加到列表中。
  3. ldd $path对每一行 运行和 :
    1. 如果存在路径(如libsqlite3.so.0 => /usr/lib64/libsqlite3.so.0),则使用 回到步骤 1 /usr/lib64/libsqlite3.so.0
    2. 如果没有路径(如linux-vdso.so.1),则尝试找到它(使用locate命令),如果找到,则使用您获得的路径返回到步骤 1。

这样我就可以收集路径所需的所有操作系统包。它工作得很好,但我正在寻找一种更好/干净的方法来解决这个任务。另外,您认为我建议的算法怎么样?

如果这很重要的话,我正在使用 OpenSUSE。

答案1

$ cat installer.sh
#! /bin/bash

mkdir -p /tmp/testdir
test -e "$1" || exit 1
zypper --installroot /tmp/testdir install $(rpm -qf "$1")

依赖树

相关内容