将交互式会话导入文件

14
我做了一个互动式的玩具控制台程序,基本上是一个解释器:
$ myprogram
> this is user input
this is program output

我想将完整的会话,包括用户输入和程序输出,导入到日志文件中。可以像这样操作:

$ cat | tee >(myprogram | tee -a file.log) >> file.log
> this is user input
this is program output
$ cat file.log
> this is user input
this is program output

所以上述会话将像往常一样显示在终端上,但也会被复制到日志文件中。

有更好的方法吗?我不喜欢必须两次写入日志文件,也不喜欢必须记得在运行此命令之前擦除它。


Tee命令用于将输出重定向到文件。基本上,如果您编写$output | tee file.log,它会将输出复制到file.log文件中。 - Hussain Shabbir
4个回答

14

脚本 - 将终端会话制作成typescript:

script -c "myprogram" file.log

整个会话将被记录到file.log文件中。


1
这个可以工作,但它捕获了所有字符(包括转义序列),这可能会使日志文件难以阅读。 - tehwallz
然后,您可以在 ansifilter(https://gitlab.com/saalen/ansifilter)或 highlight(https://gitlab.com/saalen/highlight)中使用 file.log 进行重新处理。 - MacMartin
默认情况下,它还会出现一些奇怪的口吃,即使关闭回显也是如此。例如,在IRB中输入print "HI"会出现以下情况:irb(main):001:0> irb(main):001:0> pirb(main):001:0> prirb(main):001:0> priirb(main):001:0> prinirb(main):001:0> printirb(main):001:0> print irb(main):001:0> ... - undefined

7

由于两个进程无法读取相同的输入,因此需要两个Tee。一个Tee用于读取终端输入并将其写入程序标准输入和file.log文件,另一个Tee用于读取程序标准输出并将其写入终端输出和file.log文件。

tee -a file.log | program | tee -a file.log

2
谢谢。我把答案给了konsolebox,因为他比你快了大约3分钟,但是解释帮助我更好地理解了两次使用tee的原因。 - Dave

6
更简单的形式可以是:
tee >(myprogram) | tee -a file.log

如果您想防止输入再次显示在屏幕上:

tee -a file.log | myprogram | tee -a file.log

1
谢谢,我没有意识到tee默认从stdin读取,这使得调用cat变得多余。我需要写两次file.log有点可惜,但也不是世界末日。 - Dave

2

一个简单的方法是使用 script 命令。它可以记录整个终端会话。使用以下命令运行:

script my-interactive-session.log program

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接