Using the wasm version

I’m using: SWI-Prolog version 9.0.4

I have a few questions, I’m somewhat of a newbie with prolog in general. Trying to use swipl-wasm in node.

  1. How to clear the slate for a session? I tried creating multiple (hundreds) instances of Swipl and it quickly run out of memory - the linked discussion below asks how to properly “destroy” the instances to not run out of memory.

Continuing the discussion from Question: How to properly destroy `SWIPL` · Issue #23 · SWI-Prolog/npm-swipl-wasm · GitHub

For my use case, I have many little programs saved as strings that I want to evaluate - I tried doing it in one session and just re-consulting. It mostly worked very well.

However I stumbled on a couple of cases where the session would remember errors from a previous code (for example, I accidentally redefined an existing predicate member with my own, the problem it created persisted after reconsulting).

  1. I tried calling my own JS function from prolog, in nodejs I had to define a window object under global (makes sense) to get it to work.

it all worked until I tried turning my function into async. Before using await/2 it correctly stringified into <js_Promise> or something like that. I tried using await/2 but all was getting after using it was “bus error”.

Thanks!

That suggests you are not reconsulting the right way. Just tried writing a file with a broken member/2, removed and used member/2. works fine… Note there is Prolog.load_string(String, Id). You kust use the same Id to turn this into a reconsult.

But, as said in the github issue, in_temporary_module/3 provides an interface that cleans better.

I don’t know whether or not this can work as is. Note that the initial Prolog goal must be called with forEach() to be async enabled. Try work from the promise examples, see whether these work and then slowky go where you want to be. Note that Prolog can only be involved in a single asynchronous task as is. We need engines (proof of concept available) and some further work on the WASM binding to allow for multiple tasks.

Note there is Prolog.load_string(String, Id). You must use the same Id to turn this into a reconsult.

Thank you! I was doing something else entirely:

	swipl.FS.writeFile('file.pl', contents);
	swipl.prolog.call(`consult('file.pl').`);

I didn’t see load_string in the typescript autocompletion and I completely missed that page on the docs site. It does work, I’ll try to find that member problem again to see that it’s fixed now.

I do have a question though. I see that I don’t need to call consult manually anymore - should modules be also pushed via load_string? like if I have module_a using module_b, do I need to load_string both? or should I load_string one and fs.writeFile the other? Does reconsulting something else as module_a gets rid of the module_b predicates?

I also totally missed that forEach is the one that supports async, ugh… I thought I re-read every single thing multiple times.


I just found that this causes safe_goal to time out in swish (my local node process freezes entirely, is there a way to abort like in swish?), is this bug something special that it can’t detect?

one(no).
two(yes).

get :-
    one(No),
    two(Yes),
    (No = no, Yes = no -> 
    		format(string(C1), 'both no'),
            writeln(C1)
            ;
            format(string(C2), 'not both no'),
            writeln(C2)
        ).

As is, Proloh.load_string() is initiated from JavaScript, so while you can use this to create a module, you cannot use it to “use another module from a string”. I don’t really see how that would work. Note that use_module takes a file as argument, not a module name. We could add something that allows use_module/1,2 to target a module rather than a file.

Is this a swish or wasm question? As is, these are unrelated?

See the tests on SWI-Prolog WASM demos