Support » Developing with WordPress » Using set_query_var to pass parameters between template parts

  • Hi,

    I have a page template that calls some template parts using get_template_part(). On each of the template parts I need to get some data from external sources, some of them being the same for different parts. So, I thought that it would be more efficient if I did all the calls once on the main page template, set the variables using set_query_var() and then use those variables on the template parts using get_query_var(), as per the official example.

    Since some of my template parts needed the same variables, I thought that it would be tidier if I could gather all my get_query_vars() on one place instead of repeating them on every template part. So, I started experimenting and I noticed the following:

    – If I use set_query_var('my_var', $my_data) on the main page template, then I can use $my_var on my template parts all right, getting the correct results. On that case, though, Code Sniffer was complaining about the “Undefined variable $my_var).

    – If I go to the template part and define the variable using $my_var = get_query_var('my_var'), then the complain goes away and the output is correct.

    – Experimenting a bit more, I tried to gather all my get_query_var() in one place, in order to keep them better organized. So, I noticed that when I put them on the page template, right after all the set_query_var(), Code Sniffer will still complain for undefined variables on the template parts. If I gather them all together in one of the template parts, it doesn’t matter which one, the complain goes away and everything works fine. In fact, it will work if I put my get_query_var() in other php files as well, as long as they aren’t in the page template holding the set_query_var() (e.g., I tried putting it in functions.php and it still worked).

    So, my questions are:

    1. Why does the Code Sniffer complain when I have the get_query_var() on the same file with the set_query_var() but not when I put it on a template part?
    2. Is it a good practice to pass variables like that or should it be avoided for some reason?
    3. Should I somehow “unset” the query_var at the end of the template?

    My code works fine, I just wanted to better understand how set_query_var() works and which is considered to be the best practice.

    Thanks!

Viewing 3 replies - 1 through 3 (of 3 total)
  • Joy

    (@joyously)

    Best practice is to minimize the use of global variables.
    Best practice would be to write a function to handle it and call that function from the template parts. Or don’t even make template parts out of it. Keep the code together.

    You don’t say which version of the Theme Sniffer you are using, but some effort was being made to make it smarter about which files are template files and so the global variable warnings could be more appropriate.

    You shouldn’t need to use get_query_var in a template file because all the query vars are declared as global so that the template will work. See the code at
    https://developer.wordpress.org/reference/functions/load_template/

    Hello Joy, thank you for your reply.

    The reason I am not keeping the code in a single file is because it becomes too big and difficult to manage, since each part can have many lines of code.

    Initially I kept everything on the template parts, fetching the same data on each part. But I thought that I shouldn’t make unnecessary calls, especially when some of the data could be quite big and I had already called them once earlier.

    You are right about get_query_var – the only reason I used it is because it made the complains go away. Apart from that, my code works the same without it.

    As for the Code Sniffer, I use the latest version (updated today) of WordPress Coding Standards with PHPStorm.

    Joy

    (@joyously)

    The template files are not for lots of code. The code should be in functions that the template calls. And if there is a lot of stuff, it doesn’t belong in a page template anyway.
    Create a class to encapsulate the data and make calls to its functions to output it in the template. It sounds like those template parts should just be functions that return output.

Viewing 3 replies - 1 through 3 (of 3 total)
  • You must be logged in to reply to this topic.