Support

Account

Home Forums Bug Reports acf/update_value filters working improperly

Solving

acf/update_value filters working improperly

  • Hey team,

    Looking at the filter, I think the intended functionality for this to provide 4 variables to the function. The 1st is the new field value and the last is the original field value before modification. However, both the 1st and last variables provide the new value.

    The documentation within the code specifies as follows:
    @param mixed $original The original value before modification

    But that’s not the case.

    The filter is found on line 188 on file acf-value-functions.php

  • That would depend on the priority of your filter. When a field is updated, not only is your filter used but ACF uses the same hook to update the value. If the priority of your function is < 10 then both values will be the same. If your priority is the default of 10, well, it’s hard to say as there’s no way of knowing if your filter will run first or the acf filter will run first. When using ACF filters like this is is always best to use a priority > 10, this ensures that ACF has done all of it’s internal filtering before your filter is called.

    This 4th parameter is not documented, and ACF does not use it. I suspect that this value will eventually be used to test if the field value has been altered and if it has that ACF will not override the new value, but that’s just a guess.

  • I noticed this as well. Sorry if I’m just being dense, but I’m not sure how the priority could matter here, as the same variable is passed in both parameters.

        /**
    	 * Filters the $value before it is updated.
    	 *
    	 * @date	28/09/13
    	 * @since	5.0.0
    	 *
    	 * @param	mixed $value The value to update.
    	 * @param	string $post_id The post ID for this value.
    	 * @param	array $field The field array.
    	 * @param	mixed $original The original value before modification.
    	 */
    	$value = apply_filters( "acf/update_value", $value, $post_id, $field, $value );

    I would also expect a call to grab the original value before line 188 if the original value was intended to be passed.

  • So, the way ACF works is that its internal functions are called using the same hooks provided for us. ACF has an internal filter/method, usually inside of the class for each field type, that runs when it calls acf/update_value. All ACF internal filters run on the default priority of 10.

    At the point where this filter is called the original value is the same as the value that’s it’s passing when the hook is run. This will always be the case at this point in the code.

    When it comes to ACF’s internal update value filters it does not look at or consider if the value has already been modified. This can be confirmed by looking at any update_value() method in any of the field classes. This may be something that will happen in the future, but it is not yet the case. It may very will be some improvement that is being worked on because until this topic I did not know that it passed the original value and it is not documented here https://www.advancedcustomfields.com/resources/acf-update_value/

    So, right now, if your filter runs before ACF’s internal filter then the value and the orginal value will be the same.

    So, here’s the thing. If you do not give your filter a priority that means that both your filter and ACF’s internal filter will have the same default priority of 10 and in this case there is almost no way of knowing which one of these filters will run first. It depends on the order that they are added and other things. You’re best bet when adding a filter in ACF is to always use a priority > 10 if you want to ensure that it runs after ACF’s internal filters.

  • I’m also running in to this issue. I don’t see how priority would have any effect as the actual filter code is literally passing $value to both the $value and $orig_value parameters. There doesn’t appear to be any way that those would NOT be the same value which renders the $orig_value parameter useless.

  • the code

    
    $value = apply_filters( "acf/update_value", $value, $post_id, $field, $value );
    

    is called before any filters are applied. At this point the original value will always be the same as the current value.

    Filters can only modify the $valueand cannot alter the$orig_value` (argument #4). Every filter may get a different value but they will always get the same original value.

    Testing this with multiple filters set at different priories and displaying both the current value and the original value in each one I get a constantly changing $value while $orig_value (argument #4 to my filters) remains unchanged.

    I don’t understand how is this working in a way that’s unexpected?

  • Alternatively, I used the get_post_meta() function inside acf/update_value. This give me “$original” value.
    Example:

    function my_acf_update_value( $value, $post_id, $field, $original ) {
    	
        $ex_meta = get_post_meta( $post_id, 'META_FIELD_NAME', true );
        
        if ( $ex_meta == 'SOME_EX_VAL' ) {
         # some code....
        }
        
        return $value;
    }
    
    add_filter('acf/update_value/name=date_expir', 'my_acf_update_value', 20, 4);
  • I suspect there is a miscommunication about what ‘original’ means in the context of this filter.

    The purpose of the filter is to modify the value that needs to be saved into the database, after input, before saving it in the database. For instance to sanitise it, or do some normalisation on it (i.e. if inputing hashtags, change all characters to lowercase).

    I believe ‘original’ is the original value as has been inputted by the user, before any other plugins have changed the value using this filter. Not the value it was before the user is changing it (i.e. the value currently in the database).

    Is that correct @hube2 ?

    Perhaps changing the name from ‘original’ into ‘first’ or ‘original_input’ could avoid confusion.

  • Yes, @morksinaanab you are correct. The value entered into the field by the user, before it was altered by any filters, not the value in the database before it was changed.

    I don’t have any control of the documentation, but I never found this confusing.

Viewing 9 posts - 1 through 9 (of 9 total)

The topic ‘acf/update_value filters working improperly’ is closed to new replies.