PublicShow sourcepengines_io.pl -- Provide Prolog I/O for HTML clients

This module redefines some of the standard Prolog I/O predicates to behave transparently for HTML clients. It provides two ways to redefine the standard predicates: using goal_expansion/2 and by redefining the system predicates using redefine_system_predicate/1. The latter is the preferred route because it gives a more predictable trace to the user and works regardless of the use of other expansion and meta-calling.

Redefining works by redefining the system predicates in the context of the pengine's module. This is configured using the following code snippet.

:- pengine_application(myapp).
:- use_module(myapp:library(pengines_io)).
pengines:prepare_module(Module, myapp, _Options) :-
      pengines_io:pengine_bind_io_to_html(Module).

Using goal_expansion/2 works by rewriting the corresponding goals using goal_expansion/2 and use the new definition to re-route I/O via pengine_input/2 and pengine_output/1. A pengine application is prepared for using this module with the following code:

:- pengine_application(myapp).
:- use_module(myapp:library(pengines_io)).
myapp:goal_expansion(In,Out) :-
      pengine_io_goal_expansion(In, Out).
Source pengine_writeln(+Term)
Emit Term as <span class=writeln>Term<br></span>.
Source pengine_nl
Emit a <br/> to the pengine.
Source pengine_tab(+N)
Emit N spaces
Source pengine_flush_output
No-op. Pengines do not use output buffering (maybe they should though).
Source pengine_write_term(+Term, +Options)
Writes term as <span class=Class>Term</span>. In addition to the options of write_term/2, these options are processed:
class(+Class)
Specifies the class of the element. Default is write.
Source pengine_write(+Term) is det
Source pengine_writeq(+Term) is det
Source pengine_display(+Term) is det
Source pengine_print(+Term) is det
Source pengine_write_canonical(+Term) is det
Redirect the corresponding Prolog output predicates.
Source pengine_format(+Format) is det
Source pengine_format(+Format, +Args) is det
As format/1,2. Emits a series of strings with <br/> for each newline encountered in the string.
To be done
- : handle ~w, ~q, etc using term//2. How can we do that??
Source pengine_listing is det
Source pengine_listing(+Spec) is det
List the content of the current pengine or a specified predicate in the pengine.
Source user:message_hook(+Term, +Kind, +Lines) is semidet[multifile]
Send output from print_message/2 to the pengine. Messages are embedded in a <pre class=msg-Kind></pre> environment.
Source message_lines_to_html(+MessageLines, +Classes, -HTMLString) is det
Helper that translates the Lines argument from user:message_hook/3 into an HTML string. The HTML is a <pre> object with the class 'prolog-message' and the given Classes.
Source send_html(+HTML) is det
Convert html//1 term into a string and send it to the client using pengine_output/1.
Source binding_term(+Term, +Vars, +WriteOptions)// is semidet[multifile]
Hook to render a Prolog result term as HTML. This hook is called for each non-variable binding, passing the binding value as Term, the names of the variables as Vars and a list of options for write_term/3. If the hook fails, term//2 is called.
Arguments:
Vars- is a list of variable names or [] if Term is a residual goal.
Source prolog_help:show_html_hook(+HTML)[multifile]
Hook into help/1 to render the help output in the SWISH console.
Source pengine_io_predicate(?Head)
True when Head describes the head of a (system) IO predicate that is redefined by the HTML binding.
Source pengine_bind_io_to_html(+Module)
Redefine the built-in predicates for IO to send HTML messages using pengine_output/1.

Undocumented predicates

The following predicates are exported, but not or incorrectly documented.

Source pengine_io_goal_expansion(Arg1, Arg2)
Source pengine_read(Arg1)
Source pengine_read_line_to_codes(Arg1, Arg2)
Source pengine_read_line_to_string(Arg1, Arg2)
Source pengine_print(Arg1)
Source pengine_write_canonical(Arg1)
Source pengine_listing(Arg1)
Source pengine_portray_clause(Arg1)
Source pengine_writeq(Arg1)
Source pengine_format(Arg1, Arg2)
Source pengine_display(Arg1)