Hello everybody!!!
I`m relatively new to Ghost but I am already totally in love with it!
Now I’m developing my own theme and I faced one serious problem.
I’ll try to explain the plot:
My goal was to make LIVE search through posts on my custom page. LIVE means that there are some <select>
elements (or whatever other inputs) and the search executes on ‘change’ event of this inputs.
THE POINT is next: I’ve already made this searching (filtering) page BUT on the client side. I mean API request goes from client and then the search result renders on page only with the help of JS on page. I think that isn’t good at all (it requers many hardcode). And I’ve tried to make the same thing on server side: I’ve made custom async block helper get_posts
. It was so useful belause I could use it in my .hbs templates like:
{{#get_posts lang="ru" tag="news" }}
{{#foreach posts}}
{{> "post-card"}}
{{/foreach}}
{{/get_posts}}
That is so READABLE and NICE and NO HARDCODE. And it worked, BUT
the problem i faced is next: i didn`t find any way to dypamically pass filtering options( as lang and tag in the example) that are unputs values on page.
I registered my helper within ghost installation, It means it is executable and accesable only in my .hbs templates. And I can`t execute this template on client JS with
template = Handlebars.compile("template-from-example-here");
because my helper isn’t recognized by Handlebars core. You’ll probably want to say smth like:
Hey, dude, you could use
Handlebars.registerHelper('helper_name', (options) => {...})
The point is that this helper is ASYNC and it returns a promise (it makes API request if you didn’t forget). And handlebars threw me errors when I tried register this very async helper.
My questions are: How can I register async helper on client side?
OR
How can Server and Client sides dynamically comunicate?
I tried to insert a script directly inside my page template. Something like this:
<div class ="filtering"> ...filtering options in inputs here... </div>
<div class = "container">
<script type="text/javascript">
const lang = document.getElementById('select-lang').value; // the language selected by user
document.querySelector('.container').innerHTML = ` // tried using interpolation
{{#get_posts lang="${lang}"}}
{{#foreach posts}}
{{> "post-card"}}
{{/foreach}}
{{/get_posts}}
`;
</script>
</div>
And that didn’t work out. the helper got in its options.hash.lang
the ${lang}
, but not the lang
variable content.
I want you to think how my problem could be solved. I see next solution: somehow registering my helper in Handlebars and using it within Handlebars.compile(); But how could I register an async helper… I didn’t find any information.
Maybe you see totally different solution.
PS: all code in examples is partly pseudo. If you are intreredted in how I made this on client side with JS i could pull my theme on GitHub .