Passing variables between hooks in WordPress - php

I am writing plugin that uses init() action and the_content() filter.
In init I would like to do some cookie checks and set some variables based on result (lets say $mycookieset = 1). In the_content filter I would like to modify article based on $mycookieset variable.
How to pass $mycookieset variable in safe way between these two hooks? I would prefer not to use sessions. It also should be multiple users safe (hundreds of people browsing the web same time).
Any ideas? Thanks

You can add the filter inside a function that is hooked into init, and use the cookie value as a variable in the $function_to_add parameter:
add_action( 'init', 'my_init_function' );
function my_init_function(){
// do the cookie stuff
add_filter( 'the_content', 'my_variable_cookie_func_' . $mycookieset );
}
Of course, you should have an appropriate callback function for each possible cookie value.

Related

How can I pass my own variables between functions tied to action hooks in wordpress plugins

I am writing a Wordpress plugin in PHP and I want to be able to use a variable that is not provided in the action hook (of other separate) plugin. I want to pass a variable from one hook to another.
These functions are in my functions.php file (not the theme functions file).
I cannot nest the action hooks because they happen at different times, specifically, the one with the variable happens after the one with where I want it.
I don't think I can use a closure because the variable is inside another hook.
I can't use a class because if I set the class in action 1 then it's not in scope in action 2 and I need to make a new one.
I could use a global or access the DB but I feel like there should be a better way than either of those.
action 1 - my plugin
function foo($level){
do stuff
}
add_action('change-membership', 'foo');
action 2 - my plugin
function bar(){
if($level==0){
do stuff
}
}
add_action('put-in-checkout-text', 'bar');
Other devs plugin
do_action('change_membership', $level);
// a little later
do_action('put_in_checkout_text');
$levels exists at the time I want it - but there is no action hook at that point to grab it.
What I understand is you have something like this:
// Plugin 2, the plugin you are writing.
do_action('put_in_checkout'); // --> bar()
// Plugin 1, another author's plugin
$level = "definition of level";
do_action('change_membership', $level); // --> foo($level)
You say you need to access to $level before the change_membership action happens, so $level may not be defined at that time. Even if it was, it may be in a scope not reachable from put_in_checkout handler functions.
Just in case, check if plugin 2 instanciates a global variable where you have access to the value of $level. Otherwise, you need to take it from the database (if it is stored there) or generate it somehow.

Delete a Wordpress transient from a shortcode on Page/Post update

I need to delete a transient for all shortcodes located on a post/page when that page is updated. So the page update should delete the transient just for the shortcodes located on that page. If that isn't possible it would help if all shortcode transients are deleted on any page update.
I tried using the save_post action but nothing happens, so I must be doing something wrong.
Also, the problem is that I'm generating a shortcode ID, based on post ID and incrementation of a static variable.
So, only when I call the method to delete a transient in shortcode-template.php I have access to the current page's ID and then I can delete a transient related to page ID/Shortcode ID combination. But then the transient is deleted every time the shortcode is loaded. And if I don't call the delete_transient function, it seems like it is not hooked to save_post action, because nothing happens. I guess that is because the current page ID can't be fetched in a Class but only when used somewhere on the page. But I have no idea how to go around that.
Here is my Class:
class MainClass {
private static $shortcode_increment = 0;
private function __construct() {
add_action( 'save_post', array( $this, 'update_page_delete_transient') );
}
public static function increment_id() {
global $post;
self::$shortcode_increment++;
return 'shortcode_' . $post->ID . "_" . self::$shortcode_increment;
}
// delete the shortcode cache on page update
public function update_page_delete_transient() {
delete_transient( 'weather_'.self::increment_id() );
}
}
Any help is appreciated. Thanks.
UPDATE: I'm not sure how actions should work, as I understand it, the funcion added to the action should be activated when that action occurs, so there is no need to call that function? Or is there? Will the function be added to the action be activated automatically after the Class is instantiated in shortcode-template.php for example, since the action itself is in the construct?
Or do I need to call the delete_transient function in shortcode-template.php in order for it to work? But when I do that, it just runs every time widget is loaded, and not on save post/page.
UPDATE 2: So, if I remove the post ID from the increment ID function, I can badly resolve the issue from update 1 above. Delete_transient function is activated when I create an instance of an object and it is called on page/post save. Now the problem that remains is how do I pass the unique Shortcode ID to delete_transient function, if the ID is increased only in the shortcode-template.php when a new shortcode is created. Or it would be even better if I could somehow pass the Page ID and Shortcode ID somehow to the delete_transient function in the Main Class, so I could delete a specific transient for a specific shortcode on update. Is there a way to pass the data from the shortcode-template.php back to the Object method?

WordPress do_action and add_action; running arguments in add_action call

