Dispatcher-Pipeline: simplify JobTicket and remove channel differentiation

The existing implementation of the Player from 2012~2015 inclduded
an additional differentiation by media channel (for multichannel media)
and would build a separate CalcStream for each channel.

The in-depth analysis conducted for the ongoing »Vertical Slice« effort
revealed that this differentiation is besides the point and would never
be materialised: Since -- by definition -- all media processing has
to be done by the engine, also the generation of the final output format
including any channel multiplexing will happen in render nodes.
The only exception would be when only a single channel of multichannel
media is extracted -- yet this case would then translate into a
dedicated ModelPort.

Based on this reasoning, a lot of complexity (and some contradictions)
within the JobTicket implementation can be removed -- together with
some further leftovers of the fist attempt to build JobTickets always
from a Mock specification (we now use construction by the Segment,
based on an ExitNode, which is the expected actual implementation
for production setup)
This commit is contained in:
Fischlurch 2023-06-11 18:31:00 +02:00
parent b18e79d077
commit 0933d2bba8
6 changed files with 132 additions and 189 deletions

View file

@ -292,7 +292,7 @@ namespace engine {
this->expandAll([](TicketDepend& currentLevel)
{
JobTicket const* parent = currentLevel.second;
return lib::transformIterator (parent->getPrerequisites(0)
return lib::transformIterator (parent->getPrerequisites()
,[&parent](JobTicket const& prereqTicket)
{ // parent shifted up to first pos
return TicketDepend{parent, &prereqTicket};

View file

@ -44,69 +44,19 @@ namespace engine {
} // (END) Details...
// using mobject::Placement;
// using mobject::session::Effect;
using vault::engine::JobParameter;
using vault::engine::JobClosure;
using lib::HashVal;
using lib::unConst;
class FrameJobClosure
: public JobClosure
{
// data members?
private: /* === JobClosure Interface === */
JobKind
getJobKind() const
{
return CALC_JOB;
}
bool
verify (Time nominalTime, InvocationInstanceID invoKey) const
{
UNIMPLEMENTED ("access the underlying JobTicket and verify the given job time is within the relevant timeline segment");
return false;
}
InvocationInstanceID
buildInstanceID (HashVal seed) const override
{
UNIMPLEMENTED ("systematically generate an invoKey, distinct for the nominal time");
}
size_t
hashOfInstance (InvocationInstanceID invoKey) const override
{
UNIMPLEMENTED ("interpret the invoKey and create a suitable hash");
}
void
invokeJobOperation (JobParameter parameter) override
{
UNIMPLEMENTED ("representation of the job functor");
}
void
signalFailure (JobParameter parameter, JobFailureReason reason) override
{
UNIMPLEMENTED ("what needs to be done when a job cant be invoked?");
}
public:
};
/** special »do nothing« JobTicket marker */
const JobTicket JobTicket::NOP{}; //////////////////////////////////////////////////////////////TICKET #725 : do we actually need that for the final data structure?
JobTicket::JobTicket()
: provision_{nopFunctor(), ExitNode::NIL}
{ }
/**
@ -129,10 +79,8 @@ namespace engine {
else
{
REQUIRE (this->isValid(), "Attempt to generate render job for incomplete or unspecified render plan.");
REQUIRE (coordinates.channelNr < provision_.size(), "Inconsistent Job planning; channel beyond provision");
Provision const& provision = provision_[coordinates.channelNr];
JobClosure& functor = static_cast<JobClosure&> (unConst(provision.jobFunctor)); ////////////////TICKET #1287 : fix actual interface down to JobFunctor (after removing C structs)
InvocationInstanceID invoKey{timeHash (nominalTime, provision.invocationSeed)};
JobClosure& functor = static_cast<JobClosure&> (unConst(provision_.jobFunctor)); ////////////////TICKET #1287 : fix actual interface down to JobFunctor (after removing C structs)
InvocationInstanceID invoKey{timeHash (nominalTime, provision_.invocationSeed)};
return Job(functor, invoKey, nominalTime);
}
@ -166,12 +114,8 @@ namespace engine {
bool
JobTicket::verifyInstance (JobFunctor& functor, InvocationInstanceID const& invoKey, Time nominalTime) const
{
for (Provision const& p : provision_)
if (util::isSameObject (p.jobFunctor, functor)
and invoKey == timeHash (nominalTime, p.invocationSeed)
)
return true;
return false;
return util::isSameObject (provision_.jobFunctor, functor)
and invoKey == timeHash (nominalTime, provision_.invocationSeed);
}

View file

@ -69,8 +69,6 @@ using lib::OrientationIndicator;
using util::isnil;
using lib::HashVal;
using lib::LUID;
//
//class ExitNode;
/**
@ -86,20 +84,19 @@ using lib::LUID;
* Job tickets are created by a classical recursive descent call on the exit node,
* which figures out everything to be done for generating data from this node.
* To turn a JobTicket into an actual job, we need the additional information
* regarding the precise frame number (=nominal time) and the channel number
* to calculate (in case the actual feed is multichannel, which is the default).
* This way, the JobTicket acts as _higher order function:_ a function
* generating on invocation another, specific function (= the job).
* regarding the precise frame number (=nominal time) and a handle for the
* DataSink exposing buffers to output generated data. Thus effectively
* the JobTicket acts as _higher order function:_ a function generating
* on invocation another, specific function (= the job).
*
* @todo 4/23 WIP-WIP-WIP defining the invocation sequence and render jobs
* @todo maybe the per-channel specialisation can be elided altogether...?
*/
class JobTicket
: util::NonCopyable
{
struct Prerequisite
{
Prerequisite* next{nullptr};
Prerequisite* next{nullptr}; // for intrusive list
JobTicket const& prereqTicket;
template<class ALO>
@ -109,14 +106,14 @@ using lib::LUID;
};
using Prerequisites = LinkedElements<Prerequisite>;
/** what handling this task entails */
struct Provision
{
Provision* next{nullptr};
JobFunctor& jobFunctor;
ExitNode const& exitNode;
JobFunctor& jobFunctor;
ExitNode const& exitNode;
InvocationInstanceID invocationSeed;
Prerequisites requirements{};
Prerequisites requirements{};
Provision (JobFunctor& func, ExitNode const& node, HashVal seed =0)
: jobFunctor{func}
@ -125,25 +122,15 @@ using lib::LUID;
{ } /////////////////TICKET #1293 : Hash-Chaining for invocation-ID... size_t hash? or a LUID?
};
LinkedElements<Provision> provision_; //////////////////////////////////////////////////TICKET #1297 : retract differentiation into channels here (instead use ModelPorts in the Segment)
/// @internal reference to all information required for actual Job creation
Provision provision_;
template<class IT>
static LinkedElements<Provision> buildProvisionSpec (IT);
JobTicket(); ///< @internal as NIL marker, a JobTicket can be empty
template<class ALO>
static LinkedElements<Provision> buildProvisionSpec (ExitNode const&, ALO&);
static Provision buildProvisionSpec (ExitNode const&, ALO&);
private:
JobTicket() { } ///< @internal as NIL marker, a JobTicket can be empty
protected:
template<class IT>
JobTicket(IT featureSpec_perChannel)
: provision_{buildProvisionSpec (featureSpec_perChannel)}
{ }
public:
template<class ALO>
JobTicket (ExitNode const& exitNode, ALO& allocator)
@ -151,32 +138,33 @@ using lib::LUID;
{ }
static const JobTicket NOP;
/////////////////////////////////////////////////////////////////////////////////////////////////////////////TICKET #1276 : likely to become obsolete
class ExplorationState;
friend class ExplorationState;
ExplorationState startExploration() const; ////////////////////////////TICKET #1276 : likely to become obsolete
ExplorationState discoverPrerequisites (uint channelNr =0) const; ////////////////////////////TICKET #1276 : likely to become obsolete
/////////////////////////////////////////////////////////////////////////////////////////////////////////////TICKET #1276 : likely to become obsolete
Job createJobFor (FrameCoord coordinates) const;
auto
getPrerequisites (uint slotNr =0) const
getPrerequisites () const
{
return lib::transformIterator (this->empty()? Prerequisites::iterator()
: provision_[slotNr].requirements.begin()
,[](Prerequisite& prq) -> JobTicket const&
return lib::transformIterator (this->empty()? Prerequisites::const_iterator()
: provision_.requirements.begin()
,[](Prerequisite const& prq) -> JobTicket const&
{
return prq.prereqTicket;
});
}
Job createJobFor (FrameCoord coordinates) const;
bool
empty() const
{
return isnil (provision_);
return isnil (provision_.exitNode);
}
bool
@ -195,6 +183,7 @@ using lib::LUID;
};
/////////////////////////////////////////////////////////////////////////////////////////////////////////////TICKET #1276 : likely to become obsolete
class JobTicket::ExplorationState
{
typedef Prerequisites::iterator SubTicketSeq;
@ -288,14 +277,17 @@ using lib::LUID;
}
}
};
/////////////////////////////////////////////////////////////////////////////////////////////////////////////TICKET #1276 : likely to become obsolete
/** @internal prepare and assemble the working data structure to build a JobTicket.
* @tparam IT iterator to yield a sequence of specifications for each channel,
* given as `std::pair` of a JobFunctor and a further Sequence of
* JobTicket prerequisites.
* @tparam ALO type of an allocator front-end for generating prerequisite JobTicket(s)
* @param exitNode a (possibly recursive) tree of ExitNode, detailing points where to
* pull and process data from the render nodes network; these can refer
* to nested ExitNodes(s), which need to be processed beforehand, as
* prerequisite for invoking the given (dependent) ExitNode.
* @return the final wired instance of the data structure to back the new JobTicket
* @remark Note especially that those data structures linked together for use by the
* JobTicket are themselves allocated "elsewhere", and need to be attached
@ -306,55 +298,22 @@ using lib::LUID;
* frequently after each strike of edit operations, yet traversed
* and evaluated on a sub-second scale for ongoing playback.
*/
template<class IT>
inline LinkedElements<JobTicket::Provision>
JobTicket::buildProvisionSpec (IT featureSpec)
{ /* ---- validate parameter type ---- */
static_assert (lib::meta::can_IterForEach<IT>::value); // -- can be iterated
using Spec = typename IT::value_type;
static_assert (lib::meta::is_Tuple<Spec>()); // -- payload of iterator is a tuple
using Node = typename std::tuple_element<0, Spec>::type;
using Seed = typename std::tuple_element<1, Spec>::type;
using Func = typename std::tuple_element<2, Spec>::type;
using Preq = typename std::tuple_element<3, Spec>::type;
static_assert (lib::meta::is_basically<Node, ExitNode>()); // -- first component refers to the ExitNode in the model
static_assert (lib::meta::is_basically<Seed, HashVal>()); // -- second component provides a specific seed for Invocation-IDs
static_assert (lib::meta::is_basically<Func, JobFunctor>()); // -- third component specifies the JobFunctor to use
static_assert (lib::meta::can_IterForEach<Preq>::value); // -- fourth component is again an iterable sequence
static_assert (std::is_same<typename Preq::value_type, JobTicket>()); // -- which yields JobTicket prerequisites
REQUIRE (not isnil (featureSpec)
,"require at least specification for one channel");
LinkedElements<Provision> provisionSpec; //////////////////////////////////////////////////TICKET #1292 : need to pass in Allocator as argument
for ( ; featureSpec; ++featureSpec) ///////////////////////////////////////////////////TICKET #1297 : this additional iteration over channels will go away
{
ExitNode& node = std::get<0> (*featureSpec);
HashVal invoSeed = std::get<1> (*featureSpec);
JobFunctor& func = std::get<2> (*featureSpec);
auto& provision = provisionSpec.emplace<Provision> (func, node, invoSeed);
for (Preq pre = std::get<3> (*featureSpec); pre; ++pre)
provision.requirements.emplace<Prerequisite> (*pre);
}
provisionSpec.reverse(); // retain order of given definitions per channel ////////////TICKET #1297 : obsolete; instead we differentiate by OutputSlot in the Segment
ENSURE (not isnil (provisionSpec));
return provisionSpec;
}
template<class ALO>
inline LinkedElements<JobTicket::Provision>
inline JobTicket::Provision
JobTicket::buildProvisionSpec (ExitNode const& exitNode, ALO& allocTicket)
{
REQUIRE (not isnil (exitNode)); // has valid functor
LinkedElements<Provision> provisionSpec;
HashVal invoSeed = exitNode.getPipelineIdentity();
JobFunctor& func = exitNode.getInvocationFunctor();
auto& provision = provisionSpec.emplace<Provision> (func, exitNode, invoSeed);
Provision provisionSpec{func, exitNode, invoSeed};
for (ExitNode const& preNode: exitNode.getPrerequisites())
provision.requirements.emplace(preNode, allocTicket); ////////////////////////////////////TICKET #1292 : need to pass in generic Allocator as argument
provisionSpec.requirements.emplace(preNode, allocTicket); //////////////////////////////////////////TICKET #1292 : need to pass in generic Allocator as argument
return provisionSpec;
}
/////////////////////////////////////////////////////////////////////////////////////////////////////////////TICKET #1276 : likely to become obsolete
/// @deprecated : could be expendable ... likely incurred solely by the use of Monads as design pattern
inline JobTicket::ExplorationState
JobTicket::startExploration() const
@ -373,13 +332,10 @@ using lib::LUID;
inline JobTicket::ExplorationState
JobTicket::discoverPrerequisites (uint channelNr) const
{
REQUIRE (channelNr < provision_.size() or not isValid());
return isnil (provision_)? ExplorationState()
: ExplorationState (provision_[channelNr].requirements);
return empty()? ExplorationState()
: ExplorationState (util::unConst(provision_).requirements);
}
/////////////////////////////////////////////////////////////////////////////////////////////////////////////TICKET #1276 : likely to become obsolete
}} // namespace steam::engine

View file

@ -138,10 +138,6 @@ namespace test {
: JobTicket{defineSimpleSpec (seed), allocator()}
{ }
// template<class IT>
// MockJobTicket (HashVal seed, IT&& prereq)
// : JobTicket{defineSpec (seed, std::forward<IT> (prereq))}
// { }
/* ===== Diagnostics ===== */

View file

@ -53,7 +53,7 @@ namespace test {
/*****************************************************************************//**
* @test Verify properties and behaviour of a single Segment in the Segmentation
* - construction of a mocked Segment
* - TODO
* - on-demand allocation of a JobTicket for a ModelPort(index)
* - TODO
* @see steam::fixture::Segment
* @see JobPlanningSetup_test

View file

@ -74102,13 +74102,20 @@ Date:&#160;&#160;&#160;Thu Apr 20 18:53:17 2023 +0200<br/>
</node>
<node BACKGROUND_COLOR="#eee5c3" COLOR="#990000" CREATED="1685979146435" ID="ID_1554403810" MODIFIED="1685979205259" TEXT="Zugang zum JobTicket kl&#xe4;ren">
<icon BUILTIN="flag-yellow"/>
<node BACKGROUND_COLOR="#eee5c3" COLOR="#990000" CREATED="1685979157473" ID="ID_1156902335" MODIFIED="1685979175008" TEXT="allgemein (Plan f&#xfc;r operative L&#xf6;sung)">
<icon BUILTIN="flag-yellow"/>
<node CREATED="1685986615408" ID="ID_114144357" MODIFIED="1685986639127" TEXT="JobTickets werden on-demand erzeugt"/>
<node CREATED="1685986639787" ID="ID_966871848" MODIFIED="1685986640616" TEXT="aber in der Segment-Storage (AllocationCluster)"/>
<node CREATED="1685986728208" ID="ID_720100639" MODIFIED="1685986736792" TEXT="also: Array-Access mit NULL-Check"/>
<node CREATED="1685999762297" ID="ID_551644524" MODIFIED="1686000423984" TEXT="es gibt ein Koppel-Objekt zum low-level-Model">
<arrowlink COLOR="#656486" DESTINATION="ID_826544806" ENDARROW="Default" ENDINCLINATION="469;-18;" ID="Arrow_ID_1372033454" STARTARROW="None" STARTINCLINATION="486;32;"/>
<node COLOR="#435e98" CREATED="1685979157473" ID="ID_1156902335" MODIFIED="1686498920114" TEXT="allgemein (Plan f&#xfc;r operative L&#xf6;sung)">
<icon BUILTIN="yes"/>
<node COLOR="#338800" CREATED="1685986615408" ID="ID_114144357" MODIFIED="1686498905115" TEXT="JobTickets werden on-demand erzeugt">
<icon BUILTIN="button_ok"/>
</node>
<node COLOR="#338800" CREATED="1685986639787" ID="ID_966871848" MODIFIED="1686498905117" TEXT="aber in der Segment-Storage (AllocationCluster)">
<icon BUILTIN="button_ok"/>
</node>
<node COLOR="#338800" CREATED="1685986728208" ID="ID_720100639" MODIFIED="1686498905116" TEXT="also: Array-Access mit NULL-Check">
<icon BUILTIN="button_ok"/>
</node>
<node COLOR="#338800" CREATED="1685999762297" ID="ID_551644524" MODIFIED="1686498909689" TEXT="es gibt ein Koppel-Objekt zum low-level-Model">
<arrowlink COLOR="#656486" DESTINATION="ID_826544806" ENDARROW="Default" ENDINCLINATION="469;-18;" ID="Arrow_ID_1372033454" STARTARROW="None" STARTINCLINATION="487;30;"/>
<icon BUILTIN="button_ok"/>
</node>
<node BACKGROUND_COLOR="#eee5c3" COLOR="#990000" CREATED="1686014265346" ID="ID_1087682281" MODIFIED="1686014444967" TEXT="Diskrepanz zwischen ModelPort und PortNr">
<arrowlink COLOR="#945b74" DESTINATION="ID_1552872944" ENDARROW="Default" ENDINCLINATION="-661;-43;" ID="Arrow_ID_1211078783" STARTARROW="None" STARTINCLINATION="-496;30;"/>
@ -74118,14 +74125,16 @@ Date:&#160;&#160;&#160;Thu Apr 20 18:53:17 2023 +0200<br/>
</node>
<node BACKGROUND_COLOR="#eee5c3" COLOR="#990000" CREATED="1685979177023" ID="ID_886135870" MODIFIED="1685979181526" TEXT="Mock-L&#xf6;sung">
<icon BUILTIN="flag-yellow"/>
<node BACKGROUND_COLOR="#eee5c3" COLOR="#990000" CREATED="1685979197228" ID="ID_545092486" MODIFIED="1685979201501" TEXT="Thema: ModelPort">
<node COLOR="#338800" CREATED="1685979197228" ID="ID_545092486" MODIFIED="1686498877227" TEXT="Thema: ModelPort">
<arrowlink COLOR="#6290c0" DESTINATION="ID_377967489" ENDARROW="Default" ENDINCLINATION="1458;-612;" ID="Arrow_ID_1683217879" STARTARROW="None" STARTINCLINATION="36;5;"/>
<icon BUILTIN="flag-yellow"/>
<node CREATED="1685986752098" ID="ID_225154274" MODIFIED="1685986765295" TEXT="erst der konkrete JobFunktor mu&#xdf; die ExitNode aufl&#xf6;sen"/>
<node CREATED="1685987227501" ID="ID_1649977820" MODIFIED="1685987251374" TEXT="daf&#xfc;r gen&#xfc;gt ihm eine Index-Nr als Parameter">
<icon BUILTIN="button_ok"/>
<node CREATED="1685986752098" ID="ID_225154274" MODIFIED="1686498869630" TEXT="erst der konkrete JobFunktor mu&#xdf; die ExitNode aufl&#xf6;sen">
<icon BUILTIN="idea"/>
</node>
<node COLOR="#5b280f" CREATED="1685987227501" ID="ID_1649977820" MODIFIED="1686498874368" TEXT="daf&#xfc;r gen&#xfc;gt ihm eine Index-Nr als Parameter">
<icon BUILTIN="stop-sign"/>
</node>
<node CREATED="1685986766172" HGAP="28" ID="ID_491497133" MODIFIED="1685987523448" TEXT="Nein! besser direkt als Pointer durchschieben" VSHIFT="-5">
<node COLOR="#435e98" CREATED="1685986766172" HGAP="28" ID="ID_491497133" MODIFIED="1686498858490" TEXT="Nein! besser direkt als Pointer durchschieben" VSHIFT="-5">
<arrowlink COLOR="#3e3f9b" DESTINATION="ID_666925478" ENDARROW="Default" ENDINCLINATION="426;-58;" ID="Arrow_ID_1306644139" STARTARROW="None" STARTINCLINATION="311;19;"/>
</node>
</node>
@ -74240,12 +74249,21 @@ Date:&#160;&#160;&#160;Thu Apr 20 18:53:17 2023 +0200<br/>
</node>
</node>
</node>
<node BACKGROUND_COLOR="#bfe9e4" COLOR="#338800" CREATED="1686498037899" ID="ID_1339088600" MODIFIED="1686498073888" TEXT="ExitNodes sind vorerst ein Stub und eine Facade">
<icon BUILTIN="yes"/>
</node>
<node BACKGROUND_COLOR="#fdfdcf" COLOR="#ff0000" CREATED="1686090622242" ID="ID_671795357" MODIFIED="1686090648184" TEXT="MockSupport_test l&#xe4;uft weiterhin ohne jedwede Anpassung">
<icon BUILTIN="flag-pink"/>
</node>
</node>
<node BACKGROUND_COLOR="#eee5c3" COLOR="#990000" CREATED="1685988083711" ID="ID_1973560674" MODIFIED="1685988105725" TEXT="Prerequisites von der Wurzel aus optional nach ModelPort-Nr filtern">
<icon BUILTIN="flag-yellow"/>
<node BACKGROUND_COLOR="#d2beaf" COLOR="#5c4d6e" CREATED="1685988083711" ID="ID_1973560674" MODIFIED="1686498792167" TEXT="Prerequisites von der Wurzel aus optional nach ModelPort-Nr filtern">
<icon BUILTIN="hourglass"/>
<node BACKGROUND_COLOR="#f0d5c5" COLOR="#990033" CREATED="1686498710958" ID="ID_200132237" MODIFIED="1686498774995" TEXT="nicht klar ob das f&#xfc;r die Mock-L&#xf6;sung &#xfc;berhaupt gebraucht wird">
<icon BUILTIN="help"/>
</node>
<node COLOR="#435e98" CREATED="1686498723556" ID="ID_1464720710" MODIFIED="1686498781151" TEXT="derzeit erzeugt die Mock-L&#xf6;sung nur ein NodeGraphAttachment f&#xfc;r ModelPort-Index &#x2254; 0">
<icon BUILTIN="info"/>
</node>
</node>
</node>
<node BACKGROUND_COLOR="#eee5c3" COLOR="#990000" CREATED="1685989418199" ID="ID_1214082390" MODIFIED="1685989432582" TEXT="Mock-Repr&#xe4;sentation f&#xfc;r Exit-Node bereitstellen">
@ -74279,12 +74297,12 @@ Date:&#160;&#160;&#160;Thu Apr 20 18:53:17 2023 +0200<br/>
<node CREATED="1685990112190" ID="ID_463883334" MODIFIED="1685990125693" TEXT="blo&#xdf; nicht verr&#xfc;ckt machen mit dem konkreten Model"/>
<node CREATED="1685990126424" ID="ID_933157694" MODIFIED="1685990149034" TEXT="sehr wahrscheinlich werden die Mocks niemals ein differenziertes Model bespielen"/>
</node>
<node BACKGROUND_COLOR="#eee5c3" COLOR="#990000" CREATED="1685990173459" ID="ID_920554071" MODIFIED="1686000314740" TEXT="im Segment einen indizierten Zugriff vorsehen">
<icon BUILTIN="flag-yellow"/>
<node COLOR="#338800" CREATED="1685990173459" ID="ID_920554071" MODIFIED="1686498551489" TEXT="im Segment einen indizierten Zugriff vorsehen">
<icon BUILTIN="button_ok"/>
</node>
<node BACKGROUND_COLOR="#eee5c3" COLOR="#990000" CREATED="1686000316132" ID="ID_826544806" LINK="#ID_1237481687" MODIFIED="1686000406522" TEXT="Kopplung per &#xbb;NodeGraphAttachment&#xab;">
<linktarget COLOR="#656486" DESTINATION="ID_826544806" ENDARROW="Default" ENDINCLINATION="469;-18;" ID="Arrow_ID_1372033454" SOURCE="ID_551644524" STARTARROW="None" STARTINCLINATION="486;32;"/>
<icon BUILTIN="flag-yellow"/>
<node COLOR="#338800" CREATED="1686000316132" ID="ID_826544806" LINK="#ID_1237481687" MODIFIED="1686498909689" TEXT="Kopplung per &#xbb;NodeGraphAttachment&#xab;">
<linktarget COLOR="#656486" DESTINATION="ID_826544806" ENDARROW="Default" ENDINCLINATION="469;-18;" ID="Arrow_ID_1372033454" SOURCE="ID_551644524" STARTARROW="None" STARTINCLINATION="487;30;"/>
<icon BUILTIN="button_ok"/>
<node COLOR="#338800" CREATED="1686008339600" HGAP="28" ID="ID_181839329" MODIFIED="1686092787399" TEXT="Dummy-Implementierung anlegen" VSHIFT="13">
<icon BUILTIN="button_ok"/>
<node COLOR="#338800" CREATED="1686008354738" ID="ID_1875142825" MODIFIED="1686092748594" TEXT="ExitNode : Platzhalter">
@ -74301,7 +74319,7 @@ Date:&#160;&#160;&#160;Thu Apr 20 18:53:17 2023 +0200<br/>
<icon BUILTIN="hourglass"/>
</node>
</node>
<node BACKGROUND_COLOR="#fdfdcf" COLOR="#ff0000" CREATED="1686009434197" ID="ID_1874481686" MODIFIED="1686009466526" TEXT="mu&#xdf; nun Segment / JobTicket-Erzeugung umstellen">
<node COLOR="#435e98" CREATED="1686009434197" ID="ID_1874481686" MODIFIED="1686498522807" TEXT="mu&#xdf; nun Segment / JobTicket-Erzeugung umstellen">
<icon BUILTIN="messagebox_warning"/>
<node COLOR="#338800" CREATED="1686088955494" ID="ID_683990266" MODIFIED="1686263708546" TEXT="Segment bekommt nun ein NodeGraphAttachment">
<icon BUILTIN="button_ok"/>
@ -74341,16 +74359,17 @@ Date:&#160;&#160;&#160;Thu Apr 20 18:53:17 2023 +0200<br/>
</html></richcontent>
<icon BUILTIN="yes"/>
</node>
<node COLOR="#338800" CREATED="1686364650603" ID="ID_1148029855" MODIFIED="1686450295671" TEXT="Allozieren der prerequisite-JobTickets">
<node COLOR="#338800" CREATED="1686364650603" FOLDED="true" ID="ID_1148029855" MODIFIED="1686450295671" TEXT="Allozieren der prerequisite-JobTickets">
<linktarget COLOR="#366caa" DESTINATION="ID_1148029855" ENDARROW="Default" ENDINCLINATION="599;43;" ID="Arrow_ID_433931878" SOURCE="ID_812723541" STARTARROW="None" STARTINCLINATION="205;12;"/>
<icon BUILTIN="clanbomber"/>
<node COLOR="#435e98" CREATED="1686365033392" HGAP="42" ID="ID_73811690" MODIFIED="1686450276388" TEXT="zwei M&#xf6;glichkeiten?" VSHIFT="-2">
<icon BUILTIN="help"/>
<node CREATED="1686365053474" ID="ID_1746219617" MODIFIED="1686365061592" TEXT="wie das Haupt-Ticket im Segment">
<node COLOR="#144c4e" CREATED="1686365053474" ID="ID_1746219617" MODIFIED="1686497957768" TEXT="wie das Haupt-Ticket im Segment">
<icon BUILTIN="forward"/>
<node CREATED="1686413111863" ID="ID_1744350817" MODIFIED="1686413361556" TEXT="pa&#xdf;t so gar nicht in das sch&#xf6;ne einfache Schema">
<icon BUILTIN="smiley-angry"/>
</node>
<node CREATED="1686413174454" ID="ID_987285372" MODIFIED="1686413369340" TEXT="erfodert Fallback-L&#xf6;sung f&#xfc;r Unit-Tests">
<node COLOR="#435e98" CREATED="1686413174454" ID="ID_987285372" MODIFIED="1686497928488" TEXT="erfodert Fallback-L&#xf6;sung f&#xfc;r Unit-Tests">
<icon BUILTIN="yes"/>
</node>
<node CREATED="1686413193278" ID="ID_350369436" MODIFIED="1686413373537" TEXT="ist aber kongruent mit der l&#xe4;ngerfristigen L&#xf6;sung">
@ -74359,7 +74378,7 @@ Date:&#160;&#160;&#160;Thu Apr 20 18:53:17 2023 +0200<br/>
<node COLOR="#338800" CREATED="1686418348105" ID="ID_785034065" MODIFIED="1686450634782" TEXT="also gleich einen Allocator durchgeben">
<linktarget COLOR="#5fcb3f" DESTINATION="ID_785034065" ENDARROW="Default" ENDINCLINATION="62;-466;" ID="Arrow_ID_67103593" SOURCE="ID_471950405" STARTARROW="None" STARTINCLINATION="131;9;"/>
<icon BUILTIN="button_ok"/>
<node BACKGROUND_COLOR="#e0ceaa" COLOR="#690f14" CREATED="1686418360062" ID="ID_39870309" MODIFIED="1686450266086" TEXT="AllocationCluster nutzbar?">
<node BACKGROUND_COLOR="#e0ceaa" COLOR="#690f14" CREATED="1686418360062" FOLDED="true" ID="ID_39870309" MODIFIED="1686450266086" TEXT="AllocationCluster nutzbar?">
<icon BUILTIN="help"/>
<node CREATED="1686418368407" ID="ID_1859944923" MODIFIED="1686418378925" TEXT="naja.... OK">
<icon BUILTIN="smiley-oh"/>
@ -74468,7 +74487,8 @@ Date:&#160;&#160;&#160;Thu Apr 20 18:53:17 2023 +0200<br/>
</node>
</node>
</node>
<node CREATED="1686365062469" ID="ID_1687391140" MODIFIED="1686365089197" TEXT="direkt in der Prerequisite-Struktur im Haupt-Ticket">
<node COLOR="#5b280f" CREATED="1686365062469" ID="ID_1687391140" MODIFIED="1686497970752" TEXT="direkt in der Prerequisite-Struktur im Haupt-Ticket">
<icon BUILTIN="button_cancel"/>
<node CREATED="1686413048626" ID="ID_327677209" MODIFIED="1686413356388" TEXT="w&#xe4;re zun&#xe4;chst billig zu haben">
<icon BUILTIN="idea"/>
</node>
@ -74483,8 +74503,8 @@ Date:&#160;&#160;&#160;Thu Apr 20 18:53:17 2023 +0200<br/>
</node>
</node>
</node>
<node BACKGROUND_COLOR="#fdfdcf" COLOR="#ff0000" CREATED="1686186370164" ID="ID_1270139229" MODIFIED="1686186389790" TEXT="Problem: Klon-Segmente wegen Split-Splice">
<icon BUILTIN="messagebox_warning"/>
<node BACKGROUND_COLOR="#e0ceaa" COLOR="#690f14" CREATED="1686186370164" ID="ID_1270139229" MODIFIED="1686498520200" TEXT="Problem: Klon-Segmente wegen Split-Splice">
<icon BUILTIN="bell"/>
<node CREATED="1686186392505" ID="ID_581141216" MODIFIED="1686186413737" TEXT="der Algo k&#xfc;rzt Segmente oder teilt sie auf"/>
<node CREATED="1686186419019" ID="ID_1101347188" MODIFIED="1686186435605" TEXT="daf&#xfc;r wird ein Segment kopiert und &#xbb;umgeschrieben&#xab;"/>
<node BACKGROUND_COLOR="#eee5c3" COLOR="#990000" CREATED="1686186436835" ID="ID_909527462" MODIFIED="1686186454445" TEXT="das widerspricht der Referenz-Semantik f&#xfc;r ExitNodes">
@ -74496,8 +74516,8 @@ Date:&#160;&#160;&#160;Thu Apr 20 18:53:17 2023 +0200<br/>
</node>
</node>
</node>
<node BACKGROUND_COLOR="#eee5c3" COLOR="#990000" CREATED="1686089743535" ID="ID_1592596965" MODIFIED="1686089766715" TEXT="JobTicket-Erzeugung (vorl&#xe4;ufig) endg&#xfc;litig implementieren">
<icon BUILTIN="flag-yellow"/>
<node COLOR="#338800" CREATED="1686089743535" ID="ID_1592596965" MODIFIED="1686498536536" TEXT="JobTicket-Erzeugung (vorl&#xe4;ufig) endg&#xfc;litig implementieren">
<icon BUILTIN="button_ok"/>
<node COLOR="#5b280f" CREATED="1686089827509" ID="ID_213320277" MODIFIED="1686270676731" TEXT="Spec-Erzeugung in das Segment verlagern">
<icon BUILTIN="button_cancel"/>
<node COLOR="#5b280f" CREATED="1686270962172" ID="ID_883202873" MODIFIED="1686270983572" TEXT="hier nun das Spec-Tupel rekursiv aufbauen">
@ -74543,22 +74563,22 @@ Date:&#160;&#160;&#160;Thu Apr 20 18:53:17 2023 +0200<br/>
<icon BUILTIN="idea"/>
</node>
</node>
<node BACKGROUND_COLOR="#eee5c3" COLOR="#990000" CREATED="1686089789689" ID="ID_1968297332" MODIFIED="1686090078439" STYLE="bubble" TEXT="Aufruf: bekommt ExitNode">
<node COLOR="#435e98" CREATED="1686089789689" HGAP="31" ID="ID_1968297332" MODIFIED="1686498466909" STYLE="bubble" TEXT="Aufruf: bekommt ExitNode" VSHIFT="12">
<edge COLOR="#4b6f99"/>
<linktarget COLOR="#334242" DESTINATION="ID_1968297332" ENDARROW="Default" ENDINCLINATION="-57;70;" ID="Arrow_ID_1911874934" SOURCE="ID_634741286" STARTARROW="None" STARTINCLINATION="14;65;"/>
<icon BUILTIN="flag-yellow"/>
<node BACKGROUND_COLOR="#eee5c3" COLOR="#990000" CREATED="1686089934319" ID="ID_1303596509" MODIFIED="1686090078438" STYLE="bubble" TEXT="entnimmt Pipeline-Identity">
<icon BUILTIN="button_ok"/>
<node COLOR="#435e98" CREATED="1686089934319" ID="ID_1303596509" MODIFIED="1686498432609" STYLE="bubble" TEXT="entnimmt Pipeline-Identity">
<edge COLOR="#4b6f99"/>
<icon BUILTIN="flag-yellow"/>
<icon BUILTIN="button_ok"/>
</node>
<node BACKGROUND_COLOR="#eee5c3" COLOR="#990000" CREATED="1686089946582" ID="ID_1500234215" MODIFIED="1686090078439" STYLE="bubble" TEXT="entnimmt ExitNode*">
<node COLOR="#435e98" CREATED="1686089946582" ID="ID_1500234215" MODIFIED="1686498432609" STYLE="bubble" TEXT="entnimmt ExitNode*">
<edge COLOR="#4b6f99"/>
<icon BUILTIN="flag-yellow"/>
<icon BUILTIN="button_ok"/>
</node>
<node BACKGROUND_COLOR="#eee5c3" COLOR="#990000" CREATED="1686089957609" ID="ID_634741286" MODIFIED="1686090078440" STYLE="bubble" TEXT="on-demand-Mapping &#x27fc; prerequisite-ExitNode(s)">
<node COLOR="#435e98" CREATED="1686089957609" ID="ID_634741286" MODIFIED="1686498432597" STYLE="bubble" TEXT="on-demand-Mapping &#x27fc; prerequisite-ExitNode(s)">
<edge COLOR="#4b6f99"/>
<arrowlink COLOR="#334242" DESTINATION="ID_1968297332" ENDARROW="Default" ENDINCLINATION="-57;70;" ID="Arrow_ID_1911874934" STARTARROW="None" STARTINCLINATION="14;65;"/>
<icon BUILTIN="flag-yellow"/>
<icon BUILTIN="button_ok"/>
</node>
</node>
<node COLOR="#338800" CREATED="1686090113552" HGAP="35" ID="ID_1222153026" MODIFIED="1686361148882" TEXT="ExitNode (wie bisher die Spec) an JobTicket-ctor weitergeben" VSHIFT="43">
@ -74587,6 +74607,33 @@ Date:&#160;&#160;&#160;Thu Apr 20 18:53:17 2023 +0200<br/>
<arrowlink COLOR="#599eb9" DESTINATION="ID_1552363345" ENDARROW="Default" ENDINCLINATION="623;43;" ID="Arrow_ID_940031570" STARTARROW="None" STARTINCLINATION="738;-108;"/>
</node>
</node>
<node COLOR="#338800" CREATED="1686498590686" ID="ID_383464116" MODIFIED="1686520395591" TEXT="R&#xfc;ckbau Differenzierung nach Channel">
<richcontent TYPE="NOTE"><html>
<head>
</head>
<body>
<p>
urspr&#252;nglich dachte ich, im Ticket w&#252;rde intern noch nach einer Channel-ID (f&#252;r Mehrkanal-Medien) differenziert; die Analyse im Detail ergab jedoch, da&#223; dies stets unter dem Konstrukt &#187;ModelPort&#171; subsummiert werden kann &#8212; viele interne Komplexit&#228;ten fallen damit weg
</p>
</body>
</html></richcontent>
<icon BUILTIN="button_ok"/>
<node COLOR="#338800" CREATED="1686500288945" ID="ID_1009233034" MODIFIED="1686520383542" TEXT="neue L&#xf6;sung f&#xfc;r empty()">
<icon BUILTIN="button_ok"/>
<node COLOR="#435e98" CREATED="1686500639546" ID="ID_1295818477" MODIFIED="1686520381909" TEXT="ExitNode::NIL">
<icon BUILTIN="idea"/>
</node>
<node COLOR="#435e98" CREATED="1686500644738" ID="ID_1383857132" MODIFIED="1686520380349" STYLE="fork" TEXT="nopFunctor verwenden">
<icon BUILTIN="idea"/>
<node CREATED="1686520342843" ID="ID_1348881404" MODIFIED="1686520352350" TEXT="aber grunds&#xe4;tzlich nochmal pr&#xfc;fen"/>
<node CREATED="1686520353527" ID="ID_1138778172" MODIFIED="1686520370009" TEXT="es k&#xf6;nnte ja auch der Hash==0 sein"/>
</node>
</node>
<node BACKGROUND_COLOR="#eef0c5" COLOR="#990000" CREATED="1686500296179" ID="ID_988077733" MODIFIED="1686520404258" TEXT="neue L&#xf6;sung f&#xfc;r Validity self-check">
<icon BUILTIN="pencil"/>
</node>
</node>
<node COLOR="#338800" CREATED="1686092906718" HGAP="35" ID="ID_1605426517" MODIFIED="1686450454254" TEXT="FixtureSegment_test" VSHIFT="-3">
<linktarget COLOR="#5aec6d" DESTINATION="ID_1605426517" ENDARROW="Default" ENDINCLINATION="-104;-6;" ID="Arrow_ID_658388334" SOURCE="ID_31746915" STARTARROW="None" STARTINCLINATION="570;-91;"/>
<icon BUILTIN="button_ok"/>
@ -74938,7 +74985,7 @@ Date:&#160;&#160;&#160;Thu Apr 20 18:53:17 2023 +0200<br/>
<linktarget COLOR="#4b3ea5" DESTINATION="ID_87044302" ENDARROW="Default" ENDINCLINATION="248;-35;" ID="Arrow_ID_594271482" SOURCE="ID_953619048" STARTARROW="None" STARTINCLINATION="669;36;"/>
<icon BUILTIN="flag-yellow"/>
</node>
<node BACKGROUND_COLOR="#eee5c3" COLOR="#990000" CREATED="1685986803653" ID="ID_666925478" MODIFIED="1685987270290" TEXT="Exit-Node-Index-Nr">
<node BACKGROUND_COLOR="#eee5c3" COLOR="#990000" CREATED="1685986803653" ID="ID_666925478" MODIFIED="1686498849033" TEXT="Exit-Node(Referenz)">
<linktarget COLOR="#3e3f9b" DESTINATION="ID_666925478" ENDARROW="Default" ENDINCLINATION="426;-58;" ID="Arrow_ID_1306644139" SOURCE="ID_491497133" STARTARROW="None" STARTINCLINATION="311;19;"/>
<icon BUILTIN="flag-yellow"/>
</node>