Support dynamic script injection of script/@src
We would transform:
<scxml>
<script src="foo.js"/>
<script src="bar.js"/>
<state id="A"/>
</scxml>
To:
<scxml initial="$generate-before-scripts-loaded">
<parallel id="$generate-before-scripts-loaded">
<onentry>
<fetch id="foo" url="foo.js"/>
<fetch id="bar" url="bar.js"/>
</onentry>
<state id="$generated-loading-script-foo.js">
<state id="$generated-before-script-script-foo.js-loaded">
<transition target="$generated-after-script-script-foo.js-loaded" event="fetch.response.success.foo"/>
</state>
<state id="$generated-after-script-script-foo.js-loaded">
<onentry>
<!-- eval downloaded script -->
<script> eval(_event.data); </script>
</onentry>
</state>
</state>
<state id="$generated-loading-script-bar.js">
<state id="$generated-before-script-script-bar.js-loaded">
<transition target="$generated-after-script-script-bar.js-loaded" event="fetch.response.success.bar"/>
</state>
<state id="$generated-after-script-script-bar.js-loaded">
<onentry>
<!-- eval downloaded script -->
<script> eval(_event.data); </script>
</onentry>
</state>
</state>
<transition
event="fetch.response.success.*"
target="$generated-after-script-tags-loaded-successfully"
cond="In('$generated-after-script-script-foo.js-loaded') &&
In('$generated-after-script-script-bar.js-loaded') "/>
<transition
event="fetch.response.failure"
target="$generated-after-script-tags-loaded-failed" />
</parallel>
<state id="$generated-after-script-tags-loaded-successfully">
<onentry>
<!-- TODO: init the datamodel -->
</onentry>
<transition event="scion.internal.start" target="A"/>
</state>
<state id="$generated-after-script-tags-loaded-successfully">
<transition event="scion.internal.start" target="A"/>
</state>
<state id="$generated-after-script-tags-loaded-failed"></state>
<state id="A"/>
</scxml>
<fetch>
would be parameterizable on the scripting context.
eval
could potentially be replaced with something safer such as the nodejs vm
module.