HackerOne users: Testing against this community violates our program's Terms of Service and will result in your bounty being denied.
Options

How to parse smarty tags from a plugin?

Any way to do something like this?

$myValue = 'Hello this is the id {$BodyID}, and some other cool stuff custom {$myPlugin.cssUrl}'
$myValue = $this->myPluginHookSmartyParser($myValue);

Many imaginative thoughtful wonders to come depend on this ...


Thanks in advance

Comments

  • Options
    R_JR_J Ex-Fanboy Munich Admin

    Smarty is for views. If you put a smarty template in the views folder and call sender->render('viewnamewithoutextension', '', '/plugins/yourplugin'), that smarty view gets rendered

  • Options

    Ah! There must be a way to parse raw text at hand (which source is from anywhere)

  • Options
    R_JR_J Ex-Fanboy Munich Admin

    Well, I bet you can but that is not efficient. Smarty is made to deal with blocks, sub-templates, can handle logic, etc. But if you really want to go that way, here is what I found out.

    Vanilla exposes Smarty in its Gdn_Smarty class. It creates an instance of Smarty like that:

       $smarty = new SmartyBC();
    
       $smarty->setCacheDir(PATH_CACHE.'/Smarty/cache');
       $smarty->setCompileDir(PATH_CACHE.'/Smarty/compile');
       $smarty->addPluginsDir(PATH_LIBRARY.'/SmartyPlugins');
       Gdn::pluginManager()->callEventHandlers($smarty, 'Gdn_Smarty', 'Init');
    

    If you look at /vendor/smarty/smarty/demo/index.php you see that you have to "assign" data so that it can be used in the template: $smarty->assign("option_selected", "NE");

    Now you have to find a way/method that doesn't take a template name but a string.


    I'm not sure that this is really possible. One of Smartys advantages is that it compiles templates and only recompiles them if the source changes. Therefore I assume it would always expect a template file. You might be able to create a template object manually but this is getting quite complicated.


    Smarty can do a lot more than only replacing some strings. The first thing that comes to my mind is "Why not simply use sprintf?" The second thing is "I think I have seen something similar being used in Vanilla". And that second thought has brought me to the HeadlineFormat of the Activities:

    $Activity['HeadlineFormat'] = t('HeadlineFormat.Mention', '{ActivityUserID,user} mentioned you in <a href="{Url,html}">{Data.Name,text}</a>');

    That looks quite similar to Smarty...

    Look at functions.general.php formatString() to see that there is something included which is far more easy than Smarty but might fulfil the purpose.

  • Options

    Thanks.

    The HeadlineFormat seems to be a mere predefined mapping of variables. Which might actually work in my case, if I was not so ambitious as to want to allow all possible vanilla smarty tags in this blob to be parsed.

    As I dig further about the Gdn_Smartyclass, I wonder if I should even invest in smarty codes at all and not switch altogether to Twig. I hear that vanilla core shall be moving that direction, as it already supports it.

  • Options
    R_JR_J Ex-Fanboy Munich Admin

    I also think Twig will be the future. But I do not think Smarty will get ditched soon.

    You've said:

    if I was not so ambitious as to want to allow all possible vanilla smarty tags

    and that you wanted to convert strings like "Hello this is the id {$BodyID}, and some other cool stuff custom {$myPlugin.cssUrl}"

    There are no such things as "Vanilla Smarty tags". Look at the init() method of class.smarty.php. There you will find $smarty->assign() calls which define those placeholders.

    A small and lean search and replace function like formatString together with the data assigned in the Gdn_Smarty->init() will be a much more efficient approach. Using a template engine for one string only is a waste of resources.

Sign In or Register to comment.