Activity-Lang: allow to verify invocation param in test
requires to supplement EventLog matching primitives to pick and verify a specific positional argument. Moreover, it is more or less arbitrary which job invocation parameters are unpacked and exposed for verification; we'll have to see what is actually required for writing tests...
This commit is contained in:
parent
161f604cbd
commit
1c6ee62c1a
6 changed files with 90 additions and 20 deletions
|
|
@ -150,6 +150,17 @@ namespace test{
|
|||
}; // otherwise the sizes do not match...
|
||||
}
|
||||
|
||||
/** refinement filter to match a specific positional argument */
|
||||
inline auto
|
||||
matchArgument (size_t idx, string match)
|
||||
{
|
||||
return [=](Entry const& entry)
|
||||
{
|
||||
return idx < entry.childSize()
|
||||
and contains (entry.child(idx), match);
|
||||
};
|
||||
}
|
||||
|
||||
|
||||
/** refinement filter, to cover all arguments by regular expression(s)
|
||||
* @param regExpSeq several regular expressions, which, when applied
|
||||
|
|
@ -494,7 +505,17 @@ namespace test{
|
|||
|
||||
|
||||
/**
|
||||
* @internal refine filter condition additionally to match the call arguments.
|
||||
* @internal refine filter condition additionally to match a specific positional call argument.
|
||||
*/
|
||||
void
|
||||
EventMatch::refineSerach_matchArgument (size_t idx, string match)
|
||||
{
|
||||
refineSerach (solution_, matchArgument(idx, match));
|
||||
evaluateQuery ("match-argument(["+util::toString(idx)+"]="+match+")");
|
||||
}
|
||||
|
||||
/**
|
||||
* @internal refine filter condition additionally to match a sequence of call arguments.
|
||||
*/
|
||||
void
|
||||
EventMatch::refineSerach_matchArguments (ArgSeq&& argSeq)
|
||||
|
|
|
|||
|
|
@ -230,6 +230,14 @@ namespace test{
|
|||
return *this;
|
||||
}
|
||||
|
||||
/** refine filter to additionally require match on a specific positional argument */
|
||||
template<typename ARG>
|
||||
EventMatch&
|
||||
argPos (size_t idx, ARG const& arg)
|
||||
{
|
||||
refineSerach_matchArgument (idx, util::toString(arg));
|
||||
return *this;
|
||||
}
|
||||
|
||||
|
||||
/* query builders to augment and refine the currently defined search condition*/
|
||||
|
|
@ -252,6 +260,7 @@ namespace test{
|
|||
bool foundSolution();
|
||||
void evaluateQuery (string matchSpec, Literal rel = "after");
|
||||
|
||||
void refineSerach_matchArgument (size_t idx, string match);
|
||||
void refineSerach_matchArguments (ArgSeq&& argSeq);
|
||||
void refineSerach_matchArgsRegExp (RExSeq&& regExpSeq, string rendered_regExps);
|
||||
};
|
||||
|
|
|
|||
|
|
@ -236,10 +236,19 @@ namespace test{
|
|||
CHECK (log.verifyCall("fun3").arg("facts", 3.2, 1));
|
||||
CHECK (log.verifyCall("fun3").arg(string("facts"), 3.2f, int64_t(1)));
|
||||
CHECK (log.verifyCall("fun3").arg("facts", "3.2", "1"));
|
||||
CHECK (log.verifyCall("fun3").argPos(0, "facts"));
|
||||
CHECK (log.verifyCall("fun3").argPos(0, "act"));
|
||||
CHECK (log.verifyCall("fun3").argPos(1, ".2"));
|
||||
CHECK (log.verifyCall("fun3").argPos(1, 3.2));
|
||||
CHECK (log.verifyCall("fun3").argPos(2, 1u));
|
||||
|
||||
CHECK (log.ensureNot("fun").arg(" facts ","3.2", "1"));
|
||||
CHECK (log.ensureNot("fun").arg(" facts ","3.2", "1")); // the match is on the exact textual representation...
|
||||
CHECK (log.ensureNot("fun").arg("facts", "3.20","1"));
|
||||
CHECK (log.ensureNot("fun").arg("facts", "3.2", "1L"));
|
||||
CHECK (log.ensureNot("fun").argPos(1, "anything")); // matches first invocation, which has no arguments
|
||||
CHECK (log.ensureNot("fun3").argPos(3, 5555)); // the "fun3" invocation has only 3 arguments
|
||||
CHECK (log.ensureNot("fun3").argPos(1, 3.3)); // the second argument is 2.3, not 3.3
|
||||
CHECK (log.ensureNot("fun3").argPos(2, 5)); // the last argument is 1, not 5
|
||||
|
||||
CHECK (log.verifyCall("fun1").arg());
|
||||
CHECK (log.verifyCall("fun2").arg());
|
||||
|
|
|
|||
|
|
@ -142,15 +142,19 @@ namespace test {
|
|||
|
||||
|
||||
|
||||
/** @test TODO diagnostic setup to detect a JobFunctor activation
|
||||
* @todo WIP 7/23 🔁 define 🔁 implement
|
||||
/** @test diagnostic setup to detect a JobFunctor activation
|
||||
* - the ActivityDetector provides specifically rigged JobFunctor instances
|
||||
* - these capture all invocations, based on generic invocation logging
|
||||
* - special match qualifier to verify the job's nominal invocation time parameter
|
||||
* - event verification can be combined with other verifications to cover
|
||||
* complex invocation sequences
|
||||
*/
|
||||
void
|
||||
verifyMockJobFunctor()
|
||||
{
|
||||
ActivityDetector detector;
|
||||
InvocationInstanceID invoKey;
|
||||
TimeVar nominal{FSecs{5,2}};
|
||||
Time nominal{FSecs{5,2}};
|
||||
invoKey.part.a = 55;
|
||||
|
||||
Job dummyJob{detector.buildMockJobFunctor ("mockJob")
|
||||
|
|
@ -160,7 +164,17 @@ namespace test {
|
|||
CHECK (detector.ensureNoInvocation ("mockJob"));
|
||||
dummyJob.triggerJob();
|
||||
CHECK (detector.verifyInvocation ("mockJob"));
|
||||
CHECK (detector.verifyInvocation ("mockJob").arg(nominal, invoKey.part.a));
|
||||
CHECK (detector.verifyInvocation ("mockJob").arg(TimeValue{nominal}, invoKey.part.a));
|
||||
CHECK (detector.verifyInvocation ("mockJob").nominalTime(nominal));
|
||||
|
||||
++detector; // note: sequence number incremented between invocations
|
||||
dummyJob.parameter.nominalTime += 5 * Time::SCALE; // different job parameter (later nominal time point)
|
||||
dummyJob.triggerJob();
|
||||
|
||||
CHECK (detector.verifyInvocation ("mockJob").nominalTime(nominal).seq(0)
|
||||
.beforeInvocation ("mockJob").nominalTime(nominal + Time{FSecs{5}}) // matching first invocation and then second...
|
||||
.afterSeqIncrement(1) // note: searching backwards from the 2nd invocation
|
||||
);
|
||||
}
|
||||
|
||||
|
||||
|
|
|
|||
|
|
@ -118,9 +118,12 @@ namespace test {
|
|||
// using vault::gear::JobClosure;
|
||||
|
||||
|
||||
namespace {// Event markers
|
||||
namespace {// Diagnostic markers
|
||||
const string MARK_INC{"IncSeq"};
|
||||
const string MARK_SEQ{"Seq"};
|
||||
|
||||
using SIG_JobDiagnostic = void(TimeValue, int32_t);
|
||||
const size_t JOB_ARG_POS_TIME = 0;
|
||||
}
|
||||
|
||||
class ActivityDetector;
|
||||
|
|
@ -200,6 +203,19 @@ namespace test {
|
|||
_Parent::beforeEvent(MARK_INC, util::toString(seqNr));
|
||||
return *this;
|
||||
}
|
||||
ActivityMatch&
|
||||
afterSeqIncrement (uint seqNr)
|
||||
{
|
||||
_Parent::afterEvent(MARK_INC, util::toString(seqNr));
|
||||
return *this;
|
||||
}
|
||||
|
||||
/** qualifier: additionally match the nominal time argument of JobFunctor invocation */
|
||||
ActivityMatch&
|
||||
nominalTime (TimeValue const& time)
|
||||
{
|
||||
return delegate (&EventMatch::argPos<TimeValue const&>, size_t(JOB_ARG_POS_TIME), time);
|
||||
}
|
||||
|
||||
|
||||
private:
|
||||
|
|
@ -293,11 +309,7 @@ namespace test {
|
|||
class MockJobFunctor
|
||||
: public NopJobFunctor
|
||||
{
|
||||
public:
|
||||
using SIG_Diagnostic = void(TimeValue, int32_t);
|
||||
|
||||
private:
|
||||
using MockOp = typename _DiagnosticFun<SIG_Diagnostic>::Type;
|
||||
using MockOp = typename _DiagnosticFun<SIG_JobDiagnostic>::Type;
|
||||
|
||||
MockOp mockOperation_;
|
||||
|
||||
|
|
@ -385,7 +397,7 @@ namespace test {
|
|||
buildMockJobFunctor (string id)
|
||||
{
|
||||
return mockOps_.emplace_back (
|
||||
buildDiagnosticFun<MockJobFunctor::SIG_Diagnostic> (id));
|
||||
buildDiagnosticFun<SIG_JobDiagnostic> (id));
|
||||
}
|
||||
|
||||
|
||||
|
|
|
|||
|
|
@ -81792,7 +81792,7 @@ Date:   Thu Apr 20 18:53:17 2023 +0200<br/>
|
|||
<node CREATED="1691876688987" ID="ID_1053525826" MODIFIED="1691876722777" TEXT="für einen dedizierten Verifikator müßte eine Struktur analog zum EventLog aufgebaut werden"/>
|
||||
<node CREATED="1691876724045" ID="ID_599766465" MODIFIED="1691876757873" TEXT="insofern ist es eine „Abkürzung“, das EventLog hierfür einzusetzen"/>
|
||||
</node>
|
||||
<node BACKGROUND_COLOR="#eee5c3" COLOR="#990000" CREATED="1691876355275" ID="ID_165347645" MODIFIED="1691876406949" TEXT="brauche komplexere verknüpfte Matches">
|
||||
<node BACKGROUND_COLOR="#eef0c5" COLOR="#990000" CREATED="1691876355275" ID="ID_165347645" MODIFIED="1692121937862" TEXT="brauche komplexere verknüpfte Matches">
|
||||
<richcontent TYPE="NOTE"><html>
|
||||
<head/>
|
||||
<body>
|
||||
|
|
@ -82034,23 +82034,23 @@ Date:   Thu Apr 20 18:53:17 2023 +0200<br/>
|
|||
</node>
|
||||
<node BACKGROUND_COLOR="#eee5c3" COLOR="#990000" CREATED="1689205081622" ID="ID_1440811513" MODIFIED="1689205086027" TEXT="Meßpunkte">
|
||||
<icon BUILTIN="flag-yellow"/>
|
||||
<node BACKGROUND_COLOR="#eee5c3" COLOR="#990000" CREATED="1689205105640" ID="ID_1975472338" MODIFIED="1689205112281" TEXT="Dummy-Funktor">
|
||||
<icon BUILTIN="flag-yellow"/>
|
||||
<node COLOR="#338800" CREATED="1689205105640" ID="ID_1975472338" MODIFIED="1692120794297" TEXT="Dummy-Funktor">
|
||||
<icon BUILTIN="button_ok"/>
|
||||
<node COLOR="#435e98" CREATED="1692114609799" ID="ID_742671204" MODIFIED="1692114749800" TEXT="was wird erzeugt?">
|
||||
<icon BUILTIN="help"/>
|
||||
<node CREATED="1692114616486" ID="ID_1022358077" MODIFIED="1692114650342" TEXT="eine (opaque) JobFunctor-Subklasse"/>
|
||||
<node CREATED="1692114630221" ID="ID_827680196" MODIFIED="1692114643823" TEXT="wird vom ActivitiyDetector selber gemanaged"/>
|
||||
<node CREATED="1692114652402" ID="ID_1621166525" MODIFIED="1692114714280" TEXT="überschreiben: invokeJobOperation (JobParameter)"/>
|
||||
</node>
|
||||
<node BACKGROUND_COLOR="#eee5c3" COLOR="#990000" CREATED="1692114723724" ID="ID_944641822" MODIFIED="1692114743688" TEXT="Zusatz-Verifikationen ermöglichen">
|
||||
<icon BUILTIN="flag-yellow"/>
|
||||
<node COLOR="#338800" CREATED="1692114723724" ID="ID_944641822" MODIFIED="1692120791354" TEXT="Zusatz-Verifikationen ermöglichen">
|
||||
<icon BUILTIN="button_ok"/>
|
||||
<node CREATED="1692114853703" ID="ID_1214470182" MODIFIED="1692114856906" TEXT="Parameter">
|
||||
<node CREATED="1692114757875" ID="ID_912452095" MODIFIED="1692114765987" TEXT="nominalTime"/>
|
||||
<node CREATED="1692114766498" ID="ID_266252168" MODIFIED="1692114771333" TEXT="invocation Key"/>
|
||||
</node>
|
||||
<node BACKGROUND_COLOR="#eee5c3" COLOR="#990000" CREATED="1692114860699" ID="ID_568488214" MODIFIED="1692114887859" TEXT="Problem: Daten-Transport">
|
||||
<node COLOR="#435e98" CREATED="1692114860699" ID="ID_568488214" MODIFIED="1692120740957" TEXT="Problem: Daten-Transport">
|
||||
<icon BUILTIN="messagebox_warning"/>
|
||||
<node BACKGROUND_COLOR="#eee5c3" COLOR="#990000" CREATED="1692114909759" ID="ID_162471010" MODIFIED="1692114928969" TEXT="es handelt sich um erweiterte/Binärdaten">
|
||||
<node BACKGROUND_COLOR="#e0ceaa" COLOR="#690f14" CREATED="1692114909759" ID="ID_162471010" MODIFIED="1692120746950" TEXT="es handelt sich um erweiterte/Binärdaten">
|
||||
<icon BUILTIN="messagebox_warning"/>
|
||||
</node>
|
||||
<node CREATED="1692114932716" ID="ID_309749065" MODIFIED="1692114949959" TEXT="das EventLog speichert nur strukturierte String-Daten">
|
||||
|
|
@ -82092,6 +82092,11 @@ Date:   Thu Apr 20 18:53:17 2023 +0200<br/>
|
|||
</node>
|
||||
</node>
|
||||
</node>
|
||||
<node COLOR="#338800" CREATED="1692120756085" ID="ID_1263278422" MODIFIED="1692120779850" TEXT="Qualifier: .nominalTime">
|
||||
<icon BUILTIN="button_ok"/>
|
||||
<node CREATED="1692122360712" ID="ID_681779390" MODIFIED="1692122368841" TEXT="erfordert Zugriff auf bestimmte Argumente"/>
|
||||
<node CREATED="1692122369443" ID="ID_142985202" MODIFIED="1692122387124" TEXT="dafür Nachrüsten entsprechender Match-Primitive im EventLog notwendig"/>
|
||||
</node>
|
||||
</node>
|
||||
</node>
|
||||
<node BACKGROUND_COLOR="#eee5c3" COLOR="#990000" CREATED="1689205129709" ID="ID_355308944" MODIFIED="1689205163520" TEXT="Invocation-Activity">
|
||||
|
|
|
|||
Loading…
Reference in a new issue