有没有什么方法可以与 shell 交互但保持相同的会话打开?

有没有什么方法可以与 shell 交互但保持相同的会话打开?

我正在为涉及 Unix 命令行的教程准备一些课程材料(PDF)。因为我追求自动化(有些人称之为懒惰),所以我编写了一个小包,允许我使用\write18(with --shell-escape)和verbatim包来

  1. 运行命令(例如ls在命令处期间编辑我的.tex文档并将它们排版在我的文档中,
  2. 将结果重定向stdoutstderr外部文件,
  3. 在我的文档中输入那些外部文件进行排版stdoutstderr.tex

但是,我的理解是每次调用都会\write18打开和关闭自己的 shell 会话。这很不幸,因为它需要一些扭曲和代码重复。特别是,

  • 在一个会话期间定义的所有 shell 变量在下一个会话中均不可用;
  • 我必须cd在每个文件的开头都进入相同的目录\write18,才能回到前一个文件末尾的相同目录\write18

请参阅下面我的玩具示例。

有什么方法可以在pdflatex运行期间与 shell 交互,但又能以某种方式保持 shell 会话在一次\write18调用和下一次调用之间保持打开状态?或者有没有更好的方法可以满足我的需求?

\documentclass{article}

\usepackage{lipsum}

\begin{document}

First, initialise the repository.

% pretend that the following is an environment that both
% - runs commands at the CL
% - typesets them in the .tex document
\immediate\write18{%
  cd $HOME/Desktop;
  mkdir myrepo;
  cd myrepo;
  git init;
}

Let's see what git has to say...

\immediate\write18{%
  # I'm back in $HOME :(
  # I have to cd to $HOME/Desktop/myrepo, here, but I'd like to avoid it...
  cd $HOME/Desktop/myrepo;
  git status
  # ...
}

\end{document}

答案1

在此处输入图片描述

\documentclass{article}

\begin{document}

\immediate\write18{echo pwd > /tmp/zzpipe}

\texttt{\input{result.txt}}

\immediate\write18{echo cd > /tmp/zzpipe}

\immediate\write18{echo pwd > /tmp/zzpipe}

\texttt{\input{result.txt}}

\immediate\write18{echo 'FOO=wibble' > /tmp/zzpipe}

\immediate\write18{echo 'echo FOO is $FOO' > /tmp/zzpipe}

\texttt{\input{result.txt}}

\end{document}

a)设置一个“服务器”来接受命令,我只使用一个命名管道:

$ cd /tmp


$ mkfifo zzpipe

$ while true ; do eval `cat /tmp/zzpipe` >/tmp/result.txt  ; done

然后运行上述 tex 文件(在/tmp或排列result.txt在其他地方写入)输出应如下所示。

这是在带有 cygwin bash 的 Windows 上,其他命令行将类似,但可能需要不同的引用约定。并且正如您所看到的,cd和的设置FOO在从一次写入到另一次写入时仍然存在。

答案2

我已经为...添加了基本的 bash 支持pythontex,最终只用了不到 20 行代码。要使用此功能,您需要最新版本GitHubpythontex。每当您需要执行新的 bash 代码时,您都需要使用标准的3 步编译(运行 LaTeX、运行 PythonTeX 脚本、运行 LateX)。当您没有需要执行的新代码时,您可以直接运行 LaTeX。由于这不使用\write18,因此您不需要 shell-escape(代码执行由 PythonTeX 脚本处理)。

一切似乎都正常,但如果你发现任何错误,请告诉我。错误行号应与执行的代码行号正确同步。

这是一个示例文档,其输出如下所示。 \stdoutpythontex默认情况下是逐字逐句的,因此不必像\printpythontex(或等效的\stdoutpythontex)那样指定格式。

\documentclass{article}

\usepackage[makestderr, usefamily=bash]{pythontex}
\setpythontexfv{numbers=left, firstnumber=last}

\begin{document}

A block of bash...
\begin{bashblock}
myvar="myvar's value"
echo $myvar
\end{bashblock}
...with output:
\printpythontex[verbatim]

Another block, accessing the previous variable...
\begin{bashblock}
echo "In another LaTeX environment later on..."
echo $myvar
\end{bashblock}
...with output:
\printpythontex[verbatim]

A block with an error.
\begin{bashblock}
echo "In another LaTeX environment later on..."
echo $myvar
lsERROR
\end{bashblock}
Stdout:
\printpythontex[verbatim]
Stderr:
\stderrpythontex

\end{document}

在此处输入图片描述

相关内容