Carrington Core1 loads template files through a function rather than including them directly within the global scope. This means that global variables need to be explicitly brought into scope rather than just being there and available to you.
I’ve considered this a feature, because it means that you’re much less likely to stomp on an important WordPress global variable from within a template, and having the explicit declaration of which variables you want available makes things a bit easier to follow.
However, it also has drawbacks. For anyone already familiar with WordPress theming, there is a “this is broken” reaction when trying to access $post
doesn’t work until they declare global $post;
. I’m on the fence about which approach is better (enforcing better development best practices or making the platform more accessible to new devs), but I’ve been exploring some options (in case we decide a more accessible platform is better).
You’ll see the three approaches I’m considering in the comments at the start of the function. Each has pros and cons.
Option #1: Selectively bring in globals. This was my initial solution. It makes a reasonable set of global variables available. However, if someone needs to hit a global we didn’t choose to include, I think that becomes more confusing. If the global $post
was already in scope (without having to declare global $post;
), why would they need to declare global $_wp_using_ext_object_cache;
to get that variable?
Option #2: Bring all globals into scope. I think this is an interesting idea, but likely not a good solution. Developers would assume that these variables are global and run into surprises when they find out they aren’t.
Option #3: Bring in all globals. I’m leaning towards this, but it just feels wrong to me – likely due to an overall aversion to globals. It basically makes all templates loaded by Carrington Core work like standard WordPress templates. There is potential for confusion here since all of the globals are present and a developer can interact with them just like their template file is being loaded into the global scope; with a pretty big exception that variables created in the templates are not created in the global scope.
There is also a concern about this change causing problems with existing Carrington powered sites. Previously variables set in template files wouldn’t pollute the global scope or stomp on global variables. With options #1 and #3, this would be a possibility.
So I’m soliciting feedback. Fellow WordPress developers, what say you? Anyone have a “silver bullet” solution? Perhaps no action is the best action?
- Carrington Core is a template selection engine for WordPress sites. It helps you easily create custom views that are used for various data conditions (I want this header for this category, add this author bio information for posts written by anyone with an editor role, etc.) without writing conditional PHP code in your templates. There are more details here. ↩
This post is part of the project: Carrington Core. View the project timeline for more context on this post.
I have bumped up against this when using Carrington core. I’d say that bringing in the same globals as WP makes the most sense.
load_template()
starts with:global $posts, $post, $wp_did_header, $wp_did_template_redirect, $wp_query, $wp_rewrite, $wpdb, $wp_version, $wp, $id, $comment, $user_ID;
That might be a good way to go. I think there is still a concern about existing templates accidentally stomping globals (for examples, I could see
$posts
getting stomped if someone is doing a custom query in a template).Justin recommended using a filter. I think this would be a good option as it makes things easier for new devs and also allows anyone to go back to the current behavior easily.
I’m currently liking this solution best.
I know this’ll sound funny coming from someone who tends to overarchitect everything, but I like @mattweibe’s suggestion the best and the other options are too much.
Its simple in that it sets the bar to the baseline that WordPress builds on. The filter adds too much overhead. I think people will just keep going to the easiest path (which is also very pervasive within WordPress) of going for the globals instead of setting up a function and filter.
Take a closer look at the commit I linked to above. The globals are in by default, the filter just allows them to be turned off if necessary.
Yeah. I saw that. The filter just seems like over engineering. I feel it also presents the possibility of becoming a foot gun and/or causing globals to be declared elsewhere anyway when someone forgets that the filter is enforcing a limitation.
I can’t see an update that breaks existing sites with no way to “fix it” (no backward compatibility option) as a very good solution… perhaps you can come up with another idea?
[…] gone ahead and merged in the global variables changes into version 3.4 of Carrington […]