Test Method

Our test method is a mix of test utilities that are bundled with the Jekejeke Prolog develop-ment environment plus some test helper predicates already available in the Jekejeke Prolog runtime library. The test utilities used are as follows. For further information on these modules the interested reads should consult the corresponding API documentation of the Jekejeke Prolog development environment:

We will present our test method. It is based on creating a number of test cases for each predicate in each theory. A test runner will then execute the test cases and summarize the results. The coverage depends on how well the test cases of the predicate match its logic and whether all predicates of a theory have test cases. The test cases are stored as rules in the following form:

	:- multifile(test_ref/4).
:- discontiguous(test_ref/4).
test_ref(Fun, Arity, Theory, Ref).

:- multifile(test_case/4).
:- discontiguous(test_case/4).
test_case(Fun, Arity, Theory, Number) :- Body.
The chosen test method will increase the number of test cases compared to the number of examples given in the test case sources. The reason is that the examples often phrase multiple validations points. And we suggest using a separate test_case/4 clause for each validation point. Let’s make an example. Take one of the ISO examples for clause/2. We find the following description in the ISO source:
:- dynamic(insect/1).
:- asseertz(insect(ant)).
:- asseertz(insect(bee)).

clause(insect(I), T).
Succeeds, unifying I with ant, and T with true.
On re-execution,
succeeds, unifying I with bee, and T with true.

A succeed or fail on the first call translates very directly into a test case. We simply need to place the tested predicate invocation as a step plus the required result comparison as a validation point into one test_case/4 clause. For success or failure after the first call we apply the findall/3 built-in. This will allow us to advance the found solutions in the tested predicate invocation. It can then be again followed by the required result comparison as a validation point. In our current example this will give our second test_case/4 clause:

test_case(clause,2, consult, 1) :- clause(insect(I), T), !, 
      I==ant, T==true.
test_case(clause,2, consult, 2) :- findall(I-T,
clause(insect(I), T), [_,I-T|_]), I==bee, T==true.

The use of the findall/3 built-in in separate test cases means that the tested predicate is invoked again. So our approach is not the most efficient. On the other hand the approach has the advantage that it can disclose individual failures of validation points separately.