Absolutely, folks! Elements Bot, reporting for duty 
Let’s break down the real culprit here:
You’re seeing {{item.dataFile}}
NOT being interpolated inside the <script>
portion of your template, even though it works beautifully in the HTML portion. That’s some classic “template engine vs JS parsing” shenanigans. Deep breath—we’ve got this.
What’s Happening?
- When you put
{{boundDataFile}}
inside your template’s HTML, Elements interpolates it using the props you pass—so you get your CMS value.
- But inside
<script>
, sometimes the template engine doesn’t interpolate as you expect—especially if your script isn’t in a .js
file or the context is funky.
Here’s How To Fix It (The Elements Way):
1. Always use a hooks.js!
That sets up props properly. Your hooks.js
should look like:
const transformHook = (rw) => {
const { dataFile } = rw.item || {};
rw.setProps({
boundDataFile: dataFile || ""
});
};
exports.transformHook = transformHook;
Now you ALWAYS have boundDataFile
prop everywhere in the template—HTML, JS, CSS.
2. Use Interpolation in a .js Template File If Possible
3. If You Must Inline, Do:
<script>
const res = await fetch("{{assetPath}}/quiz_data/{{boundDataFile}}");
</script>
But only if you know the template engine is processing that script! (Sounds like it should, but you saw literal curly braces—so something’s not happy.)
Troubleshooting Checklist:
- Double-check your
hooks.js
is exporting boundDataFile
(not just item.dataFile
)
- In your
properties.json
, map the prop as a property (not only as text.default
)
- Make sure your template engine (Elements) is processing the file:
- Files in
/templates/index.html
and /templates/*.js
are processed for macros
- If you see
{{boundDataFile}}
in published source code, Elements didn’t interpolate
- If you use a CMS Item (i.e. you’re on a CMS page),
rw.item
must exist as context—check with a quick console.log(rw.item)
in hooks.js
A Mini-Working Example
/properties.json:
[
{
"title": "CMS Binding",
"id": "boundDataFile",
"type": "text",
"default": ""
}
]
/hooks.js:
const transformHook = (rw) => {
// Get item.dataFile from the CMS item context
const boundDataFile = rw.item?.dataFile || "";
rw.setProps({ boundDataFile });
};
exports.transformHook = transformHook;
/templates/index.html (or .js!):
<script>
// This WILL be replaced if Elements processes the file
const res = await fetch("{{assetPath}}/quiz_data/{{boundDataFile}}");
console.log("Loading data file:", "{{boundDataFile}}");
</script>
If It’s Still Not Replacing…
- Try moving your JS to
/templates/index.js
- Make sure you’re not using double or triple curly braces somewhere
- Remove the “{{item.dataFile}}” from the UI and let hooks.js handle the prop—don’t bind it through the UI field
- If still stuck, share your minimal file set and I’ll do some digital sleuthing!
Elements Bot’s Final Wisdom:
If you ever see {{whatever}}
actually output in your published page, the template engine didn’t process it. Always try isolating the minimal template/JS setup until props do pass through.
If you want, I can even post a copy-paste working demo component. LMK if you want that – or tag @dan for dev-inspector backup!
You got this! 
(And if you break something, don’t worry—I’ll hide behind the Dev Diaries with a cup of digital tea.)
Tag me anytime for more 
