查找在会话期间正在读取哪些文件(python 代码)

Finding which files are being read from during a session (python code)

我有一个用 python 编写的大型系统。当我 运行 它时,它会从我的文件系统上的许多不同文件中读取各种数据。几千行代码,几百个文件,大部分都没有实际使用。我想查看系统实际访问了哪些文件 (ubuntu),并希望查看它们在代码中的什么位置被打开。文件名是使用变量等动态决定的,因此仅通过查看代码无法确定实际的文件名。 我当然可以访问代码,并且可以更改它。

我试图找出如何有效地做到这一点,同时对代码进行最少的更改:

  1. 是否有 Linux 方法来确定访问了哪些文件以及访问时间?这可能很有用,尽管它不会告诉我代码中发生的位置
  2. 有没有一种简单的方法可以让“打开文件”命令同时记录打开文件的文件名、时间等...?希望不必进入代码并更改每个打开的命令,它们有很多,有些在 运行 时间没有被使用。

谢谢

对于 1 - 您可以使用

ls -la /proc/<PID>/fd`

正在用您的进程 ID 替换 <PID>。 请注意,它会为您提供所有打开的文件描述符,其中一些是 stdin stdout stderr,通常还有其他东西,例如打开的 websockets(使用文件描述符),但是过滤文件应该很容易。

对于 2- 请参阅此处提出的出色解决方案 -

例如用你自己的函数覆盖 open 函数,这可能包括额外的日志记录。

一种可能的方法是“重载”open 函数。这将产生许多取决于代码的效果,所以如果需要我会非常小心地这样做,但基本上这里有一个例子:

>>> _open = open
>>> def open(filename):
...     print(filename)
...     return _open(filename)
...
>>> open('somefile.txt')
somefile.txt
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File "<stdin>", line 3, in open
FileNotFoundError: [Errno 2] No such file or directory: 'somefile.txt'

如您所见,我的新 open 函数将 return 原始 open(重命名为 _open),但会首先打印出参数(文件名) .如果需要,可以通过更复杂的方式来记录文件名,但最重要的是,这需要 运行 在代码中使用 open 之前

您可以使用 strace 跟踪文件访问,而无需修改您的代码。 要么你用strace启动你的程序,像这样

strace -f -e trace=file your_program.py

否则你将 strace 附加到像这样的 运行 程序

strace -f -e trace=file -p <PID>