Evidently, if the goal fails, and you ouput to a variable, you will have nothing:
?- with_output_to(string(T),(format("Hello",),format(",World",))). T = "Hello,World".
?- with_output_to(string(T),(format("Hello",),format(",World",),false)). false.
Suppose I go to a fishing expedition down some call, and want to capture logging anyway... 🤔 To the caller, it will have to look like I/O, to be pulled in at the end, a remainder of the pocket universe in which Goal was run.
The general approach:
call_and_log(Goal) :- set_up_output_stream(Stream), shield_from_failure_or_exception(Goal,S,ReturnValue), % Goal may fail or throw pull_in_logging_data(String,Stream).
The "Stream" can be anything the enclosing OS provides and is accessible to open/4 (generally process-independent on-disk-files, but may be process-attached memory-based-files or files or something else).
But what if one wants to accumulate output in some in-Prolog term?