EricGT
December 11, 2025, 3:54pm
1
$ swipl --version
SWI-Prolog version 10.0.0 for x64-win64
Using library(prolog_coverage) on a module that uses library(persistency) .
For code coverage for persistent/1 was able to increase the code coverage by adding tests for the dynamicly created four predicates resulting in this
90 ### ⮰
++20 ⮰
++4,727 ⮰
++21,486 ⮰
+55,950-20 :- persistent(pred_def(name:atom, arity:integer, module:atom, file:atom, line:integer)).
There is now just the one remaining ### that I have no idea of what it could be.
Any ideas? Is it a predicate, an artifact of code coverage that can be removed, other?
Any ideas on how to get a line in the cov report to show what it could be?
Gave Claude the links to the SWI-Prolog library code on GitHub and noted the relevant files in the project and Claude thinks
90 ### ⮰ ← The directive itself: never "executed"
++20 ⮰ ← Generated predicate variant 1
++4,727 ⮰ ← Generated predicate variant 2
++21,486 ⮰ ← Generated predicate variant 3
+55,950-20 ← Generated predicate variant 4
:- persistent(pred_def(name:atom, arity:integer, module:atom, file:atom, line:i
If that is true would like to find a way to remove such lines from the cov report so that the report shows 100% coverage for the module. Currently Claude will search for ### lines and thus it is like having a wrench thrown into the clock works.
jan
December 12, 2025, 12:41pm
3
I don’t think that is true. The directive is term-expanded to a set of predicates. I suspect one of them is not used by your tests. Which one is a bit hard to tell. Ideally the system should provide better feedback for this, but I’m not sure how.
I’d create a module with only this declaration and list the content so you can understand what is going on.
1 Like
EricGT
December 13, 2025, 8:18pm
4
Result confirms that is true.
There are five, not four generated predicates from persistent/1.
From documentation
The persistent/1 expands each declaration into four predicates:
name(Arg, ...)
assert_name(Arg, ...)
retract_name(Arg, ...)
retractall_name(Arg, ...)
using
:- persistent(pred_def(name:atom, arity:integer, module:atom, file:atom, line:integer)).
the following are generated
Generated predicate
type
pred_def/5
base
assert_pred_def/5
assert_
asserta_pred_def/5
asserta_
retract_pred_def/5
retract_
retractall_pred_def/5
retractall_
90 ++21,486 ⮰
++20 ⮰
++4,987 ⮰
+55,950-20 ⮰
++20 :- persistent(pred_def(name:atom, arity:integer, module:atom, file:atom, line:integer)).
Jan updated the SWI-Prolog documentation for library(persistency)
committed 10:04AM - 15 Dec 25 UTC
EricGT
December 13, 2025, 8:42pm
5
Filename: test_persistency.pl
% Minimal Fixture: Single persistent/1 directive with arity 1
% Purpose: Isolate coverage behavior for one persistent declaration
%
% This module tests the simplest case:
% - One persistent/1 directive
% - Arity 1 (single argument)
% - Generates 5 predicates: foo/1, assert_foo/1, asserta_foo/1, retract_foo/1, retractall_foo/1
:- module(test_persistency, []).
:- use_module(library(persistency)).
% Single persistent declaration - should generate exactly 5 predicates
:- persistent(foo(value:any)).
$ swipl
Welcome to SWI-Prolog (threaded, 64 bits, version 10.0.0)
4 ?- [test_persitency].
true.
5 ?- findall(Name/Arity, (current_predicate(test_persistency:Name/Arity), sub_atom(Name, _, _, _, foo)), Preds),sort(Preds,
SortedPreds),forall(member(Name/Arity, SortedPreds), format('~w/~w~n', [Name, Arity])).
assert_foo/1
asserta_foo/1
foo/1
retract_foo/1
retractall_foo/1
Preds = [retract_foo/1, retractall_foo/1, foo/1, asserta_foo/1, assert_foo/1],
SortedPreds = [assert_foo/1, asserta_foo/1, foo/1, retract_foo/1, retractall_foo/1].