使用 pathlib 获取符号 link 的目标
Getting the target of a symbolic link with pathlib
有没有办法使用 pathlib
获得符号 link 的目标?我知道这可以使用 os.readlink()
.
来完成
我想创建一个由 link 及其目标文件组成的字典。
links = [link for link in root.rglob('*') if link.is_symlink()]
files = [Path(os.readlink(str(pointed_file))) for pointed_file in links]
编辑 ...我想过滤所有不绝对的路径
link_table = {link : pointed_file for link, pointed_file in zip(links, files) if pointed_file.is_absolute()}
更新:Python 3.9 引入了 Path.readlink()
方法,因此以下说明仅适用于早期版本。
不,目前无法从 pathlib
获得 os.readlink()
给出的结果。 Path.resolve()
不适用于损坏的 links 并且会引发 FileNotFoundError
(Python <3.5) 或 returns 潜在的奇怪路径 (Python 3.6 ).人们仍然可以使用 Path.resolve(True)
获得旧行为,尽管这意味着版本之间不兼容(顺便说一下,在包文档和 Py3.6 发布文档的移植部分中没有提到)。
关于绝对路径的更新问题,os.readlink()
是检查符号 link 是绝对路径还是相对路径的唯一方法。 Path.relative_to()
顾名思义,将现有路径转换为相对路径,而不检查符号 link 目标路径是否以“/”开头。这同样适用于 Path.is_absolute()
。最后 Path.resolve()
对于现有目标,转换目标路径以便在途中销毁所需信息。
上面的 奇怪的路径 我的意思是,假设 /home/test
中有符号 link .myapp
指向 .config/myapp/config
.如果 .config/myapp
不存在并且代码是用 Py<=3.5 编写的,Path.resolve()
将引发异常并且应用程序可以通知用户丢失的文件。现在,如果在不更改代码的情况下从 Py3.6 调用,它解析为 ~/.config/myapp
,不会抛出异常,因此检查 .resolve()
是否通过,但稍后当应用程序尝试时可能会抛出另一个异常打开文件进行阅读,因此用户可能会收到 ~/config/myapp
文件未找到的消息,尽管这并不是真正缺少的文件。情况可能更糟——当应用程序执行 Path('/home/test/.myapp').resolve().open('w')
(不一定在一个步骤中,但可以说是某些清理过程的一部分)时,就会创建错误的文件。当然,下次调用该应用程序时,路径会更深一层解析为 /home/test/.config/myapp/config
(因为 Path.resolve()
不会检查 myapp
是否是一个目录),并且读写将失败并出现 NotADirectoryError
异常(带有一些误导性的 "Not a directory: /home/test/.config/myapp/config"
作为描述……)。
有没有办法使用 pathlib
获得符号 link 的目标?我知道这可以使用 os.readlink()
.
我想创建一个由 link 及其目标文件组成的字典。
links = [link for link in root.rglob('*') if link.is_symlink()]
files = [Path(os.readlink(str(pointed_file))) for pointed_file in links]
编辑 ...我想过滤所有不绝对的路径
link_table = {link : pointed_file for link, pointed_file in zip(links, files) if pointed_file.is_absolute()}
更新:Python 3.9 引入了 Path.readlink()
方法,因此以下说明仅适用于早期版本。
不,目前无法从 pathlib
获得 os.readlink()
给出的结果。 Path.resolve()
不适用于损坏的 links 并且会引发 FileNotFoundError
(Python <3.5) 或 returns 潜在的奇怪路径 (Python 3.6 ).人们仍然可以使用 Path.resolve(True)
获得旧行为,尽管这意味着版本之间不兼容(顺便说一下,在包文档和 Py3.6 发布文档的移植部分中没有提到)。
关于绝对路径的更新问题,os.readlink()
是检查符号 link 是绝对路径还是相对路径的唯一方法。 Path.relative_to()
顾名思义,将现有路径转换为相对路径,而不检查符号 link 目标路径是否以“/”开头。这同样适用于 Path.is_absolute()
。最后 Path.resolve()
对于现有目标,转换目标路径以便在途中销毁所需信息。
上面的 奇怪的路径 我的意思是,假设 /home/test
中有符号 link .myapp
指向 .config/myapp/config
.如果 .config/myapp
不存在并且代码是用 Py<=3.5 编写的,Path.resolve()
将引发异常并且应用程序可以通知用户丢失的文件。现在,如果在不更改代码的情况下从 Py3.6 调用,它解析为 ~/.config/myapp
,不会抛出异常,因此检查 .resolve()
是否通过,但稍后当应用程序尝试时可能会抛出另一个异常打开文件进行阅读,因此用户可能会收到 ~/config/myapp
文件未找到的消息,尽管这并不是真正缺少的文件。情况可能更糟——当应用程序执行 Path('/home/test/.myapp').resolve().open('w')
(不一定在一个步骤中,但可以说是某些清理过程的一部分)时,就会创建错误的文件。当然,下次调用该应用程序时,路径会更深一层解析为 /home/test/.config/myapp/config
(因为 Path.resolve()
不会检查 myapp
是否是一个目录),并且读写将失败并出现 NotADirectoryError
异常(带有一些误导性的 "Not a directory: /home/test/.config/myapp/config"
作为描述……)。