¿Por qué \msg_fatal: muestra un error aparentemente no relacionado?

¿Por qué \msg_fatal: muestra un error aparentemente no relacionado?
\documentclass{article}
\usepackage{expl3}
\usepackage{everypage}

\ExplSyntaxOn
\AddEverypageHook { \sean_test: }

\msg_new:nnnn { test } { message }
  { this ~ is ~ a ~ rubbish ~ message }
  { it's ~ a ~ minimal ~ example }

\cs_new_protected:Npn \sean_test:
  {
    \typeout{++before++}
    \msg_fatal:nn { test } { message }
    \typeout{++after++}
  }

\ExplSyntaxOff

\usepackage{mwe}
\begin{document}
\lipsum[1-1000]
\end{document}

Estoy bastante sorprendido de haber podido hacer un ejemplo mínimo de esto, pero lo anterior producirá (muchas copias de)

++after++
[26]
++before++

!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
!
! Fatal test error: "message"
! 
! this is a rubbish message
! 
! See the test documentation for further information.
! 
! For immediate help type H <return>.
!...............................................  

l.23 \lipsum[1-1000]

! You can't use `\end' in internal vertical mode.
\__msg_fatal_code:nnnnnn ...l_text_tl }\tex_end:D 

l.23 \lipsum[1-1000]

++after++
[27]
++before++

¿Qué pasa con este negocio?

! You can't use `\end' in internal vertical mode.
\__msg_fatal_code:nnnnnn ...l_text_tl }\tex_end:D 

Intenté introducir ambos \leavevmode\tex_end:Dy \clearpage\tex_end:Dsin resultado.

Respuesta1

No puedes morir allí.

El gancho que está utilizando presumiblemente se ejecuta dentro de la rutina de salida, que siempre es el modo vertical interno (ya que, por definición, no está en la lista vertical principal), por lo que no puede detenerse allí, primero debe salir de la rutina de salida.


Es posible hacer algo para intentar morir fuera de la caja interior.Muere otro día(citado Paulo) pero no se garantiza que el token del grupo posterior aterrice en algún lugar seguro (si es que alguna vez es seguro ejecutar un error fatal)

\documentclass{article}
\usepackage{expl3}
\usepackage{everypage}

\ExplSyntaxOn

\AddEverypageHook { \sean_do_test: }
\cs_new:Nn \sean_do_test:
 {
  \bool_if:nTF { \mode_if_inner_p: || \mode_if_horizontal_p: }
   {
    \group_insert_after:N \sean_do_test:
   }
   {
    \sean_test:
   }
 }


\msg_new:nnnn { test } { message }
  { this ~ is ~ a ~ rubbish ~ message }
  { it's ~ a ~ minimal ~ example }

\cs_new_protected:Npn \sean_test:
  {
    \typeout{++before++}
    \msg_fatal:nn { test } { message }
    \typeout{++after++}
  }

\ExplSyntaxOff

\usepackage{mwe}
\begin{document}
\lipsum[1-1000]
\end{document}

Respuesta2

La fatalclase de errores en realidad está destinada a problemas importantes, casi con certeza en el momento de la carga. En su ejemplo, terminó con él dentro de una caja: TeX no nos permite "saltar" allí, de ahí el error. Quizás podríamos agregar un guardia para verificar el modo actual y solo intentarlo \endsi está permitido, pero esencialmente este no es el lugar "correcto" para dar un error fatal.

información relacionada