¿Hay alguna forma de interactuar con el Shell pero mantener abierta la misma sesión?

¿Hay alguna forma de interactuar con el Shell pero mantener abierta la misma sesión?

Estoy preparando material del curso (PDF) para un tutorial que involucra la línea de comandos de Unix. Debido a que me esfuerzo por la automatización (algunos llaman a eso pereza), he escrito un pequeño paquete que me permite, usando \write18(with --shell-escape) y el verbatimpaquete,

  1. ejecutar comandos (por ejemplo ls) en el comandodurantecompilación de mi .texdocumento y componerlos en mi documento,
  2. redirigir el resultado stdouty stderra archivos externos,
  3. Ingrese esos archivos externos para componer el stdouty stderren mi .texdocumento.

Sin embargo, tengo entendido que cada invocación \write18abre y cierra su propia sesión de shell. Esto es desafortunado, ya que requiere algunas contorsiones y duplicación de código. En particular,

  • todas las variables de shell definidas durante una sesión no están disponibles en la siguiente;
  • Tengo que cdir al mismo directorio al principio de cada uno \write18para volver al mismo directorio en el que estaba al final del anterior \write18.

Vea mi ejemplo de juguete a continuación.

¿Hay alguna manera de poder interactuar con el Shell durante una pdflatexejecución, pero de alguna manera mantener abierta una sesión de Shell de una \write18llamada a la siguiente? ¿O existe un enfoque mejor que se adapte a mis necesidades?

\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}

Respuesta1

ingrese la descripción de la imagen aquí

\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) configurar un "servidor" para aceptar los comandos, solo uso una canalización con nombre:

$ cd /tmp


$ mkfifo zzpipe

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

luego ejecute el archivo tex anterior (en /tmpu organizar result.txtse escribe en otro lugar) el resultado debería ser como se muestra.

Esto es en Windows con cygwin bash, otras líneas de comando serán similares pero pueden necesitar convenciones de comillas diferentes. y como puede ver, la cdconfiguración y la configuración FOOsobreviven de una escritura a la otra.

Respuesta2

Agregué soporte básico de bash para pythontex... terminé tomando menos de 20 líneas de código. Para utilizar esto, necesitará la última versión deGitHub. Deberá utilizar la pythontexcompilación estándar de 3 pasos siempre que tenga un nuevo código bash que deba ejecutarse (ejecute LaTeX, ejecute el script PythonTeX, ejecute LateX). Cuando no tenga código nuevo que deba ejecutarse, puede ejecutar LaTeX por sí solo. Como esto no usa \write18, no necesita Shell-escape (la ejecución del código se maneja mediante el script PythonTeX).

Todo parece estar funcionando, pero tendrás que avisarme si encuentras algún error. Los números de línea de error deben sincronizarse correctamente con los del código que se ejecuta.

A continuación se muestra un documento de muestra, cuyo resultado se muestra a continuación. \stdoutpythontexes palabra por palabra de forma predeterminada, por lo que no es necesario especificar el formato como lo hace con \printpythontex(o su equivalente \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}

ingrese la descripción de la imagen aquí

información relacionada