I am currently writing a plugin for WordPress, and I'm stumped with the add_action and do_action functions. I think I may be trying to use them in the wrong context, and if that's the case - could someone point me in the right direction?
I've come from hating WordPress to loving it, I never thought I'd write a wordpress plugin but now I am getting the hang of things, it's not all that different from normal PHP Development.
Anyway, if I was to have the following code in a plugin:
class aCoolPlugin {
function __construct() {
add_action('clear_auth_cookie', array( $this, 'aCoolFunction' ), 10, 2 );
}
function aCoolFunction( $arg1, $arg2 ) {
// Do something with the arguments
}
}
How would I actually run the aCoolFunction function? Now, I have tried the following:
do_action( 'init', "arg1 value", "arg2 value" );
However, before even trying to run that code I realised:
It makes no sense, since it will essentially be running the init action far too early, and;
It just doesn't work anyway!
So, from that I learnt:
I use add_action to hook into already existing functions for WP
do_action is reserved for new hooks really, can't really think of a useful situation where a hook should be called earlier, and then again later?
So, my question now is: How the heck can I pass my variables into the add_action code? The Codex doesn't say anything regarding arguments, so what are my options? or, is my logic and understanding flawed?
And what is the overall goal? The goal is to have a function with set arguments run every time a specific hook is called, and for the original hook to not be called any earlier/later than it should be
The add action does not accept any new variables nor will it return any variables to the function that runs it. But you can access variables that are passed to the function.
function custom_function($arga){
echo $arga;
}
add_action ('callname', 'custom_function', 10, 1);// 1= number of arguments accepted, use 2 for 2 etc...must add variables to do action call
//sometime later in the code
do_action('callname', $arga);
If you want to inject variables in you have to think a little bit back to basics. If you want to access variables within functions that are not passed you have 2 options:
Retrieve them from DB or server storage or similar
Use the Global declaration. You can accesss all variables that are set at the time the do_action is run.
You would rarely call do_action for wordpress hooks (see note below), but you may end up in a situation where you are coding a template FILE (which runs after plugins and then after themes) and you want to keep your logic in the plugin you could add do_action() into the template file and the actions set in the plugin will run at that point. Or similarly if you design a plugin that you want to be able to modify in the theme you could add an action to a late wp hook, within the called function, you could call do_action for your custom hook and hook functions to it in your theme. Loads of possibilities.
Whatever your logic for calling a WP hook early is, don't if you are within the WP load pattern

WordPress get_query_var()

I am busy developing a WordPress application and I need to be able to pass url parameters using WordPress functions. I use add_query_arg() function to add a url parameter. However, when I try to get the passed value in the other page using get_query_var() nothing gets returned. When I used $_GET['var_name'] the values gets returned.
What is the possible cause of this situation? I can successfully add arguments to the url but I am not able to access them.
I managed to get the get_query_var() function to work.
To use the two functions successfully, you need to add the query vars to wordpress's query vars array. Here is a code sample.
function add_query_vars_filter( $vars ){
$vars[] = "query_var_name";
return $vars;
}
//Add custom query vars
add_filter( 'query_vars', 'add_query_vars_filter' );
Now you can use get_query_var() and add_query_arg() as follows:
Add the query var and value
add_query_arg( array('query_var_name' => 'value'), old_url );
Get the query var value
$value = get_query_var('query_var_name');
More information and code samples can be found at the Codex: get_query_var and add_query_arg
To troubleshoot, what variables are being used in the request use following code
global $wp_query;
var_dump($wp_query->query_vars);
If you check out the Codex, you'll see you actually need to do some fiddling to get WP to start reading your query string.
Codex (under Custom Query Vars)
Excerpt:
In order to be able to add and work with your own custom query vars that you append to URLs (eg: "mysite com/some_page/?my_var=foo" - for example using add_query_arg()) you need to add them to the public query variables available to WP_Query. These are built up when WP_Query instantiates, but fortunately are passed through a filter 'query_vars' before they are actually used to populate the $query_vars property of WP_Query.

Custom hooks in WordPress across plugins

I'm trying to create a hook in one Wordpress plugin that could be used by other plugins. First off, is this even possible? I'm also sending some additional args so this may be 2 questions in one since I've been having trouble finding definitive information on how to do this.
Here is what I've tried so far:
In the plugin that is creating the hook (call it Plugin 1) I added:
do_action('plugin1_hook', $customArg1, $customArg2, $customArg3);
at the point that I want the hook to fire. Then, in a different plugin (Plugin 2), I added:
add_action('plugin1_hook', 'my_function');
and
function my_function($customArg1, $customArg2, $customArg3) { //my code }
This does not seem to be firing the function, however.
My refence for this has been the Wordpress hook comment_post, which is defined by Wordpress as:
do_action('comment_post', $comment_ID, $commentdata['comment_approved']);
and I am using as:
add_action('comment_post', 'my_comment');
function my_comment($comment_id) { //my code }
The above snippet is functioning properly.
I thought I'd post this as an answer as it's a little clearer to explain :)
When you hook a function, but do not specify the number of arguments, WordPress will always pass back one argument.
You won't get errors for something like this;
function do_my_hook($arg1, $arg2 = '', $arg3 = '') {}
add_action('my_hook', 'do_my_hook');
But you will for something like this;
function do_my_hook($arg1, $arg2, $arg3) {}
add_action('my_hook', 'do_my_hook');
WordPress is trying to call do_my_hook(), but it's only passing back one argument. The first example uses PHP default function arguments, so that you can call a function without passing all available arguments, but without error.
The second example will trigger a 'missing argument(s)' PHP error, as all three arguments are required.
The fix?
add_action('my_hook', 'do_my_hook', 10, 3);
The idea behind defining how many arguments your function takes is to avoid errors like these (though technically they are as easily avoided using default arguments!).
My guess is the second plugin is loading after the first one, so the hook has already fired by the time you add an action to it. You might try this for the first plugin:
function my_custom_hook_insertion($arg1, $arg2, $arg3){
do_action('plugin1_hook', $arg1, $arg2, $arg3);
}
add_action('plugins_loaded', 'my_custom_hook_insertion');
That will wait until all plugins are loaded before firing the hook.
Changing my add_action to this fixed the problem:
add_action('plugin1_hook', 'my_function', 10, 3);
The 10 represents the priority, and the 3 represents the number of args that the function will take. I'm not exactly sure how the matching works, since the default is 1, and I use plenty of hooks without specifying 0 args and I've used hooks that pass more than 1 arg but only used 1 arg in my function signature. Source: WordPress Codex: Function Reference/add action
It is working though, so cross plugin hooks are possible.

Categories