使用ADD_ACTION修改要发送到数据库的值

时间:2018-08-18 作者:hede

我已经为这个问题挣扎了好几个小时,现在发生的是在将值插入db之前的某个地方,调用了这个操作。

do_action_ref_array(\'h5p_alter_user_result\', array(&$data, $result_id, $content_id, $user_id));
以下是值及其填充方式。

$user_id = get_current_user_id();
    $result_id = $wpdb->get_var($wpdb->prepare(
        "SELECT id
        FROM {$wpdb->prefix}h5p_results
        WHERE user_id = %d
        AND content_id = %d",
        $user_id,
        $content_id
    ));

$table = $wpdb->prefix . \'h5p_results\';
$data = array(
  \'score\' => filter_input(INPUT_POST, \'score\', FILTER_VALIDATE_INT),
  \'max_score\' => filter_input(INPUT_POST, \'maxScore\', FILTER_VALIDATE_INT),
  \'opened\' => filter_input(INPUT_POST, \'opened\', FILTER_VALIDATE_INT),
  \'finished\' => filter_input(INPUT_POST, \'finished\', FILTER_VALIDATE_INT),
  \'time\' => filter_input(INPUT_POST, \'time\', FILTER_VALIDATE_INT)
);
if ($data[\'time\'] === NULL) {
  $data[\'time\'] = 0;
}
$format = array(
  \'%d\',
  \'%d\',
  \'%d\',
  \'%d\',
  \'%d\'
);

$content_id = 1;
我想做的是,我想在将这些值保存到数据库之前修改它们(是的,在保存到db之前调用这个钩子),为此,我在插件中创建了以下功能。

add_action( \'h5p_alter_user_result\',           \'diff_test_callback\' );

function diff_test_callback($args)
{
    global $wpdb;
  $user_id = 1;
    $result_id = 1;
$content_id = 1;
    $table = $wpdb->prefix . \'h5p_results\';
    $data = array(
      \'score\' => 777,
      \'max_score\' => 189,
      \'opened\' => 333,
      \'finished\' => 222,
      \'time\' => 111
    );
    if ($data[\'time\'] === NULL) {
      $data[\'time\'] = 0;
    }
    $args = array( $data, $result_id, $content_id, $user_id );
    return $args;
}
但是这些值没有被修改,有什么不对吗?

1 个回复
最合适的回答,由SO网友:Fayaz 整理而成

使用挂钩修改变量的正确方法如果要使用挂钩修改变量或任何值,最好使用过滤器挂钩(而不是操作挂钩)。虽然内部对操作和过滤器的实施几乎相同,但公约是:

使用动作挂钩,您可以在回调函数内执行某些操作、回显输出等,但既不返回任何内容,也不更改回调函数范围外的参数。

使用过滤器挂钩,您可以从回调函数返回一个值,然后在某个地方使用它,或者将其分配给回调函数外部的变量。

因此,请使用apply_filters 代码如下:

// using apply_filters() instead of the following do_action_ref_array() line
// do_action_ref_array( \'h5p_alter_user_result\', array( &$data, $result_id, $content_id, $user_id ) );
$data = apply_filters( \'h5p_alter_user_result\', $data, $result_id, $content_id, $user_id );
要与此匹配,请使用add_filter 回调函数如下:

// Declare number of parameters to be passed in add_filter.
// According to our apply_filters() call,
// we expect 4 parameters to be passed to the callback function
add_filter( \'h5p_alter_user_result\', \'diff_test_callback\', 10, 4 );
function diff_test_callback( $data, $result_id, $content_id, $user_id ) {
    // do something with $data
    // remember: manipulation of $data doesn\'t have any affect
    // outside of this function
    // So we need this return
    return $data;
}

do_action_ref_array 代码中的问题:

来自do_action_ref_array 打电话,看起来你想通过$data 作为参考:

do_action_ref_array( \'h5p_alter_user_result\', array( &$data, $result_id, $content_id, $user_id ) );
然而,自PHP 5.4以来,这种行为已经改变。do_action_ref_array 不再将参数的引用传递给回调函数,而是传递一个副本。

而且call time pass by reference 自PHP 5.4以来不接受。所以最好是使用apply_filters 方法,如上面的代码所示。

尽管not recommended, 可以使用引用指针作为数组中的函数参数来完成您尝试的操作。像这样:

// add_action without passing the number of parameters
add_action( \'h5p_alter_user_result\', \'diff_test_callback\' );
// callback function implementation with reference pointer `&`
// for parameters you are expecting with reference
function diff_test_callback( $args ) {
    // we need the reference of $data, so using & operator here.
    $data = &$args[0];
    $result_id = $args[1];
    $content_id = $args[2];
    $user_id = $args[3];

    // now making changes to $data
    // will be reflected outside the scope of this function
    // no return is necessary
}

// at the time of executing the action,
// create the $args array with reference to $data
$args = array( &$data, $result_id, $content_id, $user_id );
do_action_ref_array( \'h5p_alter_user_result\', array( $args ) );
Warning: 再一次,尽管do_action_ref_array 如果您仔细地处理引用,方法就可以工作,强烈建议您在此场景中使用filter-hook方法。

结束

相关推荐

theme functions (hooks)

WordPress已经提出了这个问题,但没有答案。我只是想在这个论坛上试试,如果有人知道的话,因为我也有同样的问题。要使用jquery滑块编辑我的主题,如何转到该脚本?,显示“$主题->挂钩(\'content\\u before\');”在content div标记中。有人能帮忙吗?我的主题索引。php包含以下内容<div id=\"main\"> <?php $theme->hook(\'main_before\'); ?> &#x